#2904: fix :func:title <target> behavior.

This commit is contained in:
Georg Brandl 2008-05-24 16:18:54 +00:00
parent 1d963f682d
commit d7fcfb76f8
3 changed files with 41 additions and 34 deletions

View File

@ -33,6 +33,8 @@ Bugs fixed
* Use a binary TOC in HTML help generation to fix issues links without * Use a binary TOC in HTML help generation to fix issues links without
explicit anchors. explicit anchors.
* Fix behavior of references to functions/methods with an explicit title.
Release 0.3 (May 6, 2008) Release 0.3 (May 6, 2008)
========================= =========================

View File

@ -16,10 +16,6 @@ directory`, the extension is stripped, and path separators are converted to
slashes. All values, parameters and suchlike referring to "documents" expect slashes. All values, parameters and suchlike referring to "documents" expect
such a document name. such a document name.
.. function:: test()
refer to :func:`test func <test>`.
The TOC tree The TOC tree
------------ ------------

View File

@ -102,9 +102,7 @@ innernodetypes = {
'option': addnodes.literal_emphasis, 'option': addnodes.literal_emphasis,
} }
def xfileref_role(typ, rawtext, text, lineno, inliner, options={}, content=[]): def _fix_parens(typ, text, env):
env = inliner.document.settings.env
text = utils.unescape(text)
if typ in ('func', 'meth', 'cfunc'): if typ in ('func', 'meth', 'cfunc'):
if text.endswith('()'): if text.endswith('()'):
# remove parentheses # remove parentheses
@ -112,9 +110,14 @@ def xfileref_role(typ, rawtext, text, lineno, inliner, options={}, content=[]):
if env.config.add_function_parentheses: if env.config.add_function_parentheses:
# add them back to all occurrences if configured # add them back to all occurrences if configured
text += '()' text += '()'
return text
def xfileref_role(typ, rawtext, text, lineno, inliner, options={}, content=[]):
env = inliner.document.settings.env
text = utils.unescape(text)
# if the first character is a bang, don't cross-reference at all # if the first character is a bang, don't cross-reference at all
if text[0:1] == '!': if text[0:1] == '!':
text = text[1:] text = _fix_parens(typ, text[1:], env)
return [innernodetypes.get(typ, nodes.literal)( return [innernodetypes.get(typ, nodes.literal)(
rawtext, text, classes=['xref'])], [] rawtext, text, classes=['xref'])], []
# we want a cross-reference, create the reference node # we want a cross-reference, create the reference node
@ -122,49 +125,55 @@ def xfileref_role(typ, rawtext, text, lineno, inliner, options={}, content=[]):
modname=env.currmodule, classname=env.currclass) modname=env.currmodule, classname=env.currclass)
# we may need the line number for warnings # we may need the line number for warnings
pnode.line = lineno pnode.line = lineno
innertext = text # the link title may differ from the target, but by default they are the same
# special actions for Python object cross-references title = target = text
if typ in ('data', 'exc', 'func', 'class', 'const', 'attr', 'meth', 'mod'): titleistarget = True
# if the first character is a dot, search more specific namespaces first # look if explicit title and target are given with `foo <bar>` syntax
# else search builtins first
if text[0:1] == '.':
text = text[1:]
pnode['refspecific'] = True
# if the first character is a tilde, don't display the module/class parts
# of the contents
elif text[0:1] == '~':
text = text[1:]
dot = text.rfind('.')
if dot != -1:
innertext = text[dot+1:]
# look if explicit title and target are given
brace = text.find('<') brace = text.find('<')
if brace != -1: if brace != -1:
titleistarget = False
pnode['refcaption'] = True pnode['refcaption'] = True
m = caption_ref_re.match(text) m = caption_ref_re.match(text)
if m: if m:
target = m.group(2) target = m.group(2)
innertext = m.group(1) title = m.group(1)
else: else:
# fallback: everything after '<' is the target # fallback: everything after '<' is the target
target = text[brace+1:] target = text[brace+1:]
innertext = text[:brace] title = text[:brace]
# else, generate target from title # special target for Python object cross-references
else: if typ in ('data', 'exc', 'func', 'class', 'const', 'attr', 'meth', 'mod'):
target = text # fix-up parentheses in link title
# some special cases if titleistarget:
if typ == 'option' and text[0] in '-/': title = _fix_parens(typ, title.lstrip('.~'), env)
# remove parentheses from the target too
if target.endswith('()'):
target = target[:-2]
# if the first character is a dot, search more specific namespaces first
# else search builtins first
if target[0:1] == '.':
target = target[1:]
pnode['refspecific'] = True
# if the first character is a tilde, don't display the module/class parts
# of the contents
elif target[0:1] == '~':
target = target[1:]
dot = target.rfind('.')
if dot != -1:
title = target[dot+1:]
# some other special cases for the target
elif typ == 'option' and target[0] in '-/':
# strip option marker from target # strip option marker from target
target = target[1:] target = target[1:]
if typ == 'term': elif typ == 'term':
# normalize whitespace in definition terms (if the term reference is # normalize whitespace in definition terms (if the term reference is
# broken over a line, a newline will be in text) # broken over a line, a newline will be in target)
target = ws_re.sub(' ', target).lower() target = ws_re.sub(' ', target).lower()
else: else:
# remove all whitespace to avoid referencing problems # remove all whitespace to avoid referencing problems
target = ws_re.sub('', target) target = ws_re.sub('', target)
pnode['reftarget'] = target pnode['reftarget'] = target
pnode += innernodetypes.get(typ, nodes.literal)(rawtext, innertext, classes=['xref']) pnode += innernodetypes.get(typ, nodes.literal)(rawtext, title, classes=['xref'])
return [pnode], [] return [pnode], []