I am trying to replace one color with another in NSAttributedString
to enable a dark mode in a pre-Mojave-app. I have a long NSTextView
which holds the string.
Is there any way to remap or mutate the color that is already set in the NSTextView, similar to what the Mojave dark mode does with NSColor.textColor
? If there are multiple documents open, formatting the string by enumerating through ranges and attributes one by one is very slow.
Hints & tips using Swift or Objective-C are greatly appreciated!
Short Answer: Make your own "adaptable" colors.
Long Answer
Make a subclass of NSColor
which has two readonly (to keep with
NSColor being immutable) instance NSColor
properties for the
standard and dark colors.
Add a class property to get/set which color should be used.
Define your own init
/new
methods which take the underlying standard and dark colors.
Add all of NSColor
's creation methods to your colors @interface
marking them all NS_UNAVAILBLE
– this prevents accidental use of
them.
Override all the methods required – see NSColor.h
(use "Jump to
Definition" in Xcode to open it). Each override simply directs the
method to the appropriate standard or dark color. This is just a
bunch of boilerplate code.
Now use your subclass to color your NSAttributedString
. When you
wish to switch mode use the class property to switch all the colors
on-the-fly and redraw your string.
HTH