国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 系統 > Android > 正文

android自定義View實現手勢解鎖

2019-10-22 18:10:09
字體:
來源:轉載
供稿:網友

有時候為了程序的安全性,我們經常要采取一些安全措施,就像我們常用的支付寶那樣,隔一定的時間再回到應用程序時會讓用戶利用手勢去解鎖應用程序,最近由于項目需求,也要求做這樣一個功能,當用戶切出本應用程序15分鐘后回來,讓用戶手勢解鎖,整個需求的難點就在如何實現這個手勢鎖,開始一點頭緒也沒有,沒有一點思路去實現這個手勢解鎖功能,在google了一番后看了一篇非常好的博客后,按照博主的思路的確是可以實現一個十分不錯的手勢鎖View,也參考了下那位大神的代碼,下面是我根據他的思路和代碼片段實現的一個自定義手勢解鎖 View,先看效果圖.

這是自定義View的初始效果圖:

android,View,手勢解鎖

以下是繪制手勢時的效果圖:

android,View,手勢解鎖

下面是實現的demo代碼:

package com.example.gesturelock;  import java.util.ArrayList; import java.util.List; import java.util.Timer; import java.util.TimerTask;  import android.content.Context; import android.graphics.Canvas; import android.graphics.Color; import android.graphics.Paint; import android.graphics.Path; import android.util.AttributeSet; import android.view.MotionEvent; import android.view.View;  import com.example.gesturelock.GestureLockView.OnGestureFinishListener;  public class MyGestureLockView extends View {    /**    * 不同狀態的畫筆    */   private Paint paintNormal;   private Paint paintOnTouch;   private Paint paintInnerCycle;   private Paint paintLines;   private Paint paintKeyError;    private MyCycle[] cycles;   private Path linePath = new Path();   private List<Integer> linedCycles = new ArrayList<Integer>();   private OnGestureFinishListener onGestureFinishListener;   private String key;   private int eventX, eventY;   private boolean canContinue = true;   private boolean result;   private Timer timer;    /**    * 不同狀態下的色值    */   private int OUT_CYCLE_NORMAL = Color.rgb(108, 119, 138); // ??????????   private int OUT_CYCLE_ONTOUCH = Color.rgb(025, 066, 103); // ?????????   private int INNER_CYCLE_ONTOUCH = Color.rgb(002, 210, 255); // ?????????   private int LINE_COLOR = Color.argb(127, 002, 210, 255); // ?????????   private int ERROR_COLOR = Color.argb(127, 255, 000, 000);    public void setOnGestureFinishListener(       OnGestureFinishListener onGestureFinishListener) {     this.onGestureFinishListener = onGestureFinishListener;   }    public void setKey(String key) {     this.key = key;   }    public MyGestureLockView(Context context, AttributeSet attrs, int defStyle) {     super(context, attrs, defStyle);     init();   }    public MyGestureLockView(Context context, AttributeSet attrs) {     super(context, attrs);     init();   }    public MyGestureLockView(Context context) {     super(context);     init();   }    private void init() {      paintNormal = new Paint();     paintNormal.setAntiAlias(true);     paintNormal.setStrokeWidth(3);     paintNormal.setStyle(Paint.Style.STROKE);      paintOnTouch = new Paint();     paintOnTouch.setAntiAlias(true);     paintOnTouch.setStrokeWidth(3);     paintOnTouch.setStyle(Paint.Style.STROKE);      paintInnerCycle = new Paint();     paintInnerCycle.setAntiAlias(true);     paintInnerCycle.setStyle(Paint.Style.FILL);      paintLines = new Paint();     paintLines.setAntiAlias(true);     paintLines.setStyle(Paint.Style.STROKE);     paintLines.setStrokeWidth(6);      paintKeyError = new Paint();     paintKeyError.setAntiAlias(true);     paintKeyError.setStyle(Paint.Style.STROKE);     paintKeyError.setStrokeWidth(3);    }    @Override   protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {     // TODO Auto-generated method stub     super.onMeasure(widthMeasureSpec, heightMeasureSpec);   }    @Override   protected void onLayout(boolean changed, int left, int top, int right,       int bottom) {     // TODO Auto-generated method stub     super.onLayout(changed, left, top, right, bottom);     int perSize = 0;     if (cycles == null && (perSize = getWidth() / 6) > 0) {        cycles = new MyCycle[9];       for (int i = 0; i < 3; i++) {         for (int j = 0; j < 3; j++) {           MyCycle cycle = new MyCycle();           cycle.setNum(i * 3 + j);           cycle.setOx(perSize * (j * 2 + 1));           cycle.setOy(perSize * (i * 2 + 1));           cycle.setR(perSize * 0.5f);           cycles[i * 3 + j] = cycle;         }       }     }   }    /**    * 繪制所需要繪制的內容    */   @Override   protected void onDraw(Canvas canvas) {     // TODO Auto-generated method stub     super.onDraw(canvas);     for (int i = 0; i < cycles.length; i++) {        if (!canContinue && !result) {         paintOnTouch.setColor(ERROR_COLOR);         paintInnerCycle.setColor(ERROR_COLOR);         paintLines.setColor(ERROR_COLOR);       } else if (cycles[i].isOnTouch()) {         paintOnTouch.setColor(OUT_CYCLE_ONTOUCH);         paintInnerCycle.setColor(INNER_CYCLE_ONTOUCH);         paintLines.setColor(LINE_COLOR);       } else {         paintNormal.setColor(OUT_CYCLE_NORMAL);         paintInnerCycle.setColor(INNER_CYCLE_ONTOUCH);         paintLines.setColor(LINE_COLOR);       }        if (cycles[i].isOnTouch()) {         canvas.drawCircle(cycles[i].getOx(), cycles[i].getOy(),             cycles[i].getR(), paintOnTouch);         drawInnerBuleCycle(cycles[i], canvas);       } else {          canvas.drawCircle(cycles[i].getOx(), cycles[i].getOy(),             cycles[i].getR(), paintNormal);       }     }     drawLine(canvas);   }    /**    * 繪制大圓里的小圓    *    * @param canvas    */   private void drawInnerBuleCycle(MyCycle cycle, Canvas canvas) {     canvas.drawCircle(cycle.getOx(), cycle.getOy(), cycle.getR() / 3,         paintInnerCycle);   }    private void drawLine(Canvas canvas) {     linePath.reset();     if (linedCycles.size() > 0) {       for (int i = 0; i < linedCycles.size(); i++) {         int index = linedCycles.get(i);         if (i == 0) {           // 設置為整條路徑的起點           linePath.moveTo(cycles[index].getOx(), cycles[i].getOy());         } else {           linePath.lineTo(cycles[i].getOx(), cycles[i].getOy());         }       }       linePath.lineTo(eventX, eventY);       canvas.drawPath(linePath, paintLines);     }   }    /**    * 根據手擇時觸摸點的不同,修改對應的狀態值    */   @Override   public boolean onTouchEvent(MotionEvent event) {      if (canContinue) {        switch (event.getAction()) {        case MotionEvent.ACTION_DOWN:       case MotionEvent.ACTION_MOVE:         eventX = (int) event.getX();         eventY = (int) event.getY();         for (int i = 0; i < cycles.length; i++) {           if (cycles[i].isPointIn(eventX, eventY)) {             cycles[i].setOnTouch(true);              if (!linedCycles.contains(cycles[i].getNum())) {               linedCycles.add(cycles[i].getNum());             }           }         }         break;       case MotionEvent.ACTION_UP:         canContinue = false;         StringBuffer sb = new StringBuffer();         for (int i = 0; i < linedCycles.size(); i++) {           sb.append(linedCycles.get(i));         }         result = key.equals(sb.toString());         if (onGestureFinishListener != null) {           onGestureFinishListener.OnGestureFinish(result);         }         timer = new Timer();         timer.schedule(new TimerTask() {            @Override           public void run() {             // 回到初始狀態             eventX = eventY = 0;             for (int i = 0; i < cycles.length; i++) {               cycles[i].setOnTouch(false);             }             linedCycles.clear();             linePath.reset();             canContinue = true;             postInvalidate();           }         }, 1000);         break;       }     }     invalidate();     return true;   } } 

自定義圓類:

package com.example.gesturelock;  public class MyCycle {   private int ox;     // ????????   private int oy;     // ?????????   private float r;     // ??????   private Integer num;   // ???????   private boolean onTouch; // false=δ???   public int getOx() {     return ox;   }   public void setOx(int ox) {     this.ox = ox;   }   public int getOy() {     return oy;   }   public void setOy(int oy) {     this.oy = oy;   }   public float getR() {     return r;   }   public void setR(float r) {     this.r = r;   }   public Integer getNum() {     return num;   }   public void setNum(Integer num) {     this.num = num;   }   public boolean isOnTouch() {     return onTouch;   }   public void setOnTouch(boolean onTouch) {     this.onTouch = onTouch;   }   public boolean isPointIn(int x, int y) {     double distance = Math.sqrt((x - ox) * (x - ox) + (y - oy) * (y - oy));     return distance < r;   } } 

思路:

     1.自定義一個 View和MyCircle類,將九個MyCircle類的實例繪制到View中.

     2.處理onTouch事件,根據不同的事件修改MyCircle實例的狀態,并調用更新invaildate更新View

     3.重寫onDraw()方法,根據不同的狀態去重新繪制整個View

以上就是本文的全部內容,希望對大家的學習有所幫助,也希望大家多多支持VEVB武林網。


注:相關教程知識閱讀請移步到Android開發頻道。
發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
主站蜘蛛池模板: 咸阳市| 嘉峪关市| 古丈县| 淮北市| 建水县| 深泽县| 武穴市| 庄浪县| 钟山县| 天柱县| 太白县| 资源县| 舒城县| 太原市| 久治县| 永胜县| 平阴县| 阿巴嘎旗| 安顺市| 安泽县| 高邑县| 柳河县| 同仁县| 夏津县| 浦县| 祁连县| 崇礼县| 安顺市| 五寨县| 平阴县| 德令哈市| 辽中县| 葫芦岛市| 子洲县| 九龙城区| 怀仁县| 资源县| 墨玉县| 集安市| 开化县| 奎屯市|