I'm having an issue with a TextKit2 NSTextView (AppKit). In my subclass's keyDown, I'm doing a bit of manipulation of the textStorage but it seems that if I try to alter any part of the textStorage where a text paragraph and accompanying fragment have already been created, I then get duplicate paragraphs and fragments.
For example, say I want to insert new text at the end of an existing paragraph. I've tried:
- Inserting a new attr string (with attrs matching the preceding text) at the end of the existing paragraph text
- Replacing the existing paragraph text with a new attr string that includes the new text
- First deleting the existing paragraph text and then inserting the new full attr string including the new text
I am wrapping those edits in a textContentStorage.performEditingTransaction closure.
But in all cases, it seems that TextKit 2 wants to create new NSTextParagraph and NSTextFragment objects and doesn't remove the old ones, resulting in duplicate elements in my UI.
Some sample code:
let editLocation = editRange.location
guard editLocation > 0 else {
break
}
let attrs = textStorage.attributes(at: editLocation, effectiveRange: nil)
// paragraphStartLocation is in an NSAttributedString extension not shown
guard let paragraphStartLoc = textStorage.paragraphStartLocation(from: editLocation) else {
assertionFailure(); return
}
var paragraphRange = NSRange(location: paragraphStartLoc, length: editLocation - paragraphStartLoc + 1)
var fullParagraph = textStorage.attributedSubstring(from: paragraphRange).string
fullParagraph += newText
let newAttrStr = NSAttributedString(string: fullParagraph, attributes: attrs)
textContentStorage.performEditingTransaction {
textStorage.deleteCharacters(in: paragraphRange)
textStorage.insert(newAttrStr, at: paragraphStartLoc)
}