I want to implement undo action after replacing portion of text in an NSTextView. I am replacing portion of text with following code
- (void)omeAction
{
NSString *fullString = [self.textView string];
NSRange selectedRange = [self.textView selectedRange];
NSString *selectedString = [fullString substringWithRange:selectedRange];
NSString *stringToReplace = ...;
[[self.textView textStorage] beginEditing];
[[self.textView textStorage] replaceCharactersInRange:selectedRange withString:stringToReplace];
[[self.textView textStorage] endEditing];
}
While performing undo I couldn't really undo the text replacement
From Cocoa Text Architecture Guide: Text Editing – Text Change Notifications and Delegate Messages:
In actually making changes to the text, you must ensure that the changes are properly performed and recorded by different parts of the text system. You do this by bracketing each batch of potential changes with shouldChangeTextInRange:replacementString: and didChangeText messages. These methods ensure that the appropriate delegate messages are sent and notifications posted. …
In my experience, that includes generating the relevant undo operation.
So, you would do:
if ([self.textView shouldChangeTextInRange:selectedRange replacementString:stringToReplace])
{
[[self.textView textStorage] beginEditing];
[[self.textView textStorage] replaceCharactersInRange:selectedRange withString:stringToReplace];
[[self.textView textStorage] endEditing];
[self.textView didChangeText];
}
First I tried to solve undo and shouldChangeTextInRange:replacementString: did the trick. However I found that insertText:replacementRange: had the same effect.
[self insertText:attributedString replacementRange:range];
Or:
if ([textView shouldChangeTextInRange:range replacementString:string]) { //string
[textStorage beginEditing];
[textStorage replaceCharactersInRange:range withAttributedString:attributedString];
[textStorage endEditing];
[textView didChangeText];
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With