Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix block styling to support empty lines in editor #13

Open
amyworrall opened this issue Apr 6, 2023 · 0 comments
Open

Fix block styling to support empty lines in editor #13

amyworrall opened this issue Apr 6, 2023 · 0 comments
Assignees
Labels
architectural-decision For if we need to make a decision before diving in to writing code difficult An issue where the code required to solve it is difficult to write. textkit Requires interacting with Apple's TextKit framework

Comments

@amyworrall
Copy link
Contributor

Background

TextKit 1, which Lexical uses, doesn't really support block level elements. Margins/padding are applied at a paragraph level, where paragraph is defined as any text separated by newlines.

In Lexical, we wanted to allow nodes to behave like block level elements like they do on the web. For example, our Code node has some top/bottom margin and some padding in order to draw its bordered box.

The way Lexical iOS accomplishes this is by taking the node that is calling for top/bottom margin/padding, and applying the top margin to the first paragraph within that node, and the bottom margin to the last paragraph within that node.

Issues

I wrote the block level styling system as part of the Feed Inlines project, which uses read-only Lexical. I'm now making sure it works well with editable Lexical too.

There are two main issues that need addressing:

  • The metrics (i.e. spacing above/below) of a line don't update until the user has typed a character on that line. E.g. when switching paragraph style, or when entering a newline within a paragraph style that has expanded top/bottom margins.
  • There is a separate issue regarding when a paragraph style applies to the last line of the document, and the last line is empty.

Metric updating

There are/were two problems here:

  • The code for applying the block level attributes looked only at dirty nodes (and their range cache locations). It did not check if the node was unattached. And since this code was running before the garbage collection happened. it was finding unattached nodes, with a stale range cache, and applying the old block level attributes to that node's stale range.
  • When calculating which paragraphs needed to have top/bottom margin, the calculation was excluding the last line of the document (if said line was empty), because that's not a paragraph with any content in it according to TextKit.

Last line drawing

As well as the last line being excluded when calculating which paragraphs need top/bottom margin (as mentioned above), we also have the issue of how to actually apply any form of styling to the last line at all. As mentioned, it does not correspond to any range in the backing attributed string, so where do we apply attributes?

The last line is handled as a special case by TextKit, and is known as the extraLineFragment. TextKit places and styles it (as far as I can see) according to the last character on the previous line's attributes.

Status

I have written code (as yet unpublished) to fix the first part of this. I'm working on the extraLineFragment support, and am having some trouble getting it to work reliably.

@amyworrall amyworrall added textkit Requires interacting with Apple's TextKit framework difficult An issue where the code required to solve it is difficult to write. architectural-decision For if we need to make a decision before diving in to writing code labels Apr 6, 2023
@amyworrall amyworrall self-assigned this Apr 6, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
architectural-decision For if we need to make a decision before diving in to writing code difficult An issue where the code required to solve it is difficult to write. textkit Requires interacting with Apple's TextKit framework
Projects
None yet
Development

No branches or pull requests

1 participant