なぜフラグメント化し、アクティビティの代わりにフラグメントを使用するのはいつですか?


485

Android API 11以降で、Googleはという新しいクラスをリリースしましたFragment

動画では、Googleは可能な限り(ことを示唆しているリンク1リンク2)、私たちが代わりに活動の断片を使用する必要がありますが、彼らは正確に理由を説明しませんでした。

フラグメントの目的とそれらのいくつかの可能な用途は何ですか(単純なビュー/レイアウトで簡単に実現できるいくつかのUIの例を除く)?

私の質問はフラグメントについてです:

  1. フラグメントを使用する目的は何ですか?
  2. アクティビティ/ビュー/レイアウトを使用する場合と比較して、フラグメントを使用する利点と欠点は何ですか?

ボーナス質問:

  1. フラグメントの本当に興味深い使い方を教えてください。Googleが動画で言及しなかったことは?
  2. フラグメントとそれらを含むアクティビティの間で通信するための最良の方法は何ですか?
  3. フラグメントを使用するときに覚えておくべき最も重要なことは何ですか?あなたの経験からのヒントと警告はありますか?


回答:


282

#1&#2フラグメントを使用する目的は何ですか?アクティビティ/ビュー/レイアウトを使用する場合と比較して、フラグメントを使用する利点と欠点は何ですか?

フラグメントは、再利用可能なユーザーインターフェイスを作成するためのAndroidのソリューションです。アクティビティとレイアウトを使用して(たとえば、インクルードを使用して)同じことのいくつかを実現できます。しかしながら; フラグメントは、HoneyComb以降からAndroid APIに接続されています。詳しく説明します。

  • ActionBar。アプリをナビゲートするためにそこにタブが必要な場合は、ActionBar.TabListenerインターフェースがメソッドFragmentTransactionへの入力引数としてを提供することがすぐにわかりますonTabSelected。あなたはおそらくこれを無視して、何か他の賢いことをすることができますが、あなたはそれに対してではなく、APIに対して取り組んでいるでしょう。

  • FragmentManager非常に巧妙な方法であなたのためにハンドル«戻ります»。戻るとは、通常のアクティビティのように、最後のアクティビティに戻ることを意味しません。前のフラグメント状態に戻ることを意味します。

  • でクールViewPagerを使用して、FragmentPagerAdapterスワイプインターフェイスを作成できます。FragmentPagerAdapterコードは、通常のアダプタよりもはるかにきれいであり、それは個々のフラグメントのインスタンスを制御します。

  • 携帯電話とタブレットの両方のアプリケーションを作成しようとするときにフラグメントを使用すると、あなたの人生はずっと簡単になります。フラグメントはHoneycomb + APIと密接に結びついているため、コードを再利用するために電話でも使用する必要があります。互換性ライブラリが役に立ちます。

  • 電話専用のアプリにフラグメントを使用することもできます。移植性を念頭に置いている場合。私はActionBarSherlockと互換性ライブラリを使用して、バージョン1.6までずっと同じに見える「ICSに見える」アプリを作成しています。ActionBarタブ、オーバーフロー、スプリットアクションバー、ビューページャーなどののような最新の機能を利用できます。

ボーナス2

フラグメント間で通信する最良の方法はインテントです。フラグメント内の何かを押すと、通常StartActivity()、そのデータを呼び出します。インテントは、起動するアクティビティのすべてのフラグメントに渡されます。


5
まず、thanks.iマニュアルへのリンクを提供するだけでなく、有益な(まだ短い)回答を提供してくれた人々に感謝します?
Android開発者、

4
私はあなたが質問する際により直接的である必要があると思います。上記の4つの主な利点を挙げました。
Glenn Bech、2012年

2
わかりました、カスタマイズされたビューやアクティビティと比較したデメリットはどうですか?
Android開発者、

