我有一个实现 UITextInput 的视图,并添加了对撤消的支持。现在,每个单独的击键或退格键都被记录为可撤消的事件。
我知道我可以对事件进行分组,并且可以在第一次击键时打开一个撤消组。但是我该去哪里关闭这个小组呢?如果当用户摇动设备时该组是打开的,我会得到一个例外。撤消时,您不能有一个打开的组。
我会以某种方式需要在 NSUndoManager 实例显示操作菜单之前关闭打开的组。
我是否需要继承 NSUndoManager 才能做到这一点?或者有人知道如何在操作之前及时关闭输入撤消组吗?
注意:第一响应者在显示撤消操作时不会辞职。
实际上,在我看来,普通文本输入会以某种方式打开打字组,因为如果您取消撤消/重做警报,那么您可以继续打字,所有这些击键随后都可以一起撤消。
我想我不明白何时分组操作以及是否以及何时需要关闭一个组。
更新:我发现以下工作正常:我创建了一个 NSUndoManager 的子类,它跟踪打开组的数量。在 -undo 我正在关闭所有打开的组以避免异常,然后调用[super undo]
#import "DTUndoManager.h"
@implementation DTUndoManager
{
NSUInteger _numberOfOpenGroups;
}
- (void)beginUndoGrouping
{
_numberOfOpenGroups++;
[super beginUndoGrouping];
}
- (void)endUndoGrouping
{
_numberOfOpenGroups--;
[super endUndoGrouping];
}
- (void)closeAllOpenGroups
{
while (_numberOfOpenGroups>0)
{
[self endUndoGrouping];
}
}
- (void)undo
{
[self closeAllOpenGroups];
[super undo];
}
#pragma mark - Properties
@synthesize numberOfOpenGroups = _numberOfOpenGroups;
@end
每当一个新操作开始时,比如更改段落样式,我都会调用[self.undoManager closeAllOpenGroups]
这会导致关闭输入的撤消组。
在-deleteBackward:
and-insertText:
方法中,我知道需要启动一个新的打字块:
- (void)insertText:(NSString *)text
{
DTUndoManager *undoManager = (DTUndoManager *)self.undoManager;
if (!undoManager.numberOfOpenGroups)
{
[self.undoManager beginUndoGrouping];
}
现在这不是太多额外的代码,但我希望不必使用我自己的 DTUndoManager 子类......所以我愿意接受建议。