http://blog.csdn.net/caesardadi/article/details/20387645
Android 可以自定义View,同时我们也可以为我们的自定义的View添加自定义属性,对系统的控件实现扩展,使用方式如同系统控件在xml布局文件中的使用形式。
扩展方式:自定义属性,然后再布局文件中使用这些属性,在自定义View中获取这些自定义属性的值。
具体方式如下:
1.定义属性:在res/values目录下创建attrs.xml文件
- <?xml version="1.0" encoding="utf-8"?>
- <resources>
- <declare-styleable name="RoundAngleImageView">
- <attr name="roundWidth" format="dimension" />
- <attr name="roundHeight" format="dimension" />
- </declare-styleable>
- </resources>
其中name为该属性集的名字,在第三部获取属性值时
roundWidth = a.getDimensionPixelSize(R.styleable.RoundAngleImageView_roundWidth, roundWidth);需要在每个参数名前面添加这个name和下划线。
属性的类型即format有string , integer , dimension , reference , color , enum.,如果可以同时使用不同的类型。用”|“分割。
枚举类型的设置略有不同
- <attr name="flowDirection" format="enum">
- <enum name="leftToRight" value="0" />
- <enum name="topDown" value="1" />
- <enum name="rightToLeft" value="2" />
- <enum name="bottomUp" value="3" />
- </attr>
2.在布局文件中使用属性
- <?xml version="1.0" encoding="utf-8"?>
- <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:app="http://schemas.android.com/apk/res-auto"
- android:orientation="vertical"
- android:layout_width="fill_parent"
- android:layout_height="fill_parent"
- >
- <com.liupan.app.RoundImage android:id="@+id/roundImage"
- android:layout_width="fill_parent"
- android:layout_height="wrap_content"
- android:layout_alignParentBottom="true"
- android:background="@drawable/control_bar"
- android:gravity="center"
- app:roundWidth = "5dp"
- app:roundHeight="10dp"/>
- </RelativeLayout>
- xmlns:app="http://schemas.android.com/apk/res-auto"
3. 在自定义组件中的构造函数中获取设置的属性值
- public RoundCornerImageView(Context context) {
- super(context);
- init(context, null);
- }
- public RoundCornerImageView(Context context, AttributeSet attrs) {
- super(context, attrs);
- init(context, attrs);
- }
- public RoundCornerImageView(Context context, AttributeSet attrs, int defStyle) {
- super(context, attrs, defStyle);
- init(context, attrs);
- }
第一个构造函数没有AttributeSet参数,我们需要设置默认值。
在获取属性值得时候,需要设置默认值,在用户没有设置本属性时,使用默认值。
- private void init(Context context, AttributeSet attributeSet) {
- if (attributeSet != null) {
- TypedArray a = context.obtainStyledAttributes(attributeSet, R.styleable.RoundAngleImageView);
- assert a != null;
- roundWidth = a.getDimensionPixelSize(R.styleable.RoundAngleImageView_roundWidth, roundWidth);
- roundHeight = a.getDimensionPixelSize(R.styleable.RoundAngleImageView_roundHeight, roundHeight);
- } else {
- float density = context.getResources().getDisplayMetrics().density;
- roundWidth = (int) (roundWidth * density);
- roundHeight = (int) (roundHeight * density);
- }
- paint = new Paint();
- paint.setColor(Color.WHITE);
- paint.setAntiAlias(true);
- paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.DST_OUT));
- paint2 = new Paint();
- paint2.setXfermode(null);
- a.recycle();//为了保持以后使用的一致性,需要回收
注意最后调用TypedArray的recycle方法。
以上三步,搞定。
————————————————————————补充内容—————————————————————
res与res-auto的区别
通常我们在布局文件中使用自定义属性的时候会这样写xmlns:app="http://schemas.android.com/apk/res/包路径"
但如果你当前工程是做为lib使用,那么你如上所写 ,会出现找不到自定义属性的错误 。这时候你就必须 写成xmlns:app="http://schemas.android.com/apk/res-auto/包路径"