facebook / lexical

Lexical is an extensible text editor framework that provides excellent reliability, accessibility and performance.
https://lexical.dev
MIT License
19.88k stars 1.69k forks source link

Bug: Import from html removes paragraph's inline style, such as fontSize, color etc. #4926

Closed sakib412 closed 1 year ago

sakib412 commented 1 year ago

I am facing issue when i try to convert html (that I got previously from editor export) to lexical state. All the inline style is disappear like font size font family , color, bg color etc. I am using this function for exporting this is working fine.

  const onEditorChange = (
    editorState: EditorState,
    editor: LexicalEditor,
    _tags: Set<string>
  ) => {
    editorState.read(() => {
      const htmlString = $generateHtmlFromNodes(editor, null);
      onChange(htmlString);
    });
  };

this function is called from this plugin <OnChangePlugin onChange={onEditorChange} /> I think the problem is from $generateNodesFromDOM this function or Pargraphnode's importDOM method, somehow it is not parsed or ignore the style tag, inside the p tag's span. as all inline style is adding into span tag , somehow it got ignored, I am not sure which is cause for this, I can fix this ,is there anyone from the team can assure me the source of this problem.

Lexical version: 0.12.0

Steps To Reproduce

  1. Make a Plugin with this code,
    
    import {useEffect} from 'react';
    import { $getRoot, $insertNodes} from 'lexical';
    import {useLexicalComposerContext} from '@lexical/react/LexicalComposerContext';
    import {$generateNodesFromDOM} from '@lexical/html';

type Props = {initialContent?: string};

const LoadInitialContent = ({initialContent}: Props) => { const [editor] = useLexicalComposerContext();

useEffect(() => { if (!initialContent) { return; } editor.update(() => { const parser = new DOMParser(); const dom = parser.parseFromString(initialContent, 'text/html'); const nodes = $generateNodesFromDOM(editor, dom); // Select the root $getRoot().select(); // Insert them at a selection. $insertNodes(nodes); }); }, []); return null; };

export default LoadInitialContent;

2. Then use it with :
```ts
<LoadInitialContent
          initialContent={`
         <p class="PlaygroundEditorTheme__paragraph" dir="ltr">
            <span style="font-size: 16px;">Font size</span>
            <span style="font-size: 16px; background-color: rgb(194, 59, 59);">font size and bg color</span>
          </p>
         `}
        />

in the editor.

Link to code example:

The current behavior

This is removing any inline style so it is output this code exporting from editor:

<p class="PlaygroundEditorTheme__paragraph" dir="ltr">
  <span>Font size font size and bg colorFont size font size and bg color</span>
</p>

The expected behavior

I want to get output same as I input as I got this html before from editor, If I style again export html is not same as input.

   <p class="PlaygroundEditorTheme__paragraph" dir="ltr">
            <span style="font-size: 16px;">Font size</span>
            <span style="font-size: 16px; background-color: rgb(194, 59, 59);">font size and bg color</span>
    </p>
ivailop7 commented 1 year ago

You need to override the nodes to handle the extended html styling on importing, as described here:

https://lexical.dev/docs/concepts/serialization#handling-extended-html-styling

sakib412 commented 1 year ago

You need to override the nodes to handle the extended html styling on importing, as described here:

https://lexical.dev/docs/concepts/serialization#handling-extended-html-styling

Thank you.