QUndoView
Qt的Undo框架是命令模式(Command pattern) 的实现,用于在应用程序中实现撤消/重做功能.
继承自QListView,它显示在推送到撤销堆栈QUndoStack上命令列表
常用方法:
push(): 将命令推入堆栈或将其与最近执行的命令合并;
undo(): 通过调用QUndoCommand.undo()撤消当前命令下方的命令。减少当前命令索引。如果堆栈为空,或者堆栈上的底部命令已被撤消,则此功能不执行任何操作;
redo(): 通过调用QUndoCommand.redo()重做当前命令。增加当前命令索引。如果堆栈为空,或者已经重做了堆栈上的顶层命令,则此功能不执行任何操作;
createUndoAction(): 创建一个撤销QAction对象;
createRedoAction(): 创建一个重做QAction对象;
clear(): 清除命令堆栈,然后将堆栈返回到干净状态。命令不会被撤消或重做;编辑对象的状态保持不变。当放弃文档内容时,通常使用此功能。
常用信号:
canRedoChanged: 当canRedo()的值发生改变时,发射此信号,它用于启用或禁用createRedoAction()返回的QAction对象的触发操作;
canUndoChanged: 当canUndo()的值发生改变时,发射此信号,它用于启用或禁用createUndoAction()返回的QAction对象的触发操作;
QUndoCommand:
是存储在QUndoStack上的所有命令的基类, 对操作命令的撤销和重做功能的实现必须在其派生类里提供。
QUndoCommand对象由它们被压入的堆栈所拥有。如果已撤消命令并推送了新命令,则QUndoStack会删除该命令。
当命令被压入QUndoStack时,它成为堆栈上最顶层的命令。
QUndoCommand常用方法:
actionText(): 返回一个简短的文本字符串,描述此命令的作用;例如“插入文本”;
child(): 返回指定索引处的子命令;
childCount(): 返回此命令中子命令的数目;
redo(): 重做操作,该函数必须在派生类里实现;
undo(): 撤销操作,该函数必须在派生类里实现;
setText(): 将命名的文本信息设置为指定的文本;
text(): 返回命令的文本信息。
QUndoGroup:
是一组QUndoStack对象,其中一个可能是活动状态。
QUndoGroup有一个undo()和redo()函数,它调用处于活动状态的QUndoStack.undo()和QUndoStack.redo()。
使用addStack()将堆栈加入到组中,使用removeStack将堆栈移除组。
当使用QUndoGroup作为QUndoStack的父对象时,QUndoStack对象将隐式地添加到组中。
QUndoGroup常用方法:
createUndoAction(): 创建一个撤销QAction对象;
createRedoAction(): 创建一个重做QAction对象;
redo(): 在活动堆栈上调用QUndoStack.redo()。如果没有一个堆栈处于活动状态,或者该组为空,则此功能不执行任何操作;
undo(): 在活动堆栈上调用QUndoStack.undo()。如果没有一个堆栈处于活动状态,或者该组为空,则此功能不执行任何操作。
QUndoGroup常用信号:
activeStackChanged(): 当组的活动堆栈发生改变时,发射此信号;
canRedoChanged(): 当活动堆栈发出QUndoStack.canRedoChanged()信号或者活动堆栈发生改变时,发射此信号;
canUndoChanged(): 当活动堆栈发出QUndoStack.canUndoChanged()信号或者活动堆栈发生改变时,发射此信号;
redoTextChanged(): 当活动堆栈发出QUndoStack.redoTextChanged()信号或者活动堆栈发生改变时,发射此信号;
undoTextChanged(): 当活动堆栈发出QUndoStack.undoTextChanged()信号或者活动堆栈发生改变时,发射此信号。
代码
widgetundoview.h
#ifndef WIDGETUNDOVIEW_H
#define WIDGETUNDOVIEW_H
#include <QWidget>
#include <QUndoCommand>
#include <QUndoStack>
#include <QAction>
namespace Ui {
class WidgetUndoView;
}
class OperateCommand;
class WidgetUndoView : public QWidget
{
Q_OBJECT
public:
explicit WidgetUndoView(QWidget *parent = nullptr);
~WidgetUndoView();
void initUndoView();
protected:
void changeEvent(QEvent* event);
private slots:
void on_pushButton_clicked();
private:
void retranslateUi();
private:
QAction* m_pUndoAction;
QAction* m_pRedoAction;
private:
QUndoStack* m_pUndoStack;
private:
Ui::WidgetUndoView *ui;
};
//继承于QUndoCommand,实现撤销和重做功能
class OperateCommand : public QUndoCommand
{
public:
OperateCommand();
void redo() override;
void undo() override;
};
#endif // WIDGETUNDOVIEW_H
widgetundoview.cpp
#include "widgetundoview.h"
#include "ui_widgetundoview.h"
#include "commondef.h"
WidgetUndoView::WidgetUndoView(QWidget *parent) :
QWidget(parent),
ui(new Ui::WidgetUndoView)
{
ui->setupUi(this);
initUndoView();
}
WidgetUndoView::~WidgetUndoView()
{
delete ui;
}
void WidgetUndoView::initUndoView()
{
m_pUndoStack = new QUndoStack(this);
//创建一个撤销QAction对象
m_pUndoAction = m_pUndoStack->createUndoAction(this, "Undo");
//指定快捷键
m_pUndoAction->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_Z));
//创建一个重做QAction对象;
m_pRedoAction = m_pUndoStack->createRedoAction(this, "Redo");
//指定快捷键
m_pRedoAction->setShortcut(QKeySequence(Qt::CTRL + Qt::Key_Y));
//添加QAction对象
addAction(m_pUndoAction);
addAction(m_pRedoAction);
//设置视图显示的堆栈
ui->undoView->setStack(m_pUndoStack);
}
void WidgetUndoView::changeEvent(QEvent *event)
{
switch(event->type())
{
case QEvent::LanguageChange:
retranslateUi();
break;
default:
QWidget::changeEvent(event);
}
}
void WidgetUndoView::retranslateUi()
{
ui->label->setText(tr("Use Undo View"));
}
OperateCommand::OperateCommand()
{
setText("OperateCommand");
}
//接收到QUndoStack的canRedoChanged信号时触发
void OperateCommand::redo()
{
setText("Redo");
}
//接收到QUndoStack的canUndoChanged信号时触发
void OperateCommand::undo()
{
setText("Undo");
}
//将命令推入堆栈中
void WidgetUndoView::on_pushButton_clicked()
{
QUndoCommand* operCmd = new OperateCommand();
m_pUndoStack->push(operCmd);
}
实现效果:
工程代码下载:
https://download.csdn.net/download/linyibin_123/86512679