本文介绍如何使用 Ace和 CodeMirror来实现一个基于
react
的markdown
输入+
即时预览在线编辑器
Ace版本
Ace
算是一个久经考验的老牌编辑器插件了,现在很多大公司都在用这个东西,似乎 Github曾经就使用 Ace
用于构建它的在线编辑器(虽然现在不用了)。
Ace
在Github上只是存放了其项目,更多详细的介绍,例如如何开始以及 API
等文档都放在它的官网上
温馨提示:
- 如果你打开其 官网发现加载失败,或者页面不全,那么可能需要你翻墙重新请求一遍才行,因为虽然其官网的大部分资源墙内就能访问,但一些脚本文件,例如
jQuery
是墙外的,所以可能出现数据加载失败的情况。Ace
的文档读起来可能有些困难,这里的困难并不是指其文档都是英文的,如果只是英文阅读障碍,在线翻译一下也就ok
了,而是说你可能不知道该从哪里阅读,不知从何下手,这也是大部分开源项目的通病,这个问题可能就需要你多翻看几遍,找到文档编写规律后再阅读应该就容易多了。
引入 Ace
本文所要实现的编辑器虽然是基于 Ace
,但是没有直接使用 Ace
,而是使用了其一个封装插件 brace,至于为什么不直接使用 Ace
,brace项目也有说明,可以自己去看看,另外,由于本文所要实现的编辑器还是基于 React
的,所以为了使用方便,需要对 Ace
进行一层封装,将其包裹成一个 React
组件。
Github
上也有人做过这种事情了,例如 react-ace,由于此项目规模较大,API
和方法很多,此项目只是封装了其部分功能,我看了下react-ace的封装代码,可能它的封装无法满足我的需求,所以我就抽出了其中一部分代码,并进行了稍微的修改。
另外,本文所要实现的编辑器是间接基于 Ace
,直接基于 brace
的,所以所要安装的包是 brace:
npm i brace -S
基本的 DOM
结构和 100行代码实现基于react的markdown输入+即时预览在线编辑器是差不多的,只不过在左侧输入容器的子元素由原来具有 contentEditable="plaintext-only"
属性的 div
换成了 Ace
组件:
<AceEditor
mode="markdown"
theme="github"
wrapEnabled={
true}
tabSize={
2}
fontSize={
14}
showGutter={
false}
height={state.aceBoxH + 'px'}
width={
'100%'}
debounceChangePeriod={
60}
onChange={
this.onContentChange}
onScroll={
this.containerScroll.bind(this, 1)}
name="aceEditorMain"
editorProps={
{$blockScrolling: true}}/>
上述 <AceEditor/>
的组件属性都是能在 Ace文档里找到的,这里只简单说明一下:
mode
:编辑器的整体模式或样式,这里取值为markdown
,表明需要用这个编辑器来输入markdown
文本,这样编辑器就会进行相应的初始设置。theme
:编辑器主题,这里使用了github
这个主题。wrapEnabled
:当输入的一句文本比一行的长度要长时,是否允许换行。tabSize
:使用几个空格来表示表示一次Tab
按键。fontSize
:文本的字体大小height
:编辑器的高度,单位为px<