Advise needed on Undo Framework

  • I am in the process of creating a Qt-based IDE for so-called dataflow models. I now have a first prototype editor available. It has however only very basic functionality and one important aspect that is missing is undo functionality. However, I already created a way to visually inform the user where changes to a dataflow model have been made by using an * at relevant places (see screenshot below).


    I would now like to add undo functionality to my application by using the undo framework of Qt. I studied the QUndoStack and QUndoGroup classes to find a way in which I can keep the * indications consistent with the undo/redo status. I believe that I could use a QUndoStack for each of the elements that I track for an * visualisation and an QUndoGroup for the overall dataflow model document. However, from what I understand in the idea of how to use these classes, I need to ensure that the user somehow initiated setting the active QUndoStack to direct an undo action to the relevant tracked i.e., asterisked element. I however would need this to be automated as any undo command should immediately go to the latest used QUndoStack independent of whether the user switched for example tabs in the shown screenshot.

    Would anybody have a suggestion of how to do this in an easy way? The only thing that I could imagine is to have a special QUndoStack that tracks which QUndoStack of a tracked (asterisked) item received an undo/redo-able action but this seems rather complicated to me...

  • Lifetime Qt Champion


    From the looks of it, it seems you would need the QUndoGroup class.

  • Yes, I tend to agree to that:

    • A QUndoGroup for the overall dataflow model resulting in the * in the window title
    • A QUndoStack for each of the elements represented by the tabs to have their own *

    However, directing undo/redo actions in the edit menu created from the QUndoGroup to the correct QUndoStack requires setting the active QUndoStack. I could imagine that I change the active QUndoStack when the user switches tabs. However, this means that any undo/redo command from the user will end up at that particular QUndoStack. If the user switches tabs (e.g., to one without * as no changes took place there), this would change directing the undo/redo commands and not undo/redo the change that was made in another tab at which the latest change happened. Even though switching tabs the, undo/redo commands should end up at the place where the latest changes where med (which ever tab that was).

    I imagine a 'super stack' for the whole application where the undo/redo commands end up to udnor/redo things anywhere in the dataflow model. This is the functionality that I want, but in combination with the appropriate asterisks status for each of the individual tabs. How can I do this?

  • Sorry for changing my last post a bit, but I was trying to find a better explanation of what I hope to achieve...

  • Lifetime Qt Champion

    So you want that each tab has it's own stack but if on an untouched tab, it should switch back to the latest tab that was modified and continue from there ?

  • Basically yes (that means: the model part belonging to the tab view)

  • Lifetime Qt Champion

    Then it looks like you should rather have one stack with custom commands containing enough information to allow to go back to the corresponding tab or if you want to keep each stack independent have a manager object that should handle the history of which tab was modified and when.

  • Ok thanks. I was already afraid of that...

Log in to reply