QUndoStack Class

QUndoStack 类是QUndoCommand 对象的堆栈。更多

头文件: #include <QUndoStack>
CMake: find_package(Qt6 REQUIRED COMPONENTS Gui)
target_link_libraries(mytarget PRIVATE Qt6::Gui)
qmake: QT += gui
继承: QObject

属性

公共功能

QUndoStack(QObject *parent = nullptr)
virtual ~QUndoStack()
void beginMacro(const QString &text)
bool canRedo() const
bool canUndo() const
int cleanIndex() const
void clear()
const QUndoCommand *command(int index) const
int count() const
QAction *createRedoAction(QObject *parent, const QString &prefix = QString()) const
QAction *createUndoAction(QObject *parent, const QString &prefix = QString()) const
void endMacro()
int index() const
bool isActive() const
bool isClean() const
void push(QUndoCommand *cmd)
QString redoText() const
void setUndoLimit(int limit)
QString text(int idx) const
int undoLimit() const
QString undoText() const

公共插槽

void redo()
void resetClean()
void setActive(bool active = true)
void setClean()
void setIndex(int idx)
void undo()

信号

void canRedoChanged(bool canRedo)
void canUndoChanged(bool canUndo)
void cleanChanged(bool clean)
void indexChanged(int idx)
void redoTextChanged(const QString &redoText)
void undoTextChanged(const QString &undoText)

详细说明

有关 Qt 撤消框架的概述,请参阅概述文档

撤销堆栈维护着已应用于文档的命令堆栈。

新命令通过push() 推入堆栈。可以使用undo() 和redo() 或通过createUndoAction() 和createRedoAction() 触发返回的操作来撤销和重做命令。

QUndoStack 会跟踪current 命令。下一次调用redo() 时将执行该命令。该命令的索引由index() 返回。编辑对象的状态可以通过setIndex() 向前或向后滚动。如果堆栈中最顶层的命令已被重做,则index() 等于count() 。

QUndoStack 支持撤销和重做操作、命令压缩、命令宏,并支持干净状态的概念。

撤销和重做操作

QUndoStack 提供方便的撤销和重做QAction 对象,可将其插入菜单或工具栏。当命令被撤销或重做时,QUndoStack 会更新这些操作的文本属性,以反映它们将触发的变化。当没有命令可供撤销或重做时,这些操作也会被禁用。这些操作由QUndoStack::createUndoAction() 和QUndoStack::createRedoAction() 返回。

命令压缩和宏

如果可以将多个命令压缩成一个命令,并在一次操作中撤销和重做,那么命令压缩就非常有用。例如,当用户在文本编辑器中键入一个字符时,就会创建一条新命令。该命令在光标位置将字符插入文档。不过,对用户来说,撤销或重做整个单词、句子或段落的键入操作更为方便。通过命令压缩,可以将这些单字符命令合并为一条插入或删除文本部分的命令。更多信息,请参阅QUndoCommand::mergeWith() 和push()。

命令宏是一连串的命令,所有命令都可以一次性撤销和重做。命令宏是通过给一条命令提供一个子命令列表来创建的。撤销或重做父命令会导致撤销或重做子命令。命令宏可以通过在QUndoCommand 构造函数中指定父命令或使用便捷函数beginMacro() 和endMacro() 明确创建。

虽然命令压缩和宏在用户看来具有相同的效果,但它们在应用程序中往往有不同的用途。如果不需要单独记录对文档进行小改动的命令,而且只有较大的改动才与用户相关,那么对这些命令进行压缩可能是有用的。不过,对于需要单独记录的命令或无法压缩的命令,使用宏可以提供更方便的用户体验,同时保留每条命令的记录。

清洁状态

QUndoStack 支持干净状态的概念。当文档保存到磁盘时,可以使用setClean() 将堆栈标记为干净状态。每当堆栈通过撤销和重做命令返回到该状态时,它都会发出cleanChanged() 信号。当堆栈离开清洁状态时,也会发出该信号。该信号通常用于启用或禁用应用程序中的保存操作,以及更新文档标题以反映其包含未保存的更改。

过时的命令

如果不再需要命令,QUndoStack 可以从堆栈中删除该命令。例如,当两个命令合并在一起,合并后的命令没有任何功能时,就可以删除该命令。移动命令就属于这种情况,用户将鼠标移动到屏幕的某个位置,然后再移动到原来的位置。合并后的命令会导致鼠标移动速度为 0。由于这条命令没有任何作用,因此可以将其删除。另一个例子是由于连接问题而失败的网络命令。在这种情况下,该命令应从堆栈中删除,因为redo() 和undo() 函数在出现连接问题后已不起作用。

