一、自定义带图片的组合控件
这次的自定义组合控件在前面Android自定义组合控件(一)的基础上进行,将添加带图片,以及文字可以使用引用的组合空件。具体原理是一样的,只是现在在布局里添加了一个ImageView控件,下面给出具体的步奏:
图1 带图片的组合控件效果图
1、编写自定义组合控件布局。自定义组合控件布局如下:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="center">
<!-- 添加一个显示图片的ImageView控件 -->
<ImageView
android:id="@+id/id_show_icon"
android:layout_width="40dp"
android:layout_height="40dp"
android:layout_centerVertical="true"/>
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_toRightOf="@id/id_show_icon"
android:layout_marginLeft="5dp"
android:orientation="vertical" >
<TextView
android:id="@+id/id_title_tv"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
<TextView
android:id="@+id/id_decscribe_tv"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="5dp" />
</LinearLayout>
</RelativeLayout>
2、创建自定义属性。在values文件下新建sttrs.xml文件,创建我们需要的属性。注意:此时文字的format就不在是单一的“string”了,而是引用和字符串结合的“reference|string”,顺便也说一下字体颜色、字体大小的设置,由于图片也可以是纯颜色,因此我们也加上颜色的引用。如下代码中的“showIcon”的format。
<?xml version="1.0" encoding="utf-8"?>
<resources>
<!-- 名称随便取,但建议还是要有意义 -->
<declare-styleable name="CustomUI">
<attr name="titleTip" format="reference|string" />
<attr name="describe" format="reference|string" />
<attr name="showIcon" format="reference|color" />
<attr name="titleTextSize" format="dimension" />
<attr name="describeTextSize" format="dimension" />
</declare-styleable>
</resources>
3、构造自定义组合控件类。新建一个类继承Relativelayout或者LinearLayout,添加它的构造函数,自定义一个函数,将布局引入进来,并在构造方法里调用。自定义函数引入布局代码如下:
/**
* 将写好的布局引入进来
* @param context
*/
private void initView(Context context) {
View.inflate(context, R.layout.item_my_relativelayout, this);
id_show_icon = (ImageView) this.findViewById(R.id.id_show_icon);
id_title_tv = (TextView) this.findViewById(R.id.id_title_tv);
id_decscribe_tv = (TextView) this.findViewById(R.id.id_decscribe_tv);
}
4、获取自定义属性的值。获取属性的值有两种(我所熟悉的,要是有更好的办法,谢谢告知)。
(1)第一种是属性数组。我们用这种方式来获取字体大小(不知道是不是我弄错了,我用直接获取的方法去获取dimension属性,程序直接Over,你可以试一试,也许是我弄错了),具体代码如下:
//R.styleable.CustomUI 这里的CustomUI就是我们定义的属性名称
TypedArray a = context.obtainStyledAttributes(attrs,
R.styleable.CustomUI);
//取得文本大小,它需要填写一个默认值
float titleTextSize = a.getDimension(R.styleable.Relativelayout_titleTextSize, 18);
float describeTextSize = a.getDimension(R.styleable.Relativelayout_describeTextSize, 14);
这样,我们便得到了设置字体大小的值,就可以直接通过Java代码设置控件的字体大小了。不不不,别着急,这里得到的字体大小的单位是px,我们还要将它转化为sp,否则手机不兼容哦!(DensityUtil.px2sp(,)是一个屏幕像素转换工具类后面会给出)
// 转化单位
titleTextSize = DensityUtil.px2sp(context, titleTextSize);
describeTextSize = DensityUtil.px2sp(context, describeTextSize);
(2)第二种是直接获取。首先获取带引用的字体属性吧!带引用的字符串获取到后,我们并不能直接得到它的值,他返回该字符串的引用ID,如:“@7f050000”,直接将它设置的话,将会完整的给你显示出来,我用了一个最笨的方法,就是判断字符串里是否含有“@”,如果有,再去获取资源里的字符串,没有说明就是我们想要的字符串(相信你会有更好的办法)。获取方法如下:
//我们将命名空间定义为一个局部常量
private final String NAMESPACE = "http://schemas.android.com/apk/res/com.myinterpserson";
/******************我是华丽的分割线************************/
String titleTip = attrs.getAttributeValue(NAMESPACE, "titleTip");
String describe = attrs.getAttributeValue(NAMESPACE, "describe");
if(titleTip.indexOf("@") != -1){
String temp = StringUtils.substring(titleTip,1, titleTip.length());
titleTip = context.getResources().getString(Integer.parseInt(temp));
}
if(describe.indexOf("@") != -1){
String temp = StringUtils.substring(describe,1, titleTip.length());
describe = context.getResources().getString(Integer.parseInt(temp));
}
图片的获取,比字符串简单多了,都不用判断了。得到这个ID后,拿着这个ID就往控件上那么一塞,就O了!
int showIcon = attrs.getAttributeResourceValue(NAMESPACE, "showIcon",R.drawable.img_item_add);
到此,带图片,带引用,带设置字体大小的组合控件就完成了,其用法和教程(一)中的方法是一样的,一些get,set方法也是一样的,不在鳌诉。如有错误,还望指正!
屏幕像素转换工具类DensityUtil.java如下:
/**
* 将dip转换为px
* @param context
* @param dpValue
* @return
*/
public static int dip2px(Context context, float dpValue) {
final float scale = context.getResources().getDisplayMetrics().density;
return (int) (dpValue * scale + 0.5f);
}
/**
* 将px转换为dip
* @param context
* @param pxValue
* @return
*/
public static int px2dip(Context context, float pxValue) {
final float scale = context.getResources().getDisplayMetrics().density;
return (int) (pxValue / scale + 0.5f);
}
/**
* 将px值转换为sp值,保证文字大小不变
*
* @param pxValue
* @param fontScale
* (DisplayMetrics类中属性scaledDensity)
* @return
*/
public static int px2sp(Context context, float pxValue) {
final float fontScale = context.getResources().getDisplayMetrics().scaledDensity;
return (int) (pxValue / fontScale + 0.5f);
}
/**
* 将sp值转换为px值,保证文字大小不变
*
* @param spValue
* @param fontScale
* (DisplayMetrics类中属性scaledDensity)
* @return
*/
public static int sp2px(Context context, float spValue) {
final float fontScale = context.getResources().getDisplayMetrics().scaledDensity;
return (int) (spValue * fontScale + 0.5f);
}