我开始开发 Android SDK 中的示例 Finger Paint 应用程序,以更加熟悉图形。最近,我一直在尝试实现撤消/重做,但我尝试过的各种方法都遇到了障碍。我发现了一些与此相关的主题,但没有一个主题能让我解决这些问题。以下是我的主要 2 个试验:
策略 1:
保存一堆路径(或 Canvas ),并在撤消时清除屏幕并重新绘制除最后一个路径之外的每条路径(或恢复最近的 Canvas )。
这里的问题可能很简单,但我就是无法让 View 重绘任何内容。如何绘制保存的路径(或恢复保存的 Canvas )?
策略2:
每次触摸后使用 getDrawingCache() 保存一堆位图。撤消时,将最后一个位图放回原处。
保存必须通过可运行的 post() 运行,因此它在 onDraw() 完成后执行(post 将其添加到 invalidate() 之后的系统消息行)。问题是,当从可运行的 getDrawingCache() 运行时,它总是返回绘画的初始版本,就像它在第一次之后看不到任何更改一样。
为什么从可运行对象调用 getDrawingCache() 时看不到 View 的当前状态?
我已经为此奋斗了一段时间。谢谢。
case MotionEvent.ACTION_UP:
touch_up();
invalidate();
Runnable r = new Runnable(){
@Override
public void run() {
myView.storeView();
}
};
myView.post(r);
}
public void storeView(){
historyCount++;
if(historyCount > historySize) historyCount = 6; //We don't want more than 6
history.add(Bitmap.createBitmap(myView.getDrawingCache()),historyCount);
}
最佳答案
对于策略 1,您需要定义一个数据结构来表示渲染绘图的一部分所需的所有信息。因此,举例来说,如果您通过跟踪用户的触摸位置来绘制绘图的一部分,请定义一个数据结构,其中包含当前颜色、绘图形状以及由一个用户手势生成的坐标的 ArrayList。当您跟随用户的触摸、绘制到屏幕时,还将触摸坐标附加到当前手势的 ArrayList 中。当触摸结束时,将数据结构推送到撤消堆栈上,并等待下一个用户手势来创建下一个结构实例并开始填充它。
如果您有多种手势(填充、手绘描线、直线等),则可以为每种手势设置单独的结构。它们都可以从抽象类继承,因此它们都可以进入堆栈。
第二个策略让我觉得它是一个可怕的内存消耗者。我认为我们必须查看您的代码才能理解为什么它没有按预期工作。
关于Android在绘图应用程序中实现撤消堆栈,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6804380/