我正在参与「启航计划」,这是我参与的第4篇文章。

从之前的 完成一个自定义有限制区域的图例(角度自辨认)涂鸦东西类 三部曲到 自定义View完成签名带笔锋效果 基本完成了一整套关于手签名的完成流程。这篇主要说说关于手签名跟着内容越来越多呈现越来越卡的优化计划。

首先让咱们想想为什么会跟着内容的增多变得越来越卡呢?

override fun onDraw(canvas: Canvas) {
    super.onDraw(canvas)
    //手动画图
    drawPic()
}
//画图
private fun drawPic() {
    //制作一切线条
    for (i in allList.indices) {
        drawLines(allList[i], paints[i])
    }
    //实时线条
    drawLines(allPoints, paint)
}
override fun onTouchEvent(event: MotionEvent): Boolean {
    super.onTouchEvent(event)
    val p = Point(event.x.toInt(), event.y.toInt())
    when (event.action) {
        MotionEvent.ACTION_DOWN -> {//用户按下
            ......
        }
        MotionEvent.ACTION_UP -> {//用户松开
            ......
            postInvalidate() //重绘
        }
        MotionEvent.ACTION_MOVE -> {//移动
            ......
            postInvalidate() //重绘
        }
    }
    return true
}

能够看到,在用户不断移动和抬起的时分都在不断重绘以便界面能实时显现当时的线条。跟着内容的增多,则线条累积越多,在移动的时分会不断制作很多线条,那必定会越来越卡。

如何才能处理这个问题呢?

答案是:防止很多制作和重绘。

设想咱们能不能只制作当时正在签名的这条实时线,当这条线制作完成后咱们将其保存为一个Bitmap,并将该Bitmap制作为背景。制作第二条线完成后生成第二个Bitmap,此时的Bitmap包含了第一个Bitmap和第二条线的内容。以此类推,必然也能到达之前的效果。而且现在制作的内容其实最多就只有最后一张Bitmap和当时实时线条。

//创立bitmap
mBitmap = Bitmap.createBitmap(mWidth, mHeight, Bitmap.Config.ARGB_4444);
//mCanva用于制作前史线条,仅在抬起时制作
mCanvas = new Canvas(mBitmap);
@Override
protected void onDraw(Canvas canvas) {
    //制作bitmap
    canvas.drawBitmap(mBitmap, 0, 0, mPaint);
    ......
    super.onDraw(canvas);
}
@Override
public boolean onTouchEvent(MotionEvent event) {
         ......
    case MotionEvent.ACTION_UP:
         bitmaps.addBitmap(mBitmap);//添加前史图片
         break;

由于使用了Bitmap,当然涉及到内存分配和图片回收的相关处理,这里能够自行网上处理,本文不做分享。关于签名的撤回、取消、清空对应的便是对bitmaps调集的操作,咱们本地需要保护一个bitmaps的管理类。

好了,到这里基本上满屏画满内容也不会呈现明显的卡顿了,期望对我们有所协助。

我是一个喜爱Jay、Vae的安卓开发者,喜欢结交五湖四海的兄弟姐妹,欢迎我们到沸点来点歌!