3
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

【Android】by viewModels()を使い分けよう

Last updated at Posted at 2025-12-18

はじめに

Android開発において、JetpackライブラリのViewModelは、今や当たり前のように利用されるお馴染みのコンポーネントです。特にKotlinを使用する場合、by viewModels() デリゲートプロパティを活用することで、ViewModelのインスタンス化と管理を非常に簡潔に行うことができます。

この便利な by viewModels() にはいくつかの種類が存在し、それぞれの状況に応じた適切な使い分けをすることで、より効果的に利用できます。この記事では、by viewModels() の基本的な使い方から、知っておくべき種類とそれらの使い分けについて詳しく解説します。ViewModelをより効果的に活用し、堅牢でメンテナンス性の高いAndroidアプリケーション開発を目指しましょう。

by viewModels()は主に3種類ある

  • by viewModels()
  • by activityViewModels()
  • by navGraphViewModels()

これら3つのデリゲートプロパティの違いと使い方について説明します。
これらの委譲プロパティは、ViewModelの「スコープ」と「ライフサイクル」を決定する点で異なります。どのViewModelを使用すべきかは、データの共有範囲と、どのライフサイクルに紐付けるかによって決まります。

by viewModels()について

スコープ

各ActivityまたはFragmentのインスタンスに紐付きます。
by viewModels用画像-viewModels.drawio.png

ライフサイクル

そのActivityまたはFragmentのライフサイクルに完全に依存します。ActivityやFragmentが破棄されると、対応するViewModelも同時に破棄されます。

使い方

ActivityやFragmentが他のコンポーネントと独立した独自のデータを持ちたい場合に、最も一般的に使用されます。

    // Activityで使用する場合
    class MyActivity : AppCompatActivity() {
        private val viewModel: MyActivityViewModel by viewModels()
        // ...
    }

    // Fragmentで使用する場合
    class MyFragment : Fragment() {
        private val viewModel: MyFragmentViewModel by viewModels()
        // ...
    }

by activityViewModels()

スコープ

Fragmentの親となるActivityに紐付きます。
by viewModels用画像-activity.drawio.png

ライフサイクル

親Activityのライフサイクルに依存します。親Activityが破棄されるまで、ViewModelは生存し続けます。

使い方

複数のFragmentが親Activityに共通のデータを共有したい場合に便利です。
親Activity内の異なるFragment間でデータをやり取りしたり、Activity全体の状態を管理したりするのに適しています。

    class ParentActivity : AppCompatActivity() {
        // ActivityViewModelは通常、Fragmentから参照されるため、ここでは直接取得しないことが多い
    }

    class ChildFragmentA : Fragment() {
        // 親ActivityのViewModelを共有
        private val sharedViewModel: SharedViewModel by activityViewModels()
        // ...
    }

    class ChildFragmentB : Fragment() {
        // 親ActivityのViewModelを共有
        private val sharedViewModel: SharedViewModel by activityViewModels()
        // ...
    }

by navGraphViewModels()

スコープ

特定のナビゲーショングラフに紐付きます。
by viewModels用画像-navGraph.drawio.png

ライフサイクル

指定したナビゲーショングラフがバックスタックに存在する間、ViewModelは生存し続けます。ナビゲーショングラフがバックスタックから削除されると、対応するViewModelも破棄されます。

使い方

by navGraphViewModels(<ナビゲーションID>) のように、Navigationコンポーネントを使用している場合に、特定のナビゲーショングラフ内の複数のFragment間でデータを共有したいときに使用します。
例えば、ユーザー登録フローのように、いくつかの画面(Fragment)にまたがる一連の操作で共通のデータが必要な場合に非常に有効です。

    // navigation/nav_graph.xml で定義されたナビゲーショングラフのIDを使用
    class StepOneFragment : Fragment() {
        private val navGraphViewModel: RegistrationViewModel by navGraphViewModels(R.id.registration_nav_graph) // ナビゲーショングラフIDを指定
        // ...
    }

    class StepTwoFragment : Fragment() {
        private val navGraphViewModel: RegistrationViewModel by navGraphViewModels(R.id.registration_nav_graph) // ナビゲーショングラフIDを指定
        // ...
    }

まとめ

ここまで見てきたように、適切な by 委譲プロパティを選択することは、アプリケーションのデータの整合性を保ちながら、ViewModelのスコープとライフサイクルを効率的に管理するために非常に重要です。これらのデリゲートを適切に使い分けることで、より堅牢でメンテナンス性の高いAndroidアプリケーション開発を実現できます。

3
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
3
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?