前面咱們已經實現了用Markdown語法寫文章了。可是文章的評論用Markdown就不太合適了,你不能強求用戶也花時間去熟悉語法啊。另外評論中一般還有表情、帶顏色的字體等功能,這些也是Markdown不具有的。javascript
所以富文本編輯器Django-ckeditor就派上用場了。css
在虛擬環境中安裝django-ckeditor:html
(env) > pip install django-ckeditor
安裝成功後仍是老規矩,在settings.py
中註冊app:java
my_blog/settings.py ... INSTALLED_APPS = [ ... 'ckeditor', ... ] ...
接下來須要修改模型了。用django-ckeditor庫本身的富文本字段RichTextField
替換普通的文本字段TextField
:python
comment/models.py ... # django-ckeditor from ckeditor.fields import RichTextField class Comment(models.Model): ... # 以前爲 body = models.TextField() body = RichTextField() ...
記得每次修改模型後要遷移數據:jquery
(env) > python manage.py makemigrations (env) > python manage.py migrate
爲方便測試,修改comment/admin.py
文件,將評論模塊註冊到後臺中:git
comment/admin.py from django.contrib import admin from .models import Comment admin.site.register(Comment)
啓動服務器,進入後臺的評論頁面,發現已經可使用django-ckeditor了:github
功能至關齊全,字體、字號、顏色、連接、表情應有盡有。django
若是我只須要部分功能怎麼辦呢?好比插入flash動畫基本就用不到。另外彷佛也沒看到插入代碼塊的功能。瀏覽器
ckeditor
容許你在settings.py
中進行自定義配置:
my_blog/settings.py ... CKEDITOR_CONFIGS = { # django-ckeditor默認使用default配置 'default': { # 編輯器寬度自適應 'width':'auto', 'height':'250px', # tab鍵轉換空格數 'tabSpaces': 4, # 工具欄風格 'toolbar': 'Custom', # 工具欄按鈕 'toolbar_Custom': [ # 表情 代碼塊 ['Smiley', 'CodeSnippet'], # 字體風格 ['Bold', 'Italic', 'Underline', 'RemoveFormat', 'Blockquote'], # 字體顏色 ['TextColor', 'BGColor'], # 連接 ['Link', 'Unlink'], # 列表 ['NumberedList', 'BulletedList'], # 最大化 ['Maximize'] ], # 加入代碼塊插件 'extraPlugins': ','.join(['codesnippet']), } }
在toolbar_Custom
中定義須要使用的功能模塊;沒列出的功能就再也不顯示了。代碼塊功能是編輯器自帶的插件,須要在extraPlugins
中指定使用。效果以下:
編輯富文本搞定後,還須要在前臺界面中展現出來。富文本是以相似html
的格式進行保存的,所以還要在展現評論的代碼加入|safe
過濾器,防止瀏覽器進行轉義。
修改detail.html
中展現評論的部分代碼:
templates/article/detail.html ... <!-- 顯示評論 --> <h4>共有{{ comments.count }}條評論</h4> <div> {% for comment in comments %} ... <!-- 修改這裏 --> <div>{{ comment.body|safe }}</div> {% endfor %} </div> ...
進入文章詳情頁面看看效果:
代碼高亮須要添加額外的插件Prism。在Prism插件官方頁面下載(也能夠點擊這裏直接下載)後,將解壓出來的prism
放到env\Lib\site-packages\ckeditor\static\ckeditor\ckeditor\plugins
目錄下。注意env是你建立的虛擬環境的目錄。
以前你安裝的全部庫都在這個env目錄中的。
而後在Prism官網選擇主題:
DOWNLOAD CSS
下載樣式在static
目錄中新建prism
目錄,將下載好的CSS文件放進去。
注意這裏的static是項目中的靜態文件目錄(與前面的章節相同),而不是env文件夾中的static目錄。
而後在須要代碼高亮的模板文件中引用prism的靜態文件,對代碼進行渲染:
templates/article/detail.html ... <script src="{% static 'ckeditor/ckeditor/plugins/prism/lib/prism/prism_patched.min.js' %}"></script> <link rel="stylesheet" href="{% static 'prism/prism.css' %}"> ...
將Prism、widget、lineutils插件添加到配置文件中。後面兩個編輯器自帶,不用單獨下載,添上就能夠了:
my_blog/settings.py ... CKEDITOR_CONFIGS = { 'default': { ... # 添加 Prism 相關插件 'extraPlugins': ','.join(['codesnippet', 'prism', 'widget', 'lineutils']), } }
這樣就完成了:
代碼高亮效果不錯!
爲了讓用戶在前臺也能使用富文本編輯器,還得對代碼稍加改動。
首先須要把評論的表單傳遞到文章詳情頁面中。所以修改article_detail
視圖:
article/views.py ... # 引入評論表單 from comment.forms import CommentForm ... # 文章詳情 def article_detail(request, id): ... # 引入評論表單 comment_form = CommentForm() context = { ... 'comment_form': comment_form, } ...
而後將detail.html
原來評論表單中的正文部分(即前面章節寫的<textarea>
)替換以下:
templates/article/detail.html ... <!-- 發表評論 --> <form ...> {% csrf_token %} <div class="form-group"> <label for="body">...</label> <!-- 將以前的<textarea>替換掉 --> <!-- <textarea type="text" class="form-control" id="body" name="body" rows="2"></textarea> --> <div> {{ comment_form.media }} {{ comment_form.body }} </div> </div> <!-- 提交按鈕 --> ... </form> ...
其中的comment_form.media
是編輯器自身的渲染代碼,comment_form.body
則是評論正文字段。
看看效果:
不錯,編輯器已經能夠正常使用了,但還有一個小問題:彷佛編輯器寬度沒有自適應,右邊大片白白的空間也太浪費了。繼續努力。
首先在配置文件中將寬度設置爲auto
,這一步咱們已經作好了。
Ckeditor編輯器自己有一個inline-block
的樣式,阻礙了自適應效果,須要用Jquery
語法將其清除掉。在詳情頁面底部加入代碼:
templates/article/detail.html <!-- 注意這是錯誤的示範! --> ... <!-- 新增代碼 --> <script> $(".django-ckeditor-widget").removeAttr('style'); </script> <!-- 這個已經有了 --> {% endblock content %}
$
符號表明Jquery語句。這句的意思是:找到頁面中class='django-ckeditor-widget'
的容器,而後刪除這個容器的style
屬性。
看似沒什麼問題,然而Bug藏在細節中。注意這是個Jquery語句,那麼就要求運行以前先載入Jquery.js
。然而在渲染頁面時,包含$
語句的{% block content %}
會插入到base.html
模板的Jquery.js
標籤的前面,致使語句不會生效,而且控制檯會報出$ is not defined
的錯誤。
比較容易想到的辦法是將引入Jquery.js的標籤提到更頂部的位置,在block模板插入前就加載。這樣作的問題是JS文件加載一般較慢,它會阻塞後面的代碼,從而減緩頁面總體加載速度。本文不採用這種辦法。
解決方案是在base.html
中新增專門用於拼接JavaScript
腳本的位置,命名爲{% block script %}
。注意它必須放置在Jquery
標籤的後面:
templates/base.html ... <body> ... <!-- 已有代碼 --> <script src="{% static 'jquery/jquery-3.3.1.js' %}"></script> ... <!-- 新增代碼 --> {% block script %}{% endblock script %} </body>
而後將detail.html
中的JS代碼放到這個塊中:
templates/article/detail.html ... {% block script %} <script> $(".django-ckeditor-widget").removeAttr('style'); </script> {% endblock script %}
這種方法能夠靈活的定義JS腳本的運行順序,而且代碼看起來更加整潔。推薦全部的JS代碼都採起這種方法插入。
刷新頁面,編輯器就可以寬度自適應了:
發表含有代碼塊的評論,詳情頁面的顯示以下:
如今,博文和其評論均可以漂亮的排版了。對於有些不喜歡Markdown的人來講,甚至能夠連博文都使用django-cdeditor
提供的富文本編輯器。我本身仍是傾向用Markdown寫文章:寫做效率比好看更重要,而且主流網站幾乎都支持Markdown,多平臺發稿很方便。
感謝 Aaron Zhao 的我的博客提供了本文的參考。博主還講解了django-ckeditor上傳圖片的設置,有興趣能夠前往瞭解。