可以使用QUndoCommand::setObsolete() 函数将命令标记为过时。在调用QUndoCommand::undo(),QUndoCommand::redo() 和QUndoCommand:mergeWith() 后,会在QUndoStack::push(),QUndoStack::undo(),QUndoStack::redo() 和QUndoStack::setIndex() 中检查QUndoCommand::isObsolete() 标志。

如果一条命令被设置为过时,且清除索引大于或等于当前的命令索引,那么当该命令从堆栈中删除时,清除索引将被重置。

另请参阅 QUndoCommandQUndoView

属性文档

active : bool

此属性表示此堆栈的活动状态。

一个应用程序通常有多个撤销堆栈,每个打开的文档都有一个。活动堆栈是与当前活动文档相关联的堆栈。如果该堆栈属于QUndoGroup ,则在该堆栈处于活动状态时,对QUndoGroup::undo() 或QUndoGroup::redo() 的调用将被转发到该堆栈。如果QUndoGroupQUndoView 监视,则视图将在该堆栈处于活动状态时显示其内容。如果堆栈不属于QUndoGroup ,则使其处于活动状态不会产生任何影响。

程序员有责任通过调用 setActive() 来指定哪个堆栈处于活动状态,通常是在相关文档窗口获得焦点时。

访问函数:

bool isActive() const
void setActive(bool active = true)

另请参阅 QUndoGroup

[read-only] canRedo : const bool

该属性表示堆栈是否可以重做。

该属性表示是否有命令可以重做。

访问功能:

bool canRedo() const

Notifier 信号:

void canRedoChanged(bool canRedo)

另请参阅 canRedo(),index() 和canUndo()。

[read-only] canUndo : const bool

此属性表示堆栈是否可以撤销。

该属性表示是否存在可以撤销的命令。

访问功能:

bool canUndo() const

Notifier 信号:

void canUndoChanged(bool canUndo)

另请参阅 canUndo(),index() 和canRedo()。

[read-only] clean : const bool

此属性表示堆栈的清洁状态。

该属性表示堆栈是否清洁。例如,当文档已保存时,堆栈就是干净的。

访问功能:

bool isClean() const

Notifier 信号:

void cleanChanged(bool clean)

另请参阅 isClean(),setClean(),resetClean() 和cleanIndex().

[read-only] redoText : const QString

该属性保存下一条重做命令的重做文本。

该属性保存下一次调用redo() 时要重做的命令文本。

访问功能:

QString redoText() const

Notifier 信号:

void redoTextChanged(const QString &redoText)

另请参阅 redoText()、QUndoCommand::actionText() 和undoText()。

undoLimit : int

此属性用于保存堆栈中命令的最大数量。

当堆栈中的命令数量超过堆栈的 undoLimit 时,命令将从堆栈底部删除。宏命令(带有子命令的命令)被视为一条命令。默认值为 0,即没有限制。

只有在撤销堆栈为空时才能设置该属性,因为在非空堆栈中设置该属性可能会删除当前索引处的命令。在非空堆栈上调用 setUndoLimit() 会打印警告,但不会有任何效果。

访问函数

int undoLimit() const
void setUndoLimit(int limit)

[read-only] undoText : const QString

该属性保存下一条被撤销命令的撤销文本。

该属性保存下一次调用undo() 时要撤销的命令文本。

访问功能:

QString undoText() const

Notifier 信号:

void undoTextChanged(const QString &undoText)

另请参阅 undoText()、QUndoCommand::actionText() 和redoText()。

成员函数文档

[explicit] QUndoStack::QUndoStack(QObject *parent = nullptr)

用父parent 构建一个空的撤销堆栈。堆栈最初将处于 "清除 "状态。如果parentQUndoGroup 对象,则栈会自动添加到组中。

另请参阅 push() 。

[virtual noexcept] QUndoStack::~QUndoStack()

销毁撤销堆栈,删除堆栈中的所有命令。如果堆栈位于QUndoGroup 中,堆栈会自动从组中删除。

另请参阅 QUndoStack() 。

void QUndoStack::beginMacro(const QString &text)

开始使用给定的text 描述编写宏命令。

一个由指定的text 描述的空命令会被推入堆栈。在调用endMacro() 之前,推入堆栈的任何后续命令都将追加到空命令的子命令中。

对 beginMacro() 和endMacro() 的调用可以嵌套,但对 beginMacro() 的每次调用都必须与对endMacro() 的调用相匹配。

在宏的编译过程中,堆栈是禁用的。这意味着

当调用最外层宏endMacro() 时,堆栈将被启用并发出相应的信号。

stack.beginMacro("insert red text");
stack.push(new InsertText(document, idx, text));
stack.push(new SetColor(document, idx, text.length(), Qt::red));
stack.endMacro(); // indexChanged() is emitted

该代码等同于

QUndoCommand *insertRed = new QUndoCommand(); // an empty command
insertRed->setText("insert red text");

