为什么使用碎片?

使用Fragment比使用在不同布局中重用的自定义View有什么优势?

在原来的博客文章介绍片段 ,黛安娜哈克博恩说

[Fragments]使开发人员可以更轻松地编写可在各种屏幕尺寸范围内扩展的应用程序,而不仅仅是平台中已有的function。

然后她继续在为应用程序制作平板电脑布局的上下文中解释片段,该应用程序结合了来自同一应用程序的电话版本的两个活动的UI。

但似乎使用自定义视图可以实现相同的重用。 片段和观点之间的主要区别似乎是它们有不同的生命周期。

Fragment生命周期是:

onAttach()onCreate()onCreateView()onActivityCreated()onStart()onResume()onPause()onStop()onDestroyView()onDestroy()onDetatch()

View生命周期是:

onFinishInflate()onAttachedToWindow()onMeasure()onLayout()onDetatchedFromWindow()

我想听听有开发经验的开发人员编写大型应用程序,了解他们在使用片段vs自定义视图中看到的好处(如果有的话),将UI划分为可重用的片断。

主要原因是片段比自定义视图更具可重用性。

有时你不能单独依靠视图来创build完全封装的UI组件。 这是因为有些东西是你想放进你的视图的,但是不能,因为只有一个Activity可以处理它们,从而强迫一个Activity和一个View之间的紧密耦合。

这是一个这样的例子。 比方说,你想创build一个可重用的用户界面组件,在许多事情中,要捕获一张照片,并与之做一些事情。 传统上,你会触发一个意图,启动相机,并返回与捕获的图像。

请注意,您的自定义用户界面组件不能完全封装此function,因为它将不得不依靠托pipe活动的startActivityForResult因为视图不接受活动的结果(他们可以通过上下文间接触发意图)。

现在,如果您想在不同的活动中重复使用您的自定义UI组件,您将重复Activity.startActivityForResult的代码。

另一方面片段干净地解决了这个问题。

同样,你的片段可以将项目贡献给你的选项菜单,传统上只有一个活动可以做。 如果您的自定义视图的状态决定了菜单中的内容,这也是非常重要的。

片段不仅仅是一个视图。 其实它甚至可以完全没有意见。 它可以有各种各样的东西,包括AsyncTasks,各种监听器,文件和数据库访问等等。

把它想象成一个小型的活动,但是你可以在屏幕上看到它们的多个,并且与它们一起工作,包括在它们可见的时候相互通信。

例如,您可以在一个片段中显示购物车列表,并在另一个片段中详细显示当前选定的购物车。 然后您可以例如在详细视图中更改项目的数量,并可以通知列表视图并更新列表视图中的总价格。 你可以很好地协调这样的交互,例如在一个较小的屏幕设备上仍然只能看到其中的一个。

我已经重构了一个大型商业应用程序(> 15个活动)从活动到碎片以获得良好的平板电脑支持,我永远不会开始一个没有碎片的新应用程序。

2016年2月更新 :虽然上述情况仍然如此,但是碎片的复杂性使许多人完全避免使用它们。 较新的模式,如使用MVC方法和更强大的视图提供了替代scheme。 正如他们所说… YMMV。

一些描述:

把活动想象成一块拿着一块大蛋糕的盘子。 片段将是一个容器,将同一块蛋糕切成块。 每片包含它自己的逻辑(听众等)。 总的来说,他们和一个大蛋糕几乎没有什么不同。

好处:

  1. 当你盘子不能抱大蛋糕。 (屏幕很小)您可以轻松地使用几个盘子(活动)来保存它们中的每一个,而无需将您的逻辑移动到新的活动中。

  2. 更好的可重用性。 我有一些情况下,我可以在另一个应用程序中完全重用一个片段。 您可能会声称自定义视图也可以这样做。 但是,参考第1点,我可以重新使用它只需几行布局更改,但对于自定义视图,它必须find一种方法将其插入布局和代码。

  3. 从某种意义上说,在Android编程中组织用户界面逻辑的OO方法更多。 当你有一个function(例如在屏幕上的一个新的分区),你创build一个新的片段类,对现有的活动类稍作修改。 但是,如果你只用活动编程,你将需要添加逻辑,并对被testing的类进行大的修改。

只是我2美分。 🙂

生命周期方法可能是您最大的暗示。 如果你仔细想一想,它们就会密切关联到活动的生命周期(对活动和视图有一些挂钩)。 事实上,在你链接的文章中,哈克博恩说:

在某些方面,您可以将片段视为一个小型活动

与软件devise/开发中的许多事情一样,有许多方法可以做事。 有许多不同的地方你可以把你的代码。 是的,你可以把很多东西放在一个视图中,但是把不同的关注点分开放在不同的类中是件好事。 这种经典模式是MVC,适用于这种情况。 你不想把太多的控制器逻辑烧入你的视野。 最好把它保存在类似控制器的类中,这是活动,现在是片段。 这就是为什么片段的生命周期更像是活动的观点而已 – 是为了促进这种组织。

自定义视图比使用碎片代替您的活动要多得多。 如果您决定使用活动和自定义视图,则必须创build自定义视图,然后必须在活动中实施相同的活动生命周期方法(对于片段使用非常类似的生命周期)。

使用片段还允许您将组件分离到自己的类(片段)中,而不是在单个活动中包含太多的逻辑。 让我以一个例子为基础:

假设您正在实施杂志阅读器应用程序。 使用片段,您可以创build一个片段:显示文章列表的ArticleList,以及处理显示内容逻辑的另一个片段:ArticleDisplay。 然后可以指定这些片段如何使用片段工具进行交互,以便在手机上可以使用全屏幕实时显示ArticleDisplay,而在平板电脑上,可以并排显示片段。

如果你想用活动/自定义视图进行尝试,那么你需要在整体活动中使用这两个片段的逻辑,你必须写一个自定义视图,而且你必须debugging这个笨重的怪物。

一般来说,碎片是编写应用程序的更复杂和更强大的方式。 他们可以做一切活动可以做的事情,等等。 如果你不需要额外的function,默认值可能会让你需要去的地方,而且工作量less。

我碰了一下碎片,发现它们不是很有用(见这篇文章 )。 从我读过的内容来看, 片段实际上是一个可以访问活动上下文的对象 。 我喜欢忽略我的工作中的碎片,而只是自己创build这些对象。 我通过将Activity传递给构造函数而不是Context来创build非常大且要求非常苛刻的应用程序。 然而,使用Fragments的一个主要好处是它们被View布局系统支持 – 所以你可以很容易地将它们添加到Android的XML(如果你使用它的布局)。