命令设计模式实现行为+数据的撤销undo/恢复redo功能

前言

公司最近有个需求就是要解析用户的画图行为动作,客户端记录保存了用户的行为+数据,然后将各端实现不同的需求,比如用户的画图行为回放,还要实现比如常用编辑器的撤销恢复等功能,在此可以使用命令设计模式实现,看了网上很多文章千篇一律,也只是实现了简单的undo、redo功能,所以也请教同事给了一份写好的客户端算法代码作为参考,然后融合到自己的后端代码中。

实现原理

大概实现原理:将每次执行过的命令和数据保存到undo回退队列中,当执行undo操作时候取出队列数据进行执行即可,若是添加操作,undo时则执行删除操作,若是删除操作,undo时则实行添加操作,每次执行完后放入redo队列中,用于下一次的redo。
思维导图撤销恢复

由于公司代码不允许外传,所以自己模拟写了一个简单的说话后悔药的功能分享给大家,看懂代码理论上适用于95%以上的撤销恢复场景。

后悔药DEMO案例实现功能:允许你随便说,记录过程+行为,然后只呈现你最终要说出去的话。

代码实现

SomeThingDomain.java:任意数据和行为实体,可以根据自己业务扩展,这里做demo只是呈现保存一句话desc;

/**
 * SomeThingDomain
 * 任意数据和行为
 * @author lcry
 */
@Data
@Builder
public class SomeThingDomain implements Serializable, Cloneable {
    /**
     * 操作类型
     */
    private OperateTypeEnum operateType;
    /**
     * 索引
     */
    private List<Integer> index;
    /**
     * 说的一句话
     */
    private String desc;



    /**
     * 克隆对象
     */
    @Override
    public SomeThingDomain clone() {
        try {
            return (SomeThingDomain) super.clone();
        } catch (CloneNotSupportedException e) {
            e.printStackTrace();
        }
        return null;
    }
}

OperateTypeEnum.java:操作枚举,可以自己添加更多

/**
 * OperateTypeEnum
 * 操作类型枚举
 *
 * @author lcry
 */
public enum OperateTypeEnum {
    /**
     * 未知
     */
    UNKNOWN(0),
    /**
     * 说一句话
     */
    ADD(1),
    /**
     * 删除随机几段话
     */
    DEL(2),
    /**
     * 清空所有说话
     */
    CLEAR(3),
    /**
     * 撤销说的一些话
     */
    UNDO(4),
    /**
     * 恢复说过的话
     */
    REDO(5);

    OperateTypeEnum(Integer type) {

    }
}

Action.class:动作接口

/**
 * Action
 * 动作接口
 *
 * @author lcry
 */
public interface Action {
    /**
     * 执行命令,可以是增加、删除、清空、剪切、粘贴等操作
     */
    void exec();

    /**
     * 撤销
     */
    void undo();

    /**
     * 恢复
     */
    void redo();
}

AddAction.java:添加操作实现类

/**
 * AddAction
 * 添加操作
 * 添加一句话或者多句话
 * @author lcry
 */
public class AddAction implements Action {
    /**
     * 最终要说出的话
     */
    private final List<SomeThingDomain> result;
    /**
     * 缓存添加的那一句话
     */
    private final List<SomeThingDomain> temp = new ArrayList<>();
    /**
     * 当前要添加的那句话
     */
    private final SomeThingDomain addSomeThingDomain;

    public AddAction(List<SomeThingDomain> result, SomeThingDomain addSomeThingDomain) {
        this.result = result;
        this.addSomeThingDomain = addSomeThingDomain;
    }

    @Override
    public void exec() {
//       添加一句话
        result.add(addSomeThingDomain);
    }

    @Override
    public void undo() {
//        撤销添加的那一句话
        result.remove(addSomeThingDomain);
//        清空缓存
        temp.clear();
//        把撤销的那句话添加到缓存中,方便下一次在redo
        temp.add(addSomeThingDomain);
    }

    @Override
    public void redo() {
//        恢复撤销的那一句话
        result.add(addSomeThingDomain);
//        清空缓存
        temp.clear();
//        把恢复的那句话添加到缓存中,方便下一次再undo
        temp.add(addSomeThingDomain);
    }
}

CleanAction.java、DeleteAction.java和AddAction.java代码差不多,只是逻辑不一样,篇幅有限参考文章前面的思路编写即可。

OperateManager.java:操作管理类

/**
 * OperateManager
 * 操作管理
 *
 * @author lcry
 */
