| 序号 | 步骤名称 | 目的 |
|---|---|---|
| 1 | 判断当前机器是否支持Pencil Engine一笔成形,以免功能失效。 | |
| 2 | 实例化功能类,后续功能均由该类提供。 | |
| 3 | 设置一笔结束后手写笔/手指在屏幕上的停顿时间,停顿达到该时长将触发一笔成形功能。 | |
| 4 | 将当前绘制控件的宽高传入底层引擎,用于进行识别的点位的坐标归一化处理。 | |
| 5 | 在onTouchEvent处理时,将触摸事件传递给底层引擎,用于记录一笔的起始位置,点位信息等,进而用于后续识别。 | |
| 6 | 在触发一笔成形的图形识别能力后,获取规整图形结果用于绘制。 | |
| 7 | 在触发一笔成形的图形识别能力后,在结束抬笔时,获取规整图形的关键信息,用于后续保存和加载。 | |
| 8 | 在笔迹加载或其他需要的场景,通过已保存的规整图形的关键信息,将其还原为可绘制的图形。 | |
| 9 | 清理空间,释放资源。 |
if (!HwPenEngineManager.isSupportFeature(context, VersionInfo.API_LEVEL_2))) { Log.w(TAG, "feature not supported"); return; }
在初始化阶段进行实例化,后续功能均依赖该实例化对象
InstantShapeGenerator mInstantShapeGenerator= new InstantShapeGenerator (context);
初始化阶段进行设置,单位:ms。若不设置则默认为300ms;若设置的值小于0或大于5000,则使用默认值。
/** 设置停顿时间为400ms **/ mInstantShapeGenerator.setStopTime(400);
在onSizeChanged(控件大小发生变化时)中,将新的控件的宽度和高度传入引擎,用于点位的归一化处理。
@Override public void onSizeChanged(int width, int height, int oldwidth, int oldheight) { super.onSizeChanged(width, height, oldwidth, oldheight); if (mInstantShapeGenerator != null) { mInstantShapeGenerator.notifyViewSizeChange(width, height); } }
@Override public boolean onTouchEvent(MotionEvent event) { if (mInstantShapeGenerator != null) { mInstantShapeGenerator.processTouchEvent(event); } /** 其他应用自定义行为 **/ … return true; }
在触发了一笔成形的识别能力后,可以自行选择在ACTION_MOVE的事件处理中直接获取,或者在onDraw的时候获取。
private Path mFormedShapePath = new Path(); … @Override public void onDraw(Canvas canvas) { /** 绘制原始笔迹 **/ mPaint.setColor(Color.BLACK); canvas.drawPath(mOriginalPath, mPaint); /** 绘制规整图形 **/ mPaint.setColor(Color.RED); if (mInstantShapeGenerator != null) { mFormedShapePath = mInstantShapeGenerator.getPath(); } canvas.drawPath(mFormedShapePath, mPaint); }
在需要将图形识别结果进行保存的场景,在触发了一笔成形的识别能力后,可以通过获取图形识别结果的String信息,将String信息进行保存。可以在一笔结束ACTION_UP的时候进行获取。
private List<String> mFormedShapeResults = new ArrayList<>(); … @Override public boolean onTouchEvent(MotionEvent event) { if (mInstantShapeGenerator != null) { mInstantShapeGenerator.processTouchEvent(event); } switch (event.getAction()) { case MotionEvent.ACTION_DOWN: /** 其他应用自定义行为 **/ case MotionEvent.ACTION_MOVE: /** 其他应用自定义行为 **/ case MotionEvent.ACTION_UP: if (mInstantShapeGenerator == null) { break; } String strResult = mInstantShapeGenerator.getStringResult(); if (strResult != null && strResult.length() > 0) { /** 将结果保存至String List **/ mFormedShapeResults.add(strResult); } break; } /** 其他应用自定义行为 **/ … return true; }
在图形识别结果的String信息被保存后,可以在需要加载的时候将保存的String信息恢复为Path信息以便绘制。
private Path mOrigninalPath = new Path(); private Path mFormedShapePath = new Path(); … @Override public void onDraw(Canvas canvas) { /** 绘制原始笔迹 **/ mPaint.setColor(Color.BLACK); canvas.drawPath(mOriginalPath, mPaint); /** 绘制规整图形 **/ mPaint.setColor(Color.RED); if (mInstantShapeGenerator != null) { mFormedShapePath = mInstantShapeGenerator.getPath(); } canvas.drawPath(mFormedShapePath, mPaint); if (mInstantShapeGenerator == null) { return; } /** 将保存的关键信息恢复成可绘制的path **/ mPaint.setColor(Color.GREEN); for (String shape : mFormedShapeResults) { canvas.drawPath(mInstantShapeGenerator.getPathFromString(shape, mPaint.getStrokeWidth()), mPaint); } }
@Override public void onDetachedFromWindow() { if (mInstantShapeGenerator != null) { mInstantShapeGenerator.destroy(); mInstantShapeGenerator = null; } super.onDetachedFromWindow(); }