Attributes
If you haven't yet, read introduction to Zefyr document model called Notus here.
Style attributes in Notus documents are simple key-value pairs, where keys identify the attribute and value describes the style applied, for instance, { "heading": 1 }
defines heading style for a line of text with value 1
(equivalent of h1
in HTML).
Note that one attribute can describe multiple different styles depending on the current value. E.g. attribute with key "heading" can be set to values 1
, 2
or 3
, equivalents of h1
, h2
and h3
in HTML. This prevents a line of text from being formatted as h1
and h2
heading at the same time, which is intentional.
Additionally, each attribute gets assigned one of two scopes. An attribute can be either inline-scoped or line-scoped, but not both. A good example of an inline-scoped attribute is "bold" attribute. Bold style can be applied to any character within a line, but not to the line itself. Similarly "heading" style is line-scoped and has effect only on the line as a whole.
Below table summarizes information about all currently supported attributes in Zefyr:
Name
Key
Scope
Type
Valid values
Bold
b
inline
bool
true
Italic
i
inline
bool
true
Link
a
inline
String
Non-empty string
Heading
heading
line
int
1
, 2
and 3
Block
block
line
String
"ul"
, "ol"
, "code"
and "quote"
Embed
embed
inline
Map
"hr"
, "image"
Removing a specific style is as simple as setting corresponding attribute to null
.
Here is an example of applying some styles to a document:
How attributes are stored in Deltas
As mentioned previously a document delta consists of a sequence of insert
operations. Attributes (if any) are stored as metadata on each of the operations.
There is a difference in how line and inline-scoped attributes are handled. Since Deltas are essentially a flat data structure there is nothing in the format itself to represent a line of text, which is required to allow storing line-scoped style attributes.
To solve this issue Notus document (similarly to Quill.js) reserves the newline character (aka \n
and 0x0A
) as storage for line-scoped styles.
Notus document model is designed to enforce this rule and prevents malformed changes from being composed into a document. For instance, an attempt to apply "bold" style to a newline character will have no effect.
Below is an example of Notus document's Delta with two lines of text. The first line is formatted as an h1
heading and on the second line there is bold-styled word "Flutter":
Note that there is no block-level scope for style attributes. Again, given flat structure of Deltas there is nothing that can represent a block of lines which share the same style, e.g. bullet list. And we already reserved newline character for line styles.
As it turns out, this is not a big issue and it is possible to achieve a friendly user experience without this extra level in a document model.
The block
attribute in Notus documents is line-scoped. To change a group of lines from "bullet list" to "number list" we need to update block style on each of the lines individually. Zefyr editor abstracts away such details with help of heuristic rules.
Last updated