mirror of
https://github.com/sphinx-doc/sphinx.git
synced 2025-02-25 18:55:22 -06:00
#504: Add an `index
` role, to make inline index entries.
This commit is contained in:
parent
22b5751eb5
commit
40e692e6c3
2
CHANGES
2
CHANGES
@ -10,6 +10,8 @@ Release 1.1 (in development)
|
|||||||
|
|
||||||
* #460: Allow limiting the depth of section numbers for HTML.
|
* #460: Allow limiting the depth of section numbers for HTML.
|
||||||
|
|
||||||
|
* #504: Add an ``index`` role, to make inline index entries.
|
||||||
|
|
||||||
* #443: Allow referencing external graphviz files.
|
* #443: Allow referencing external graphviz files.
|
||||||
|
|
||||||
* #221: Add Swedish locale.
|
* #221: Add Swedish locale.
|
||||||
|
@ -309,6 +309,7 @@ in a different style:
|
|||||||
If you don't need the "variable part" indication, use the standard
|
If you don't need the "variable part" indication, use the standard
|
||||||
````code```` instead.
|
````code```` instead.
|
||||||
|
|
||||||
|
There is also an :rst:role:`index` role to generate index entries.
|
||||||
|
|
||||||
The following roles generate external links:
|
The following roles generate external links:
|
||||||
|
|
||||||
|
@ -62,6 +62,85 @@ Meta-information markup
|
|||||||
:confval:`show_authors` configuration value is True.
|
:confval:`show_authors` configuration value is True.
|
||||||
|
|
||||||
|
|
||||||
|
Index-generating markup
|
||||||
|
-----------------------
|
||||||
|
|
||||||
|
Sphinx automatically creates index entries from all object descriptions (like
|
||||||
|
functions, classes or attributes) like discussed in :ref:`domains`.
|
||||||
|
|
||||||
|
However, there is also explicit markup available, to make the index more
|
||||||
|
comprehensive and enable index entries in documents where information is not
|
||||||
|
mainly contained in information units, such as the language reference.
|
||||||
|
|
||||||
|
.. rst:directive:: .. index:: <entries>
|
||||||
|
|
||||||
|
This directive contains one or more index entries. Each entry consists of a
|
||||||
|
type and a value, separated by a colon.
|
||||||
|
|
||||||
|
For example::
|
||||||
|
|
||||||
|
.. index::
|
||||||
|
single: execution; context
|
||||||
|
module: __main__
|
||||||
|
module: sys
|
||||||
|
triple: module; search; path
|
||||||
|
|
||||||
|
The execution context
|
||||||
|
---------------------
|
||||||
|
|
||||||
|
...
|
||||||
|
|
||||||
|
This directive contains five entries, which will be converted to entries in
|
||||||
|
the generated index which link to the exact location of the index statement
|
||||||
|
(or, in case of offline media, the corresponding page number).
|
||||||
|
|
||||||
|
Since index directives generate cross-reference targets at their location in
|
||||||
|
the source, it makes sense to put them *before* the thing they refer to --
|
||||||
|
e.g. a heading, as in the example above.
|
||||||
|
|
||||||
|
The possible entry types are:
|
||||||
|
|
||||||
|
single
|
||||||
|
Creates a single index entry. Can be made a subentry by separating the
|
||||||
|
subentry text with a semicolon (this notation is also used below to
|
||||||
|
describe what entries are created).
|
||||||
|
pair
|
||||||
|
``pair: loop; statement`` is a shortcut that creates two index entries,
|
||||||
|
namely ``loop; statement`` and ``statement; loop``.
|
||||||
|
triple
|
||||||
|
Likewise, ``triple: module; search; path`` is a shortcut that creates
|
||||||
|
three index entries, which are ``module; search path``, ``search; path,
|
||||||
|
module`` and ``path; module search``.
|
||||||
|
module, keyword, operator, object, exception, statement, builtin
|
||||||
|
These all create two index entries. For example, ``module: hashlib``
|
||||||
|
creates the entries ``module; hashlib`` and ``hashlib; module``. (These
|
||||||
|
are Python-specific and therefore deprecated.)
|
||||||
|
|
||||||
|
For index directives containing only "single" entries, there is a shorthand
|
||||||
|
notation::
|
||||||
|
|
||||||
|
.. index:: BNF, grammar, syntax, notation
|
||||||
|
|
||||||
|
This creates four index entries.
|
||||||
|
|
||||||
|
.. rst:role:: index
|
||||||
|
|
||||||
|
While the :rst:dir:`index` directive is a block-level markup and links to the
|
||||||
|
beginning of the next paragraph, there is also a corresponding role that sets
|
||||||
|
the link target directly where it is used.
|
||||||
|
|
||||||
|
The content of the role can be a simple phrase, which is then kept in the
|
||||||
|
text and used as an index entry. It can also be a combination of text and
|
||||||
|
index entry, styled like with explicit targets of cross-references. In that
|
||||||
|
case, the "target" part can be a full entry as described for the directive
|
||||||
|
above. For example::
|
||||||
|
|
||||||
|
This is a normal reST :index:`paragraph` that contains several
|
||||||
|
:index:`index entries <pair: index; entry>`.
|
||||||
|
|
||||||
|
.. versionadded:: 1.1
|
||||||
|
|
||||||
|
|
||||||
.. _tags:
|
.. _tags:
|
||||||
|
|
||||||
Including content based on tags
|
Including content based on tags
|
||||||
|
@ -144,68 +144,6 @@ For local tables of contents, use the standard reST :dudir:`contents directive
|
|||||||
<contents>`.
|
<contents>`.
|
||||||
|
|
||||||
|
|
||||||
Index-generating markup
|
|
||||||
-----------------------
|
|
||||||
|
|
||||||
Sphinx automatically creates index entries from all object descriptions (like
|
|
||||||
functions, classes or attributes) like discussed in :ref:`domains`.
|
|
||||||
|
|
||||||
However, there is also an explicit directive available, to make the index more
|
|
||||||
comprehensive and enable index entries in documents where information is not
|
|
||||||
mainly contained in information units, such as the language reference.
|
|
||||||
|
|
||||||
.. rst:directive:: .. index:: <entries>
|
|
||||||
|
|
||||||
This directive contains one or more index entries. Each entry consists of a
|
|
||||||
type and a value, separated by a colon.
|
|
||||||
|
|
||||||
For example::
|
|
||||||
|
|
||||||
.. index::
|
|
||||||
single: execution; context
|
|
||||||
module: __main__
|
|
||||||
module: sys
|
|
||||||
triple: module; search; path
|
|
||||||
|
|
||||||
The execution context
|
|
||||||
---------------------
|
|
||||||
|
|
||||||
...
|
|
||||||
|
|
||||||
This directive contains five entries, which will be converted to entries in
|
|
||||||
the generated index which link to the exact location of the index statement
|
|
||||||
(or, in case of offline media, the corresponding page number).
|
|
||||||
|
|
||||||
Since index directives generate cross-reference targets at their location in
|
|
||||||
the source, it makes sense to put them *before* the thing they refer to --
|
|
||||||
e.g. a heading, as in the example above.
|
|
||||||
|
|
||||||
The possible entry types are:
|
|
||||||
|
|
||||||
single
|
|
||||||
Creates a single index entry. Can be made a subentry by separating the
|
|
||||||
subentry text with a semicolon (this notation is also used below to
|
|
||||||
describe what entries are created).
|
|
||||||
pair
|
|
||||||
``pair: loop; statement`` is a shortcut that creates two index entries,
|
|
||||||
namely ``loop; statement`` and ``statement; loop``.
|
|
||||||
triple
|
|
||||||
Likewise, ``triple: module; search; path`` is a shortcut that creates
|
|
||||||
three index entries, which are ``module; search path``, ``search; path,
|
|
||||||
module`` and ``path; module search``.
|
|
||||||
module, keyword, operator, object, exception, statement, builtin
|
|
||||||
These all create two index entries. For example, ``module: hashlib``
|
|
||||||
creates the entries ``module; hashlib`` and ``hashlib; module``. (These
|
|
||||||
are Python-specific and therefore deprecated.)
|
|
||||||
|
|
||||||
For index directives containing only "single" entries, there is a shorthand
|
|
||||||
notation::
|
|
||||||
|
|
||||||
.. index:: BNF, grammar, syntax, notation
|
|
||||||
|
|
||||||
This creates four index entries.
|
|
||||||
|
|
||||||
|
|
||||||
Glossary
|
Glossary
|
||||||
--------
|
--------
|
||||||
|
|
||||||
|
@ -13,9 +13,9 @@ from docutils import nodes
|
|||||||
from docutils.parsers.rst import Directive, directives
|
from docutils.parsers.rst import Directive, directives
|
||||||
|
|
||||||
from sphinx import addnodes
|
from sphinx import addnodes
|
||||||
from sphinx.locale import pairindextypes, _
|
from sphinx.locale import _
|
||||||
from sphinx.util import url_re, docname_join
|
from sphinx.util import url_re, docname_join
|
||||||
from sphinx.util.nodes import explicit_title_re
|
from sphinx.util.nodes import explicit_title_re, process_index_entry
|
||||||
from sphinx.util.compat import make_admonition
|
from sphinx.util.compat import make_admonition
|
||||||
from sphinx.util.matching import patfilter
|
from sphinx.util.matching import patfilter
|
||||||
|
|
||||||
@ -157,10 +157,6 @@ class Index(Directive):
|
|||||||
final_argument_whitespace = True
|
final_argument_whitespace = True
|
||||||
option_spec = {}
|
option_spec = {}
|
||||||
|
|
||||||
indextypes = [
|
|
||||||
'single', 'pair', 'double', 'triple',
|
|
||||||
]
|
|
||||||
|
|
||||||
def run(self):
|
def run(self):
|
||||||
arguments = self.arguments[0].split('\n')
|
arguments = self.arguments[0].split('\n')
|
||||||
env = self.state.document.settings.env
|
env = self.state.document.settings.env
|
||||||
@ -170,28 +166,7 @@ class Index(Directive):
|
|||||||
indexnode = addnodes.index()
|
indexnode = addnodes.index()
|
||||||
indexnode['entries'] = ne = []
|
indexnode['entries'] = ne = []
|
||||||
for entry in arguments:
|
for entry in arguments:
|
||||||
entry = entry.strip()
|
ne.extend(process_index_entry(entry, targetid))
|
||||||
for type in pairindextypes:
|
|
||||||
if entry.startswith(type+':'):
|
|
||||||
value = entry[len(type)+1:].strip()
|
|
||||||
value = pairindextypes[type] + '; ' + value
|
|
||||||
ne.append(('pair', value, targetid, value))
|
|
||||||
break
|
|
||||||
else:
|
|
||||||
for type in self.indextypes:
|
|
||||||
if entry.startswith(type+':'):
|
|
||||||
value = entry[len(type)+1:].strip()
|
|
||||||
if type == 'double':
|
|
||||||
type = 'pair'
|
|
||||||
ne.append((type, value, targetid, value))
|
|
||||||
break
|
|
||||||
# shorthand notation for single entries
|
|
||||||
else:
|
|
||||||
for value in entry.split(','):
|
|
||||||
value = value.strip()
|
|
||||||
if not value:
|
|
||||||
continue
|
|
||||||
ne.append(('single', value, targetid, value))
|
|
||||||
return [indexnode, targetnode]
|
return [indexnode, targetnode]
|
||||||
|
|
||||||
|
|
||||||
|
@ -18,7 +18,7 @@ from docutils.parsers.rst import roles
|
|||||||
from sphinx import addnodes
|
from sphinx import addnodes
|
||||||
from sphinx.locale import _
|
from sphinx.locale import _
|
||||||
from sphinx.util import ws_re
|
from sphinx.util import ws_re
|
||||||
from sphinx.util.nodes import split_explicit_title
|
from sphinx.util.nodes import split_explicit_title, process_index_entry
|
||||||
|
|
||||||
|
|
||||||
generic_docroles = {
|
generic_docroles = {
|
||||||
@ -268,6 +268,27 @@ def abbr_role(typ, rawtext, text, lineno, inliner, options={}, content=[]):
|
|||||||
return [addnodes.abbreviation(abbr, abbr, explanation=expl)], []
|
return [addnodes.abbreviation(abbr, abbr, explanation=expl)], []
|
||||||
|
|
||||||
|
|
||||||
|
def index_role(typ, rawtext, text, lineno, inliner, options={}, content=[]):
|
||||||
|
# create new reference target
|
||||||
|
env = inliner.document.settings.env
|
||||||
|
targetid = 'index-%s' % env.new_serialno('index')
|
||||||
|
targetnode = nodes.target('', '', ids=[targetid])
|
||||||
|
# split text and target in role content
|
||||||
|
has_explicit_title, title, target = split_explicit_title(text)
|
||||||
|
title = utils.unescape(title)
|
||||||
|
target = utils.unescape(target)
|
||||||
|
# if an explicit target is given, we can process it as a full entry
|
||||||
|
if has_explicit_title:
|
||||||
|
entries = process_index_entry(target, targetid)
|
||||||
|
# otherwise we just create a "single" entry
|
||||||
|
else:
|
||||||
|
entries = [('single', target, targetid, target)]
|
||||||
|
indexnode = addnodes.index()
|
||||||
|
indexnode['entries'] = entries
|
||||||
|
textnode = nodes.Text(title, title)
|
||||||
|
return [indexnode, targetnode, textnode], []
|
||||||
|
|
||||||
|
|
||||||
specific_docroles = {
|
specific_docroles = {
|
||||||
# links to download references
|
# links to download references
|
||||||
'download': XRefRole(nodeclass=addnodes.download_reference),
|
'download': XRefRole(nodeclass=addnodes.download_reference),
|
||||||
@ -281,6 +302,7 @@ specific_docroles = {
|
|||||||
'file': emph_literal_role,
|
'file': emph_literal_role,
|
||||||
'samp': emph_literal_role,
|
'samp': emph_literal_role,
|
||||||
'abbr': abbr_role,
|
'abbr': abbr_role,
|
||||||
|
'index': index_role,
|
||||||
}
|
}
|
||||||
|
|
||||||
for rolename, func in specific_docroles.iteritems():
|
for rolename, func in specific_docroles.iteritems():
|
||||||
|
@ -14,6 +14,7 @@ import re
|
|||||||
from docutils import nodes
|
from docutils import nodes
|
||||||
|
|
||||||
from sphinx import addnodes
|
from sphinx import addnodes
|
||||||
|
from sphinx.locale import pairindextypes
|
||||||
from sphinx.util.pycompat import class_types
|
from sphinx.util.pycompat import class_types
|
||||||
|
|
||||||
|
|
||||||
@ -72,6 +73,37 @@ def split_explicit_title(text):
|
|||||||
return False, text, text
|
return False, text, text
|
||||||
|
|
||||||
|
|
||||||
|
indextypes = [
|
||||||
|
'single', 'pair', 'double', 'triple',
|
||||||
|
]
|
||||||
|
|
||||||
|
def process_index_entry(entry, targetid):
|
||||||
|
indexentries = []
|
||||||
|
entry = entry.strip()
|
||||||
|
for type in pairindextypes:
|
||||||
|
if entry.startswith(type+':'):
|
||||||
|
value = entry[len(type)+1:].strip()
|
||||||
|
value = pairindextypes[type] + '; ' + value
|
||||||
|
indexentries.append(('pair', value, targetid, value))
|
||||||
|
break
|
||||||
|
else:
|
||||||
|
for type in indextypes:
|
||||||
|
if entry.startswith(type+':'):
|
||||||
|
value = entry[len(type)+1:].strip()
|
||||||
|
if type == 'double':
|
||||||
|
type = 'pair'
|
||||||
|
indexentries.append((type, value, targetid, value))
|
||||||
|
break
|
||||||
|
# shorthand notation for single entries
|
||||||
|
else:
|
||||||
|
for value in entry.split(','):
|
||||||
|
value = value.strip()
|
||||||
|
if not value:
|
||||||
|
continue
|
||||||
|
indexentries.append(('single', value, targetid, value))
|
||||||
|
return indexentries
|
||||||
|
|
||||||
|
|
||||||
def inline_all_toctrees(builder, docnameset, docname, tree, colorfunc):
|
def inline_all_toctrees(builder, docnameset, docname, tree, colorfunc):
|
||||||
"""Inline all toctrees in the *tree*.
|
"""Inline all toctrees in the *tree*.
|
||||||
|
|
||||||
|
@ -132,6 +132,8 @@ Adding \n to test unescaping.
|
|||||||
|
|
||||||
Test :abbr:`abbr (abbreviation)` and another :abbr:`abbr (abbreviation)`.
|
Test :abbr:`abbr (abbreviation)` and another :abbr:`abbr (abbreviation)`.
|
||||||
|
|
||||||
|
Testing the :index:`index` role, also available with
|
||||||
|
:index:`explicit <pair: title; explicit>` title.
|
||||||
|
|
||||||
.. _with:
|
.. _with:
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user