(2020/11/8 更新)
NavigationView配下での画面遷移について解説します。
環境
この記事の情報は次のバージョンで動作確認しています。
【Swift】5.3
【iOS】14.1
【macOS】Catalina バージョン 10.15.7
基本的な画面遷移
まずは、NavigationView配下での基本的な画面遷移の例を紹介します。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
struct ContentView: View { var body: some View { NavigationView { NavigationLink(destination: SecondView()) { Text("Go Second View").font(.title) } .navigationTitle("Top View") } } } struct SecondView: View { var body: some View { Text("SecondView").font(.title) } } |
NavigationView配下での画面遷移にはNavigationLinkを使用します。
1 2 3 4 5 |
NavigationLink(destination: 遷移先View) { // 画面遷移のトリガーとなるViewを定義 } |
引数destinationで遷移先のビューの指定、続くクロージャーで画面遷移のトリガーとなるView(ラベル)を定義します。
ラベルに画像を使う場合の注意点
通常、ラベルとして指定されたViewは、タップ可能であるのがわかるようSwiftUIによって青色で表示されます。
次のように画像(Image)を使った場合も青一色で表示されてしまいます。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 |
struct ContentView: View { var body: some View { NavigationView { NavigationLink(destination: SecondView()) { HStack { Text("Go Second View").font(.title) Image("right.arrow") .resizable() .frame(width: 50, height: 50) } } .navigationTitle("Top View") } } } |
画像をオリジナルの色調で表示するには、Imageビューの.renderingMode(.original)モディファイアを使用します。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
struct ContentView: View { var body: some View { NavigationView { NavigationLink(destination: SecondView()) { HStack { Text("Go Second View").font(.title) Image("right.arrow") .renderingMode(.original) // オリジナル画像を表示 .resizable() .frame(width: 50, height: 50) } } .navigationTitle("Top View") } } } |
代わりにNavigationLinkの.buttonStyle(PlainButtonStyle())モディファイアを使用するとラベル全体をオリジナルの色調にできます。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
struct ContentView: View { var body: some View { NavigationView { NavigationLink(destination: SecondView()) { HStack { Text("Go Second View").font(.title) Image("right.arrow") .resizable() .frame(width: 50, height: 50) } } .buttonStyle(PlainButtonStyle()) // ラベル全体をオリジナルの色調にする .navigationTitle("Top View") } } } |
ListやFormでの画面遷移
NavigationLinkをListやForm内で使用した場合は、表示形式が通常と変わります。
ラベルが青表示にはならず、代わりに右端にグレーの開示インジケーターが表示されます。
これは行をタップすると右から別の画面がスライドして表示される事をユーザーに知らせる、iOSの標準的なUIです。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 |
struct ContentView: View { var body: some View { NavigationView { Form { NavigationLink(destination: SecondView()) { HStack { Text("Go Second View").font(.title) } } } .navigationTitle("Top View") } } } |
条件指定による画面遷移
ラベルのタップでは無く、別の条件で画面遷移させるには次のイニシャライザを使います。
1 2 3 4 5 |
NavigationLink(destination: 遷移先View, isActive: $条件フラグ) { EmptyView() } |
引数(isActive)に画面遷移の条件となるフラグ(Bool型のバインド変数)を指定します。
このフラグがtrueになった時に画面遷移します。
ラベルに EmptyView() を指定して「ラベルViewを表示しない」ようにすると、タップによる遷移を排除可能です。
次は、正しい合言葉を入力すると画面遷移するサンプルです。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 |
struct ContentView: View { @State private var password = "" @State private var showingSecondView = false var body: some View { NavigationView { VStack { Text("合言葉を入力") TextField("", text: $password, onCommit: { if self.password == "SwiftUI" { self.showingSecondView = true } }) .textFieldStyle(RoundedBorderTextFieldStyle()) .padding(.horizontal) NavigationLink(destination: SecondView(), isActive: $showingSecondView) { EmptyView() } } .navigationTitle("Top View") } } } struct SecondView: View { var body: some View { Text("SecondView").font(.title) } } |
遷移元画面に戻る方法
NavigationLinkで遷移した画面から遷移元画面に戻るには方法がいくつかあります。
戻るボタンをタップする
画面左上に自動で表じされる戻るボタンをタップします。
画面を右にスワイプする
コードで実装する
環境変数の「presentationMode」プロパティで「dismiss」メソッドを呼び出します。
必要なのは次の2行です。
①presentationMode環境変数を取得
②dismiss()メソッド呼び出し
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
struct SecondView: View { /// ①presentationMode環境変数を取得 @Environment(\.presentationMode) var presentationMode var body: some View { VStack { Text("SecondView").font(.title) Button("戻る") { /// ②dismiss()メソッド呼び出し presentationMode.wrappedValue.dismiss() } } } } |
条件指定により画面遷移した場合は、isActiveで指定した条件フラグをfalseする方法も有効です。
また、ナビゲーションバーの戻るボタンが不要な場合は、次のModifierで非表示にします。
この場合は、右スワイプによる戻り処理も使えなくなります。
1 2 3 |
.navigationBarBackButtonHidden(true) |