本文讨论如何自定义Draft默认Block Render。自定义块渲染 被用来 定义支持的块类型元素和它们各自的渲染器,还可以转换粘贴的内容成已知的Draft块类型。
当粘贴内容时或者当用convertFromHTML,Draft会转换粘贴的内容成相应的块渲染类型,方法是将Draft块渲染映射与对应匹配的标签进行匹配。
Draft default block render map
| HTML element | Draft block type |
|---|---|
<h1/> |
header-one |
<h2/> |
header-two |
<h3/> |
header-three |
<h4/> |
header-four |
<h5/> |
header-five |
<h6/> |
header-six |
<blockquote/> |
blockquote |
<pre/> |
code-block |
<figure/> |
atomic |
<li/> |
unordered-list-item,ordered-list-item** |
<div/> |
unstyled* |
** -块类型会基于父元素<ul/> 或者 <ol/>
* - 任何一个不会被识别的区块会被认为是unstyled
Configuring block render map(定义块渲染的映射)
默认的块渲染可以通过传递Immutable Map给编辑器blockRenderMap函数来覆盖掉默认的blockRenderMap。
覆盖默认块_BlockRenderMap_的例子:
// The example below deliberatly only allows// 'heading-two' as the only valid block type and// updates the unstyled element to also become a h2.// 下面这个例子只允许'head -two'作为唯一有效的块类型// 并且更新所有的unstyled块类型元素都转化成h2const blockRenderMap = Immutable.Map({'header-two': {element: 'h2'},'unstyled': {element: 'h2'}});class RichEditor extends React.Component {render() {return (<Editor...blockRenderMap={blockRenderMap}/>);}}
下面一个例子,与重写默认的不同,我们仅仅是想添加一个新的块类型。我们可以使用DefaultDraftBlockRenderMap创建一个新的blockRenderMap。
扩展默认_blockRenderMap_的例子:
const blockRenderMap = Immutable.Map({'section': {element: 'section'}});// Include 'paragraph' as a valid block and updated the unstyled element but// keep support for other draft default block types// 段落 会被作为一个有效的区块,并且其他的默认块类型依然会被支持const extendedBlockRenderMap = Draft.DefaultDraftBlockRenderMap.merge(blockRenderMap);class RichEditor extends React.Component {render() {return (<Editor...blockRenderMap={extendedBlockRenderMap}/>);}}
当Draft解析粘贴的HTML时,它将HTML元素映射回Draft块类型。如果你想指定其他的HTMl元素变成一个特有的块类型,你可以在块配置中加一个数据aliasedElements
unstyled 块类型alias用法:
'unstyled': {element: 'div',aliasedElements: ['p'],}
Custom block wrappers(自定义块包装)
默认情况下,html元素用于包装块类型。但是,也可以向blockRenderMap提供react组件来包装EditorBlock。
在粘贴过程中,或者在调用convertFromHTML时,html将被扫描以查找匹配的标记元素。当在blockRenderMap上有定义时,将使用定义的包装器 来包装 特定的块类型。例如:
Draft使用包装器将<li/>包装在<ul/>或<ol/>中,但是包装器也可以用于包装任何其他自定义块类型。
用一个针对自定义块的React组件拓展默认的块渲染映射的例子:
_
class MyCustomBlock extends React.Component {constructor(props) {super(props);}render() {return (<div className='MyCustomBlock'>{/* here, this.props.children contains a <section> container, as that was the matching element */}{this.props.children}</div>);}}const blockRenderMap = Immutable.Map({'MyCustomBlock': {// element is used during paste or html conversion to auto match your component;// it is also retained as part of this.props.children and not stripped outelement: 'section',wrapper: <MyCustomBlock />,}});// keep support for other draft default block types and add our myCustomBlock typeconst extendedBlockRenderMap = Draft.DefaultDraftBlockRenderMap.merge(blockRenderMap);class RichEditor extends React.Component {...render() {return (<Editor...blockRenderMap={extendedBlockRenderMap}/>);}}