public class OperateManager {
    /**
     * 最终要说出的话
     */
    private final List<SomeThingDomain> result = new ArrayList<>();
    /**
     * 动作管理,保存每次操作用于undo、redo
     */
    private final ActionManager actionManager = new ActionManager();

    /**
     * 解析说话过程->最终要表达的话
     *
     * @param paths 每次说出的一句话,行为+数据
     * @return 显示的最终笔迹
     */
    public List<SomeThingDomain> getResults(List<SomeThingDomain> paths) {
        result.clear();
        for (SomeThingDomain op : paths) {
            Action action = null;
            switch (op.getOperateType()) {
                case ADD:
                    System.out.println("执行添加操作" + print());
                    action = new AddAction(result, op.clone());
                    break;
                case DEL:
                    System.out.println("执行删除操作" + print());
                    action = new DeleteAction(result, op.getIndex());
                    break;
                case CLEAR:
                    System.out.println("执行删除操作" + print());
                    action = new CleanAction(result);
                    break;
                case UNDO:
                    System.out.println("执行撤销操作" + print());
                    actionManager.undo().undo();
                    break;
                case REDO:
                    System.out.println("执行恢复操作" + print());
                    actionManager.redo().redo();
                    break;
                default:
                    break;
            }
            if (action != null) {
//                命令模式:封装成对象去执行操作,而不是直接去执行操作
                action.exec();
                actionManager.setLastAction(action);
            }
        }
        // 清空之前的undo redo 操作队列
        actionManager.clear();
        return result;
    }

    /**
     * 打印每个步骤的结果
     */
    private String print() {
        StringBuffer resultTalk = new StringBuffer("   -> 结果:");
        result.forEach(a -> resultTalk.append(a.getDesc()));
        return resultTalk.toString();
    }
}

测试用例代码:

/**
 * TestSomeThing
 * 测试用例
 *
 * @author lcry
 */
public class TestSomeThing {

    /**
     * 测试整个说话流程
     *
     * @param args
     */
    public static void main(String[] args) {
        OperateManager operateManager = new OperateManager();
        List<SomeThingDomain> results = operateManager.getResults(getDemoSomeThing());
        StringBuffer resultTalk = new StringBuffer();
        results.forEach(a -> resultTalk.append(a.getDesc()));
        System.out.println("最终要说出的话为:" + resultTalk);
    }


    /**
     * 模拟数据
     *
     * @return 模拟完整的一个说话流程
     */
    private static List<SomeThingDomain> getDemoSomeThing() {
//        结果:第一句话|
        SomeThingDomain oneAdd = SomeThingDomain.builder().operateType(OperateTypeEnum.ADD).index(Collections.singletonList(0)).desc("第一句话|").build();
//       结果: 第一句话|第二句话|
        SomeThingDomain twoAdd = SomeThingDomain.builder().operateType(OperateTypeEnum.ADD).index(Collections.singletonList(1)).desc("第二句话|").build();
//       结果: 第一句话| 第二句话| 第三句话|
        SomeThingDomain threeAdd = SomeThingDomain.builder().operateType(OperateTypeEnum.ADD).index(Collections.singletonList(2)).desc("第三句话|").build();
//       结果: 第一句话| 第二句话| 第三句话| 第四句话|
        SomeThingDomain fourAdd = SomeThingDomain.builder().operateType(OperateTypeEnum.ADD).index(Collections.singletonList(3)).desc("第四句话|").build();
//       结果: 第一句话| 第二句话| 第三句话| 第四句话| 第五句话|
        SomeThingDomain fivesAdd = SomeThingDomain.builder().operateType(OperateTypeEnum.ADD).index(Collections.singletonList(4)).desc("第五句话|").build();
//       结果:  第四句话| 第五句话
        SomeThingDomain delete = SomeThingDomain.builder().operateType(OperateTypeEnum.DEL).index(Arrays.asList(0, 1, 2)).build();

        SomeThingDomain undo = SomeThingDomain.builder().operateType(OperateTypeEnum.UNDO).build();
        SomeThingDomain redo = SomeThingDomain.builder().operateType(OperateTypeEnum.REDO).build();
        SomeThingDomain clear = SomeThingDomain.builder().operateType(OperateTypeEnum.CLEAR).build();

        return Arrays.asList(oneAdd, twoAdd, threeAdd, fourAdd, fivesAdd, delete, undo, redo, clear, undo);

    }
}

执行结果:

