android 自定义View 之自定义属性
1:新建 attrs文件 目录 res/value/attrs.xml
属性类型一共有8种:string,color,demension,integer,enum,reference,float,boolean,fraction,flag;
<?xml version="1.0" encoding="utf-8"?>
2:布局中使用:
一定要引入 xmlns:custom="http://schemas.android.com/apk/res/com.example.customview01"我们的命名空间,后面的包路径指的是项目的package 或者 xmlns:custom="http://schemas.android.com/apk/res-auto"
xmlns的作用
xml布局中使用最多的是android:id、andorid:layout_width等形式,在我们自定义的xml中,添加了app:Text、app:TextAllow等这样的写法,其实冒号前面的单词并不重要,重要的是后面引号中的内容,前面的单词可以任意取名,我们在最开始指定了这样一句代码:
xmlns:app="http://schemas.android.com/apk/res-auto"
包括系统自动为我们添加的这一句代码:
xmlns:android="http://schemas.android.com/apk/res/android"
正是这两句代码的存在,才使得我们能够使用android、app这样的标签,为什么呢?
<--或者声明这个--> <-- xmlns:custom="http://schemas.android.com/apk/res-auto"-->
3:自定义view中使用
public class CustomView extends View { public CustomView(Context context, AttributeSet attrs) { super(context, attrs); TypedArray ta = context.obtainStyledAttributes(attrs, R.styleable.CustomView); String text = ta.getString(R.styleable.CustomeView_titletext); Bitmap mImage = BitmapFactory.decodeResource(getResources(), ta.getResourceId(R.styleable.CustomeView_image, 0)); int mTextSize = ta.getDimensionPixelSize(R.styleable.CustomeView_titleTextSize, (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_SP,16, getResources().getDisplayMetrics())); ta.recycle(); } public CustomView(Context context,AttributeSet attrs,int defStyleAttr){ super(context, attrs,defStyleAttr); TypedArray typedArray =context.getTheme().obtainStyledAttributes(attrs, R.styleable.CustomView,defStyleAttr,0); }}
4:TypedArray和AttributeSet的不同
AttributeSet
中的确保存的是该View声明的所有的属性,并且外面的确可以通过它去获取属性自定义和原有的属性
public CustomView(Context context, AttributeSet attrs) { super(context, attrs); int count = attrs.getAttributeCount(); for (int i = 0; i < count; i++) { String attrName = attrs.getAttributeName(i); String attrVal = attrs.getAttributeValue(i); Log.e(TAG, "attrName = " + attrName + " , attrVal = " + attrVal); } }
通过AttributeSet
可以获得布局文件中定义的所有属性的key和value,但通过AttributeSet
获取的值,如果是值是@的资源,那么引用都变成了@+数字的字符串。
ypedArray其实是用来简化我们的工作的,比如上例,如果布局中的属性的值是引用类型(比如:@dimen/dp100),如果使用AttributeSet去获得最终的像素值,那么需要第一步拿到id,第二步再去解析id。而TypedArray正是帮我们简化了这个过程。
贴一下:如果通过AttributeSet获取最终的像素值的过程:
int widthDimensionId = attrs.getAttributeResourceValue(0, -1); Log.e(TAG, "layout_width= "+getResources().getDimension(widthDimensionId));
5:declare-styleable
直接在attrs.xml中使用android:text属性。
注意,这里我们是使用已经定义好的属性,不需要去添加format属性(注意声明和使用的区别,差别就是有没有format)。
然后在类中这么获取:ta.getString(R.styleable.test_android_text);布局文件中直接android:text="@string/hello_world"即可。
declare-styleable的标签也可以不写
<?xml version="1.0" encoding="utf-8"?>
<?xml version="1.0" encoding="utf-8"?>
public class MyTextView extends View { private static final String TAG = MyTextView.class.getSimpleName(); private static final int[] mAttr = { android.R.attr.text, R.attr.testAttr }; private static final int ATTR_ANDROID_TEXT = 0; private static final int ATTR_TESTATTR = 1; public MyTextView(Context context, AttributeSet attrs) { super(context, attrs); // ==>use typedarray TypedArray ta = context.obtainStyledAttributes(attrs, mAttr); String text = ta.getString(ATTR_ANDROID_TEXT); int textAttr = ta.getInteger(ATTR_TESTATTR, -1); //输出 text = Hello world! , textAttr = 520 Log.e(TAG, "text = " + text + " , textAttr = " + textAttr); ta.recycle(); }}
可以看到我们声明了一个int数组,数组中的元素就是我们想要获取的attr的id。并且我们根据元素的在数组中的位置,定义了一些整形的常量代表其下标,然后通过TypedArray
进行获取。
https://blog.csdn.net/lmj623565791/article/details/45022631
更多相关文章
- RecyclerView手指按下时,item背景变色
- Android(安卓)setContentView() 详解
- android自定义Dialog实现底部弹窗
- Android(安卓)GridView属性集合
- Android(安卓)应用开发笔记 - 单项选择(RadioGroup, RadioButton)
- Android(安卓)中使用自定义字体的方法
- android带返回按钮的自定义标题栏
- android studio 导入 融云问题之一 兼容4.0一下版本
- Android手机防止休眠