30次发布
0.1.5-beta.1 | 2024年5月6日 |
---|---|
0.1.4 | 2024年5月6日 |
0.1.4-beta.9 | 2023年12月23日 |
0.1.4-beta.8 | 2023年10月9日 |
0.1.1-beta.17 | 2022年10月23日 |
#393 in 编码
1,995 每月下载
在 2 个crate中使用 (via klavier-core)
98KB
2K SLoC
Serdo
序列化撤销/重做库。
摘要
- GoF命令模式的实现。
- 通过使命令可序列化,可以将所有撤销信息序列化到文件中。即使重启应用程序,也可以执行撤销/重做操作。
- 可以在任何点将状态保存为快照,然后从快照中恢复状态。即使从快照恢复后,也可以执行撤销/重做。
图1说明了架构。应用程序使用带有撤销信息的do()调用。
图1 摘要
1. 架构
1.1 命令
Serdo存储对模型的变化。这个变化单位被称为'命令'。让我们考虑一个可以加数的微小计算器。
flowchart LR;
State0["State0 (=0)"]-- "Command0 (add 2)" -->State1["State1 (=2)"];
State1-- "Command1 (add 3)" -->State2["State2 (=5)"];
State2-- "Command2 (add 4)" -->State3["State3 (=9)"];
Latest["Latest value = 9"]-..->State3;
图1.1.1 命令
图1.1.1说明了命令。在这个例子中,应用了三个命令。每个命令分别添加2、3和4。状态是模型在特定点的值。如果模型的初始状态为零,最新值将是9。
如果您执行撤销,最新的命令'Command2'将被取消,模型状态将回到'Command1'应用后的状态。最新指针将更新为指向'State2',值将为5(图1.1.2)。
flowchart LR;
State0["State0 (=0)"]-- "Command0 (add 2)" -->State1["State1 (=2)"];
State1-- "Command1 (add 3)" -->State2["State2 (=5)"];
State2-- "Command2 (add 4)" -->State3["State3 (=9)"];
Latest["Latest value = 5"]-.->State2;
图1.1.2 执行撤销后
在图1.1.2的状态下,您可以执行重做以进入'State3',或者您可以执行撤销以进一步返回到'State0'。在这两种情况下,最新指针将分别更新为'State3'或'State0'。
那么在执行撤销后添加的新命令怎么办?如果您在此时添加另一个命令,Command 3,添加100,此时将为命令创建新的State 3,如图1.1.3所示。
flowchart LR;
State0["State0 (=0)"]-- "Command0 (add 2)" -->State1["State1 (=2)"];
State1-- "Command1 (add 3)" -->State2["State2 (=5)"];
State2-- "Command3 (add 100)" -->State3["State3 (=105)"];
Latest["Latest value = 105"]-.->State3;
图1.1.3 撤销后添加命令(Command 3)
可以指定撤销限制。如果指定了撤销限制,当命令的数量超过限制时,最旧的命令将被删除。
1.2 内存模式和非持久模式
InMemoryUndoStore
是一个存储在内存中的撤销存储库,而 SqliteUndoStore
将命令存储在 SQLite 数据库中。
- 内存模式方便且快速,但如果你重启应用程序,所有命令都将丢失。
- 如果你使用持久模式,命令将被持久化。即使你重启应用程序,你也可以执行撤销操作。
依赖项
~0.5–4.5MB
~81K SLoC