android-由于视图测量而导致的版面设计性能不佳?

android-由于视图测量而导致的版面设计性能不佳?,第1张

概述我遇到了性能问题,我认为这是由于对我的观点进行衡量所致.我的布局是通过编程方式构建的,因此无法显示我的布局的xml.但是,这里有一些可能导致此问题的观点:>一个用于包装所有内容的ScrollView(宽度:MATCH_PARENT,高度:MATCH_PARENT)>包含所有不同内容部分的LinearLayout(宽度:MATCH_

我遇到了性能问题,我认为这是由于对我的观点进行衡量所致.
我的布局是通过编程方式构建的,因此无法显示我的布局的xml.但是,这里有一些可能导致此问题的观点:

>一个用于包装所有内容的ScrollVIEw(宽度:MATCH_PARENT,高度:MATCH_PARENT)
>包含所有不同内容部分的linearLayout(宽度:MATCH_PARENT,高度:MATCH_PARENT,前一个视图的子级)
>两个异步填充的LinearListViews(linearLayout)(宽度:MATCH_PARENT,高度:WRAP_CONTENT,上一个视图的子代)

当我填充linearListVIEw时,似乎只会出现此问题.添加视图似乎会触发VIEw.measure被多次调用:

为什么多次调用VIEw.measure? linearLayout的大小为MATH_PARENT,这意味着在添加子项时不必再次对其进行测量,对吗?

我不太确定如何防止这种情况的发生或如何调试问题.我尝试将linearListVIEw的可见性设置为GONE,直到添加了所有项目,但这并没有改变.

我希望我能提供足够的信息,以便有人指出正确的方向.

编辑#1(07/01):

这是用于linearListVIEws的适配器基类的某些部分:

public abstract class DataProvIDerAdapter<T> extends BaseAdapter{    ...    @OverrIDe    public VIEw getVIEw(int position, VIEw convertVIEw, VIEwGroup parent)    {        VIEw row = convertVIEw;        T item = getItem(position);        Log.d(TAG, "getVIEw(): position: " + position + ", ConvertVIEw: "                + (convertVIEw == null ? "null" : convertVIEw) + ", TotalCount: " + getCount());        if (row == null) {            row = buildrow(position);            markRowAsLoading(row);        }        if (item == null) {            if (convertVIEw != null) {                markRowAsLoading(row);            }            int skip;            if (itemsRequestParams != null) {                int pageSize = itemsRequestParams.getTake();                // determine how many items to skip                skip = position - (position % pageSize);            }            else {                skip = 0;            }            // if the page isn't already being fetched            if (!pagesReceiving.contains(skip)) {                pagesReceiving.add(skip);                AsyncTaskUtil.executeMultiThreaded(new ReceiveItemsTask(), skip);            }        }        else {            Log.d(TAG, getClass().getSimplename() + " - PrepareRow: " + getItemID(position)                    + ", Pos: " + position);            prepareRow(row, item, position);        }        return row;    }    protected voID processDataResult(int skip, DataResult<T> result)    {        if (result instanceof GroupedDataResult<?>) {            GroupedDataResult<T> groupedResult = (GroupedDataResult<T>)result;            totalitemCount = groupedResult.getTotalGroupCount() + groupedResult.getTotalitemCount();        }        else {            totalitemCount = result.getTotalitemCount();        }        for (int i = 0; i < result.getItems().size(); i++) {            itemList.put(skip + i, result.getItems().get(i));        }        Log.d(TAG, "processDataResult(" + skip + ")");        notifyDataSetChanged();    }    static protected class CellHolder    {        public Progressbar Progressspinner;        public List<androID.Widget.ImageVIEw> Images;        public List<TextVIEw> Labels;        private final HashMap<String, Object> _extras = new HashMap<String, Object>();        public voID putExtra(String key, Object value)        {            _extras.put(key, value);        }        @SuppressWarnings("unchecked")        public <T> T getExtra(String key)        {            return _extras.containsKey(key) ? (T)_extras.get(key) : null;        }    }    ...    private class ReceiveItemsTask extends AsyncTask<Integer, VoID, DataResult<T>>    {        private int skip;        @OverrIDe        protected DataResult<T> doInBackground(Integer... params)        {            skip = params[0];            DataResult<T> items = getItems(skip);            Log.d(TAG, "doInBackground(" + skip + ")");            return items;        }        @OverrIDe        protected voID onPostExecute(DataResult<T> result)        {            Log.d(TAG,                    "onPostExecute("                            + (result == null ? "null" : result.getItems().size() + "/"                                    + result.getTotalitemCount()) + ")");            if (result == null) {                return;            }            processDataResult(skip, result);            Log.d(TAG, "onPostExecute end");        }    }}

编辑#2(07/01):

我将relativeLayout子类化,并覆盖了onMeasure,以便我可以记录正在测量哪些视图以及以什么顺序进行记录.
结果如下:

07-01 15:37:37.434: V/DefaultLayout(8172): DefaultLayout.onMeasure07-01 15:37:37.434: V/DefaultLayout(8172): TabVIEw.onMeasure07-01 15:37:37.434: V/DefaultLayout(8172): ItemDetailsContainerVIEw.onMeasure07-01 15:37:37.438: V/DefaultLayout(8172): headerVIEw.onMeasure07-01 15:37:37.438: V/DefaultLayout(8172): ItemDetailsInfoFIEldsLayout.onMeasure07-01 15:37:37.438: V/DefaultLayout(8172): ItemRevIEwtableVIEw.onMeasure07-01 15:37:37.438: V/DefaultLayout(8172): InfoFIEldsLayout.onMeasure07-01 15:37:37.438: V/DefaultLayout(8172): InfoFIEldsLayout.onMeasure07-01 15:37:37.442: V/DefaultLayout(8172): InfoFIEldsLayout.onMeasure07-01 15:37:37.442: V/DefaultLayout(8172): InfoFIEldsLayout.onMeasure07-01 15:37:37.442: V/DefaultLayout(8172): InfoFIEldsLayout.onMeasure07-01 15:37:37.442: V/DefaultLayout(8172): InfoFIEldsLayout.onMeasure07-01 15:37:37.442: V/DefaultLayout(8172): InfoFIEldsLayout.onMeasure07-01 15:37:37.442: V/DefaultLayout(8172): InfoFIEldsLayout.onMeasure07-01 15:37:37.446: V/DefaultLayout(8172): ItemRevIEwtableVIEw.onMeasure07-01 15:37:37.446: V/DefaultLayout(8172): InfoFIEldsLayout.onMeasure07-01 15:37:37.446: V/DefaultLayout(8172): InfoFIEldsLayout.onMeasure07-01 15:37:37.446: V/DefaultLayout(8172): InfoFIEldsLayout.onMeasure07-01 15:37:37.446: V/DefaultLayout(8172): InfoFIEldsLayout.onMeasure07-01 15:37:37.450: V/DefaultLayout(8172): InfoFIEldsLayout.onMeasure07-01 15:37:37.450: V/DefaultLayout(8172): InfoFIEldsLayout.onMeasure07-01 15:37:37.450: V/DefaultLayout(8172): InfoFIEldsLayout.onMeasure07-01 15:37:37.450: V/DefaultLayout(8172): InfoFIEldsLayout.onMeasure07-01 15:37:37.450: V/DefaultLayout(8172): RelatedItemstableVIEw.onMeasure07-01 15:37:37.454: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.458: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.462: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.466: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.470: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.474: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.478: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.478: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.482: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.482: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.486: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.486: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.490: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.490: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.494: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.494: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.498: V/DefaultLayout(8172): RelatedItemstableVIEw.onMeasure07-01 15:37:37.498: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.498: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.502: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.502: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.506: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.506: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.510: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.510: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.514: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.514: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.518: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.518: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.522: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.522: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.526: V/DefaultLayout(8172): ratingVIEw.onMeasure07-01 15:37:37.526: V/DefaultLayout(8172): ratingVIEw.onMeasure...

此列表会持续一段时间.但是对我来说似乎很奇怪,它始于测量顶视图(DefaultLayout.onMeasure),然后还测量所有子视图(因此所有视图).它多次这样做!

是什么导致onMeasure在顶视图上被调用?

编辑#3(07/02):

可能是notifyDataSetChanged()触发了顶视图的测量?

编辑#4(07/03):

是的,似乎notifyDataSetChanged()触发了要测量的顶级视图(我能够在新的测试项目中重现此视图).并且由于我的适配器的工作方式,notifyDataSetChanged()被多次调用.

当我调用notifyDataSetChanged()时,测量所有视图的原因是什么?有什么方法可以防止这种情况发生吗?

解决方法:

您没有说相对布局的位置,这是列表的包装器吗?

根据罗曼·盖伊(Romain Guy)的说法,相对布局始终执行两次度量传递,因此这可能会导致某些速度降低.您是否甚至有嵌套的相对布局?显然,这可能具有指数的时间复杂度.

请参阅以下答案以供参考(以及指向他实际说过的Google io视频的链接):

https://stackoverflow.com/a/17496262/1281144

总结

以上是内存溢出为你收集整理的android-由于视图测量而导致的版面设计性能不佳?全部内容,希望文章能够帮你解决android-由于视图测量而导致的版面设计性能不佳?所遇到的程序开发问题。

如果觉得内存溢出网站内容还不错,欢迎将内存溢出网站推荐给程序员好友。

欢迎分享,转载请注明来源:内存溢出

原文地址: http://www.outofmemory.cn/web/1087839.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2022-05-27
下一篇 2022-05-27

发表评论

登录后才能评论

评论列表(0条)

保存