2
インテントを使用してフラグメント間でどのように通信しますか?フラグメントが互いに通信できるように、すべてのフラグメントを「生きている」(アクティビティに追加する)必要がありますか?
Androidデベロッパー

55
1つのフラグメントが別のフラグメントと直接通信することはありません。代わりに、親アクティビティを経由します。このようにすれば、スパゲッティコードがなくなるだけでなく、コードの管理も簡単になります。
スロット

70

どのビデオを参照しているのかはわかりませんが、直接交換することはできないため、アクティビティの代わりにフラグメントを使用するべきだと言っているのではないでしょうか。開発ガイドには実際にはかなり詳細なエントリがあります。詳細については、それを読むことを検討してください。

つまり、フラグメントはアクティビティ内に存在し、各アクティビティは多くのフラグメントをホストできます。アクティビティと同様に、アクティビティとは異なり、特定のライフサイクルがあり、トップレベルのアプリケーションコンポーネントではありません。フラグメントの利点には、コードの再利用とモジュール性(たとえば、多くのアクティビティで同じリストビューを使用する)が含まれ、マルチペインインターフェースを構築する機能(主にタブレットで有用)が含まれます。主な欠点は、(一部の)複雑さが増すことです。一般に、(カスタム)ビューを使用して同じことを非標準で堅牢性の低い方法で実現できます。


1
更新された質問。今ではグーグルのビデオへのリンクがあります。また、説明に感謝しますが、質問についてはまだ説明が必要です。
Android開発者、

5
開発ガイドのエントリを読んでください。十分な詳細があります。SOで「フラグメントのクールな使用法」に対する答えが得られる可能性は低く、あいまいな方法であり、単一の答えはありません。ナンバー4はspecificlly DEV guide--に答えているdeveloper.android.com/guide/topics/fundamentals/...
ニコライElenkov

1
私の知る限り、このメソッドはどのアクティビティがどのフラグメントを含むことができるかという依存関係を作成します。また、主な質問(最初の2つ)にもお答えください。
Android開発者、

3
基本的な質問への回答を主張してくれたandroid開発者に感謝します。ATM Fragmentクラスでは、XMLの "include"タグを使用するよりも便利なものを見たことがありません。私が貴重だと思う種類のことは、すべての解像度で最高のユーザーエクスペリエンスに魔法のように変形する1つのレイアウトを指定する機能です。私が言うことができることから、あなたはまだ自分でコードでそれをする必要があります。別の潜在的な価値は、コード+リソースを、再利用するアプリにはない再利用可能なコンポーネントにバンドルする方法ですが、ここにもありません。本当に良い理由が欲しい。
Melinda Green

2
私は、Googleが断片を使用することをお勧めする方法を理解し始めていますが、私はかなり私には... @NikolayElenkovに同意し、活動は依然として最も堅牢かつあまり複雑な方法であると思わ使用して...
andrea.rinaldi

49

フラグメントは、よりモジュール化されたアクティビティ設計を可能にするアクティビティに配置できるアプリケーションのユーザーインターフェイスまたは動作の一部です。フラグメントがサブアクティビティの一種だと言っても間違いありません。

以下は、フラグメントに関する重要なポイントです。

  1. フラグメントには、独自のレイアウトと独自の動作があり、独自のライフサイクルコールバックがあります。

  2. アクティビティの実行中に、アクティビティのフラグメントを追加または削除できます。

  3. 1つのアクティビティで複数のフラグメントを組み合わせて、マルチペインUIを構築できます。

  4. フラグメントは複数のアクティビティで使用できます。

  5. フラグメントのライフサイクルは、そのホストアクティビティのライフサイクルと密接に関連しています。

  6. アクティビティが一時停止すると、アクティビティで使用可能なすべてのフラグメントも停止されます。

  7. フラグメントは、ユーザーインターフェイスコンポーネントを持たない動作を実装できます。

  8. フラグメントは、APIバージョン11のAndroid 3(Honeycomb)のAndroid APIに追加されました。

