summaryrefslogtreecommitdiff
path: root/sphinx/domains/javascript.py
diff options
context:
space:
mode:
Diffstat (limited to 'sphinx/domains/javascript.py')
-rw-r--r--sphinx/domains/javascript.py94
1 files changed, 86 insertions, 8 deletions
diff --git a/sphinx/domains/javascript.py b/sphinx/domains/javascript.py
index 8f618a70c..d9312eee5 100644
--- a/sphinx/domains/javascript.py
+++ b/sphinx/domains/javascript.py
@@ -16,17 +16,20 @@ from sphinx.locale import l_, _
from sphinx.directives import ObjectDescription
from sphinx.domains.python import py_paramlist_re as js_paramlist_re
from sphinx.roles import XRefRole
+from sphinx.util.nodes import make_refnode
js_sig_re = re.compile(
r'''([^ .]+\.)? # object name
([^ .]+\s*) # name
- \((.*)\)$ # arguments
+ \((.*)\)$ # arguments
''', re.VERBOSE)
class JSObject(ObjectDescription):
"""
Description of a JavaScript object.
"""
+ #: If set to ``True`` this object is callable and a `desc_parameterlist` is
+ #: added
has_arguments = False
def handle_signature(self, sig, signode):
@@ -36,14 +39,14 @@ class JSObject(ObjectDescription):
nameprefix, name, arglist = match.groups()
objectname = self.env.temp_data.get('js:object')
- if objectname and nameprefix:
- # someone documenting the method of an attribute of the current
- # object? shouldn't happen but who knows...
- fullname = objectname + '.' + nameprefix + name
+ if nameprefix:
+ if objectname:
+ # someone documenting the method of an attribute of the current
+ # object? shouldn't happen but who knows...
+ nameprefix = objectname + '.' + nameprefix
+ fullname = nameprefix + name
elif objectname:
fullname = objectname + '.' + name
- elif nameprefix:
- fullname = nameprefix + '.' + name
else:
# just a function or constructor
objectname = ''
@@ -52,6 +55,7 @@ class JSObject(ObjectDescription):
signode['object'] = objectname
signode['fullname'] = fullname
+ signode += addnodes.desc_addname(nameprefix, nameprefix)
signode += addnodes.desc_name(name, name)
if self.has_arguments:
signode += addnodes.desc_parameterlist()
@@ -78,6 +82,42 @@ class JSObject(ObjectDescription):
raise ValueError()
return fullname, nameprefix
+ def add_target_and_index(self, name_obj, sig, signode):
+ objectname = self.options.get(
+ 'object', self.env.temp_data.get('js:object'))
+ fullname = name_obj[0]
+ if fullname not in self.state.document.ids:
+ signode['names'].append(fullname)
+ signode['ids'].append(fullname)
+ signode['first'] = not self.names
+ self.state.document.note_explicit_target(signode)
+ objects = self.env.domaindata['js']['objects']
+ if fullname in objects:
+ self.env.warn(
+ self.env.docname,
+ 'duplicate object description of %s, ' % fullname +
+ 'other instance in ' +
+ self.env.doc2path(objects[fullname][0]),
+ self.lineno)
+ objects[fullname] = self.env.docname, self.objtype
+
+ indextext = self.get_index_text(objectname, name_obj)
+ if indextext:
+ self.indexnode['entries'].append(('single', indextext,
+ fullname, fullname))
+
+ def get_index_text(self, objectname, name_obj):
+ name, obj = name_obj
+ if self.objtype == 'function':
+ if not obj:
+ return _('%s() (built-in function)') % name
+ return _('%s() (%s method)') % (name, obj)
+ elif self.objtype == 'data':
+ return _('%s (global variable or constant)') % name
+ elif self.objtype == 'attribute':
+ return _('%s (%s attribute)') % (name, obj)
+ return ''
+
class JSCallable(JSObject):
"""Description of a JavaScript function, method or constructor."""
has_arguments = True
@@ -116,5 +156,43 @@ class JavaScriptDomain(Domain):
roles = {
'func': JSXRefRole(fix_parens=True),
'data': JSXRefRole(),
- 'attr': JSXRefRole()
+ 'attr': JSXRefRole(),
}
+ initial_data = {
+ 'objects': {}, # fullname -> docname, objtype
+ }
+
+ def clear_doc(self, docname):
+ for fullname, (fn, _) in self.data['objects'].items():
+ if fn == docname:
+ del self.data['objects'][fullname]
+
+ def find_obj(self, env, obj, name, typ, searchorder=0):
+ if name[-2:] == '()':
+ name = name[:-2]
+ objects = self.data['objects']
+ newname = None
+ if searchorder == 1:
+ if obj and obj + '.' + name in objects:
+ newname = obj + '.' + name
+ else:
+ newname = name
+ else:
+ if name in objects:
+ newname = name
+ elif obj and obj + '.' + name in objects:
+ newname = obj + '.' + name
+ return newname, objects.get(newname)
+
+ def resolve_xref(self, env, fromdocname, builder, typ, target, node,
+ contnode):
+ objectname = node.get('js:object')
+ searchorder = node.hasattr('refspecific') and 1 or 0
+ name, obj = self.find_obj(env, objectname, target, typ, searchorder)
+ if not obj:
+ return None
+ return make_refnode(builder, fromdocname, obj[0], name, contnode, name)
+
+ def get_objects(self):
+ for refname, (docname, type) in self.data['objects'].iteritems():
+ yield refname, type, docname, refname, 1