Android 在详图片段中使用ViewHolder图案

Android 在详图片段中使用ViewHolder图案,android,android-fragments,master-detail,Android,Android Fragments,Master Detail,在我的Android项目中,我有一个使用主细节视图的活动,该视图由两个片段创建。 我的碎片给了我一些“问题” 它由50多个控件(文本视图、编辑文本、复选框、微调器)组成。在这50多个控件中,我以编程方式在我的detail片段中获取对其中32个控件的引用,并从我的SQLite数据库加载它们的数据 当我运行此命令并使用 (SomeControl).findViewById(R.id.mycontrol); LogCat不断警告我,我可能在主线程上做得太多了 我知道findViewById和膨胀视图

在我的Android项目中,我有一个使用主细节视图的活动,该视图由两个片段创建。 我的碎片给了我一些“问题”

它由50多个控件(文本视图、编辑文本、复选框、微调器)组成。在这50多个控件中,我以编程方式在我的detail片段中获取对其中32个控件的引用,并从我的SQLite数据库加载它们的数据

当我运行此命令并使用

(SomeControl).findViewById(R.id.mycontrol);
LogCat不断警告我,我可能在主线程上做得太多了

我知道findViewById和膨胀视图是一项昂贵的操作,所以我有了一个想法


我想知道是否有什么方法可以像我在ListFragment上做的那样,在我的细节片段上使用viewholder模式或视图循环。这样我就可以避免每次在ListView中选择另一项时重新初始化detailview。不要打电话,跟我一样找视频。有人对如何实现这样的东西有想法吗。如果我在detailsfragment的onCreate方法中初始化控件,会有什么不同吗?我还考虑将我的detailsfragment设置为“singleton”,然后在listfragment的选择发生变化时使用getLoaderManager().restartLoader。如果您对所有这些有任何想法,我将不胜感激。

除非您对每个控件使用完全相同的布局,否则我不确定是否有办法做到这一点

但可能有一种方法可以解决您的问题:使用异步任务


只要你的程序不需要这些控件来处理数据(根据你的解释,我认为在用户与UI元素交互之前,UI元素不会被触发),你就应该没事了,主线程可以自由地做任何它需要的事情。我看到的这种方法的唯一缺点是,一些UI元素可能会延迟半秒出现(如果您仔细想想,还不错)

找到了解决办法。但是我不得不完全改变我的实现

现在,我的实现在ListFragment和DetailFragment上都使用了加载程序

以下是我所做的更改列表:

  • 使用一个方法(onSomethingClicked(SomeObject obj))为我的ListFragment创建了一个接口,并通过该接口使ListFragment可见
  • 在my DetailFragment中实现了接口,并在ListFragment上注册了一个侦听器
  • 在DetailFragment中的onSomethingClicked()上实现了方法。触发时,我将数据从ListFragment传递到DetailFragment,重新启动DetailFragment加载程序,并将数据加载到OnLoadFinished中已初始化的控件中
    无需在列表中的选择每次更改时膨胀视图,也无需。findViewById,最重要的是不再有Choreographer警告:)

    如果您谈论的是
    Choreographer
    警告,我个人会忽略它们。我以前看过关于这方面的讨论,但从来没有一个明确的答案来解释它们的真正含义,或者它们是否真的表明了任何真正有害的东西。编舞警告正是我所说的。那么我就不应该担心这些了?正如我所说的,我从来没有看到过对警告含义的很好的解释,尽管很明显它们是由复杂的视图生成或数据处理触发的。我也看到他们的一些设备,而不是别人,但我的应用程序从来没有引起ANR弹出,所以基本上我认为他们作为低优先级。在某个时候,我会更仔细地观察,看看我是否可以在某些地方使我的代码更精简一些。我也曾想过这样做。我的问题是,这种解决方案仍然需要每次都完成工作,这将是CPU周期的浪费,没有任何性能增益。布局和控件都是一样的,只是抬头而已。一个
    片段
    不应与另一个片段直接通信-这违反了
    片段
    的设计模型。
    片段的思想是它应该是模块化的、自包含的和可重用的。务必使用接口,但在包含两个
    片段的
    活动中将其作为回调实现。在将来的某个时候,您可能希望自己重用一个
    片段
    ,或者甚至使用另一个
    片段
    。这样,直接沟通就会中断。我知道。但这将再次导致每次ListClick都必须膨胀和初始化控件,我正试图避免这种情况。就像这里显示的代码一样:那么我必须使用:FragmentTransaction=。。。事务.replace(R.id.fragment\u容器,newFragment);对不起,我看不出你对上述评论的逻辑。如果您可以使用FragmentA FragmentB方法在片段之间进行通信,那么FragmentA活动FragmentB有什么区别。活动可以在其承载的任何片段中调用公共方法,而无需将其替换为FragmentTransaction。抱歉,我误解了您的评论。你当然是对的。当谈到活动回调时,我只是认为它与谷歌的片段示例一样,但当然你也可以通过活动,这实际上是最佳实践。我最好再修改一下我的代码。没问题——也许我的第一条评论不清楚。使用一个
    活动
    ,它“知道”它正在使用什么
    片段
    (并控制它们之间的交互方式),并且拥有不需要彼此“知道”的
    片段
    ,绝对是一个更好的OOD方法。祝你好运