詳細については、公式サイトFragmentsをご覧ください。


1.#8で述べたように、レイアウトは必要ありません。6.「手段」の後の部分を逃しました。とにかく、他の人がこれをより明確にするのを助けてくれてありがとう。+1します。
Android開発者

1
#8に関して、レイアウトなしのフラグメント(つまり、「ヘッドレス」フラグメント)の考えられる例は、少し短い(短いHTTPリクエストなど)にもかかわらず、構成の変更を生き残るために必要なタスクを実行するものであり、したがって、 (フラグメントでsetRetainInstance(true)を使用して)それら全体で保持されている正確なフラグメントインスタンス。レイアウトフラグメントについては、setRetainInstance(true)はあまり意味がありません。これは、ビューに関連付けられたリソースが必要なときに解放されない(メモリリークなど)ためです。
ピオベザン

注:「#8」は「#7」になりました。
ToolmakerSteve、2016

21

これは私がフラグメントで見つけた重要な情報です:

従来、Androidアプリの各画面は個別のアクティビティとして実装されていました。Android Intentメカニズムでは、アクティビティ間で直接参照タイプ(オブジェクト)を渡すことができないため、画面間で情報を渡す際に課題が生じます。代わりに、オブジェクトをシリアル化するか、グローバルにアクセスできる参照を使用可能にする必要があります。

各画面を個別のフラグメントにすることで、このデータ転送の頭痛が完全に回避されます。フラグメントは常に特定のアクティビティのコンテキスト内に存在し、常にそのアクティビティにアクセスできます。関心のある情報をアクティビティ内に保存することにより、各画面のフラグメントは、アクティビティを介してオブジェクト参照に簡単にアクセスできます。

ソース:https : //www.pluralsight.com/blog/software-development/android-fragments


3
それは本当ですが、これには解決策があります:巨大なオブジェクトでない場合はParcelableを使用し(そしてそれを簡単にするプラグインがあります)、巨大なオブジェクトの場合は、常にnullに設定される静的参照を使用できます新しいアクティビティに到達したとき(または要件に応じて、それを破棄したとき)。
アンドロイド開発者

@androiddeveloper:「Parcelableを使用する」は、「フラグメントを使用することで回避されるデータ受け渡しの頭痛」の私の定義に適合します。一連の画面が通過する間、持続する必要がある複雑な共有状態がある場合、アクティビティ+フラグメントが適切なソリューションです。(私はフラグメントのバックスタックを放棄し、「バック」の意味を自分で管理しましたが)
ToolmakerSteve

コンテナーアクティビティを介してフラグメント間でインターフェイスデザインパターンを使用することは、オブジェクトだけでなく、クリックイベントリスナーとメソッド引数を他のフラグメントまたはメインコンテナーアクティビティに戻す、非常にモジュール化されたアプローチです。
Kaveesh Kanwal、2016年

10

アクティビティは、ツールバーを備えたアプリの全画面コンポーネントです。それ以外はすべてフラグメントであることが望ましいです。ツールバーを備えた1つのフルスクリーンの親アクティビティには、複数のペイン、スクロール可能なページ、ダイアログなど(すべてのフラグメント)を含めることができます。これらはすべて、親からアクセスでき、親を介して通信できます。

例:

アクティビティA、アクティビティB、アクティビティC:

  • たとえば基本的なツールバーを表示したり、親アクティビティから継承したりするには(管理が面倒になる)、すべてのアクティビティで同じコードを繰り返す必要があります。
  • 1つのアクティビティから別のアクティビティに移動するには、それらすべてをメモリ内(オーバーヘッド)に置くか、一方を破棄してもう一方を開く必要があります。
  • アクティビティ間の通信はインテントを介して行うことができます。

