MikeMaus
MikeMaus

Reputation: 405

How to add numbered/bulleted list in SwiftUI?

How to do this in SwiftUI in TextEditor? I thought of reading return from keyboard. TextField has onEditingChanged and onCommit, but TextEditor doesn't.

In Notes app it detects automatically the numbered list, and has button for adding bulleted list.

I specifically want it to add number/bullet after empty line. (if possible)

enter image description here

Upvotes: 6

Views: 13700

Answers (2)

Tyson Freeze
Tyson Freeze

Reputation: 123

Two improvements to @aheze's answer.

  1. Removing the latest bullet if return is hit a second time.
  2. Validating that bullet's are only created if that line itself begins with a bullet.
.onChange(of: text) { oldText, newText in
    let newLineIndex = oldText.lastIndex(where: { $0 == "\n" }) ?? oldText.startIndex
    if newText.count > oldText.count {
        if newText[newLineIndex...].starts(with: /\n?•/) { //line begins with a bullet
            if newText.suffix(3) == "\u{2022} \n"{ //user hits enter twice
                text.removeLast(3)
            } else if newText.suffix(1) == "\n" { //user hits enter once
                text.append("\u{2022} ")
            }
        }
    }
}

Upvotes: 0

aheze
aheze

Reputation: 30506

You can observe changes to the TextEditor's text with onChange. Then, by doing [text] newText, you can capture both the old and new value.

  • text is the previous text
  • newText is the current text

If you compare these, you can ensure that bullet points are only added when the user is typing, and not when they're deleting.

Note that my implementation doesn't handle pasting large ranges of text yet.

struct ContentView: View {
    @State var text = "\u{2022} "

    var body: some View {
        TextEditor(text: $text)
            .frame(height: 400)
            .border(Color.black)
            .onChange(of: text) { [text] newText in
                if newText.suffix(1) == "\n" && newText > text {
                    self.text.append("\u{2022} ")
                }
            }
    }
}

When entering new lines, a bullet point is inserted at the start of the line

Upvotes: 13

Related Questions