首页 诗词 字典 板报 句子 名言 友答 励志 学校 网站地图
当前位置: 首页 > 教程频道 > 移动开发 > Android >

Android中View作图优化之三- 优化View

2012-09-20 
Android中View绘制优化之三----优化View本文原创, 转载请注明出处:http://blog.csdn.net/qinjuning译三:优

Android中View绘制优化之三---- 优化View


                                                                                本文原创, 转载请注明出处:http://blog.csdn.net/qinjuning





译三:

                                                优化视图


  关于如何设计自定义View以及响应触摸时间等,请看Android developer :

           地址:http://developer.android.com/training/custom-views/index.html


  本文翻译地址:Optimizing the View



        通过前面的学习,现在该设计良好的View能够响应手势以及状态之间进行转换,除此之外你必须确保View

   运行的流畅快速。为了避免迟缓的UI效果或者运行的停顿,必须确保你的动画一直运行在每秒60帧。



 越少越好
        为了加速视图,从那些调用频繁的活动中减少不必要的代码。在OnDraw()方法中开始绘制,它会给你最大的 

   效益。特别低,你也应该减少在onDraw()方法中的内存分配,因为任何内存分配都可能导致内存回收,这将会

   引起不连贯。 在初始化或者动画之间分配对象。绝不要在动画运行时分配内存。


        另一方面需要减少onDraw()方法中的开销,只在需要时才调用onDraw()方法。通常invalidate()方法会调用

  onDraw()方法,因此减少对invalidate()的不必要调用。如果可能,调用它的重载版本即带有参数的invalidate()

  方法而不是无参的invalidate()方法。该带参数的方法invalidate()能使draw过程更有效,以及减少对落在该矩形

  区域(参数指定的区域)外视图的不必要重绘 。


       注,invalidate()的三个重载版本为:

            1 、public void invalidate (Rect dirty)
            2、public void invalidate (int l, int t, int r, int b)

               3、public void invalidate ()


        另外的一个高代价的操作是布局过程(layout)。 任何时刻对View调用requestLayout()方法,Android UI 框架

  都需要遍历整个View树,确定每个视图它们所占用的大小。如果在measure过程中有任何冲突,可能会多次遍历

  View树。UI设计人员有时为了实现某些效果,创建了较深层次的ViewGroup。但这些深层次View树会引发效率

  问题。确保你的View树层次尽可能浅。


        如果你有的UI设计是复杂地,你应该考虑设计一个自定义ViewGroup来实现layout过程。不同于内置View控件,

  自定义View能够假定它的每个子View的大小以及形状,同时能够避免为每个子View进行measure过程。 PieChart

  展示了如何继承ViewGroup类。 PieChart带有子View,但它从来没有measure它们。相反,它根据自己的布局算法

  去直接设置每个子View的大小。
          

       如下代码所示:

private class PieView extends View {    public PieView(Context context) {        super(context);        if (!isInEditMode()) {            setLayerType(View.LAYER_TYPE_HARDWARE, null);        }    }        @Override    protected void onDraw(Canvas canvas) {        super.onDraw(canvas);        for (Item it : mData) {            mPiePaint.setShader(it.mShader);            canvas.drawArc(mBounds,                    360 - it.mEndAngle,                    it.mEndAngle - it.mStartAngle,                    true, mPiePaint);        }    }    @Override    protected void onSizeChanged(int w, int h, int oldw, int oldh) {        mBounds = new RectF(0, 0, w, h);    }    RectF mBounds;}


          改变之后,只有View第一次显示的时候才会调用PieChart.PieView.onDraw()方法。在应用程序的其他

   时间,绘制的图像将会作为图片缓存,重绘时GPU将任意旋转图像。


         然而这只是一个折中手段。缓存图片作为硬件层导致 video memory开销,video memory却是一种受限制的

 资源。 出于这个原因,在PieChart.PieView的最终版本上,只有在用户滑动时才设置它的layer type属性为

  LAYER_TYPE_HARDWARE。在其他时间,仅仅设置它的layer type属性为 LAYER_TYPE_HARDWARE,这

  允许GPU停止缓存图片。



        最后,不要忘记分析你的代码。在一个View上做的优化技术可能会在其他View上产生不好的影响。




热点排行