您好,登錄后才能下訂單哦!
這篇文章主要介紹“怎么用android實現貝塞爾曲線之波浪效果”的相關知識,小編通過實際案例向大家展示操作過程,操作方法簡單快捷,實用性強,希望這篇“怎么用android實現貝塞爾曲線之波浪效果”文章能幫助大家解決問題。
貝塞爾曲線的幾個常用的應用:
1.波浪效果
2.qq聊天列表上的沾粘體效果
3.翻書頁效果
4.彈性球效果
原理分析:
其實這個效果應用了2個階的貝塞爾曲線來完成的,先看一下原理分析圖:
有上面的圖可以看出:在屏幕的左面畫出了1.5個波長,在屏幕中畫出1個波長,然后讓它循環的向右移動,這個就會出現波浪效果,這里有幾點需要注意:
1.為什么是1.5個波長而不是1個波長呢?
理論上1個波長就夠了,但是實際運行出來的效果會出現不協調,所以經過調試,我又加了0.5個波長
2.那條綠線是干什么用的?
在波浪線以下的所有空間都要填充成一個顏色,所以path必須是封閉的區間,只有這個才能填充。代碼中我會具體的解釋
我們在編碼的時候只需要計算最左面半個波長的坐標,其他的用for循環搞定。
好了我們看一下代碼:
public class WaveView extends View { private int width = 0; private int height = 0; private int baseLine = 0;// 基線,用于控制水位上漲的,這里是寫死了沒動,你可以不斷的設置改變。 private Paint mPaint; private int waveHeight = 100;// 波浪的最高度 private int waveWidth ;//波長 private float offset =0f;//偏移量 public WaveView(Context context, AttributeSet attrs) { super(context, attrs); initView(); } /** * 不斷的更新偏移量,并且循環。 */ private void updateXControl(){ //設置一個波長的偏移 ValueAnimator mAnimator = ValueAnimator.ofFloat(0,waveWidth); mAnimator.setInterpolator(new LinearInterpolator()); mAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() { @Override public void onAnimationUpdate(ValueAnimator animation) { float animatorValue = (float)animation.getAnimatedValue() ; offset = animatorValue;//不斷的設置偏移量,并重畫 postInvalidate(); } }); mAnimator.setDuration(1000); mAnimator.setRepeatCount(ValueAnimator.INFINITE); mAnimator.start(); } @Override protected void onDraw(Canvas canvas) { super.onDraw(canvas); canvas.drawPath(getPath(),mPaint); } //初始化paint,沒什么可說的。 private void initView(){ mPaint = new Paint(); mPaint.setColor(Color.RED); mPaint.setStyle(Paint.Style.FILL); } @Override protected void onLayout(boolean changed, int left, int top, int right, int bottom) { super.onLayout(changed, left, top, right, bottom); width = getMeasuredWidth();//獲取屏幕寬度 height = getMeasuredHeight();//獲取屏幕高度 waveWidth = width; baseLine = height/2; updateXControl(); } /** * 核心代碼,計算path * @return */ private Path getPath(){ int itemWidth = waveWidth/2;//半個波長 Path mPath = new Path(); mPath.moveTo(-itemWidth * 3, baseLine);//起始坐標 //核心的代碼就是這里 for (int i = -3; i < 2; i++) { int startX = i * itemWidth; mPath.quadTo( startX + itemWidth/2 + offset,//控制點的X,(起始點X + itemWidth/2 + offset) getWaveHeigh( i ),//控制點的Y startX + itemWidth + offset,//結束點的X baseLine//結束點的Y );//只需要處理完半個波長,剩下的有for循環自已就添加了。 } //下面這三句話很重要,它是形成了一封閉區間,讓曲線以下的面積填充一種顏色,大家可以把這3句話注釋了看看效果。 mPath.lineTo(width,height); mPath.lineTo(0,height); mPath.close(); return mPath; } //奇數峰值是正的,偶數峰值是負數 private int getWaveHeigh(int num){ if(num % 2 == 0){ return baseLine + waveHeight; } return baseLine - waveHeight; } }
核心的代碼在 getPath()方法中,其實這個坐標是有規律的:
先找到最左面的半個波長,設置貝塞爾曲線坐標,
然后用for循環,不斷的設置,
這個規律大家體會,我這里簡單提一下。
先看一個效果圖:
這個做起來小有點復雜。具體思路如下:
1.畫兩個圓,一個黏連小球固定在一個點上,一個氣泡小球跟隨手指的滑動改變坐標。隨著兩個圓間距越來越大,黏連小球半徑越來越小。
2.當間距小于一定值,松開手指氣泡小球會恢復原來位置;
3.當間距超過一定值之后,黏連小球消失,氣泡小球繼續跟隨手指移動,此時手指松開,氣泡小球消失~
關于“怎么用android實現貝塞爾曲線之波浪效果”的內容就介紹到這里了,感謝大家的閱讀。如果想了解更多行業相關的知識,可以關注億速云行業資訊頻道,小編每天都會為大家更新不同的知識點。
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。