package com.com.mr_wrong.Bezier; import android.content.Context; import android.graphics.Canvas; import android.graphics.Color; import android.graphics.Paint; import android.graphics.Path; import android.graphics.PointF; import android.graphics.RectF; import android.os.Handler; import android.os.Message; import android.util.AttributeSet; import android.view.View; import java.util.ArrayList; import java.util.List; import java.util.Timer; import java.util.TimerTask; /** * Created by Mr_Wrong on 15/7/9. */ public class MyWaveView extends View { private int mWidth; private int mHeight; private Paint mPaint; private float radius; private float centre; private Path mPath, mPath1; private List<PointF> mPoints; private float mWaveHeight; private float mWaveWidth; private RectF mRect; private float mLeftSide; private float mMoveLen; private float mLevelLine = 30; private static final float SPEED = 1.7F; private Boolean isMeasured = false; private Timer timer; private MyTimerTask mTask; Handler updateHandler = new Handler() { @Override public void handleMessage(Message msg) { mMoveLen += SPEED; mLeftSide += SPEED; // 波形平移 for (int i = 0; i < mPoints.size(); i++) { mPoints.get(i).x = (mPoints.get(i).x + SPEED); switch (i % 4) { case 0: case 2: mPoints.get(i).y = (mLevelLine); break; case 1: mPoints.get(i).y = (mLevelLine + mWaveHeight); break; case 3: mPoints.get(i).y = (mLevelLine - mWaveHeight); break; } } if (mMoveLen >= mWaveWidth) { // 波形平移超过一个完整波形后复位 mMoveLen = 0; resetPoints(); } invalidate(); } }; public MyWaveView(Context context) { super(context); init(context); } public MyWaveView(Context context, AttributeSet attrs) { super(context, attrs); init(context); } public MyWaveView(Context context, AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr); init(context); } @Override protected void onSizeChanged(int w, int h, int oldw, int oldh) { mWidth = w; mHeight = h; radius = mWidth / 2; centre = mWidth / 2; } @Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { super.onMeasure(widthMeasureSpec, heightMeasureSpec); if (!isMeasured) { isMeasured = true; mWaveHeight = mWidth / 5; mWaveWidth = (float) (mWidth * 1.5); mLeftSide = -mWaveWidth; int n = (int) Math.round(mWidth / mWaveWidth + 0.5); for (int i = 0; i < (4 * n + 5); i++) { float x = i * mWaveWidth / 4 - mWaveWidth; float y = 0; switch (i % 4) { case 0: case 2: //水平线上的点 y = mLevelLine; break; case 1://向下的 y = mLevelLine + mWaveHeight; break; case 3://向上的 y = mLevelLine - mWaveHeight; break; } mPoints.add(new PointF(x, y)); } } } private void init(Context context) { mPaint = new Paint(); mPaint.setAntiAlias(true); mPaint = new Paint(); mPaint.setAntiAlias(true); mPaint.setStyle(Paint.Style.FILL); timer = new Timer(); mPoints = new ArrayList<PointF>(); mPath = new Path(); mPath1 = new Path(); mRect = new RectF(centre - radius, centre - radius, centre + radius, centre + radius); } @Override protected void onDraw(Canvas canvas) { super.onDraw(canvas); mPaint.setColor(Color.BLACK); canvas.drawCircle(centre, centre, radius, mPaint); //mPath.reset(); mPath.moveTo(mPoints.get(0).x, mPoints.get(0).y); int i = 0; for (; i < mPoints.size() - 2; i += 2) { mPath.quadTo(mPoints.get(i + 1).x, mPoints.get(i + 1).y, mPoints.get(i + 2).x, mPoints.get(i + 2).y); } mPath.lineTo(mPoints.get(i).x, mHeight); mPath.lineTo(mLeftSide, mHeight); mPath.close(); mPath1.arcTo(mRect, 0, 360, true); canvas.clipPath(mPath1); mPaint.setColor(Color.BLUE); canvas.drawPath(mPath,mPaint); } private void resetPoints() { mLeftSide = -mWaveWidth; for (int i = 0; i < mPoints.size(); i++) { mPoints.get(i).x = (i * mWaveWidth / 4 - mWaveWidth); } } @Override public void onWindowFocusChanged(boolean hasWindowFocus) { super.onWindowFocusChanged(hasWindowFocus); // 开始波动 start(); } private void start() { if (mTask != null) { mTask.cancel(); mTask = null; } mTask = new MyTimerTask(updateHandler); timer.schedule(mTask, 0, 10); } class MyTimerTask extends TimerTask { Handler handler; public MyTimerTask(Handler handler) { this.handler = handler; } @Override public void run() { handler.sendMessage(handler.obtainMessage()); } } }