diff options
| -rw-r--r-- | bindings/bindings.py | 60 | ||||
| -rw-r--r-- | bindings/lang_php5_helpers/php_code.py | 2 | ||||
| -rw-r--r-- | bindings/lang_python.py | 72 |
3 files changed, 117 insertions, 17 deletions
diff --git a/bindings/bindings.py b/bindings/bindings.py index e8efb886..30b7c80e 100644 --- a/bindings/bindings.py +++ b/bindings/bindings.py @@ -80,6 +80,9 @@ class BindingData: if not c: continue c.methods.append(f) + if f.docstring: + # remove first parameter, which is self/this/etc. + f.docstring.parameters = f.docstring.parameters[1:] self.functions.remove(f) def look_for_docstrings(self, srcdir): @@ -103,8 +106,8 @@ class BindingData: if not func: continue func = func[0] - func.docstring = docstring - + func.docstring = DocString(func, docstring) + class Struct: @@ -160,6 +163,59 @@ class Function: self.skip = True +class DocString: + orig_docstring = None + parameters = None + return_value = None + description = None + + def __init__(self, function, docstring): + self.orig_docstring = docstring + lines = docstring.splitlines() + # ignore the first line, it has the symbol name + lines = lines[1:] + + # look for parameters + while lines[0].strip(): + if not self.parameters and not lines[0].startswith('@'): + # function without parameters + break + if not self.parameters: + self.parameters = [] + + if lines[0][0] == '@': + param_name, param_desc = lines[0][1:].split(':', 2) + self.parameters.append([param_name, param_desc]) + else: + # continuation of previous description + self.parameters[-1][1] = self.parameters[-1][1] + ' ' + lines[0].strip() + + lines = lines[1:] + + # blank line then description, till the end or the return value + lines = lines[1:] + self.description = '' + while not lines[0].startswith('Return value'): + self.description += lines[0] + '\n' + if len(lines) == 1: + self.description = self.description.strip() + return + lines = lines[1:] + self.description = self.description.strip() + + # return value + if lines[0].startswith('Return value'): + lines[0] = lines[0].split(':', 1)[1] + self.return_value = '' + while lines[0].strip(): + self.return_value = self.return_value + ' ' + lines[0].strip() + if len(lines) == 1: + break + lines = lines[1:] + self.return_value = self.return_value[1:] # remove leading space + + + def normalise_var(type, name): if name[0] == '*': type += '*' diff --git a/bindings/lang_php5_helpers/php_code.py b/bindings/lang_php5_helpers/php_code.py index 09608236..41db50ba 100644 --- a/bindings/lang_php5_helpers/php_code.py +++ b/bindings/lang_php5_helpers/php_code.py @@ -341,7 +341,7 @@ function cptrToPhp ($cptr) { print >> self.fd, '' def generate_docstring(self, func, method_name, indent): - docstring = func.docstring + docstring = func.docstring.orig_docstring if func.args: first_arg_name = func.args[0][1] else: diff --git a/bindings/lang_python.py b/bindings/lang_python.py index 4092b5b4..e872a246 100644 --- a/bindings/lang_python.py +++ b/bindings/lang_python.py @@ -22,6 +22,7 @@ import os import sys import re +import textwrap import utils @@ -407,17 +408,17 @@ Session.providerIds = property(session_get_provider_ids) print >> fd, '' def format_docstring(self, func, method_name, indent): - docstring = func.docstring if func.args: first_arg_name = func.args[0][1] else: first_arg_name = None - def rep(s): + + def format_inlines_sub(s): type = s.group(1)[0] var = s.group(1)[1:] if type == '#': # struct if var.startswith('Lasso'): - return var[5:] + return 'L{%s}' % var[5:] elif type == '%': # %TRUE, %FALSE if var == 'TRUE': return 'True' @@ -426,19 +427,62 @@ Session.providerIds = property(session_get_provider_ids) print >> sys.stderr, 'W: unknown docstring thingie: %s' % s.group(1) elif type == '@': if var == first_arg_name: - return 'self' - + var = 'self' + return 'C{%s}' % var return s.group(1) - lines = [] - for l in docstring.splitlines(): - if l.strip() and not lines: - continue - lines.append(l) - s = '\n'.join([indent * ' ' + x for x in lines[1:]]) - s = s.replace('NULL', 'None') + regex = re.compile(r'([\#%@]\w+)', re.DOTALL) - s = regex.sub(rep, s) - return s + + def format_inline(s): + s = regex.sub(format_inlines_sub, s) + return s.replace('NULL', 'None') + + docstring = func.docstring + s = [] + + if docstring.description: + for paragraph in docstring.description.split('\n\n'): + if '<itemizedlist>' in paragraph: + before, after = paragraph.split('<itemizedlist>' ,1) + if before: + s.append('\n'.join(textwrap.wrap( + format_inline(before), 70))) + + # remove tags + after = after.replace('<itemizedlist>', '') + after = after.replace('</itemizedlist>', '') + + for listitem in after.split('<listitem><para>'): + listitem = listitem.replace('</para></listitem>', '').strip() + s.append('\n'.join(textwrap.wrap( + format_inline(listitem), 70, + initial_indent = ' - ', + subsequent_indent = ' '))) + s.append('\n\n') + + else: + s.append('\n'.join(textwrap.wrap( + format_inline(paragraph), 70))) + s.append('\n\n') + + for param in docstring.parameters: + s.append('\n'.join(textwrap.wrap( + format_inline(param[1]), 70, + initial_indent = '@param %s: ' % param[0], + subsequent_indent = 4*' '))) + s.append('\n') + if docstring.return_value: + s.append('\n'.join(textwrap.wrap( + format_inline(docstring.return_value), 70, + initial_indent = '@return: ', + subsequent_indent = 4*' '))) + s.append('\n') + + + s[-1] = s[-1].rstrip() # remove trailing newline from last line + + return '\n'.join([(indent*' ')+x for x in ''.join(s).splitlines()]) + def generate_functions(self, fd): for m in self.binding_data.functions: |
