mirror of
https://github.com/sphinx-doc/sphinx.git
synced 2025-02-25 18:55:22 -06:00
Add html-page-context event for customizing the template context.
This commit is contained in:
parent
2dfad25fd0
commit
2b0e015fcc
5
CHANGES
5
CHANGES
@ -28,6 +28,11 @@ New features added
|
||||
* Defaults for configuration values can now be callables, which allows
|
||||
dynamic defaults.
|
||||
|
||||
* The new ``html-page-context`` event can be used to include custom values
|
||||
into the context used when rendering an HTML template.
|
||||
|
||||
* Add document metadata to the values in the default template context.
|
||||
|
||||
Bugs fixed
|
||||
----------
|
||||
|
||||
|
18
doc/conf.py
18
doc/conf.py
@ -162,7 +162,25 @@ def parse_role(env, sig, signode):
|
||||
return sig
|
||||
|
||||
|
||||
event_sig_re = re.compile(r'([a-zA-Z-]+)\s*\((.*)\)')
|
||||
|
||||
def parse_event(env, sig, signode):
|
||||
m = event_sig_re.match(sig)
|
||||
if not m:
|
||||
signode += addnodes.desc_name(sig, sig)
|
||||
return sig
|
||||
name, args = m.groups()
|
||||
signode += addnodes.desc_name(name, name)
|
||||
plist = addnodes.desc_parameterlist()
|
||||
for arg in args.split(','):
|
||||
arg = arg.strip()
|
||||
plist += addnodes.desc_parameter(arg, arg)
|
||||
signode += plist
|
||||
return name
|
||||
|
||||
|
||||
def setup(app):
|
||||
app.add_description_unit('directive', 'dir', 'pair: %s; directive', parse_directive)
|
||||
app.add_description_unit('role', 'role', 'pair: %s; role', parse_role)
|
||||
app.add_description_unit('confval', 'confval', 'pair: %s; configuration value')
|
||||
app.add_description_unit('event', 'event', 'pair: %s; event', parse_event)
|
||||
|
@ -162,22 +162,43 @@ package.
|
||||
Sphinx core events
|
||||
------------------
|
||||
|
||||
These events are known to the core:
|
||||
These events are known to the core. The arguments showed are given to the
|
||||
registered event handlers.
|
||||
|
||||
.. tabularcolumns:: |l|L|L|
|
||||
.. event:: builder-inited ()
|
||||
|
||||
Emitted the builder object has been created.
|
||||
|
||||
.. event:: doctree-read (doctree)
|
||||
|
||||
Emitted when a doctree has been parsed and read by the environment, and is
|
||||
about to be pickled.
|
||||
|
||||
.. event:: doctree-resolved (doctree, docname)
|
||||
|
||||
Emitted when a doctree has been "resolved" by the environment, that is, all
|
||||
references and TOCs have been inserted.
|
||||
|
||||
.. event:: page-context (pagename, templatename, context, doctree)
|
||||
|
||||
Emitted when the HTML builder has created a context dictionary to render a
|
||||
template with -- this can be used to add custom elements to the context.
|
||||
|
||||
The *pagename* argument is the canonical name of the page being rendered,
|
||||
that is, without ``.html`` suffix and using slashes as path separators. The
|
||||
*templatename* is the name of the template to render, this will be
|
||||
``'page.html'`` for all pages from reST documents.
|
||||
|
||||
The *context* argument is a dictionary of values that are given to the
|
||||
template engine to render the page and can be modified to include custom
|
||||
values. Keys must be strings.
|
||||
|
||||
The *doctree* argument will be a doctree when the page is created from a reST
|
||||
documents; it will be ``None`` when the page is created from an HTML template
|
||||
alone.
|
||||
|
||||
.. versionadded:: 0.4
|
||||
|
||||
====================== =================================== =========
|
||||
Event name Emitted when Arguments
|
||||
====================== =================================== =========
|
||||
``'builder-inited'`` the builder object has been created -none-
|
||||
``'doctree-read'`` a doctree has been parsed and read *doctree*
|
||||
by the environment, and is about to
|
||||
be pickled
|
||||
``'doctree-resolved'`` a doctree has been "resolved" by *doctree*, *docname*
|
||||
the environment, that is, all
|
||||
references and TOCs have been
|
||||
inserted
|
||||
====================== =================================== =========
|
||||
|
||||
.. _template-bridge:
|
||||
|
||||
|
@ -49,7 +49,8 @@ class ExtensionError(Exception):
|
||||
events = {
|
||||
'builder-inited': '',
|
||||
'doctree-read' : 'the doctree before being pickled',
|
||||
'doctree-resolved' : 'the doctree, the docname',
|
||||
'doctree-resolved' : 'doctree, docname',
|
||||
'html-page-context': 'pagename, context, doctree or None',
|
||||
}
|
||||
|
||||
class Sphinx(object):
|
||||
|
@ -341,19 +341,13 @@ class StandaloneHTMLBuilder(Builder):
|
||||
show_sphinx = self.config.html_show_sphinx,
|
||||
builder = self.name,
|
||||
parents = [],
|
||||
titles = {},
|
||||
logo = logo,
|
||||
len = len, # the built-in
|
||||
)
|
||||
|
||||
def write_doc(self, docname, doctree):
|
||||
destination = StringOutput(encoding='utf-8')
|
||||
doctree.settings = self.docsettings
|
||||
|
||||
self.imgpath = relative_uri(self.get_target_uri(docname), '_images')
|
||||
self.docwriter.write(doctree, destination)
|
||||
self.docwriter.assemble_parts()
|
||||
|
||||
def get_doc_context(self, docname, body):
|
||||
"""Collect items for the template context of a page."""
|
||||
# find out relations
|
||||
prev = next = None
|
||||
parents = []
|
||||
related = self.env.toctree_relations.get(docname)
|
||||
@ -383,27 +377,40 @@ class StandaloneHTMLBuilder(Builder):
|
||||
# "back to index" link already
|
||||
parents.reverse()
|
||||
|
||||
# title rendered as HTML
|
||||
title = titles.get(docname)
|
||||
if title:
|
||||
title = self.render_partial(title)['title']
|
||||
else:
|
||||
title = ''
|
||||
self.globalcontext['titles'][docname] = title
|
||||
title = title and self.render_partial(title)['title'] or ''
|
||||
# the name for the copied source
|
||||
sourcename = self.config.html_copy_source and docname + '.txt' or ''
|
||||
ctx = dict(
|
||||
title = title,
|
||||
sourcename = sourcename,
|
||||
body = self.docwriter.parts['fragment'],
|
||||
toc = self.render_partial(self.env.get_toc_for(docname))['fragment'],
|
||||
# only display a TOC if there's more than one item to show
|
||||
display_toc = (self.env.toc_num_entries[docname] > 1),
|
||||
|
||||
# metadata for the document
|
||||
meta = self.env.metadata.get(docname)
|
||||
|
||||
return dict(
|
||||
parents = parents,
|
||||
prev = prev,
|
||||
next = next,
|
||||
title = title,
|
||||
meta = meta,
|
||||
body = body,
|
||||
sourcename = sourcename,
|
||||
toc = self.render_partial(self.env.get_toc_for(docname))['fragment'],
|
||||
# only display a TOC if there's more than one item to show
|
||||
display_toc = (self.env.toc_num_entries[docname] > 1),
|
||||
)
|
||||
|
||||
self.index_page(docname, doctree, title)
|
||||
self.handle_page(docname, ctx)
|
||||
def write_doc(self, docname, doctree):
|
||||
destination = StringOutput(encoding='utf-8')
|
||||
doctree.settings = self.docsettings
|
||||
|
||||
self.imgpath = relative_uri(self.get_target_uri(docname), '_images')
|
||||
self.docwriter.write(doctree, destination)
|
||||
self.docwriter.assemble_parts()
|
||||
body = self.docwriter.parts['fragment']
|
||||
|
||||
ctx = self.get_doc_context(docname, body)
|
||||
self.index_page(docname, doctree, ctx.get('title', ''))
|
||||
self.handle_page(docname, ctx, event_arg=doctree)
|
||||
|
||||
def finish(self):
|
||||
self.info(bold('writing additional files...'), nonl=1)
|
||||
@ -569,9 +576,10 @@ class StandaloneHTMLBuilder(Builder):
|
||||
return docname + self.out_suffix
|
||||
|
||||
def handle_page(self, pagename, addctx, templatename='page.html',
|
||||
outfilename=None):
|
||||
outfilename=None, event_arg=None):
|
||||
ctx = self.globalcontext.copy()
|
||||
ctx['current_page_name'] = pagename
|
||||
# current_page_name is backwards compatibility
|
||||
ctx['pagename'] = ctx['current_page_name'] = pagename
|
||||
|
||||
def pathto(otheruri, resource=False,
|
||||
baseuri=self.get_target_uri(pagename)):
|
||||
@ -580,11 +588,11 @@ class StandaloneHTMLBuilder(Builder):
|
||||
return relative_uri(baseuri, otheruri)
|
||||
ctx['pathto'] = pathto
|
||||
ctx['hasdoc'] = lambda name: name in self.env.all_docs
|
||||
sidebarfile = self.config.html_sidebars.get(pagename)
|
||||
if sidebarfile:
|
||||
ctx['customsidebar'] = sidebarfile
|
||||
ctx['customsidebar'] = self.config.html_sidebars.get(pagename)
|
||||
ctx.update(addctx)
|
||||
|
||||
self.app.emit('html-page-context', pagename, templatename, ctx, event_arg)
|
||||
|
||||
output = self.templates.render(templatename, ctx)
|
||||
if not outfilename:
|
||||
outfilename = path.join(self.outdir, os_path(pagename) + self.out_suffix)
|
||||
|
@ -75,7 +75,7 @@
|
||||
{{ rendertemplate(customsidebar) }}
|
||||
{%- endif %}
|
||||
{%- block sidebarsearch %}
|
||||
{%- if current_page_name != "search" %}
|
||||
{%- if pagename != "search" %}
|
||||
<h3>{{ builder == 'web' and 'Keyword' or 'Quick' }} search</h3>
|
||||
<form class="search" action="{{ pathto('search') }}" method="get">
|
||||
<input type="text" name="q" size="18" /> <input type="submit" value="Go" />
|
||||
|
@ -1,6 +1,6 @@
|
||||
{% extends "layout.html" %}
|
||||
{% set title = 'Settings' %}
|
||||
{% set current_page_name = 'settings' %}
|
||||
{% set pagename = 'settings' %}
|
||||
{% block body %}
|
||||
<h1>{{ project }} Documentation Settings</h1>
|
||||
<p>
|
||||
|
Loading…
Reference in New Issue
Block a user