Slate.js bindings

Hi @6thfdwp,

It would be awesome to have someone working on this :slight_smile:

Exactly. I think the best way to model this would be using Y.XmlElement and Y.XmlFragment. The y-prosemirror binding also uses these types instead of simply Y.Map and Y.Array.

If you think of Slate nodes as an XML model you could express the following

{ type: ‘heading.h1’, children: [{ text: ‘Great Heading’ }] },

as

<heading.h1>Gread Heading</heading.h1>

Or in Yjs types:

const node = new Y.XmlElement('heading.h1')
const innerContent = new Y.Text()
innerContent.insert(0, 'Great Heading')
node.insert(0, [ytext])
// node.setAttribute('color', 'blue') // in case you want to add attributes to the model.

The advantage of using Y.XmlElement instead of YMap and Y.Array is that one Slate node can be nicely represented as a single Yjs type. This also saves a bit of bandwidth. If you define the schema correctly, you could use the same Yjs type for the ProseMirror binding (syncing Slate and ProseMirror).

Furthermore, bold and italic text can be nicely represented using formatting attributes:

const ytext = new Y.Text()
ytext.insert(0, 'Hello World!', { bold: true })
ytext.format(0, 5, { italic: true }) // format "Hello" italic