-
Getting a hold of DOM serializer’s
documentintoDOM()seems to involve:serializeNodeInner()(passdocumentto node spec’stoDOM()),serializeNode()(passdocumenttoserializeMark()),serializeMark()(passdocumentto mark spec’stoDOM()), and- updating node/mark spec’s
toDOM()TypeScript signature (backwards compatible).
For example, in case of
serializeNodeInner(), just this call (lines split for legibility) would change fromrenderSpec( doc(options), this.nodes[node.type.name](node), null, node.attrs)to
const dom = doc(options) renderSpec( dom, this.nodes[node.type.name](node, dom), null, node.attrs) -
Regarding what
documententails, for ProseMirror’s purposes (meaning both what callers must pass toserializeNode()and what it’d pass to spec’stoDOM()per (1) above) it seems to be a tiny subset ofDocumentwith only the following:.createTextNode()(called here).createDocumentFragment()(called here).createElement[NS]()(called here, and presumably in atoDOM()that wishes to return a DOM node)
Concerning the
HTMLElementorDocumentFragmentreturned from the above functions, for PM’s purposes it seems they only must implement:.nodeTypeproperty, only applicable to HTMLElement.setAttribute[NS]()(called here), only applicable to HTMLElement.appendChild()(called here and here)
This is based on prosemirror-model’s
to_dom.ts, let me know if there’re other modules of concern.Narrowing down the type can be done easily with TypeScript’s built-in
Picktype:type BareDocument = Pick<Document, | "createTextNode" | "createDocumentFragment" | ...>;
Notes;
-
The above changes are backward compatible and don’t affect existing users.
-
The changes are independent of each other, though I would say it’d be better to narrow down
Documentfirst, if it’s to be added totoDOM()’s signature. -
In fact, instead of giving
toDOM()access todocument, even a narrowed-down version, it could be worth passing just an element constructor function:toDOM( node: Node, createDOMElement: BareDocument["createElement"], ): ...