アクティビティA、フラグメント1、フラグメント2、フラグメント3:

  • コードの繰り返しはありません。すべての画面には、その1つのアクティビティからのツールバーなどがあります。
  • 1つのフラグメントから次のフラグメントに移動するいくつかの方法-ページャー、マルチペインなどを表示します。
  • アクティビティにはほとんどのデータがあるため、最小限のフラグメント間通信が必要です。それでも必要な場合は、インターフェースを介して簡単に行うことができます。
  • フラグメントはフルスクリーンである必要はなく、それらを設計する上で多くの柔軟性があります。
  • ビューが必要ない場合、フラグメントはレイアウトを拡張する必要はありません。
  • 複数のアクティビティで同じフラグメントを使用できます。

完璧な答え!
Sathesh

8

フラグメントは、すべてのページでナビゲーションドロワーを保持したい場合など、特定の場合に特に役立ちます。フレームレイアウトに必要なフラグメントを追加しても、ナビゲーションドロワーにアクセスできます。

アクティビティを使用した場合、すべてのアクティビティでドロワーを維持する必要があり、コードが冗長になります。これはフラグメントの興味深い使い方の1つです。

私はAndroidを使い始めたばかりですが、フラグメントはこの方法で役に立ちます。


はい。ただし、フラグメントの正しい使用方法についてまだ混乱していることがあります。これは、フラグメントとアクティビティの両方のライフサイクルが複雑なためです。
Android開発者

@androiddeveloperあなたは主にアクティビティを使用していますか?
マイケルアランハフ

@MichaelAlanHuffタブレットをサポートする場合、フラグメントを使用する方が良いと思います。また、向きの変更やその他の同様のイベントをサポートする場合、DialogFragmentを使用して復元することができます
android developer

@androiddeveloper、私もそう思います。DialogFragmentsをあまり使用していません。ロジックのモジュール化を支援するために、多くのAndroid開発者がカスタムビューを使用して、ロジックを正方形のモルタルに保持し始めています。ここではAirbnbからエンジニアによって与えられたカスタムビューについての最近の話ですvimeo.com/127799187
マイケル・アラン・ハフ

フラグメントを使用した@MichaelAlanHuffは、現在の画面が別の画面の一部である可能性がある場合にも役立ちます。
Android開発者

5

これについてはすでに討論されていたことがわかっていますが、もう少しポイントを追加したいと思います。

  • フラグを使用してを入力し、独自にクリックをMenu処理できMenuItemます。したがって、アクティビティにさらなる変調オプションを提供します。ContextualActionBarなどをアクティビティについて知らなくても実行でき、基本的にはアクティビティが処理する基本的なもの(ナビゲーション/設定/バージョン情報)から分離できます。

  • 子フラグを持つ親フラグは、コンポーネントをモジュール化するための追加オプションを提供できます。たとえば、フラグを簡単に入れ替えたり、新しいフラグをポケットベルに入れたり、削除したり、並べ替えたりできます。アクティビティが何も知らなくても、より高いレベルのものに焦点を当てているだけです。


0

フラグメントはアクティビティ内にあり、以下を持っています:

  • 独自のライフサイクル
  • 独自のレイアウト
  • 独自の子フラグメントなど

フラグメントは、それが属するメインアクティビティのサブアクティビティと考えてください。フラグメント自体は存在できず、何度も呼び出し/再利用できます。お役に立てれば :)


実際、2番目のポイント(「独自のレイアウト」)については、これはオプションです。フラグメントはビューを持つ必要はまったくありません。
Android開発者

0

1.フラグメントを使用する目的?

  • 回答:
    1. デバイスのフォームファクタの違いに対処する。
    2. アプリ画面間での情報の受け渡し。
    3. ユーザーインターフェイスの構成。
    4. 高度なUIメタファー。

0

フラグメントはアクティビティ内に存在しますが、アクティビティはそれ自体で生存します。


6
「それ自体」?おそらく「単独で」?それとも「それ自体」?
Peter Mortensen
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.