new InsertText(document, idx, text, insertRed); // becomes child of insertRed
new SetColor(document, idx, text.length(), Qt::red, insertRed);

stack.push(insertRed);

另请参见 endMacro()。

bool QUndoStack::canRedo() const

如果有可供重做的命令,则返回true ;否则返回false

如果堆栈为空或堆栈中最前面的命令已被重做,则此函数返回false

index() ==count() 同义。

注: 属性 canRedo 的获取函数。

另请参阅 index() 和canUndo()。

[signal] void QUndoStack::canRedoChanged(bool canRedo)

只要canRedo() 的值发生变化,就会发出该信号。createRedoAction canRedo 指定新值。

注: 属性canRedo 的通知信号。

bool QUndoStack::canUndo() const

如果有可供撤销的命令,则返回true ;否则返回false

如果堆栈为空,或堆栈中最下面的命令已被撤销,则该函数返回false

index() == 0 同义。

注: 属性 canUndo 的获取函数。

另请参阅 index() 和canRedo()。

[signal] void QUndoStack::canUndoChanged(bool canUndo)

只要canUndo() 的值发生变化,就会发出该信号。createUndoAction canUndo 指定新值。

注: 属性canUndo 的通知信号。

[signal] void QUndoStack::cleanChanged(bool clean)

每当堆栈进入或离开清洁状态时,都会发出该信号。如果clean 为 true,则堆栈处于清洁状态;否则,该信号表示堆栈已离开清洁状态。

注: 属性clean 的通知信号。

另请参阅 isClean() 和setClean()。

int QUndoStack::cleanIndex() const

返回干净索引。这是调用setClean() 时的索引。

堆栈可能没有干净索引。如果保存了文档,撤销了一些命令,然后又推送了一条新命令,就会出现这种情况。由于push() 会在推送新命令之前删除所有未执行的命令,因此堆栈无法再次恢复到干净状态。在这种情况下,此函数返回-1。在明确调用resetClean() 后,也可能返回-1。

另请参阅 isClean() 和setClean()。

void QUndoStack::clear()

删除命令堆栈中的所有命令,从而清除命令堆栈,并将堆栈恢复到清洁状态。

命令不会撤销或重做,已编辑对象的状态保持不变。

该函数通常在文档内容被放弃时使用。

另请参见 QUndoStack()。

const QUndoCommand *QUndoStack::command(int index) const

返回指向index 的命令的常量指针。

此函数返回一个常量指针,因为一旦命令被推入堆栈并执行,如果命令被撤销或重做,修改命令几乎总是会破坏文档的状态。

另请参见 QUndoCommand::child()。

int QUndoStack::count() const

返回堆栈中命令的数量。宏命令作为一条命令计算。

另请参阅 index()、setIndex() 和command()。

QAction *QUndoStack::createRedoAction(QObject *parent, const QString &prefix = QString()) const

使用给定的parent 创建重做QAction 对象。

触发此操作将导致调用redo() 。该操作的文本是下一次调用redo() 时要重做的命令文本,前缀是指定的prefix 。如果没有可重做的命令,此操作将被禁用。

如果prefix 为空,将使用默认模板 "Redo %1 "代替前缀。在 Qt 4.8 之前,默认使用前缀 "Redo"。

另请参阅 createUndoAction()、canRedo() 和QUndoCommand::text()。

QAction *QUndoStack::createUndoAction(QObject *parent, const QString &prefix = QString()) const

使用给定的parent 创建一个撤销QAction 对象。

触发此操作将导致调用undo() 。该操作的文本是下一次调用undo() 时要撤销的命令文本,前缀是指定的prefix 。如果没有可供撤销的命令,该操作将被禁用。

如果prefix 为空,将使用默认模板 "Undo %1 "代替前缀。在 Qt 4.8 之前,默认使用前缀 "Undo"。

另请参阅 createRedoAction()、canUndo() 和QUndoCommand::text()。

void QUndoStack::endMacro()

结束宏命令的组成。

如果这是一组嵌套宏中的最外层宏,则该函数会对整个宏命令发出一次indexChanged() 命令。

另请参见 beginMacro()。

int QUndoStack::index() const

返回当前命令的索引。这是下次调用redo() 时将执行的命令。它并不总是堆栈中最顶层的命令,因为可能有许多命令已被撤销。

另请参阅 setIndex()、undo()、redo() 和count()。

[signal] void QUndoStack::indexChanged(int idx)

当命令修改了文档的状态时,就会发出该信号。当命令被撤销或重做时就会发生这种情况。当宏命令被撤销或重做,或setIndex() 被调用时,该信号只发出一次。

idx 指定当前命令的索引,即下一次调用 () 时将执行的命令。redo

另请参阅 index() 和setIndex()。

