SwiftUIでの画面遷移は,
NavigationViewとNavigationLink
で行います.
Viewの上にこれらのコントロール(UI部品)を配置してアプリを作成していきます. 今回は基本部品の一つTextFieldです.
環境は,
- macOS Catalina 10.15.7
- Xcode 12.0.1
- Swift 5.3
- iOS 14.0
です.
1つのファイルで画面遷移を行う


実際のコードは次のようになります.
import SwiftUI
struct ContentView: View {
var body: some View {
NavigationView{
NavigationLink(destination: SubView()) {
Text("画面遷移")
.font(.largeTitle)
}
}
}
}
struct SubView: View {
var body: some View {
Text("移動しました!")
.font(.largeTitle)
.foregroundColor(Color.pink)
}
}
struct ContentView_Previews: PreviewProvider {
static var previews: some View {
ContentView()
}
}
詳しく見ていきましょう.

- が最初の画面の実装
- 移動した先の画面の実装
をしています. 最後の
struct ContentView_Previews: PreviewProvider {
static var previews: some View {
ContentView()
}
}
はプレビュー表示をしています. したがって, 画面遷移自体は❶と❷で実装されています.
その中核をなすのが,
NavigationView | 画面遷移を行うことができるコンテナ. | |
NavigationLink | 画面遷移の実行を行う「トリガー」の役割を果たす. ここで行き先を指定することができる. |
です. NavigationView
はコンテナの役割も果たすので,
struct ContentView: View {
var body: some View {
NavigationView{
Text("画面遷移")
.font(.largeTitle)
}
}
}
でもエラーは出ません. コードを実行すると, 「画面遷移」というテキストが出るだけで, そこから他の画面に飛ぶことはできません. この中でトリガーの役割をするNavigationLink
を入れて初めて画面遷移が可能となります.
もちろん, NavigationView
を削除して, NavigationLink
だけでも画面遷移はできません. この2つはセットで初めて機能します.
画面遷移を実装した時点で

も作成されるのもスゴイですね. このあたりはFlutterと同じです.
画面遷移における値の引き渡し【基本編】
次のブログで@State
と@Binding
については説明しようと思っていますので, ここでは省きます. これらを使うと基本的な値の受け渡しは可能になります.


import SwiftUI
struct ContentView: View {
@State private var word = "画面遷移したよ!"
var body: some View {
NavigationView{
NavigationLink(destination: SubView(word: $word)) {
Text("画面遷移")
.font(.largeTitle)
}
}
}
}
struct SubView: View {
@Binding var word: String
var body: some View {
Text(word)
.font(.largeTitle)
.foregroundColor(Color.pink)
}
}
値はSubViewのイニシャライザで渡します.
画面遷移における入力した値の引き渡し【基本編】
次の例はTextFieldに入れたテキストを次の画面に引き渡すものです.
import SwiftUI
struct ContentView: View {
@State private var name = ""
var body: some View {
NavigationView{
VStack(spacing: 30.0) {
TextField("名前を入れてください。", text: $name)
.border(Color.blue, width: 2)
.font(.title)
.padding(.horizontal, 20.0)
NavigationLink(destination: SubView(name: $name)) {
Text("画面遷移")
.font(.title)
}
.navigationTitle("最初の画面")
}
}
}
}
struct SubView: View {
@Binding var name: String
var body: some View {
Text("初めまして, \(name)さん")
.font(.largeTitle)
.foregroundColor(Color.pink)
}
}


複数回の画面遷移
最初の画面→2番目の画面→最後の画面と移動します.
import SwiftUI
struct ContentView: View {
var body: some View {
NavigationView{
NavigationLink(destination: SubView1()) {
Text("画面遷移")
.font(.largeTitle)
}
.navigationTitle("最初の画面")
}
}
}
//SubView1
struct SubView1: View {
var body: some View {
VStack(spacing: 30.0) {
Text("SubView1移動しました!")
.font(.largeTitle)
.foregroundColor(Color.pink)
NavigationLink(destination: SubView2()) {
Text("画面遷移")
.font(.largeTitle)
}
.navigationTitle("2番目の画面")
}
}
}
//SubView2
struct SubView2: View {
var body: some View {
Text("SubView2に移動しました!")
.font(.largeTitle)
.foregroundColor(Color.green)
}
}



Viewの階層をまたいでの値の受け渡しは, @State
を用いてもできなくはありません. ただ, その都度@Binding
で受け取る必要があり, 実用的ではありません. この場合はEnvironmentObject
などを用いると簡単に受け渡しをすることができます.
次回以降は, プロパティラッパーについてまとめたいと思います.
Thanks for sharing, this is a fantastic article post. Thanks Again. Great. Barbra Huntlee Darcia