Android提供的控件有时候无法满足我们项目的需求,所以需要我们自定义View的样式以及事件监听。
自定义View的步骤:
1、自定义View的属性
2、在View的构造方法中获得我们自定义的属性
3、重写onMesure
4、重写onDraw
其中3不一定是必须的,当然了大部分情况下还是需要重写的。
下面通过实现一个圆来展示进度进行分析。
1> 自定义View的属性,首先在res/values/ 下建立一个attrs.xml 。
<?xml version="1.0" encoding="utf-8"?> <resources> <attr name="firstcolor" format="color"/> <attr name="secondcolor" format="color"/> <attr name="speed" format="integer"/> <attr name="circlewidth" format="dimension"/> <declare-styleable name="CircleView"> <attr name="firstcolor"/> <attr name="secondcolor"/> <attr name="speed"/> <attr name="circlewidth"/> </declare-styleable> </resources>
2> 在布局中声明自定义view
<?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" xmlns:custom="http://schemas.android.com/apk/res-auto" android:id="@+id/activity_main" android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="vertical" tools:context="com.example.selfview.MainActivity"> <com.example.selfview.CircleView android:layout_gravity="center" android:layout_width="200dp" android:layout_height="200dp" custom:firstcolor="#FFF0" custom:secondcolor="#000" custom:circlewidth="20sp" custom:speed="10" /> </LinearLayout>
3> 在自定义view的方法中,获取我们的样式以及画图。重写了3个构造方法,默认的布局文件调用的是两个参数的构造方法。
public class CircleView extends View { private int firstcolor; private int secondcolor; private int speed; private int criclewidth; private Paint mPaint; private int mProgress; public CircleView(Context context) { this(context,null); } public CircleView(Context context, AttributeSet attrs) { this(context, attrs,0); } public CircleView(Context context, AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr); TypedArray a = context.getTheme().obtainStyledAttributes(attrs, R.styleable.CircleView, defStyleAttr, 0); firstcolor = a.getColor(R.styleable.CircleView_firstcolor, Color.GREEN); secondcolor = a.getColor(R.styleable.CircleView_secondcolor,Color.RED); criclewidth = a.getDimensionPixelSize(R.styleable.CircleView_circlewidth, (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_PX,20,getResources().getDisplayMetrics())); speed = a.getInt(R.styleable.CircleView_speed,20); a.recycle(); new Thread(new Runnable() { @Override public void run() { while (true){ try { Thread.sleep(100); } catch (InterruptedException e) { e.printStackTrace(); } if (mProgress <= 360){ mProgress += speed; }else { Thread.interrupted(); } } } }).start(); } @Override protected void onDraw(Canvas canvas) { super.onDraw(canvas); int centre = getWidth() / 2; int radius = centre - criclewidth / 2; mPaint = new Paint(); mPaint.setStrokeWidth(criclewidth); // 设置圆环的宽度 mPaint.setAntiAlias(true); // 消除锯齿 mPaint.setStyle(Paint.Style.STROKE); // 设置空心 RectF oval = new RectF(centre - radius, centre - radius, centre + radius, centre + radius); mPaint.setColor(firstcolor); // 设置圆环的颜色 canvas.drawCircle(centre, centre, radius, mPaint); // 画出圆环 mPaint.setColor(secondcolor); // 设置圆环的颜色 canvas.drawArc(oval, -90, mProgress, false, mPaint); // 根据进度画圆弧 Log.d("azheng",String.valueOf(mProgress)); invalidate(); } }
4> 因为我们是静态的自定义view,所以在MainActivity中不需要调用。
public class MainActivity extends AppCompatActivity { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); } }
到这里,我们的实例就可以运行了。
我们没有重写onMeasure方法,必要的情况下,可以通过该方法来调整我们的view的显示。当然,我们也可以为自定义的view设置事件监听,比如在构造方法中通过
this.setOnClickListener()实现点击监听。
参考:
http://blog.csdn.net/lmj623565791/article/details/24252901/
原文:http://www.cnblogs.com/xiaozhuazheng/p/6670944.html