自定义view--瓶分控件
最新在学习android自定义view,记下笔记
效果展示:(非成品)

分析:
处理用户交互部分(onTouch())
两张资源图片,没有选中的图片和选中的图片
开发流程:
1、初始化属性
2、设置宽高
3、绘制
4、处理交互逻辑
下面开始:
一、创建view,设置所要用到的属性,我最简单化
设置需要用到的属性attrs
<declare-styleable name="RateBar">
<attr name="starNormal" format="reference"/>
<attr name="starFocus" format="reference"/>
<attr name="gradeNumber" format="integer"/>
declare-styleable>
创建view
public class RateBar extends View { public RateBar2(Context context) { this(context,null); } public RateBar(Context context, @Nullable AttributeSet attrs) { this(context, attrs,0); } public RateBar(Context context, @Nullable AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr); } }
二、初始化属性
//总共有几分 private int mGradeNumber = 5; //当前几分 private int mCurrentGrade = 0; //图片 private Bitmap mStarNormalBitmap, mStarFocusBitmap;
public RateBar(Context context, @Nullable AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr); //处理属性 TypedArray typedArray = context.obtainStyledAttributes(attrs, R.styleable.RateBar); //检查资源是否设置 int starNormalResId = typedArray.getResourceId(R.styleable.RateBar_starNormal,0); if(starNormalResId == 0){ throw new RuntimeException("请设置属性 starNormal "); } int starFocusResId = typedArray.getResourceId(R.styleable.RateBar_starFocus,0); if(starFocusResId == 0){ throw new RuntimeException("请设置属性 starFocus "); } //获取总分 mGradeNumber = typedArray.getInt(R.styleable.RateBar_gradeNumber,mGradeNumber); mCurrentGrade = mGradeNumber; mStarNormalBitmap = BitmapFactory.decodeResource(getResources(), starNormalResId); mStarFocusBitmap = BitmapFactory.decodeResource(getResources(), starFocusResId); typedArray.recycle(); }
三、设置宽高
@Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { super.onMeasure(widthMeasureSpec, heightMeasureSpec); //宽:总分 * 资源的宽度 //高:资源高度 int widSize = mStarNormalBitmap.getWidth() * mGradeNumber; int heiSize = mStarNormalBitmap.getHeight(); widSize += getPaddingLeft() + getPaddingRight(); heiSize += getPaddingTop() + getPaddingBottom(); //设置宽高 setMeasuredDimension(widSize,heiSize); }
四、绘制星星
@Override protected void onDraw(Canvas canvas) { super.onDraw(canvas); //先画总分 for (int i = 0; i < mGradeNumber; i++) { int x = i * mStarFocusBitmap.getWidth(); x += getPaddingLeft(); if(i <= mCurrentGrade){ //如果比当前分小,画selectpnd canvas.drawBitmap(mStarFocusBitmap,x,getPaddingTop(),null); }else { canvas.drawBitmap(mStarNormalBitmap,x,getPaddingTop(),null); } } }
五、处理交互逻辑
@Override public boolean onTouchEvent(MotionEvent event) { Log.d("ceshi",""+event.getAction()); //当前鼠标相对宽度 switch (event.getAction()){ case MotionEvent.ACTION_DOWN: case MotionEvent.ACTION_MOVE: // case MotionEvent.ACTION_UP: // 计算分数 float moveX = event.getX(); int currentGrade = (int) ( (moveX - getPaddingLeft())/(mStarFocusBitmap.getWidth())); // 范围问题 if(currentGrade<0){ currentGrade = 0; } if(currentGrade>mGradeNumber){ currentGrade = mGradeNumber; } // 分数相同的情况下不要绘制了 , 尽量减少onDraw()的调用 if(currentGrade == mCurrentGrade){ return true; } // 再去刷新显示 mCurrentGrade = currentGrade; invalidate();// 去调用onDraw() } return true; }