bool QUndoStack::isClean() const

如果堆栈处于清洁状态,则返回true ;否则返回false

注: 属性clean 的获取函数。

另请参阅 setClean() 和cleanIndex()。

void QUndoStack::push(QUndoCommand *cmd)

cmd 推入堆栈或与最近执行的命令合并。无论哪种情况,都会通过调用redo() 函数来执行cmd

如果cmd 的 id 不是-1,且与最近执行的命令的 id 相同,则QUndoStack 会在最近执行的命令上调用QUndoCommand::mergeWith() 试图合并两条命令。如果QUndoCommand::mergeWith() 返回truecmd 将被删除。

在调用QUndoCommand::redo() 和(如适用)QUndoCommand::mergeWith() 后,将调用QUndoCommand::isObsolete() 以获取cmd 或合并后的命令。如果QUndoCommand::isObsolete() 返回true ,则cmd 或合并命令将从堆栈中删除。

在所有其他情况下,cmd 会被简单地推入堆栈。

如果在推入cmd 之前命令已被撤销,则当前命令和其上的所有命令都会被删除。因此,cmd 最终总是堆栈的最顶层。

一旦命令被推送,堆栈就拥有了它的所有权。没有返回命令的 getter,因为在命令执行后修改它几乎总是会导致文档状态的损坏。

另请参阅 QUndoCommand::id() 和QUndoCommand::mergeWith()。

[slot] void QUndoStack::redo()

调用QUndoCommand::redo() 重做当前命令。递增当前命令索引。

如果堆栈为空,或堆栈中最上面的命令已被重做,则此函数不会执行任何操作。

如果QUndoCommand::isObsolete() 返回当前命令的 true,则该命令将从堆栈中删除。此外,如果清除索引大于或等于当前的命令索引,则会重置清除索引。

另请参阅 undo() 和index()。

QString QUndoStack::redoText() const

返回下一次调用redo() 时将重做的命令文本。

注: 属性 redoText 的获取函数。

另请参阅 QUndoCommand::actionText() 和undoText()。

[signal] void QUndoStack::redoTextChanged(const QString &redoText)

只要redoText() 的值发生变化,就会发出该信号。createRedoAction redoText 指定新文本。

注: 属性redoText 的通知信号。

[slot] void QUndoStack::resetClean()

如果堆栈是干净的,则离开干净状态并发出cleanChanged() 信号。该方法会将清洁索引重置为-1。

通常在以下情况下调用此方法,即文档已被创建:

  • 根据某个模板创建,但尚未保存,因此还没有与文档关联的文件名。
  • 从备份文件恢复。
  • 在编辑器之外更改,且用户没有重新加载。

另请参阅 isClean()、setClean() 和cleanIndex()。

[slot] void QUndoStack::setClean()

将堆栈标记为已清理,如果堆栈尚未清理,则发出cleanChanged() 信号。

例如,保存文档时通常会调用此功能。

每当堆栈通过使用撤销/重做命令返回到这种状态时,就会发出cleanChanged() 信号。当堆栈离开清洁状态时,也会发出该信号。

另请参见 isClean()、resetClean() 和cleanIndex()。

[slot] void QUndoStack::setIndex(int idx)

重复调用undo() 或redo() 直到当前命令索引到达idx 。该函数可用于向前或向后滚动文档状态。indexChanged() 只发出一次。

另请参阅 index()、count()、undo() 和redo()。

QString QUndoStack::text(int idx) const

返回索引idx 处的命令文本。

另请参阅 beginMacro() 。

[slot] void QUndoStack::undo()

通过调用QUndoCommand::undo() 撤销当前命令下面的命令。减少当前命令索引。

如果堆栈为空,或堆栈最下面的命令已被撤销,则此函数不会执行任何操作。

命令撤销后,如果QUndoCommand::isObsolete() 返回true ,则将从堆栈中删除该命令。此外,如果清除索引大于或等于当前的命令索引,则会重置清除索引。

另请参阅 redo() 和index()。

QString QUndoStack::undoText() const

返回将在下一次调用undo() 时撤销的命令文本。

注: 属性 undoText 的获取函数。

另请参阅 QUndoCommand::actionText() 和redoText()。

[signal] void QUndoStack::undoTextChanged(const QString &undoText)

只要undoText() 的值发生变化,就会发出该信号。createUndoAction undoText 指定新文本。

注: 属性undoText 的通知信号。

© 2025 The Qt Company Ltd. Documentation contributions included herein are the copyrights of their respective owners. The documentation provided herein is licensed under the terms of the GNU Free Documentation License version 1.3 as published by the Free Software Foundation. Qt and respective logos are trademarks of The Qt Company Ltd. in Finland and/or other countries worldwide. All other trademarks are property of their respective owners.