I am trying to insert image to Draft.js editor.
Based on my understanding, I need update entity by mergeData
and blocks by mergeBlockData
. (I am not sure)
Now I am trying to use mergeBlockData
to insert a block.
mergeBlockData( contentState: ContentState, selectionState: SelectionState, blockData: Map<any, any> ): ContentState
Please read ment in the code.
import { Map } from 'immutable';
const selection = this.state.editorState.getSelection();
const contentState = this.state.editorState.getCurrentContent();
console.log(convertToRaw(contentState)); // for example, I have 3 blocks
const blockData = Map({ ov72: { // here how to generate a random valid key?
"key": "ov72",
"text": " ",
"type": "atomic",
"depth": 0,
"inlineStyleRanges": [],
"entityRanges": [{
"offset": 0,
"length": 1,
"key": 1
}],
"data": {}
}});
const newContentState = Modifier.mergeBlockData(contentState, selection, blockData);
console.log(convertToRaw(newContentState)); // here is wrong, still 3 blocks. Also original blocks have no change
const newEditorState = EditorState.push(this.state.editorState, newContentState);
I am trying to insert image to Draft.js editor.
Based on my understanding, I need update entity by mergeData
and blocks by mergeBlockData
. (I am not sure)
Now I am trying to use mergeBlockData
to insert a block.
mergeBlockData( contentState: ContentState, selectionState: SelectionState, blockData: Map<any, any> ): ContentState
Please read ment in the code.
import { Map } from 'immutable';
const selection = this.state.editorState.getSelection();
const contentState = this.state.editorState.getCurrentContent();
console.log(convertToRaw(contentState)); // for example, I have 3 blocks
const blockData = Map({ ov72: { // here how to generate a random valid key?
"key": "ov72",
"text": " ",
"type": "atomic",
"depth": 0,
"inlineStyleRanges": [],
"entityRanges": [{
"offset": 0,
"length": 1,
"key": 1
}],
"data": {}
}});
const newContentState = Modifier.mergeBlockData(contentState, selection, blockData);
console.log(convertToRaw(newContentState)); // here is wrong, still 3 blocks. Also original blocks have no change
const newEditorState = EditorState.push(this.state.editorState, newContentState);
Share
Improve this question
edited Dec 3, 2017 at 1:27
Hongbo Miao
asked Dec 2, 2017 at 3:57
Hongbo MiaoHongbo Miao
50.2k67 gold badges200 silver badges328 bronze badges
4
- You are merging blockData why would the size of blocks increase? – Nandu Kalidindi Commented Dec 2, 2017 at 23:44
-
@NanduKalidindi assume
mergeBlockData
is neither replace or add, what is the function of it? And which correct API should I use? – Hongbo Miao Commented Dec 2, 2017 at 23:46 -
I am working on a snippet. But I guess you should use
ContentBlock
if you want to add new blocks. – Nandu Kalidindi Commented Dec 2, 2017 at 23:48 -
@NanduKalidindi would u mind adding a demo for how to use
ContentBlock
to add new block in answer? thanks – Hongbo Miao Commented Dec 2, 2017 at 23:54
3 Answers
Reset to default 6Took a while to figure out how to insert image.
insertImage = (editorState, base64) => {
const contentState = editorState.getCurrentContent();
const contentStateWithEntity = contentState.createEntity(
'image',
'IMMUTABLE',
{ src: base64 },
);
const entityKey = contentStateWithEntity.getLastCreatedEntityKey();
const newEditorState = EditorState.set(
editorState,
{ currentContent: contentStateWithEntity },
);
return AtomicBlockUtils.insertAtomicBlock(newEditorState, entityKey, ' ');
};
Then you can use
const base64 = 'aValidBase64String';
const newEditorState = this.insertImage(this.state.editorState, base64);
this.setState({ editorState: newEditorState });
For render image, you can use Draft.js image plugin.
Live demo: codesandbox
The demo inserts a Twitter logo image.
If you want to insert a image from local file, you can try to use FileReader
API to get that base64.
For how to get base64, it is simple, check
Live demo: jsbin
Now go ahead to put them together, you can upload image from local file!
If you are using draft-js image plugin, you can achieve this as follows.
Get the base64 of your image as @Hongbo Miao explained.
const imagePlugin = createImagePlugin();//initialize image plugin
const base64 = 'aValidBase64String';
const newEditorState = imagePlugin.addImage(this.state.editorState, base64);
this.setState({ editorState: newEditorState });
If you want to insert a new Block then you probably would want to use ContentBlock
and not mergeBlockData
.
ContentBlock: https://draftjs/docs/api-reference-content-block.html#content
Please give this snippet a try.
import { genKey } from 'draft-js'
addNewBlock(editorState) {
const text = 'Alpha';
const block = new ContentBlock({
key: genKey(),
type: 'unstyled',
text,
});
const contentState = editorState.getCurrentContent();
const blockMap = contentState.getBlockMap().set(block.key, block);
return EditorState.push(editorState, contentState.set('blockMap', blockMap));
}