闲来无事,某天上网链接到燎原网站(http://liaoyuan.io/)时发现背景的动态效果挺不错的,故移到android上面实现之。代码不也很简单多,直接贴上以供参考。由于是动态刷新,所以使用了surfaceview来处理,用view应该也可以。
网站效果图:
实现效果:
ParticleView.java
import java.util.ArrayList; import android.content.Context; import android.graphics.Canvas; import android.graphics.Color; import android.graphics.Paint; import android.util.AttributeSet; import android.view.SurfaceHolder; import android.view.SurfaceView; public class ParticleViewextends SurfaceView implements SurfaceHolder.Callback { public static final int TIME_INTERVAL = 100; private DrawThread drawThr; private static final int PART_NUM = 20; private static final int CIRCLE = 2; private static final int COUNTER_DIS = 100; private ArrayList<Particle> mParticles; private ArrayList<CounterParticle> mCounterPt; private int scrWdh, scrHgt; private Paint mPtPaint, mLinePaint; public ParticleView(Context context) { super(context); init(); } private void init() { this.getHolder().addCallback(this); drawThr = new DrawThread(this, getHolder()); mPtPaint = new Paint(); mPtPaint.setColor(0xff0791ec); mLinePaint = new Paint(); mLinePaint.setColor(0xff00ffff); } private void initData() { mParticles = new ArrayList<Particle>(); mCounterPt = new ArrayList<CounterParticle>(); for (int i = 0; i < PART_NUM; i++) { mParticles.add(new Particle(scrWdh, scrHgt)); } getPtCounter(); } private void getPtCounter() { mCounterPt.clear(); int end = PART_NUM - 1; for (int i = 0; i < end; i++) { Particle mLeft = mParticles.get(i); for (int j = i + 1; j < PART_NUM; j++) { Particle mRight = mParticles.get(j); if (Math.abs(mLeft.x - mRight.x) <= COUNTER_DIS && Math.abs(mLeft.y - mRight.y) <= COUNTER_DIS) { mCounterPt.add(new CounterParticle(mLeft.x, mLeft.y, mRight.x, mRight.y)); } } } } public ParticleView(Context context, AttributeSet attrs) { super(context, attrs); init(); } @Override public void surfaceChanged(SurfaceHolder arg0, int arg1, int arg2, int arg3) { scrWdh = arg2; scrHgt = arg3; initData(); } @Override public void surfaceCreated(SurfaceHolder holder) { if (!drawThr.isAlive()) { drawThr.start(); } } @Override public void surfaceDestroyed(SurfaceHolder holder) { drawThr.isRunning = false; drawThr = null; } public void doDraw(Canvas canvas) { canvas.drawColor(Color.WHITE); // 绘制粒子 for (int i = 0; i < PART_NUM; i++) { canvas.drawCircle(mParticles.get(i).x, mParticles.get(i).y, CIRCLE, mPtPaint); } int countSize = mCounterPt.size(); for (int i = 0; i < countSize; i++) { CounterParticle mCurCount = mCounterPt.get(i); canvas.drawLines(mCurCount.pts, mLinePaint); } } public void changeData() { for (int i = 0; i < PART_NUM; i++) { Particle mCurPart = mParticles.get(i); mCurPart.x += mCurPart.hor_v; mCurPart.y += mCurPart.ver_v; if (outRange(mCurPart)) { mParticles.remove(mCurPart); mParticles.add(i, new Particle(scrWdh, scrHgt)); } } getPtCounter(); } private boolean outRange(Particle mCurPart) { return mCurPart.x < 0 || mCurPart.x > scrWdh || mCurPart.y < 0 || mCurPart.y > scrHgt; } }
Particle.java
public class Particle{ private static int SPEED = 5; double ver_v; //垂直速度 double hor_v; //水平速度 int startX; //初始X坐标 int startY; //初始Y坐标 int x; //实时X坐标 int y; //实时Y坐标 public Particle(double ver_v, double hor_v, int x, int y) { super(); this.ver_v = ver_v; this.hor_v = hor_v; this.startX = x; this.startY = y; this.x = x; this.y = y; } public Particle(int scrWdh, int scrHgt) { int curX = (int) (Math.random() * scrWdh); int curY = (int) (Math.random() * scrHgt); this.hor_v = checkSpeedAvail(curX, scrWdh); this.ver_v = checkSpeedAvail(curY, scrHgt); this.startX = this.x = curX; this.startY = this.y = curY; } private int checkSpeedAvail(int curPos, int range) { int speed = (int) (Math.random() * SPEED); speed++; return curPos > range / 2 ? -speed : speed; } }
CounterParticle.java
public class CounterParticle{ float[] pts; public CounterParticle(int sx, int sy, int ex, int ey) { pts = new float[] { sx, sy, ex, ey }; } }
DrawThread.java
import android.graphics.Canvas; import android.view.SurfaceHolder; public class DrawThread extends Thread { ParticleViewpv; SurfaceHolder suraceHolder; boolean isRunning; int sleepSpan = 100; public DrawThread(ParticleView pv, SurfaceHolder suraceHolder) { this.isRunning = true; this.pv = pv; this.suraceHolder = suraceHolder; } @Override public void run() { Canvas canvas = null; while (isRunning) { try { canvas = suraceHolder.lockCanvas(); synchronized (suraceHolder) { pv.changeData(); pv.doDraw(canvas); } } catch (Exception e) { e.printStackTrace(); } finally { if (canvas != null) { suraceHolder.unlockCanvasAndPost(canvas); } } try { Thread.sleep(sleepSpan);// 线程休眠一段时间 } catch (Exception e) { e.printStackTrace();// 捕获并打印异常 } } } }
顺带推荐一个录制屏幕gif工具:gifcam
http://pan.baidu.com/s/1mgtjZoG