返回顶部
首页 > 资讯 > 移动开发 >Android项目实战手把手教你画圆形水波纹loadingview
  • 853
分享到

Android项目实战手把手教你画圆形水波纹loadingview

实战Android 2022-06-06 09:06:21 853人浏览 八月长安
摘要

本文实例讲解的是如何画一个满满圆形水波纹loadingview,这类效果应用场景很多,比如内存占用百分比之类的,分享给大家供大家参考,具体内容如下 效果图如下: 预备的知识:

本文实例讲解的是如何画一个满满圆形水波纹loadingview,这类效果应用场景很多,比如内存占用百分比之类的,分享给大家供大家参考,具体内容如下
效果图如下:

预备的知识:

1.贝塞尔曲线    如果你不了解,可以来这里进行基础知识储备:神奇的贝塞尔曲线
2.Paint.setXfermode()  以及PorterDuffXfermode

千万不要被这个b的名字吓到,不熟悉看到可能会认为很难记,其实 只要站在巨人的丁丁上 还是很简单的。
好了 废话不多说 ,跟我一步步来做一个炫酷的view吧。

首先给一些属性,在构造器里初始化(不要再ondraw new东西不要再ondraw new东西不要再ondraw new东西不要再ondraw new东西)
 


  //绘制波纹 
  private Paint mWavePaint;  
  private PorterDuffXfermode mMode = new PorterDuffXfermode(PorterDuff.Mode.XOR);//设置mode 为XOR 
  //绘制圆 
  private Paint mCirclePaint; 
  private canvas mCanvas;//我们自己的画布 
  private Bitmap mBitmap; 
  private int mWidth; 
  private int mHeight; 
  public WaveLoadingView(Context context) { 
    this(context,null); 
  } 
  public WaveLoadingView(Context context, AttributeSet attrs) { 
    this(context, attrs,0); 
  } 
  public WaveLoadingView(Context context, AttributeSet attrs, int defStyleAttr) { 
    super(context, attrs, defStyleAttr); 
    mWavePaint = new Paint(); 
    mWavePaint.setColor(Color.parseColor("#33b5e5")); 
    mCirclePaint = new Paint(); 
    mCirclePaint.setColor(Color.parseColor("#99cc00")); 
  } 
  @Override 
  protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { 
    int widthSize = MeasureSpec.getSize(widthMeasureSpec); 
    int widthMode = MeasureSpec.getMode(widthMeasureSpec); 
    int heightSize = MeasureSpec.getSize(heightMeasureSpec); 
    int heightMode = MeasureSpec.getMode(heightMeasureSpec); 
    if (widthMode == MeasureSpec.EXACTLY) { 
      mWidth = widthSize; 
    } 
    if (heightMode == MeasureSpec.EXACTLY) { 
      mHeight = heightSize; 
    } 
    setMeasuredDimension(mWidth, mHeight); 
    mBitmap = Bitmap.createBitmap(300,300, Bitmap.Config.ARGB_8888); //生成一个bitmap 
    mCanvas = new Canvas(mBitmap);//讲bitmp放在我们自己的画布上,实际上mCanvas.draw的时候 改变的是这个bitmap对象 
  } 

然后,我们给他绘制一点东西,用来介绍PorterDuffXfermode


@Override 
  protected void onDraw(Canvas canvas) { 
    mCanvas.drawCircle(100,100,50,mCirclePaint); 
    mCanvas.drawRect(100,100,200,200,mWavePaint); 
    canvas.drawBitmap(mBitmap,0,0,null); 
    super.onDraw(canvas); 
  } 

嗯,可以看到 是我们现在自己的画布上铺了一个bitmap(这里可以理解canvas为桌子  bitmap为画纸,我们在bimap上画画), 然后在bitmap上画了 一个圆,和一个矩形。最后把我们的mBitmap画到系统的画布上(显示到屏幕上),得到了以下效果。

然后我们用setXfermode()方法给他设置一个mode,这里设置XOR。

可以发现! 相交的地方消失了! 是不是很神奇。
在改一个mode 试试


private PorterDuffXfermode mMode = new PorterDuffXfermode(PorterDuff.Mode.DST_OVER); 


