Android自定义优惠券解析

来源:互联网 发布:码云 webhook php 编辑:程序博客网 时间:2024/03/29 23:23

自定义优惠券View在github上已经很多了,自己做也没什么特色,参考了网上的实现方式,对实现原理有了一些自己的理解,看代码总是很容易的,敲的过程去揣摩别人的思路,真正去理解才是我们要做的。

首先来看效果一:

这是网上流行的效果

这里写图片描述

看效果,主要是上下画圆,思路就是draw圆来覆盖掉布局背景,从而实现波浪效果,下面来看看怎么计算。

第一步:思考我们需要设置哪些参数

   //圆的半径    private int radius=10;    //间隔长度    private int mLength=8;    //画笔    private Paint mPaint;    //圆的个数    private int mCircleNum;    //不能整除时的间隔    private int remain;

这里讲一下不能整除时的间隔,如果能整除的情况下View的width=(2*半径+间隔)*圆的个数+间隔,这样计算没有问题,但是当view的宽度比这个距离要大一点的时候,就是不满足整除的时候,最两侧的间距要稍微大一点,这就需要计算不能整除时的间隔。

 protected void onSizeChanged(int w, int h, int oldw, int oldh) {        super.onSizeChanged(w, h, oldw, oldh);        //获取不能整除时的间隔        remain = (w - mLength) % (2 * radius + mLength);        //获取圆的个数        mCircleNum = (w - mLength) / (2 * radius + mLength);    }    @Override    protected void onDraw(Canvas canvas) {        super.onDraw(canvas);        for (int i = 0; i < mCircleNum; i++) {            //计算圆x轴的坐标            float x = mLength + radius + remain / 2 + ((mLength + radius * 2) * i);            //上边花园            canvas.drawCircle(x, 0, radius, mPaint);            //下边画圆            canvas.drawCircle(x, getHeight(), radius, mPaint);        }        }

效果:

这里写图片描述

这是对前人代码的理解,当然我们还需要在考虑如何在此基础添加什么的样式!

效果1:

这里写图片描述

在两侧加虚线:

        Paint paint = new Paint();        paint.setAntiAlias(true);        paint.setColor(Color.WHITE);        paint.setStyle(Paint.Style.STROKE);        //加虚线        paint.setPathEffect(new DashPathEffect(new float[]{24, 12}, 0));        paint.setStrokeWidth(6);        //只能路径加虚线,drawLine不行        Path path=new Path();        path.moveTo(remain/2+mLength+2*radius, 2*radius);        path.lineTo(remain/2+mLength+2*radius, getHeight()-2*radius);        canvas.drawPath(path, paint);        //右侧虚线        Path path2=new Path();        path2.moveTo(getWidth()-remain/2-mLength-2*radius,2*radius);        path2.lineTo(getWidth()-remain/2-mLength-2*radius,getHeight()-2*radius);        canvas.drawPath(path2, paint);

距离可以根据需求来调整,这个没啥可说的额。

效果二:

这里写图片描述

加虚线边框

        Path path3=new Path();        //左上坐标起点        path3.moveTo(remain/2+mLength, 2*radius);        //左下坐标        path3.lineTo(remain/2+mLength, getHeight()-2*radius);        //右下坐标        path3.lineTo(getWidth()-remain/2-mLength,getHeight()-2*radius);        //右上坐标        path3.lineTo(getWidth()-remain/2-mLength,2*radius);        //关闭边框        path3.close();        canvas.drawPath(path3, paint);

考虑:这样做或许只能适应自己的需求,而并不具有通用性。

要具有通用性,必须要用到自定义的属性,将种种变量封装起来,这样就可随意控制圆的大小,背景颜色,间隔大小,虚线等。

具体就不细说了,恩就先到这吧。

全部代码:

package com.example.com.testview;import android.content.Context;import android.graphics.Canvas;import android.graphics.Color;import android.graphics.DashPathEffect;import android.graphics.Paint;import android.graphics.Path;import android.util.AttributeSet;import android.widget.LinearLayout;/** * Created by Administrator on 2016/9/23. */public class CardViews extends LinearLayout {    //圆的半径    private int radius = 10;    //间隔长度    private int mLength = 8;    //画笔    private Paint mPaint;    //圆的个数    private int mCircleNum;    //不能整除时的间隔    private int remain;    public CardViews(Context context) {        super(context);        init();    }    public CardViews(Context context, AttributeSet attrs) {        super(context, attrs);        init();    }    public CardViews(Context context, AttributeSet attrs, int defStyleAttr) {        super(context, attrs, defStyleAttr);        init();    }    private void init() {        mPaint = new Paint();        mPaint.setAntiAlias(true);        mPaint.setDither(true);        mPaint.setColor(Color.WHITE);        mPaint.setStyle(Paint.Style.FILL);    }    @Override    protected void onSizeChanged(int w, int h, int oldw, int oldh) {        super.onSizeChanged(w, h, oldw, oldh);        remain = (w - mLength) % (2 * radius + mLength);        mCircleNum = (w - mLength) / (2 * radius + mLength);    }    @Override    protected void onDraw(Canvas canvas) {        super.onDraw(canvas);        for (int i = 0; i < mCircleNum; i++) {            float x = mLength + radius + remain / 2 + ((mLength + radius * 2) * i);            canvas.drawCircle(x, 0, radius, mPaint);            canvas.drawCircle(x, getHeight(), radius, mPaint);        }        Paint paint = new Paint();        paint.setAntiAlias(true);        paint.setColor(Color.WHITE);        paint.setStyle(Paint.Style.STROKE);        paint.setPathEffect(new DashPathEffect(new float[]{24, 12}, 0));        paint.setStrokeWidth(6);//        Path path=new Path();//        path.moveTo(remain/2+mLength+2*radius, 2*radius);//        path.lineTo(remain/2+mLength+2*radius, getHeight()-2*radius);//        canvas.drawPath(path, paint);////        Path path2=new Path();//        path2.moveTo(getWidth()-remain/2-mLength-2*radius,2*radius);//        path2.lineTo(getWidth()-remain/2-mLength-2*radius,getHeight()-2*radius);//        canvas.drawPath(path2, paint);        Path path3=new Path();        path3.moveTo(remain/2+mLength, 2*radius);        path3.lineTo(remain/2+mLength, getHeight()-2*radius);        path3.lineTo(getWidth()-remain/2-mLength,getHeight()-2*radius);        path3.lineTo(getWidth()-remain/2-mLength,2*radius);        path3.close();        canvas.drawPath(path3, paint);    }}

参考:
http://blog.csdn.net/u012162503/article/details/51433490

更好的:
https://github.com/dongjunkun/CouponView

0 0
原创粉丝点击