....
执行添加操作   -> 结果:
执行添加操作   -> 结果:第一句话|
执行添加操作   -> 结果:第一句话|第二句话|
执行添加操作   -> 结果:第一句话|第二句话|第三句话|
执行添加操作   -> 结果:第一句话|第二句话|第三句话|第四句话|
执行删除操作   -> 结果:第一句话|第二句话|第三句话|第四句话|第五句话|
执行撤销操作   -> 结果:第四句话|第五句话|
执行恢复操作   -> 结果:第一句话|第二句话|第三句话|第四句话|第五句话|
执行删除操作   -> 结果:第四句话|第五句话|
执行撤销操作   -> 结果:
最终要说出的话为:第四句话|第五句话|

源码下载

https://download.csdn.net/download/qq_19244927/15578692

  • 2
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 3
    评论
第二部分 数据库管理原型系统 实践项目一 SQL语言的词法和语法分析 一.实验目的 熟练掌握基本SQL语句的写法,并为其定义文法。 二. 实验内容 1、为每一个基本SQL语句定义文法。 2、实现词法和语法分析器。 3、进行相应的语义检查。 4、形成查询的内部表示。 实践项目二 创建数据库及数据操作功能 一.实验目的 熟练掌握数据库管理系统中创建数据库、关系模式维护以及数据维护操作的实现技术 。 二. 实验内容 1、用高级语言创建数据库用户并完成权限管理功能。 (1)创建用户; (2)为用户授权; (3)撤销用户权限。 2、用高级语言建立数据库表。 (1)设计文件存储结构和存取方法; (2)属性的个数任意,属性的类型包括整数、实数和字符串; (3)定义完整性约束; (4)把表的相关信息存入数据字典。 3、用高级语言实现表的删除功能。 (1)删除表并维护数据字典; (2)如果表上有索引,删除相应的索引文件。 4、用高级语言实现属性的添加和删除功能。 (1)为基本表添加属性并维护数据字典; (2)为基本表删除属性并维护数据字典。 5、用高级语言实现视图的创建和删除功能。 (1)创建视图,维护数据字典; (2)删除视图,维护数据字典. 6、用高级语言实现表中元组的增删改功能,必要时需要维护索引文件。 (1)实现输入数据库记录的功能并维护数据字典; (2)实现删除数据库记录的功能并维护数据字典; (3)实现修改数据库记录的功能并维护数据字典。 7、用高级语言实现显示数据库表的功能,用于对上面的操作结果进行测试。 (1)实现"SELECT * FROM 表名"; (2)显示表的结构和内容。 说明:实验内容的2、3、4、6、7必做,其他任选。 实践项目三 索引的创建与删除 一.实验目的 掌握数据库管理系统中的索引技术。 二. 实验内容 1、用高级语言为数据库表的主属性建立索引,分两种情况: (1)主属性有序; (2)主属性无序。 2、用高级语言为数据库表的非主属性建立索引,分两种情况: (1)非主属性有序; (2)非主属性无序。 3、用高级语言为数据库表的任意属性建立B树索引。 4、用高级语言按数据库表的任意属性用简单散列方法存储数据库表。 5、用高级语言实现数据增删改时索引的维护功能。 6、删除建立的索引。 7、完成上述操作的同时维护数据字典。 说明:1、2、7必做,3和4选作一个,其他任选。 实践项目四 查询优化 一.实验目的 掌握启发式关系代数优化方法。 二. 实验内容 1、把查询的内部表示转换成语法树,查询功能包括: (1)选择:支持AND和OR条件 (2)投影 (3)连接:包括等值连接和自然连接 (4)集合操作:并、交、差 (5)分组聚集 2、实现启发式关系代数优化方法 利用启发式关系代数优化方法对初始查询树进行等价变换(考虑索引和视图), 形成优化的查询计划; 3、用启发式多连接查询优化方法确定多连接关系的连接顺序。 说明:1、2必做,第3项任选。 实践项目五 查询处理 一.实验目的 掌握关系代数操作的实现算法。 二. 实验内容 1、实现选择操作算法 (1)表扫描算法 (2)索引扫描算法 2、实现基于排序的分组聚集算法。 3、实现基于排序的投影算法。 4、实现基于排序的集合并、交、差算法。 5、实现连接操作,包括自然连接、等值连接。 (1)循环嵌套连接算法 (2)排序合并连接算法 (3)索引连接算法 (4)散列连接算法 6、完成与用户查询对应的完整的优化查询方案。 说明:1-6必做,其中每一项包含多个算法时,任选一个算法实现。 实践项目六 数据恢复 一.实验目的 掌握利用日志进行数据恢复的方法。 二. 实验内容 1、根据用户操作形成日志,包括两种日志 (1)REDO日志 (2)UNDO/REDO日志 2、设置系统故障,使用即时更新技术进行数据恢复。 3、设置系统故障,使用推迟更新技术进行数据恢复。 说明:2和3选作一个。 实践项目七 并发控制 一.实验目的 掌握两段锁并发控制协议和基于时间印的并发控制协议。 二. 实验内容 1、利用多进程技术产生多个并发事务同时访问数据库; 2、实现基于两段锁协议的并发控制。 3、实现基于时间印协议的并发控制。 说明:2和3选作一个。 ----------------------- 数据库管理原型系统全文共6页,当前为第1页。 数据库管理原型系统全文共6页,当前为第2页。 数据库管理原型系统全文共6页,当前为第3页。 数据库管理原型系统全文共6页,当前为第4页。 数据库管理原型系统全文共6页,当前为第5页。 数据库管理原型系统全文共6页,当前为第6页。
序号 CAD命令 简写 用途 1 3D   创建三维实体 2 3DARRAY 3A 三维阵列 3 3DCLIP   设置剪切平面位置 4 3DCORBLT   继续执行3DORBIT命令 5 3DDISTANCE   距离调整 6 3DFACE 3F 绘制三维曲面 7 3DMESH   绘制三维自由多边形网格 8 3DORBLT 3DO 三维动态旋转 9 3DPAN   三维视图平移 10 3DPLOY 3P 绘制三维多段线 11 3DSIN   插入一个3DS文件 12 3DSOUT   输出图形数据到一个3DS文件 13 3DSWIVEL   旋转相机 14 3DZOOM   三维视窗下视窗缩放 15 ABOUT   显示AutoCAD的版本信息 16 ACISIN   插入一个ACIS文件 17 ACISOUT   将AutoCAD三维实体目标输出到ACIS文件 18 ADCCLOSE   关闭AutoCAD设计中心 19 ADCENTER ADC 启动AutoCAD设计中心 20 ADCNAVIGATE ADC 启动设计中心并访问用户设置的文件名、路径或网上目录 21 ALIGN AL 图形对齐 22 AMECONVERT   将AME实体转换成AutoCAD实体 23 APERTURE   控制目标捕捉框的大小 24 APPLOAD AP 装载AutoLISP、ADS或ARX程序 25 ARC A 绘制圆弧 26 AREA AA 计算所选择区域的周长和面积 27 ARRAY AR 图形阵列 28 ARX   加载、卸载Object ARX程序 29 ATTDEF ATT、DDATTDEF 创建属性定义 30 ATTDISP   控制属性的可见性 31 ATTEDIT ATE 编辑图块属性值 32 ATTEXT DDATTEXT 摘录属性定义数据 33 ATTREDEF   重定义一个图块及其属性 34 AUDIT   检查并修复图形文件的错误 35 BACKGROUND   设置渲染背景 36 BASE   设置当前图形文件的插入点 37 BHATCH BH或H 区域图样填充 38 BLIPMODE   点记模式控制 39 BLOCK B或–B 将所选的实体图形定义为一个图块 40 BLOCKICON   为R14或更早版本所创建的图块生成预览图像 41 BMPOUT   将所选实体以BMP文件格式输出 42 BOUNDARY BO或–BO 创建区域 43 BOX   绘制三维长方体实体 44 BRDAK BR 折断图形 45 BROWSER   网络游览 46 CAL   AutoCAD计算功能 47 CAMERA   相机操作 48 CHAMFER CHA 倒直角 49 CHANGE –CH 属性修改 50 CH PROP   修改基本属性 51 CIRCLE C 绘制圆 52 CLOSE   关闭当前图形文件 53 COLOR COL 设置实体颜色 54 COMPILE   编译(Shape)文件和PostScript文件 55 CONE   绘制三维圆锥实体 56 CONVERT   将R14或更低版本所作的二维多段线(或关联性区域图样填充)转换成AutoCAD2000格式 57 COPY CO或CP 复制实体 58 COPYBASE   固定基点以复制实体 59 COPYCLIP   复制实体到WINDOWS剪贴板 60 COPYHIST   复制命令窗口历史信息到WINDOWS剪贴板 61 COPYLINK   复制当前视窗至WINDOWS剪贴板 62 CUTCLIP   剪切实体至WINDOWS剪贴板 63 CYLINDER   绘制一个三维圆柱实体 64 DBCCLOSE   关闭数据库连接管理 65 DBCONNECT DBC 启动数据库连接管理 66 DBLIST   列表显示当前图形文件中每个实体的信息 67 DDEDIT ED 以对话框方式编辑文本或属性定义 68 DDPTYPE   设置点的形状及大小 69 DDVPOINT VP 通过对话框选择三维视点 70 DELAY   设置演示(Script)延时时间 71 DIM AND DIM1   进入尺寸标注状态 72 DIMALIGNED DAL或DIMALI 标注平齐尺寸 73 DIMANGULAR DAN或DIMANG 标注角度 74 DIMBASELINE DBA或DIMBASE 基线标注 75 DIMCENTER DCE 标注圆心 76 DIMCONTINUE DCO或DIMCONT 连续标注 77 DIMDIAMETER DDI或DIMDLA 标注直径 78 DIMEDIT DED或DIMED 编辑尺寸标注 79 DIMLINEAR DLI或DIMLIN 标注长度尺寸 80 DIMORDINATE DOR或DIMROD 标注坐标值 81 DIMOVERRIDE DOR或DIMOVER 临时覆盖系统尺寸变量设置 82 DIMRADIUS DRA或DIMRAD 标注半径 83 DIMSTYLE DST或DIMSTY 创建或修改标注样式 84 DIMTEDIT DIMTED 编辑尺寸文本 85 DIST DI 测量两点之间的距离 86 DIVIDE DIV 等分实体 87 DONUT DO 绘制圆环 88 DRAGMODE   控制是否显示拖动对象的过程 89 DRAWORDER DR 控制两重叠(或有部分重叠)图象的显示次序 90 DSETTINGS DS、SE 设置栅格和捕捉、角度和目标捕捉点 自动 跟踪以及自动目标捕捉选项功能 91 DSVIEWER AV 鹰眼功能 92 DVIEW DV 视点动态设置 93 DWGPROPS   设置和显示当前图形文件的属性 94 DXBIN   将DXB文件插入到当前文件中 95 EDGE   控制三维曲面边的可见性 96 EDGESURF   绘制四边定界曲面 97 ELEV   设置绘图平面的高度 98 ELLIPSE EL 绘制椭圆或椭圆弧 99 ERASE E 删除实体 100 EXPLODE X 分解实体 101 EXPORT EXP 文件格式输出 102 EXPRESSTOOLS   如果当前AutoCAD环境中无[快捷工具]这一工具,可 启动该命令以安装AutoCAD快捷工具 103 EXTEND EX 延长实体 104 EXETRUDE EXT 将二维图形拉伸成三维实体 105 FILL F 控制实体的填充状态 106 FILLET   倒圆角 107 FILTER FI 过滤选择实体 108 FIND   查找与替换文件 109 FOG   三维渲染的雾度配置 110 GRAPHSCR   在图形窗口和文本窗口间切换 111 GRID   显示栅格 112 GROUP G或-G 创建一个指定各称的目标选择组 113 HATCH –H 通过命令行进行区域填充图样 114 HATCHEDIT HE 编辑区域填充图样 115 HELP   显示AutoCAD在线帮助信息 116 HIDE   消隐 117 HYPERLINK   插入超级链接 118 HYPERLINKOPTION HI 控制是否显示超级链接标签 119 ID   显示点的坐标 120 IMAGE I 将图像文件插入到当前图形文件中 121 IMAGEADJUST LAD 调整所选图像的明亮度、对比度和灰度 122 IMAGEATTACH LAT 附贴一个图像至当前图形文件 123 IMAGECLIP ICL 调整所选图像的边框大小 124 IMAGFRAME   控制是否显示图像的边框 125 IMAGEQUALITY   控制图像的显示质量 126 IMPORT TMP 插入其他格式文件 127 INSERT I 把图块(或文件)插入到当前图形文件 128 INSERTOBJ IO 插入OLE对象 129 INTERFERE INF 将两个或两个以上的三维实体的相交部分创 建为一个单独的实体 130 INTERSECT IN 对三维实体求交 131 ISOPLANE   定义基准面 132 LAYER LA或–LA 图层控制 133 LAYOUT LO 创建新布局或对已存在的布局进行更名、复制、保存 或删除等操作 133 JOIN J 合并 134 LAYOUTWIZARD   布局向导 135 LEADER LE或LEAD 指引标注 136 LENGTHEN LEN 改变实体长度 137 LIGHT   光源设置 138 LIMTS   设置图形界限 139 LINS L 绘制直线 140 LINETYPE LT或–LTLTYPE 创建、装载或设置线型 141 LIST LS 列表显示实体信息 142 LOAD   装入已编译过的形文件 143 LOGFILEOFF   关闭登录文件 144 LOGFILEON   将文本窗口的内容写到一个记录文件中 145 LSEDIT   场景编辑 146 LSLIB   场景库管理 147 LSNEW   添加场景 148 LTSCALE LTS 设置线型比例系数 149 LWEIGHT LW 设置线宽 150 MASSPROP   查询实体特性 151 MATCHPROP MA 属性匹配 152 MATLIB   材质库管理 153 MEASURE ME 定长等分实体 154 MENU   加载菜单文件 155 MENULOAD   加载部份主菜单 156 MENUUNLOAD   卸载部份主菜单 157 MINSERT   按矩形阵列方式插入图块 158 MIRROR MI 镜像实体 159 MIRROR3D   三维镜像 160 MLEDIT   编辑平行线 161 MLINE ML 绘制平行线 162 MLSTYLE   定义平行线样式 163 MODEL   从图纸空间切换到模型空间 164 MOVE M 移动实体 165 MSLIDE   创建幻灯片 166 MSPACE MS 从图纸空间切换到模型空间 167 MTEXT MT或T 多行文本标注 168 MULTIPLE   反复多次执行上一次命令直到 执行别的命令或按Esc键 169 MVIEW MV 创建多视窗 170 MVSETUP   控制视口 171 NEW   新建图形文件 172 OFFSET O 偏移复制实体 173 OLELINKS   更新、编辑或取消已存在的OLE链接 174 OLESCALE   显示OLE属性管理器 175 OOPS   恢复最后一次被删除的实体 176 OPEN   打开图形文件 177 OPTIONS OP、PR 设置AutoCAD系统配置 178 ORTHO   F8 切换正交状态 179 OSNAP OS 或–OS 设置目标捕捉方式及捕捉框大小 180 PAGESETUP   页面设置 181 PAN P或–P 视图平移 182 PARTIALOAD   部分装入 183 PARTIALOPEN   部分打开 184 PASTEBLOCK   将已复制的实体目标粘贴成图块 185 PASTECLIP   将剪贴板上的数据粘贴 至当前图形文件中 186 PASTEORLG   固定点粘贴 187 PASTESPEC PA 将剪贴板上的数据粘贴至当前图形文件中并控制其数据格式 188 PCINWINEARD   导入PCP或PC2配置文件的向导 189 PEDIT PE 编辑多段线和三维多边形网格 190 PFACE   绘制任意形状的三维曲面 191 PLAN   设置UCS平面视图 192 PLINE PL 绘制多段线 193 PLOT PRINT 图形输出 194 PLOTSTYLE   设置打印样式 195 PLOTTERMANAGER   打印机管理器 196 POINT PO 绘制点 197 POLYGON POL 绘制正多边形 198 PREVIEW PRE   199 PROPERTLES CH、MO、PRO 、PS、DDMODI、FX、DDCHPR OR 打印预览 目标属性管理器 200 PROPERTLESCLOSE PRCLOSE 关闭属性管理器 201 PSDRAG   控制PostScript图像显示 202 PSETUPIN   导入自定义页面设置 203 PSFILL   用PostScript图案填充二维多段线 204 PSIN   输入PostScript文件 205 PSOUT   输出PostScript文件 206 PSPACE PS 从模型空间切换到图纸空间 207 PURGE PU 消除图形中无用的对象,如图块、尺寸标注 样式、图层、线型、形和文本标注样式等 208 QDIM   尺寸快速标注 209 QLEADER LE 快速标注指引线 210 QSAVE   保存当前图形文件 211 QSELECT   快速选择实体 212 QTEXT   控制文本显示方式 213 QUIT EXIT 退出AutoCAD 214 RAY   绘制射线 215 RECOVER   修复损坏的图形文件 216 RECTANG REC 绘制矩形 217 REDEFINE   恢复一条已被取消的命令 218 REDO   恢复Undo(或U)命令取消的最后一条命令 219 REDRAW R 重新显示当前视窗中的图形 220 REDRAWALL RA 重新显示所有视窗中的图形 221 REFCLOSE   外部引用在位编辑时保存退出 222 REFEDIT   外部引用在位编辑 223 REFSET   添加或删除外部引用中的项目 224 REGEN RE 重新生成当前视窗中的图形 225 REGENALL REA 重新刷新生成所有视窗中的图形 226 REGGNAUTO   自动刷新生成图形 227 REGION REG 创建区域 228 REINIT   重新初始化AutoCAD的通信端口 229 RENAME REN 更改实体对象的名称 230 RENDER RR 渲染 231 RENDSCK   重新显示渲染图片 232 REPLAY   显示BMP、TGA或TIEF图像文件 233 RESUME   继续已暂停或中断的脚本文件 234 REVOLVE REV 将二维图形旋转成三维实体 235 REVSURF   绘制旋转曲面 236 RMAT   材质设置 237 ROTATE RO 旋转实体 238 ROTATE3D   三维旋转 239 RPREF RPR 设置渲染参数 240 RSCRIPT   创建连续的脚本文件 241 RULESURF   绘制直纹面 242 SAVE   保存图形文件 243 SAVE AS   将当前图形另存为一个新文件 244 SAVEIMG   保存渲染文件 245 SCALE SC 比例缩放实体 246 SCENE   场景管理 247 SCRIPT SCR 自动批处理AutoCAD命令 248 SECTION SEC 生成剖面 249 SELECT   选择实体 250 SETUV   设置渲染实体几何特性 251 SETVAR SET 设置AutoCAD系统变量 252 SHADE SHA 着色处理 253 SHAPE   插入形文件 254 SHELL SH 切换到DOS环境下 255 SHOWMAT   显示实体材质类型 256 SKETCH   徒手画线 257 SLICE SL 将三维实体切开 258 SNAP SN 设置目标捕捉功能 259 SOLDRAW   生成三维实体的轮廓图形 260 SOLID SO 绘制实心多边形 261 SOLIDEIDT   三维实体编辑 262 SOLPROF   绘制三维实体的轮廓图像 263 SOLVIEW   创建三维实体的平面视窗 264 SPELL SP 检查文体对象的拼写 265 SPHERE   绘制球体 266 SPLINE SPL 绘制一条光滑曲线 267 SPLINEDIT SPE 编制一条光滑曲线 268 STATS   显示渲染实体的系统信息 269 STATUS   查询当前图形文件的状态信息 270 STLOUT   将三维实体以STL格式保存 271 STRETCH S 拉伸实体 272 STYLE ST 创建文体标注样式 273 STYLESMANAGER   显示打印样式管理器 274 SUBTRACT SU 布尔求差 275 SYSWINDOWS   控制AutoCAD 文体窗口 276 TABLET TA 设置数字化仪 277 TABSURF   绘制拉伸曲面 278 TEXT   标注单行文体 279 TEXTSCR   切换到AutoCAD文体窗口 280 TIME   时间查询 281 TOLERANCE TOL 创建尺寸公差 282 TOOLBAR TO 增减工具栏 283 TORUS TOR 创建圆环实体 284 TRACE   绘制轨迹线 285 TRANSPARENCY   透水波设置 286 TREESTAT   显示当前图形文体件路径信息 287 TRIM TR 修剪 288 U   撤消上一操作 289 UCS   建立用户坐标系统 290 UCSICON   控制坐标图形显示 291 UCSMAN   UCS管理器 292 UNDEFINE   允许用户将自定义命令覆盖AutoCAD内部命令 293 UNDO   撤消上一组操作 294 UNION UNI 布 尔求并 295 UNITS –UN 或UN 设置长度及角度的单位格式和精度等级 296 VBAIDE   VBA集成开发环境 297 VBALOAD   加载VBA项目 298 VBAMAN   VBA管理器 299 VBARUN   运行VBA宏 300 VBASTMT   运行VBA语句 301 VBAUNLOAD   卸载VBA工程 302 VIEW –V 视窗管理 303 VIEWRES   设置当前视窗中目标重新生成的分辨率 304 VLISP VLIDE 打开Visual LISP集成开发环境 305 VPCLIP   复制视图实体 306 VPLAYER   设置视窗中层的可见性 307 VPOINT –VP或VP 设置三维视点 308 VPORTS   视窗分割 309 VSLIDE   显示幻灯文件 310 WBLOCK W 图块存盘 311 WEDGE WE 绘制楔形体 312 WHOHAS   显示已打开的图形文件的所属信息 313 WMFIN   输入Windows应用软件格式的文件 314 WMFOPTS   设置WMFIN命令选项 315 WMFOUT   WMF格式输出 316 XATTACH XA 粘贴外部文件至当前图形 317 XBIND –XB或XB 将一个外部引用的依赖符永久地溶入 当前图形文件中 318 XCLIP XC 设置图块或处理引用边界 319 XLINE XL 绘制无限长直线 320 XPLODE   分解图块并设置属性参数 321 XREF XR或–XR 外部引用 322 ZOOM Z 视图缩放透明命令
在 Eclipse 中,可以使用 `org.eclipse.ui.actions.ActionFactory.UNDO` 和 `org.eclipse.ui.actions.ActionFactory.REDO` 来创建 UndoRedo 动作。然后,将这些动作关联到菜单栏 Edit 中的 UndoRedo 菜单项。 要在 `ViewPart` 中实现 Undo/Redo,您需要遵循以下步骤: 1. 在 `ViewPart` 类中添加以下字段: ```java private IUndoContext undoContext; private IUndoableOperation undoOperation; private IAction undoAction; private IAction redoAction; ``` 2. 在 `createPartControl` 方法中初始化这些字段: ```java public void createPartControl(Composite parent) { // 创建 Undo/Redo 上下文 undoContext = new ObjectUndoContext(new Object()); // 创建 Undo/Redo 动作 undoAction = ActionFactory.UNDO.create(getSite().getWorkbenchWindow()); undoAction.setText("Undo"); undoAction.setImageDescriptor(PlatformUI.getWorkbench().getSharedImages() .getImageDescriptor(ISharedImages.IMG_TOOL_UNDO)); undoAction.setEnabled(false); redoAction = ActionFactory.REDO.create(getSite().getWorkbenchWindow()); redoAction.setText("Redo"); redoAction.setImageDescriptor(PlatformUI.getWorkbench().getSharedImages() .getImageDescriptor(ISharedImages.IMG_TOOL_REDO)); redoAction.setEnabled(false); // 将 Undo/Redo 动作添加到菜单栏 Edit 中 IMenuManager menuMgr = getViewSite().getActionBars().getMenuManager(); menuMgr.add(new Separator()); menuMgr.add(undoAction); menuMgr.add(redoAction); } ``` 3. 在 `createPartControl` 方法中为 Undo/Redo 动作添加处理程序: ```java public void createPartControl(Composite parent) { // ... // 为 Undo/Redo 动作添加处理程序 undoAction.setHandler(new UndoActionHandler(getViewSite(), undoContext)); redoAction.setHandler(new RedoActionHandler(getViewSite(), undoContext)); } ``` 4. 在 `createPartControl` 方法中为 `parent` 控件创建上下文菜单,并将 Undo/Redo 动作添加到上下文菜单中: ```java public void createPartControl(Composite parent) { // ... // 为 parent 控件创建上下文菜单,并将 Undo/Redo 动作添加到上下文菜单中 MenuManager menuMgr = new MenuManager(); menuMgr.add(new Separator(IWorkbenchActionConstants.MB_ADDITIONS)); getSite().registerContextMenu(menuMgr, getSite().getSelectionProvider()); parent.setMenu(menuMgr.createContextMenu(parent)); menuMgr.addMenuListener(new IMenuListener() { public void menuAboutToShow(IMenuManager manager) { manager.add(new Separator()); manager.add(undoAction); manager.add(redoAction); } }); } ``` 5. 在 `ViewPart` 类中添加以下方法: ```java public void executeCommand(final IUndoableOperation operation) { // 如果操作不可撤销,则返回 if (!operation.canUndo()) { return; } // 如果当前有未完成的撤消操作,则合并操作 if (undoOperation != null) { undoOperation.addContext(operation.getContext()); undoOperation.add(operation); } else { // 否则,开始新的撤消操作 undoOperation = operation; } // 注册撤消操作 IOperationHistory operationHistory = OperationHistoryFactory.getOperationHistory(); operationHistory.add(undoOperation); // 更新 Undo/Redo 动作的状态 undoAction.setEnabled(undoOperation.canUndo()); redoAction.setEnabled(undoOperation.canRedo()); // 将操作添加到 Undo/Redo 上下文中 undoContext.addMatch(undoOperation); } public void undo() { // 撤消上一个操作 IOperationHistory operationHistory = OperationHistoryFactory.getOperationHistory(); operationHistory.undo(undoContext, null, null); } public void redo() { // 重做上一个操作 IOperationHistory operationHistory = OperationHistoryFactory.getOperationHistory(); operationHistory.redo(undoContext, null, null); } ``` 6. 在 `ViewPart` 类中添加以下代码,以便在视图关闭时清除 Undo/Redo 上下文中的操作: ```java public void dispose() { // 清除 Undo/Redo 上下文中的操作 IOperationHistory operationHistory = OperationHistoryFactory.getOperationHistory(); operationHistory.dispose(undoContext, true, true, true); super.dispose(); } ``` 现在,您可以在 `executeCommand` 方法中执行所有需要撤消/恢复支持的操作,并且在菜单栏 Edit 中的 Undo/Redo 菜单项中使用 Undo/Redo 动作来撤消/恢复操作。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值