Android在绘图应用程序中实现撤消堆栈

标签 android view runnable ondraw

我开始开发 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/

相关文章:

Angular2 NGRX/商店 View 未更新

java - Java 对象的可序列化错误

android - SmartWatch startVibrator 处于 DIM 状态

javascript - 在 BackBone js 中调用 javascript 渲染 View 。渲染后回调?

android - 管理当前的 View 和 Class<?> 对象

java - 嵌套的 postDelayed/Runnable/Handler Android

android - 延迟效果很好;稍作修改,没有延迟——为什么?

javafx - 如何在运行 5 秒后更新 JavaFX 应用程序中的文本框?

java - 如何通过单击事件以编程方式显示/隐藏操作栏项目

android - 如何在onResume中使用Intent?