以小米时钟为demo学习自定义view过程总结

首选感谢这位博主的分享,让我等新生有很好的范例学习

http://blog.csdn.net/qq_31715429/article/details/54668668点击打开链接 点击打开链接 点击打开链接 点击打开链接


接下来从头捋一遍。

一开始我是在做一个多功能时钟类的APP,做到一半觉得界面实在是丑,而我当时用的又是小米手机,难免会参考小米的时钟,结果一种强烈的羞耻感就出来了。。。于是我开始       想学动画和ps,想找张有刻度的表盘图片和几个指针图片拼起来,凑成一个闹钟。。。结果ps装不成。。。。很气。。。很绝望。就在这时候,我无意在GitHub上搜索了时钟两个字,打开了新世界大门。。。

    attrs.xml文件作用:

     刚看代码的时候,第一眼我就发现我不会。我不知道为什么要有个 attrs 。其实很简单,它是为了简化我们的调试,方便修改一些属性值。

例如本例中



    
        
        
        
        
    
定义了这些属性,那么我们在布局文件中需要去给他们赋值,


(那些以wy开头的自定义属性就是attrs中定义的属性)

然后在自定义view类中用

        TypedArray ta = context.obtainStyledAttributes(attrs, R.styleable.MiClockView, defStyleAttr, 0);
        mBackgroundColor = ta.getColor(R.styleable.MiClockView_backgroundColor, Color.parseColor("#237EAD"));
        setBackgroundColor(mBackgroundColor);
        mLightColor = ta.getColor(R.styleable.MiClockView_lightColor, Color.parseColor("#ffffff"));
        mDarkColor = ta.getColor(R.styleable.MiClockView_darkColor, Color.parseColor("#80ffffff"));
        mTextSize = ta.getDimension(R.styleable.MiClockView_textSize, DensityUtils.sp2px(context, 14));
        ta.recycle();
来获取我们自定义属性的属性值,这些ta.getXXX()方法的第二个参数都是如果没有第一个参数的情况下的默认值。

TypeArray这一行好像都是标准格式,通常情况下只要把第二个参数改成自己在attrs中定义的declare_styleable name=“XXX”就好了,还有在写attrs文件定义属性时

declare-styleable name="MiClockView"
这一行记得写,不然TypedArray ta = .....的时候怎么知道是要从哪来获取你的自定义属性呢。

然后,回到这段文章的开始。。。定义attrs这些文件的作用:比如当你需要修改你的自定义view内的一个lightColor属性时,有很多组件都使用了这个属性,你直接去代码中一个个改就很麻烦了,这时你定义好这些attrs文件后,就只需在布局文件那像修改其他Android系统提供的组件一样修改lightColor值,这时在TypedArray这段代码内mLightColor的值就改变了,也就是后面的所有用到了它的组件都修改了。就是这么简单,但是我当初却想了很久。。。最后通过动手才了解了。。。


     

     重写view类的三个构造方法(为什么是三个,参数都有什么用)

     在构造方法中使用

TypedArray ta = context.obtainStyledAttributes(attrs, R.styleable.MiClockView, defStyleAttr, 0);
来获取到attrs中定义的各个属性值并赋值,在后面,这些属性值可用以设置画笔颜色、线条宽度等。

    通常也在构造方法中初始化各个参数(如把上面获取的属性值赋值给一些需要的paint、path等)。

   至于为什么是三个构造方法:

  1. 在代码中直接new一个Custom View(自定义view)实例的时候,会调用第一个构造函数.这个没有任何争议.
  2. 在xml布局文件中调用Custom View的时候,会调用第二个构造函数.这个也没有争议.
  3. 在xml布局文件中调用Custom View,并且Custom View标签中还有自定义属性时,这里调用的还是第二个构造函数.

也就是说,系统默认只会调用Custom View的前两个构造函数,至于第三个构造函数的调用,通常是我们自己在构造函数中主动调用的(例如,在第二个构造函数中调用第三个构造函数).

   各个参数的含义其实我也不太清楚。。。。

   所以推荐一下这篇博客,我也是从在学习到的

http://blog.csdn.net/wzy_1988/article/details/49619773#生成custom-view的自定义属性点击打开链接



接下来是onMeasure方法重写

通常在onMeasure中为自定义view设置大小

而且onMeasure中只需要一个方法

setMeasuredDimension(measureDimension(widthMeasureSpec), measureDimension(heightMeasureSpec))
而其中的measureDimension是自己写的一个测量方法
private int measureDimension(int measureSpec) {
        int result;
        int mode = MeasureSpec.getMode(measureSpec);
        int size = MeasureSpec.getSize(measureSpec);
        if (mode == MeasureSpec.EXACTLY) {
            result = size;
        } else {
            result = 800;
            if (mode == MeasureSpec.AT_MOST) {
                result = Math.min(result, size);
            }
        }
        return result;
    }
这主要是对自定义的layout_width/heigh的值进行判断

具体的晚点再补。。。不过推荐一篇我认为关于这个onMeasure写得很好的博客

http://www.jianshu.com/p/5a71014e7b1b点击打开链接



再下来就是onDraw了

把所有画图的方法都放到这里面来运行。。就能都显示出来。。。大概就是这样

记得给canvas赋值。。。

还有就是最后如果是动画需要有一个

invalidate();
方法,作用好像是重复绘制?不是很懂。。。这是个遗留问题,现在太晚了没时 间了,以后补上



最后,其实在写代码的时候有很多的基本的东西都记得不牢,比如一些画形状的方法、贝塞尔曲线什么的,初学者还是需要多练啊!光看是不行的,今天实在是太晚了,明天还有一天课,不,是一周课。。。超级课设培训。。可怕。剩下的遗留问题一定要解决!


最后的最后,第一次写博客,很多东西还不会,请大家见谅。

因为本人水平不够,分享的也只是心得,也是我走过的困难的路,希望能对一些初学者能有帮助,不过难免会有错误,各位大神看到了一定麻烦帮我指出啊。。。谢!




你可能感兴趣的:(以小米时钟为demo学习自定义view过程总结)