Android 自定義view綜合實戰

  • 好久沒寫博客了,關於自定義view之前也寫過很多,今天就來對自定義view做個總結,在自定義view中需要掌握哪些知識呢!在討論之前首先來看看今天的demo效果


  • 效果還是挺炫酷的,寫這個例子的原因也是我看到網上別人寫的一個效果,感覺不錯就拿來模仿了一下。其實每個view實現的方法有很多種,根據自己的自定義view的知識量來寫,實現方式可能都不相同,所以大家當看到比較炫酷的view的時候可以嘗試去試一試,如果有些效果實現不了,可以去看看別人的思想。“寫”也是一個“學”的過程。多了不扯,先來總結一下自定義view的知識點(如有遺漏大家下面補充):

  • 1.首先自定義view的構造方法的寫法,自定義屬性,view的測量onMusure(),ondraw()這些就不多說了,這是必須掌握的。

  • 2.既然要畫圖自然少不了;Paint畫筆這個類,paint的相關方法你是否熟練,不熟悉的趕快去看看。

  • 3.canvas 畫布,開玩笑有畫筆哪能少了畫布。

  • 4.Path路徑這個牛逼了,要想實現比較酷酷的畫面還真是不能少了他,二階貝塞爾曲線和三階貝塞爾曲線,這個還需要好好研究研究。

  • 5.有了Path 我們自然會想到他的兄弟那就是 PathMesure ,爲什麼說是他兄弟,有了路徑我們是不是要知道路徑的長度,每個點的座標,角度,沒錯PathMesure就是對Path進行測量的,這個類我之前博客裏都有講過。

  • 6.有了這些是不是就夠了呢?那可能我們的自定義view是個“殘廢”,爲什麼?因爲他動不了,怎麼讓他動起來呢?那就是需要動畫的參與了兩個重要的動畫類;ValueAnimator和ObjectAnimator 我們自定義view基本這兩個動畫足夠用了,當然動畫最重要的最難的還是自定義插值器,有些特殊的需求view移動的時候,可以自己定義速度已經點座標。

  • 7.有了這些基本你就能做出很懸的效果了,但是還有一個很重要的類;PorterDuffXfermode 恩恩這個也很重要,弄清楚他的16/18個圖形展示的效果。

  • 基本這些......應該就差不多了....夜深了,想不出來了,少的大家給個補充...............還有一個很重要的是要大膽去嘗試,哪怕弄了一半搞不動了。。。


  • 扯了半天,下面就來看看我們的這個綜合的demo,涉及到的知識點還是比較多得。

  • 首先我們先來分析一下這個動畫的過程,大致分爲三個過程:

  • 1.是大圓被小圓吞噬的過程(PorterDuffXfermode ),主要我們的矩形是不能被覆蓋的。

  • 2.是大圓被吞噬完之後我們處理圓環的繪製,這個圓環採用的是三階貝塞爾曲線(path),圓環變成直線的過程,以及回彈效果。

  • 3.矩形被彈飛的過程(爲了方便這裏我直接用的動畫,其實更好的做法是先給矩形設置一個拋物線狀的移動的path路徑)。

  • 大致分爲這幾個過程,下面就一一說明:

  • 過程一:是大圓被小圓吞噬的過程。這裏就比較簡單繪製兩個圓,利用PorterDuffXfermode顯示,

  • 首先定義一個對象

  • PorterDuffXfermode xfermode = new PorterDuffXfermode(PorterDuff.Mode.SRC_IN);

然後繪製圓:

private void drawCicle(Canvas canvas) {

    int lay = canvas.saveLayer(-r,-r,r,r,paint,Canvas.ALL_SAVE_FLAG);

    paint.setColor(Color.parseColor("#944B1E2E"));
    canvas.drawCircle(0,0,r,paint);
    paint.setXfermode(xfermode);

    paint.setColor(Color.parseColor("#FF4081"));
    canvas.drawCircle(0,0,xr,paint);
    paint.setXfermode(null);
    canvas.restoreToCount(lay);

    if (isfirstCicle)
    {
        cicleAnimation();
        isfirstCicle = false;
    }

}

這個過程基本就完了。

過程2;繪製圓環--》到直線,這個比較複雜一點需要移動的座標比較多:
private void bounceLine(Canvas canvas) {
    path1.moveTo(0,r-r_b);
    path1.cubicTo(67,r-r_b,67,-r+r_bounce,0+r_bounce*4,-r+r_bounce);

    path1.moveTo(0-r_bounce*4,-r+r_bounce);
    path1.cubicTo(-67,-r+r_bounce,-67,r-r_b,0,r-r_b);
    paint.setStyle(Paint.Style.STROKE);
    paint.setStrokeWidth(2);
    paint.setColor(Color.BLACK);
    canvas.drawPath(path1,paint);
    path1.reset();
    if (isfirstBounce)
    {
        bounceAnimation();
        isfirstBounce = false;
    }
}

這是實現圓環變化到直線的過程、、、、、

我把實現的邏輯放出來,對於動畫控制請看看源碼把,貼出來太長了,把主要邏輯拿出來

過程三:繪製矩形的移動,這個比較簡單,用動畫控制矩形移動的座標就行了

RectF f = new RectF(-10-rect_position_x,-10-rect_position_y,10-rect_position_x,10-rect_position_y);

矩形的座標控制動畫就是;

float rect_position_y = 0;
float rect_position_x = 0;
private void rectAnimation() {
    ValueAnimator a = ValueAnimator.ofFloat(0,120,30);
    a.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
        @Override
        public void onAnimationUpdate(ValueAnimator animation) {
            rect_position_y = (float) animation.getAnimatedValue();
            invalidate();
        }
    });
    a.setDuration(800);
    a.setInterpolator(new AccelerateDecelerateInterpolator());

    ValueAnimator v = ValueAnimator.ofFloat(0,4*r);
    v.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
        @Override
        public void onAnimationUpdate(ValueAnimator animation) {
            rect_position_x = (float) animation.getAnimatedValue();
            invalidate();
        }
    });
    v.setDuration(800);
    v.setInterpolator(new AccelerateDecelerateInterpolator());
    a.start();
    v.start();
}


大致的繪製過程就是這樣,有問題的大家可以留言喲........

GitHub地址:https://github.com/WangRain1/BounceView







發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章