本記事は画面上に表示されたときのみデータを読み込む(遅延読み込みする)ようにSwiftUIの LazyVStack
、LazyHStack
、List
を使用することについてお話しします。また、本記事では通常の VStack
(非推奨です) と Form
を使用した結果についてもご説明します。
遅延読み込みが必要な理由
例えば、最も人気の本を表示するアプリケーションを開発している場合、本の画像をサーバーから読み込む必要があります。
本のリストビューを表示する際、すべての本の画像が同時にダウンロードされるのを避けるべきかもしれません。代わりに、現在画面上に表示されている画像のみを読み込むのが望ましいでしょう。ユーザーがより多くの本を表示するためにスクロールすると、それらの画像がダウンロードされます。
スターターコード
完成したプロジェクトが含まれているスターターコードは、Githubからダウンロードできます。
SwiftUIがビューを読み込むタイミングをより正確に確認するために、ネットワークリクエストコードにprintステートメントがあり、そこからリクエストIDを出力します。
VStack
を使用 (遅延読み込みなし)
ScrollView {
VStack {
ForEach(Networking.shared.getAllCatIDs(), id: \.self) { catID in
ItemDisplay(catID: catID)
}
}
}
VStack
の使用を選ぶと、すべてのビューが最初に読み込まれるのが分かります。このプログラムがインターネットからデータをフェッチする場合、ユーザーがプログラムを開いた時に多くのデータがダウンロードされることになります。
詳細に関してはこちらをクリックしてください
(推奨)LazyVStack
の使用(またはLazyHStack
)
ScrollView {
LazyVStack {
ForEach(Networking.shared.getAllCatIDs(), id: \.self) { catID in
ItemDisplay(catID: catID)
}
}
}
LazyVStack
は一気に全データを読み込むものではありません。そうではなく、最大インデックス31までのデータを読み込むことになります(データを読み込む具体的な順序はありません)。ことらのログメッセージからわかるように
詳細に関してはこちらをクリックしてください
水平スタイルのディスプレイの場合には、データの表示に LazyHStack
を使用することもできます。
デモプログラムをダウンロードして実際の動きをご覧ください。LazyVStack
を下部にスクロールするに連れて、より多くのデータが自動的にロードされます。
(推奨)List
の使用
List(Networking.shared.getAllCatIDs(), id: \.self) { catID in
ItemDisplay(catID: catID)
}
List
を使用すると、ビューが表示された際に最初の数個のエレメントのみが読み込まれます。ビューを下にスクロールすると、自動的にさらに多くのデータが読み込まれていきます。
ログメッセージで確認できるように、LazyVStack
や LazyHStack
と比較すると、List
ではデータが順番に読み込まれていきます:
詳細に関してはこちらをクリックしてください
Form
を使用
Form {
ForEach(Networking.shared.getAllCatIDs(), id: \.self) { catID in
ItemDisplay(catID: catID)
}
}
また、 Form
要素内に ForEach
を含めることもできます。これはビューが表示されたとき、最初の数個のデータ要素のみが読み込まれ、ユーザーがビューをスクロールダウンするにつれて追加のデータが自動的に読み込まれます。しかし、いくつかの要素が2回読み込まれているようです:
詳細に関してはこちらをクリックしてください
結論
大量のデータを読み込んで画面に表示する場合には、プログラムにおいて LazyVStack
、LazyHStack
、List
ビューの使用を心がけるようにしてください。これにより、必要な際にビューに関連付けられたデータが読み込まれるようになります(画面にデータを表示する場合)。