ボクココ

少人数でのサービス開発運営に関するテックブログ

SwiftUIでのプレビュー機能を使えるようにしよう

ども、@kimihom です。

iOSアプリ開発でSwiftUIを使っていると、XcodeのCanvas機能を利用することができる。これを使うとわざわざエミュレーターやiPhoneで見ずとも、UIの調整が可能だ。

最初のセットアップさえうまくできれば、かなり便利に利用できるので、SwiftUIを使っているなら必ずマスターしたいものである。

プレビューの表示

私が一番ハマったのが、「ViewModel側で色々と変数を定義しているけど、その変数をどうやってプレビューに渡すのか」という点だった。例えば以下のようなコードがあったとしよう。

// MyView.swift
struct MyView: View {
    @EnvironmentObject var myViewModel : MyViewModel

    var body: some View {
        ZStack {
            if let name = myViewModel.name {
                Text("こんにちは\(name)さん")
            } else {
                Text("初めまして ゲストさん")
            }
        }
    }
}

struct MyView_Previews: PreviewProvider {
    static var previews: some View {
        MyView().environmentObject(MyViewModel())
    }
}
// MyViewModel.swift
final class MyViewModel: NSObject, ObservableObject {
    @Published var name? // WebAPIから取ってきたユーザー名
}

このコードでは MyViewModel に name が保存されていれば、その名前を表示しようとしている。しかし、nameはデフォルトで何も名前が定義されていないので、プレビューでは必ず "初めましてゲストさん" が表示されてしまう。 このサンプルの文言くらいだったらいいのだけど、ログインしている/していないでUIが大きく変わるような場合、これだとプレビューが全く使い物にならない。

ではどうすればいいのか。気づけば簡単なことだったが、 "プレビューを見たい時だけ init() にオブジェクトを入れておく" が答えだ。

final class MyViewModel: NSObject, ObservableObject {
    @Published var name? // WebAPIから取ってきたユーザー名

    override init() {
        super.init()

        // 初期化コード
        initSomething()

        // MyView テスト時
        self.name = "太郎"
    }
}

これで、WebAPIから仮に取ってきたとされる名前を事前に入れておくことで、UIの確認が無事にできるようになる。 この解決方法さえ理解できれば、SwiftUIでのプレビュー表示の便利さにびっくりすることだろう。

もちろん、実際にアプリを動かす時には、このコード(self.name = "太郎") はコメントアウトするのを忘れずに。

より便利に使う

iPhoneアプリだけでなく、iPad側のUIや、ダークモードの確認なども簡単にできるので、もはや必須と言ってもいいだろう。

これら細かい設定は、SwiftUIプレビュー画面のメニューで操作可能だ。

MyView().environmentObject(MyViewModel())
                .preferredColorScheme(.dark)
                .previewDevice("iPad mini (6th generation)")

終わりに

SwiftUIに慣れると、楽しくiOSアプリを作ることができる!

iOSアプリのエンジニアはぜひマスターしたいところである。