Android自定义控件并且使其可以在xml中自定义属性

为什么要自定义View

android开发中自定义View的好处是显而易见的。比如说下面的这个顶部导航,它被设计出现在应用的每个界面,但每次的内容却不尽相同。我们不能在每个layout资源中都配置一组相同的View吧?如果使用标签,虽然解决了布局文件的重用性,但是相关View的初始化设置还是没能够重用(集中),需要每次都采用view.findViewById(id)来初始化他们。

Android自定义控件并且使其可以在xml中自定义属性_第1张图片

有了对“可重用性”的考量,我们来完成一次对自定义View的探索。

第一步,创建自定义View的布局文件

这里创建的布局文件和平日里为Activity或Fragment创建的布局文件没有区别,例如下面的xml创建了一个上面是图片,下面是文字的自定义View布局:




    

    

第二步,创建继承自View或其子类的自定义View

这里有一个小技巧,即 继承自定义View布局中的跟元素,会为你省很多代码的编写工作。比如,上面的布局文件中,根元素是LinearLayout,那么我们的自定义View就继承LinearLayout:
package org.xiaom.customView.view;

import org.xiaom.customView.R;

public class MyView extends LinearLayout {
	private View root = null;
	//上面的img
	private ImageView imgView = null;
	//img下面的text
	private TextView txtView = null;

	public MyView(Context context, AttributeSet attrs) {
		super(context, attrs);
		initView(context);
	}

	public MyView(Context context) {
		super(context);
		initView(context);
	}

	private void initView(Context context) {
		LayoutInflater inflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
		root = inflater.inflate(R.layout.view_my_view, this,true);
		imgView = (ImageView) root.findViewById(R.id.img);
		txtView = (TextView) root.findViewById(R.id.txt);
	}

}

第三步,在xml中配置、使用自定义View

在完成上面的自定义操作后,接下来就可以像使用android原生组件那样使用我们的自定义View了。需要注意的是,自定义View在xml中声明使用时,必须采用全类名(类全名- -)。


	
    

    

接下来就很简单了,我们直接使用Activity.this.setContentView(layouId)方法即可。


同学A:说好的,在xml中使用自定义属性呢,说好的呢。。。。。
我:我他妈又卜是煞笔,再酱紫我要报警了(打dota的同学目测秒懂~~~~)

第四步,配置declare-styleable以声明自定义属性

我们在res/values/下新建一个attr.xml文件,根元素为。添加如下分支:


    
        
        
    
下的format有多个取值,此处不赘述了。更多关于这方面的资料,可以参见 这篇博文。

第五步,配置自定义属性并读取、应用

读取自定义属性的步骤我们放到该View的构造方法里:修改后的MyView.java就变成了:

package org.xiaom.customView.view;

import org.xiaom.customView.R;

public class MyView extends LinearLayout {
	private View root = null;
	// 上面的img
	private ImageView imgView = null;
	// img下面的text
	private TextView txtView = null;
	// 上面的图像资源Id
	Drawable img;
	// 文字内容
	String text;

	public MyView(Context context, AttributeSet attrs) {
		super(context, attrs);
		TypedArray ta = context.obtainStyledAttributes(attrs,R.styleable.myView);
		img = ta.getDrawable(R.styleable.myView_img);
		text = ta.getString(R.styleable.myView_text);
		initView(context);
		//记得此处要recycle();
		ta.recycle();
	}

	private void initView(Context context) {
		LayoutInflater inflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
		root = inflater.inflate(R.layout.view_my_view, this, true);
		imgView = (ImageView) root.findViewById(R.id.img);
		txtView = (TextView) root.findViewById(R.id.txt);
		//将自定义属性的值传递给对应View
		imgView.setBackgroundResource(R.drawable.icon_consultation);
		txtView.setText(text);
	}

}
下面的xml表明如何在xml中配置自定义属性:
注:请仔细查看下面xml中单注释内容





    

    

    
好,大功告成。这里是本博文 实例的Eclipse工程
任何需要积分的下载,都是耍流氓。


你可能感兴趣的:(Android)