我在Wagtail 2.0富文本字段中有一堆内容,看起来像
Page heading
(intro blurb)
heading 1
(heading-1-relevant text)
heading 2
(heading-2-relevant text)
...
我希望每个标题都为id
,以便任何文本都可以成为跳转到相关内容的链接。我似乎无法找到一个明确id
标题的选项,而富文本编辑器中的“链接”按钮似乎不允许我在内容中选择活动的片段标识符。
有没有办法在Wagtail的富文本编辑器上在同一页面上添加基于片段标识符的导航?
答案 0 :(得分:1)
一年后再次提出自己的问题,因为这仍然是我们需要的,我们想出的解决方案是简单地包装RichText html序列化,并将片段ID注入放在顶部:
import re
from django import template
from django.utils.text import slugify
from wagtail.core.rich_text import RichText
# We'll be wrapping the original RichText.__html__(), so make
# sure we have a reference to it that we can call.
__original__html__ = RichText.__html__
# This matches an h1/.../h6, using a regexp that is only
# guaranteed to work because we know that the source of
# the HTML code we'll be working with generates nice
# and predictable HTML code.
heading_re = r"<h(\d)[^>]*>([^<]*)</h\1>"
def add_id_attribute(match):
"""
This is a regexp replacement function that takes
in the above regex match results, and then turns:
<h1>some text</h1>
Into:
<h1><a id="some-text"></a><a href="#some-text">some text</a></h1>
where the id attribute value is generated by running
the heading text through Django's slugify() function.
"""
n = match.group(1)
text_content = match.group(2)
id = slugify(text_content)
return f'<h{n}><a id="{id}""></a><a href="#{id}">{text_content}</a></h{n}>'
def with_heading_ids(self):
"""
We don't actually change how RichText.__html__ works, we just replace
it with a function that does "whatever it already did", plus a
substitution pass that adds fragment ids and their associated link
elements to any headings that might be in the rich text content.
"""
html = __original__html__(self)
return re.sub(heading_re, add_id_attribute, html)
# Rebind the RichText's html serialization function such that
# the output is still entirely functional as far as wagtail
# can tell, except with headings enriched with fragment ids.
RichText.__html__ = with_heading_ids
这非常有效,不需要在drailail或wagtail中进行任何黑客攻击,并且只需在服务器启动过程中加载此代码即可非常容易地启用/停用(我们将其保存在wagtailcustom_tags.py文件中,因此,当Django加载所有模板标记集时,RichText的“ enrichment”会自动加入。
我们最初曾尝试扩展... | richtext
模板过滤器,但这是完全可行的,但它仅适用于我们自己编写的带有自定义模板的自定义块,因此,这并不是给出的解决方案认为它应该“起作用”的想法。
答案 1 :(得分:0)
使用RawHTMLBlock
和StreamField
怎么样?制作这样一个页面:
class BlogPage(Page):
body = StreamField([
('tag', blocks.RawHTMLBlock(),
('body', blocks.RichTextBlock()),
然后在您的管理员中,您可以:
choose RawHTMLBlock: <h1 id="test">
choose RichTextBlock: your staff here
choose RawHTMLBlock: </h1>
答案 2 :(得分:0)
要控制页面主体的结构,最好鼓励用户使用标题栏,而不是富文本块中的标题。然后你可以有一个标题栏类型,它有两个字段,一个&#39;文本&#39;还有一个&#39; id&#39;,您可specify a template输出h
元素和id
属性。
class Heading2Block(blocks.StructBlock):
heading = blocks.CharBlock(classname='full title')
link_id = blocks.CharBlock(help_text='For making hyperlinks to this heading')
class Meta:
template = 'blocks/h2.html'
将以下内容放入blocks/h2.html
:
<h1{% if value.link_id %} id="{{ value.link_id|slugify }}"{% endif %}>{{ value.heading }}</h1>
在早期版本的Wagtail中,可以从Hallo.js富文本编辑器中删除h
窗口小部件,这是鼓励用户采用标题块的好方法。 Draftail目前没有类似的限制,但有pull request重新实现它。