【SwiftUI】@ObservedObjectの使い方

データクラスの更新を監視する@ObservedObjectの使い方を解説します。
これを利用すると複数のViewから同一インスタンスへの同期が可能になります。

スポンサーリンク

環境

この記事の情報は次のバージョンで動作確認しています。

【Xcode】11.5
【Swift】5.2.4
【iOS】13.5
【macOS】Catalina バージョン 10.15.4

@Stateとの違い

データが更新されるとそのデータを参照しているViewも自動的に更新されるのがSwiftUIの特徴です。
@StateではViewのプロパティに対してその仕組みを実現しますが、データクラスに対しては@ObservedObjectを使用します。
@ObservedObjectを付けて宣言されたデータクラスのインスタンスは、SwiftUIの監視対象となり、プロパティが更新されると参照しているViewが自動的に再描画されます。

基本的な使い方

名前とレベルを保持するUserクラスを例に説明します。

はじめに、対象とするクラスの定義を次のように記述します。

次にViewの中で対象のデータクラスを宣言をします。

ポイントは、次の3点です。

  1. データクラスはObservableObjectプロトコル準拠とする。
  2. 監視対象とするプロパティに@Published属性を付加する。
  3. データクラスのインスタンスは@ObservedObject属性を付加してViewの中で宣言する。

これで、@Published属性を付けたプロパティがSwiftUIの監視対象となり、値が変更されると参照しているViewが自動的に再描画されるようになります。

使用例

名前をいれてボタンをタップすると、プロパティを参照しているTextViewが再描画されます。

@ObservedObjectの使用例

インスタンスを他のViewと共有する

ObservableObjectプロトコルに準拠しているデータクラスのインスタンスは、他のViewからも参照・更新が可能です。
次のコードは入力フォームを別のViewに分割し、そちらからも同じインスタンスと同期をとる例です。
入力フォームView側でも共有するインスタンスを@ObservedObject属性を付けて宣言します。

インスタンスの一部プロパティだけ他Viewと共有する場合

インスタンスの一部プロパティだけ他Viewと共有する場合は、@Stateで宣言されたプロパティと同様の扱いが可能です。
子Viewに対しては、頭に$を付けてプロパティの参照値を渡し、子View側では@Bindingを付加して対象プロパティを宣言します。

以下はレベルアップボタンのみView分割した例です。

あわせて読みたい記事

【SwiftUI】@Stateの使い方
SwiftUIのデータバインディングの仕組みの一つである、@Stateについて解説します。プロパティが更新された場合に、参照しているViewも同時に更新される仕組みが実現できます。
SwiftUI
スポンサーリンク
カピ通信