Java中的撤销和重做操作事件

3

我有一个应用程序,其中包含一个JPanel和按钮,用户可以单击按钮在面板上绘制形状。您可以对形状进行着色和调整大小,并将其移动到面板中。如何为这样的应用程序实现撤销和重做?我有一个Actions类,其中实际上实现了所有操作。在这个类中,每个操作都是它自己的类,扩展了AbstractAction。我的Actions类基本上是一个嵌套类。

例如,这是我的Actions类中的一个类:

private class RandomAction extends AbstractAction {
  private static final long serialVersionUID = 1L;
  public NewAction(String text, ImageIcon icon, String desc){
            super(text, icon);
            putValue(SHORT_DESCRIPTION, desc);
        }
        public void actionPerformed(ActionEvent e) {

        }
    }

当我创建一个按钮时,我所做的就是:
 randButton = new JButton(Actions.RandomAction);
2个回答

5
通常实现撤销/重做功能需要使用一个栈。你可以实现自己的动作栈来跟踪前面X个动作,每当用户撤消操作时,您可以弹出每个动作。您可能还需要为重做功能保留类似类型的结构。因此,当从撤销栈中弹出操作时,它首先需要进入重做栈。
如果您正在使用Java和NetBeans(尽管严格来说不需要使用NetBeans IDE),则可以查看NetBeans平台(可以单独下载)。我没有过多涉及撤销/重做,但它确实提供了该功能。
个人而言,我只会编写包装用户可以执行的任何“动作”的类,这一点您已经完成了。现在只需实现堆栈以跟踪这些动作,当从撤销栈中弹出一个动作时,您需要执行该动作的“相反”操作。将项目放置在重做堆栈上,因此当用户单击重做时,您可以简单地从重做堆栈中弹出该动作,并让应用程序正常处理它。

谢谢,我其实正在考虑以这种方式实现它。 - glenn

1

我同意Nico的帖子,并且我会补充说,可以使用一个堆栈来实现撤销/重做。

几年前在大学里,我正在编写一个数据流图编辑器,需要完整的撤销/重做功能。我创建了一个抽象的Action类,表示任何可能的用户操作(具有Undo和Do方法),以及一个ActionStack,它包装了所有执行的操作列表,并维护指向最后执行的Action的指针。撤消操作将指针向下移动堆栈,而重做操作将其向上移动。因此,如果用户执行了10个操作,则堆栈将包含操作1-10,并且指针指向操作#10。如果用户然后执行5个撤消操作,则堆栈上仍将有10个操作,但指针将返回到操作#5。如果用户然后执行新操作,则将删除指针以上的所有操作(操作6-10),新操作将添加到堆栈顶部,并相应地调整指针。

您描述的用户操作听起来并不太复杂,但对于更复杂的操作,您可能希望允许它们由子操作组成。


我正在为我的当前项目的撤销/重做功能做完全相同的事情。 - almathie
我可能会尝试这个,因为它可以使我的应用程序更加节省空间,因为不需要两个堆栈。 - glenn

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接