可以看到 圆形跑到了矩形上面来。  然后巨人给我们总结各个模式如了下图,这里给一个说明dst为先画的 src为后画的:.

大家可以根据这个规律试一下。

现在,我们把圆和矩形重叠。模式去掉。


protected void onDraw(Canvas canvas) { 
    //dst 
    mCanvas.drawCircle(150,150,50,mCirclePaint); 
/    mWavePaint.setXfermode(mMode); 
    //src 
    mCanvas.drawRect(100,100,200,200,mWavePaint); 
    canvas.drawBitmap(mBitmap,0,0,null); 
    super.onDraw(canvas); 
  } 

我的圆怎么没了。。  其实圆是被覆盖掉了。 然后我们想实现一个效果,就是在圆的范围内,显示矩形的内容,该怎么做呢。自己照着图找找吧哈哈。

我们要实现的是一个圆形的水波纹那种loadingview。。首要就是实现这个水波纹。
这时候贝塞尔曲线就派上用场了。这里采用三阶贝塞尔, 不停地改变X 模拟水波效果。


 if (x > 50) { 
      isLeft = true; 
    } else if (x < 0) { 
      isLeft = false; 
    } 
<span style="white-space:pre">    </span>if (y > -50) { //大于-50是因为辅助点是50 为了让他充满整个屏幕 
      y--; 
    }    if (isLeft) { 
      x = x - 1; 
    } else { 
      x = x + 1; 
    } 
    mPath.reset(); 
    mPath.moveTo(0, y); 
    mPath.cubicTo(100 + x*2, 50 + y, 100 + x*2, y-50, mWidth, y);//前两个参数是辅助点 
    mPath.lineTo(mWidth, mHeight);//充满整个画布 
    mPath.lineTo(0, mHeight);//充满整个画布 
    mPath.close(); 

之后用mCanvas来绘制这个bitmap,要注意的是 绘制之前要清空mBitmap,不然path会重叠


mBitmap.eraseColor(Color.parseColor("#00000000")); 
//dst 
 mCanvas.drawPath(mPath, mPaint); 
canvas.drawBitmap(mBitmap, 0, 0, null); 
    postInvalidateDelayed(10); 

 哈,水波效果出来了。   接着想办法让他画到一个圆形中。 首先绘制一个圆


mCanvas.drawCircle(mWidth / 2, mHeight / 2, mWidth / 2, mSRCPaint); 

现在让我们回到刚才的问题,如何在dst的范围内绘制src呢。。。答案是。。SRC_IN 你找对了吗。添加模式


//dst 
   mCanvas.drawCircle(mWidth / 2, mHeight / 2, mWidth / 2, mSRCPaint); 
   mPaint.setXfermode(mMode); 
   //src 
   mCanvas.drawPath(mPath, mPaint); 
   canvas.drawBitmap(mBitmap, 0, 0, null); 

是不是有点感觉了。如果不这样做 就需要考虑好多问题。动态计算沿着圆弧x,y坐标  计算arcTo的范围。

完善一下,添加一个percent来代表进度,让y来根据percent动态改变
y = (int) ((1-mPercent /100f) *mHeight); 

添加setPercent方法


public void setPercent(int percent){ 
    mPercent = percent; 
  } 

画上百分比的文字。


String str = mPercent + "%"; 
    float txtLength = mTextPaint.measureText(str); 
    canvas.drawText(mPercent + "%", mWidth / 2-txtLength/2, mHeight / 2, mTextPaint); 

然后配合seekBar,最后改改字体大小  画笔透明度。 添加个背景图 就成了效果图上的效果。

是不是很有趣,大家可以动手实现一下!

您可能感兴趣的文章:Android实现点击Button产生水波纹效果Android特效之水波纹的实现Android仿水波纹流量球进度条控制器Android自定义View 实现水波纹动画引导效果Android实现水波纹效果Android 自定义view实现水波纹动画效果Android实现自定义华丽的水波纹效果Android自定义view实现水波纹进度球效果Android实现兼容的水波纹效果Flutter InkWell实现水波纹点击效果


--结束END--

本文标题: Android项目实战手把手教你画圆形水波纹loadingview

本文链接: https://lsjlt.com/news/25799.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

猜你喜欢
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作