TextEditor was new in 2020, and it allowed users to write text that spans multiple lines. Until WWDC 2020 there was only
SecureTextField, unless you used
UIViewRepresentable to wrap
In our example, we will also give the user the ability to set the font size, weight and colour. Because I’m extracting each of the elements in our UI into separate subviews, this view only takes a
Binding for the text. The font size, weight and colour will be stored in the parent, and can only be changed by the controls for those attributes.
We need to create an enum for the various kinds of font weight. This makes it easier to have a
Picker that allows you to choose one of the options, and we have a switch that will convert the cases into a
Font.Weight that can be applied to our
FontWeightPicker only requires a
Binding for the current
WeightType, as we can get the data from the enum itself. Since the enum conforms to the
CaseIterable protocol, we have access to an array of its cases in a property called
allCases. The enum also has
String as a raw type, and I’m using these to display the options in the
Picker. If you wanted to give them better names, you would have to assign the raw values in the enum, for instance
ultraLight = “Ultra Light”.
The next control we’ll make is a button for deleting everything in the
There is potentially a lot of text there, so you may want to confirm that a user actually wants to do this before they do it.
ColorPicker was also new in 2020, and it was initially impossible to dismiss it once it was displayed. Now there is an X in the top right corner, which you can use to close it when you have chosen a colour. The only reason that this subview was extracted was to tidy away the view modifiers, which create a rounded grey rectangle behind the
FontColourPicker. This makes it match the
DeleteAllButton next to it. Only the circular icon is actually a button for bringing up the
ColorPicker interface, so the part that says Text colour doesn’t do anything.
This is another subview that I didn’t really need to extract, but it makes the main parent view neater to have everything separated out.
Bringing it all together in ContentView
ContentView stores all of the properties for the
TextEditor. I’ve put the whole thing in a
ScrollView, mainly so that we can be sure that this will work on smaller devices. We have the
TextEditor at the top, followed by an
HStack containing the
FontColourPicker. Underneath that we have the
FontSizeStepper and the
FontWeightPicker. The entire
VStack has been given horizontal padding, which gives it extra space on the left and right.
How it should look
This is how the TextEditor should look in light and dark mode: