1、前言
相信很多人都用過騰訊的手機管家,用過這個App的人都應該知道桌面的火箭一鍵加速這個功能,當然這裏我不是推薦大家去使用手機管家,相反這個功能大家還是小心爲妙,我的U8800加完速之後快是快了,但這傢伙把我手機的任務欄的進程都給搞蹦死了,去年買了個表啊。。。
吐槽不多說,來正題,最近剛好在學UI設計就去研究一下這個小火箭是怎麼做出來的。先來了解一下小火箭有神馬動作先,首先在沒有觸碰它時,就是一個電源的顯示或是
一個圖標依附在屏幕的兩側,點擊變成小火箭,可以跟隨拖動,當沒有放到指定位置就在次回去屏幕兩側。當放到了指定位置就會出現一個火箭發射的動畫。瞭解完效果,我
們繼續說。
2、完成的效果圖
3、簡單設計過程
自定義一個View完成火箭的拖動、顯示,然後拖動到指定位置後就回調一個接口播放火箭發射動畫。自定義View裏面的關鍵就是動態的改變matrix,以達到火箭移動的效果
4、核心代碼
自定義View的代碼
package com.spring.lettel;
import android.app.Activity;
import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Canvas;
import android.graphics.Matrix;
import android.graphics.Paint;
import android.graphics.Point;
import android.util.AttributeSet;
import android.view.MotionEvent;
import android.view.View;
/**
* 火箭主體類
* @author wissea
*
*/
public class Rocket extends View {
private Bitmap bitmap;
private Bitmap rocket;
//文字欄的三種狀態
private Bitmap[] stand = {
BitmapFactory.decodeResource(getResources(),
R.drawable.desktop_bg_tips_1),
BitmapFactory.decodeResource(getResources(),
R.drawable.desktop_bg_tips_2),
BitmapFactory.decodeResource(getResources(),
R.drawable.desktop_bg_tips_3) };
private Matrix matrix = new Matrix();
private Paint paint = new Paint();
// 是否觸摸
private boolean isTouch = false;
private Point point = new Point();
private LocationChangeListener changeListener =null;
//記錄屏幕的大小
private int screenW;
private int screenH;
//灰機和提示是否重合了
private boolean isFly = false;
public Rocket(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
}
public Rocket(Context context, AttributeSet attrs) {
super(context, attrs);
bitmap = BitmapFactory.decodeResource(getResources(),
R.drawable.floating_desktop_bg_danger);
rocket = BitmapFactory.decodeResource(getResources(),
R.drawable.desktop_rocket_launch_1);
screenW = ((Activity) context).getWindowManager().getDefaultDisplay()
.getWidth();
screenH = ((Activity) context).getWindowManager().getDefaultDisplay()
.getHeight();
}
public Rocket(Context context) {
super(context);
}
@Override
protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
//判斷Touch
if (!isTouch) {
matrix.reset();
if (isFly) {
if(changeListener!=null)
changeListener.onchange();
} else {
if (point.x < screenW / 2) {
matrix.postTranslate(0, point.y);
} else {
matrix.postTranslate(screenW - bitmap.getWidth(), point.y);
}
canvas.drawBitmap(bitmap, matrix, paint);
}
} else {
matrix.reset();
int c = point.x % 2;
matrix.postTranslate(screenW / 2 - stand[c].getWidth() / 2, screenH
- stand[c].getHeight() - 100);
//判斷重合
if (Math.abs(screenW / 2 - (point.x - rocket.getWidth()/2)) < stand[c]
.getWidth() / 2
&& Math.abs(screenH - stand[c].getHeight() - 100
- (point.y - rocket.getHeight())) < stand[c]
.getHeight()) {
canvas.drawBitmap(stand[2], matrix, paint);
isFly = true;
} else {
isFly =false;
canvas.drawBitmap(stand[c], matrix, paint);
}
matrix.reset();
matrix.postTranslate(point.x - rocket.getWidth()/2,
point.y - rocket.getHeight());
canvas.drawBitmap(rocket, matrix, paint);
}
}
@Override
public boolean onTouchEvent(MotionEvent event) {
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
//過濾無效點擊
if ((event.getX() < screenW - bitmap.getWidth() && event.getX() > bitmap
.getWidth())
|| Math.abs(point.y - event.getY()) > bitmap.getHeight()) {
return false;
}
isTouch = true;
break;
case MotionEvent.ACTION_MOVE:
//更新座標
point.x = (int) event.getX();
point.y = (int) event.getY();
break;
case MotionEvent.ACTION_CANCEL:
isTouch = false;
break;
case MotionEvent.ACTION_UP:
isTouch = false;
break;
}
invalidate();
return true;
}
//重置狀態
public void reset(){
isFly =false;
point.y =screenH/2;
invalidate();
}
//監聽重合
public void setOnChangeListener(LocationChangeListener changeListener){
this.changeListener =changeListener;
}
}
5、總結
這個UI製作的時候老是糾結於,在View裏面播放動畫,找了老半天沒有找到解決方法,最後就把動畫放到了外面回調一下,雖然大體的效果出來了,但個人覺得還是有
不完善的地方,比如發射動畫不是很平滑,沒有加入電量顯示,沒有控制邊界,小火箭拉到屏幕外後就看不到控制的小圓點了。最後歡迎大家的討論,和指點。
有些同學反映飛不起來,可能是版本問題2.3有些Api跟4.0不一樣導致的,這個是用4.0開發的。
有時間在補上這個問題
5、廣告
最近搞了個微信公衆號,爲各種程序員枯燥的寫碼生活添加一些生活調料,
在等待編譯的過程看一篇美麗的圖文放鬆放鬆肌肉。希望各位看官賞臉關注一下
公衆號:馬桶上的哲學
讀哲名理,提升逼格