When having custom attribute for marks like "strong", facing issue with "toggleMark" function

Codesandbox link: https://codesandbox.io/p/sandbox/agitated-glitter-r3p9z5?file=%2Fsrc%2Feditor%2Findex.jsx

Demo video link: When having custom attribute for marks like "strong", facing issue with "toggleMark" function.mov - Google Drive

Issue description:

I have style as custom attribute for the strong mark to retain styles in strong tag. While rending it works as expected. But when toggling mark using shortcut or using the menu icon, already applied mark is getting removed as in the video.

I confirmed that it is due to not passing the custom style attribute to the internal function toggleMark by playing around with a custom strike mark as below.

toggleMark(schema.marks.strike,{ style: {// some styles}})

Query:

Can you alter the toggleMark function to work properly without passing the attribute property?

That’s kind of what toggleMark does—it removes the mark when it’s present, adds it otherwise. What were you expecting to happen?

Please watch the video carefully @0:25 time stamp, where I clicked the bold icon. After that, as soon as I typed the next character(h), the bold applied for "here" word got removed. But it should retain for the word "here" and should only get removed for next chars(“he”) right?

Patching up a schema like that does not work. Pass in the strong mark definition properly when creating the Schema, and the problem goes away.

const mySchema = new Schema({
  nodes: addListNodes(schema.spec.nodes, "paragraph block*", "block"),
  marks: schema.spec.marks.update("strong", {
    ...schema.spec.marks.get("strong"),
    attrs: {
      style: {default: null}
    },
    toDOM: (node) => {
      // Ensure the strong tag retains any styles it had
      const attrs = {};
      if (node.attrs.style) {
        attrs.style = node.attrs.style;
      }
      return ["strong", attrs, 0]; // Internal implementation of the strong tag
    },
    parseDOM: [
      // Override the default strong tag with a custom implementation
      {
        tag: "strong",
        getAttrs: (node) => {
          // Retain inline styles from the <strong> tag
          return { style: node.getAttribute("style") || null };
        },
      },
    ]
  })
});
1 Like

My bad. The suggested approach worked for me.

The mark should have been customised before creating the schema using new Schema unlike as I did after creating it.

Thank you @marijn