【问题标题】:Issue with Qt Undo Framework example: add / remove itemQt Undo Framework 示例的问题:添加/删除项目
【发布时间】:2017-05-30 03:29:10
【问题描述】:

我使用 QT 撤消框架示例作为在我的工具中实现此功能的参考。但是,它调用项目的析构函数的方式似乎有一个错误。

我了解 QGraphicsScene 将在项目位于场景中时承担项目的所有权。但是,两个撤消对象:AddCommand 和 RemoveCommand 在将它们从场景中移除时都应该承担这些项目的所有权。

在 Qt undo 框架示例中,只有 AddCommand 尝试删除其析构函数中的对象,但如果该项目仍在场景中,则不会这样做。

AddCommand::~AddCommand()
{
    if (!myDiagramItem->scene())
        delete myDiagramItem;
}

在这种情况下,如果我们在相应的 AddCommand 对象离开堆栈后从场景中删除该项目(当使用撤消限制时),则该项目将永远不会被再次删除,因为 RemoveCommand 析构函数不会这样做。

【问题讨论】:

    标签: qt undo qgraphicsitem qgraphicsscene redo


    【解决方案1】:

    我在 AddCommand 和 RemoveCommand 类中都使用了一个标志来修复它。它通知此对象何时应负责项目销毁。当他们从场景中移除项目时,我将此标志设置为 true,并在调用项目的析构函数之前在撤消对象析构函数中测试此标志:

    AddCommand::AddCommand(QGraphicsScene *scene, DraftGraphicItem* item, QUndoCommand *parent):
        scene(scene), item(item), QUndoCommand(parent){
        setText("Add item to scene");
    }
    
    AddCommand::~AddCommand(){
        if(isItemOwner)
            delete item;
    }
    
    void AddCommand::undo(){
        Q_ASSERT(item->scene()); 
        scene->removeItem(item);
        isItemOwner = false;
    }
    
    void AddCommand::redo(){
        Q_ASSERT(!item->scene()); 
        scene->addItem(item);
        isItemOwner = true;
    }
    

    与 RemoveCommand 相同,只是反转 redo() 和 undo() 方法。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2019-03-25
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2018-04-29
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多