How to implement undo/redo with programatic change of the textValue of a NSTextView?

后端 未结 3 2080
日久生厌
日久生厌 2021-02-20 15:34

I created a simple demo app with a NSTextView and a button, the provided a NSTextViewDelegate to the textView and added an action:

- (IBAction)actionButtonClicke         


        
3条回答
  •  面向向阳花
    2021-02-20 15:53

    No need to add the NSUndoManager here, just let the NSTextView do the job.

    You just need to make sure you are calling the higher level methods only of NSTextView beginning with insert… and not setting the text/string of the textView or the textStorage directly:

        [self.textView insertText:newString];
    

    If you absolutely need to use setString or other lower level methods, then you just need to add the required methods handling the textDidChange delegation: -shouldChangeTextInRange:replacementString and -didChangeText (which is done by the insert... methods btw):

    if( [self.textView shouldChangeTextInRange:editedRange replacementString:editedString]) {
        // do some fancy stuff here…
        [self.textView.textStorage replaceCharactersInRange:editedRange
                              withAttributedString:myFancyNewString];
        // … and finish the editing with
        [self.textView didChangeText];
    }
    

    This automatically lets the undoManager of NSTextView kick in. I think the undoManager is preparing an undoGrouping in shouldChangeTextInRange: and invoking the undo in didChangeText:.

提交回复
热议问题