Editor: How Little Blocks Work

The editor focus is progressing at a steady pace, with some of the major elements taking shape, so it’s a good time to provide an update. This is a complicated flow so a diagram helps explain things a bit better:

The logic flow for the editor is the following:

  • ① inferring a block representation of the post content (parsing);
  • ② describing the post as an ordered list of blocks (state tree);
  • ③ representing the post in the DOM (rendering);
  • ④ attaching controls to manipulate the content a.k.a blocks (editing UI).

Generally speaking, in a declarative paradigm, the state of the application is structured in an easy machine readable format so that what is rendered is a reflection of the state of the application, and where manipulations are represented as a unidirectional flow. However, the reality is we don’t start in WordPress with a representation of the state of the post that has such structure—there’s no knowledge of “blocks” because content is stored serialized in a single flat field.

So our first step is to infer the structure we need from implicit cues. This is a crucial step that makes the double loop in the above diagram work. It is handled by the grammar and parsing mechanism which takes the flat content of the post and infers a tree of ordered block data using, preferably, syntax hints present in HTML comments. The editor is then initialized with a state representation of the block nodes (the middle yellow rectangle in the diagram) generated by the parsing of the raw post content.

We are basically augmenting the structured representation of the post to aid us in building a robust editing tool that can be expressive and limit side effects. The visual editor is then a view that contains and renders the list of block nodes from the internal state into the page, using the shape of markup defined by all registered blocks involved. This removes the need for imperative handling in both finding a block and manipulating its attributes. Blocks provide functions that describe how they want to be represented for both the editing context and the final markup to be saved. The internal representation of the post content is updated as blocks are updated, so during the editing session we can remain in the right side of the diagram above. Finally, when it is time to save the post, the data is serialized back into post_content with HTML comment delimiters to reset the cycle.

The foundation is a bit complicated, but the goal is that creating individual blocks is easier and protected from the technicalities of the process. The rendering of blocks for editing is handled by a VisualBlock component, which attaches event handlers and renders the edit function of a block definition to the document with the corresponding attributes and local state. The edit function is the markup shape of a component while in editing mode, which can be augmented to provide very rich interactions for users. You can take a glance at some of the existing blocks we have so far to get an idea for how the API works and what it takes to build a block. Keep in mind the API is not finalized and tweaks are happening frequently.

If you want to help with this project, head over to #core-editor in Slack or follow the activity in the GitHub repository.

#core-editor, #editor