1
votes

I'm currently working on a project which involves using multiple wysiwyg editors. I have previously used react-draft in the same project but has always been used with static elements eg, each editor is fixed.

In my case, my editors are created on the fly, (min 1, max 15) editors. I'm rendering these into my containers using map() with constructed object each time. Allowing the user to click + or - buttons to create / remove a editor.

for example to create a new editor into, i push to then map over the components array which looks something like the below:

components: [
    {
        id:1, 
        type: 'default',
        contentValue: [
            title: 'content-block',
            value: null,
            editorState: EditorState.CreateEmpty(),
        ]
    }
]

I am able to render multiple editors just fine and createEmpty ediorstates. My issue is when i try to update the contents editor state.

Usually to update a single editor id use:

onEditorStateChange = editorState => {
    this.setState({
        editorstate,
    })
}

However, given the fact my editors are dynamically rendered, i have the editor state isolated within the "Components" array. So i've tried the following which did not work:

In Render

this.state.components.map((obj) => {
    return (
        <Editor
        editorState={obj.contentValue.editorState}
        onEditorStateChange={(e) => this.onEditorStateChange(e, obj.id)}
        />
    );
}

onEditorStateChange

onEditorStateChange(e, id){
    const { components } = this.state;
    const x = { components };
    for (const i in x){
        if(x[i].id ==== id){
            x[i].contentValue.editorState = e;
        }
    }
    this.setState({components: x})
}

Upon debugging, the "setState" does get called in the above snippet, and it does enter the if statement, but no values are set in my editorState.

I'm happy for alternative ways to be suggested, as long as this will work with dynamically rendered components.

I require this value to be set, as i will be converting to HTML / string and using the content to save to a database.

I hope i have explained this well, if not please let me know and ill be happy to provide further information / snippets.

Thank you in advance.

1

1 Answers

1
votes

Okay, i figured out a solution.

inside my onEditorStateChange() i update the value with the parameter (e) which was initally passed in. Using draftToHtml i convert it to raw and pass it to set state as shown below:

onEditorStateChange(e, id) {
    const { components } = this.state;
    console.log(e);
    const x = components;
    for (const i in x) {
         if (x[i].id === id) {
         x[i].contentValue.editorState = e;
         x[i].value = draftToHtml(convertToRaw(e.getCurrentContent()));
         //console.log(x[i]);
      }
    }
    this.setState({    
      components: x,
    });
   }

This gives me the a HTML value which i can now convert to string and save to the database.

Hope this helps someone else with the same issue :)