iOS, SwiftUI, Swift

[SwiftUI]iPad上でNavigaitonViewでSplitViewを実現

SwiftUIでSplitViewを表現する方法がNavigationでできるようなのでまとめます。
少しトリッキーなコードになりますが、少ないコードでSplitViewレイアウトを実装することができます。

検証環境

  • Xcode 11.4

Split Viewとは?

設定アプリのように、Viewが2つ並びで左右に別れているレイアウトです。
設定アプリでは、左側のペインに設定項目が並び、それらをタップすると右側ペインに詳細画面が表示されます。

IMG_0928

NavigationViewでSplitView

SwiftUIではNavigationViewでSplitViewを表現できるようです。

NavigationView {
    NavigationLink(destination: Text("Detail")) { // ③
        Text("Master") // ①
    }
    .navigationBarTitle("Nav", displayMode: .large)

    Text("First Screen") // ②
}
.padding(0.5)

NavigationViewに2つの子View、NavigationLinkTextを入れています。
そして、ここが大事ですが、NavigationViewに対して.padding(0.5)をつけるとiPadにてSplit Viewが表示されます。
paddingは0.5以上だと効きます。

iPadで実行した際のキャプチャがこちらです。コードの①と②が対応しています。

----------2020-04-19-23.04.30-1

ちなみに「Master」のラベルをタップすると左側のペインがコードの③、destinationのViewに遷移します。

----------2020-04-19-23.17.45

iPhoneで実行するとSplit Viewにはならず、おなじみのスタック型のNavigation Viewになります。コード上の②、NavigaitonViewの二番目の子Viewは無視されます。

----------2020-04-19-23.14.23

paddingがない場合

paddingがない場合どうなるでしょうか?

NavigationView {
    NavigationLink(destination: Text("Detail")) { // ③
        Text("Master") // ①
    }
    .navigationBarTitle("Nav", displayMode: .large)

    Text("First Screen") // ②
}
//.padding(0.5)

paddingをコメントアウトしてiPadで実行します。

----------2020-04-19-23.27.44

②のViewが全面に表示され、左上のNavボタンをタップすると左横から①のViewがスライドインします。
①のリンクをタップすると右側のViewがリンク先、③のViewに変更されるという動きをするようです。

iOS 13.0で実行すると

iOS 13.0で実行するとNavigationLinkのリンクが効かない現象が起こりました。
リンクが灰色になってタップできない状態になります。

----------2020-04-19-23.21.26

おそらくiOS 13.0のバグです。

まとめ

SwiftUIでNavigationViewによるSplit Viewの方法を紹介しました。
まさかpaddingのありなしでレイアウトが変わるとは思いもしませんでした。
ちょっとトリッキーなのでチーム開発の際はコメントで補ったほうがいいかもしれません。
ただiPadのみSplitViewのレイアウトにしたいという場合はコード量が圧倒的に少なくて表現できるので便利だと思います。

宣伝

SwiftUIでアプリを作り方を解説した「1人でアプリを作る人を支えるSwiftUI開発レシピ」がBOOTHで発売中です。
SwiftUIでアプリを作りたい方、ぜひチェックしてください!

https://personal-factory.booth.pm/items/1920812



参考

Author image

About Sato Takeshi

  • Tokyo, Japan