def generate_breadcrubs(node: Node): ret = [] breadcrubs = [] parent = node.parent while parent != None: #ret.append(MdLink([Text(parent.name)], parent.generate_url())) #ret.append(Text(' > ')) breadcrubs.append(parent) parent = parent.parent is_first = True for parent in reversed(breadcrubs): if parent.kind == Kind.ROOT: ret.append(MdLink([MdBold([Text('Class List')])], 'annotated.md')) else: ret.append(MdLink([MdBold([Text(parent.name)])], parent.generate_url())) ret.append(Text(' ')) if is_first: is_first = False ret.append(MdBold([Text('>')])) else: ret.append(MdBold([Text('::')])) ret.append(Text(' ')) ret.append(MdLink([MdBold([Text(node.name)])], node.generate_url())) ret.append(Br()) return MdParagraph(ret)
def reference_as_str(self, p: Element) -> str: renderer = MdRenderer() refid = p.get('refid') if refid is not None: m = MdLink([MdBold([Text(p.text)])], refid) m.render(renderer, '') return renderer.output else: return p.text
def generate_dir(index_path: str, output_path: str, node: Node, cache: Cache) -> dict: output_file = os.path.join(output_path, node.refid + '.md') print('Generating ' + output_file) document = MdDocument() # Add title title = node.name + ' Directory Reference' document.append(MdHeader(1, [Text(title)])) # Load XML xml_root = xml.etree.ElementTree.parse( os.path.join(index_path, node.refid + '.xml')).getroot() if xml_root is None: IndexError('Root xml not found!') compounddef = xml_root.find('compounddef') if compounddef is None: IndexError('compounddef not found in xml!') document.append(MdHeader(2, [Text('Files')])) lst = MdList([]) keywords = [] for innerdir in compounddef.findall('innerdir'): lst.append( MdParagraph([ MdBold([ MdLink([Text(innerdir.text + '/')], innerdir.get('refid') + '.md') ]) ])) keywords.append(innerdir.text) for innerfile in compounddef.findall('innerfile'): lst.append( MdParagraph([ MdBold([ MdLink([Text(innerfile.text)], innerfile.get('refid') + '.md') ]) ])) keywords.append(innerfile.text) document.append(lst) if not config.noindex: document.set_keywords(keywords) document.set_title(title) # Save with open(output_file, 'w') as f: document.render(MdRenderer(f))
def generate_list_recursive(directory: dict, keywords: List[str]): lst = MdList([]) for key,value in directory.items(): if key == '#': continue if isinstance(value, dict): lst.append(MdParagraph([ MdBold([MdLink([Text(key + '/')], value['#'] + '.md')]), generate_list_recursive(value, keywords) ])) keywords.append(key) else: lst.append(MdParagraph([MdBold([MdLink([Text(key)], value + '.md')])])) keywords.append(key) return lst
def generateFile(indexDir: str, outputDir: str, node: Node, cache: Cache) -> dict: outputFile = os.path.join(outputDir, node.refid + '_source.md') print('Generating ' + outputFile) document = MdDocument() # Add title document.append(MdHeader(1, [Text(node.name + ' File Reference')])) # Load XML xmlRoot = xml.etree.ElementTree.parse(os.path.join(indexDir, node.refid + '.xml')).getroot() if xmlRoot is None: IndexError('Root xml not found!') compounddef = xmlRoot.find('compounddef') if compounddef is None: IndexError('compounddef not found in xml!') document.append(MdParagraph([MdBold([MdLink([Text('Go to the documentation of this file.')], node.refid + '.md')])])) location = compounddef.find('location') if location is not None: document.append(MdParagraph([Text('Source: '), MdCode([Text(location.get('file'))])])) programlisting = compounddef.find('programlisting') if programlisting is None: return document.append(MdParagraph(convertXmlPara(compounddef, cache))) # Save with open(outputFile, 'w') as f: document.render(MdRenderer(f))
def recursiveHierarchy(node: Node, mdl: MdList): for child in node.members: if child.kind is Kind.NAMESPACE or child.kind is Kind.CLASS or child.kind is Kind.STRUCT: p = MdParagraph([]) p.append(Text(child.getKindStr() + ' ')) p.append(MdLink([MdBold([Text(child.name)])], child.url)) sublist = MdList([]) recursiveHierarchy(child, sublist) p.append(sublist) mdl.append(p)
def recursive_hierarchy(node: Node, mdl: MdList, keywords: list): for child in node.members: if child.kind.is_parent(): p = MdParagraph([]) p.append(Text(child.get_kind_str() + ' ')) keywords.append(child.name) p.append(MdLink([MdBold([Text(child.name)])], child.url)) sublist = MdList([]) recursive_hierarchy(child, sublist, keywords) p.append(sublist) mdl.append(p)
def generate_pages(index_path: str, output_path: str, node: Node, cache: Cache) -> dict: output_file = os.path.join(output_path, 'pages.md') print('Generating ' + output_file) document = MdDocument() # Add title document.append(MdHeader(1, [Text('Related Pages')])) document.append( MdParagraph( [Text('Here is a list of all related documentation pages:')])) lst = MdList([]) modules = {} # List through all groups for child in node.members: if child.kind == Kind.PAGE: path = os.path.join(index_path, child.refid + '.xml') xml_root = xml.etree.ElementTree.parse(path).getroot() compounddef = xml_root.find('compounddef') if compounddef is not None: briefdescription = compounddef.find('briefdescription') briefdescription_paras = [] if briefdescription is not None: briefdescription_paras = compounddef.find( 'briefdescription').findall('para') p = MdParagraph([]) name = compounddef.find('title').text refid = compounddef.get('id') p.append(MdBold([MdLink([Text(name)], refid + '.md')])) modules[refid] = name p.append(Text(' ')) for para in briefdescription_paras: p.extend(convert_xml_para(para, cache)) lst.append(p) document.append(lst) document.set_title('Related Pages') # Save with open(output_file, 'w') as f: document.render(MdRenderer(f)) return modules
def generateClassIndex(outputDir: str, root: Node): outputFile = os.path.join(outputDir, 'classes.md') print('Generating ' + outputFile) document = MdDocument() # Add title document.append(MdHeader(1, [Text('Class Index')])) # Sort dictionary = {} recursiveDictionary(root, dictionary) for key in list(sorted(dictionary.keys())): document.append(MdHeader(2, [Text(key)])) mdl = MdList([]) for member in dictionary[key]: p = MdParagraph([]) p.append( MdLink([MdBold([Text(member.getFullName(False))])], member.url)) namespace = member.getNamespace() if namespace is not None: p.append(Text(' (')) p.append( MdLink([MdBold([Text(namespace.getFullName(False))])], namespace.url)) p.append(Text(')')) mdl.append(p) document.append(mdl) document.append(Br()) # Save with open(outputFile, 'w') as f: document.render(MdRenderer(f))
def make_groups_list(index_path: str, node: Node, keywords: list, modules: dict, cache: Cache): lst = MdList([]) is_empty = True # List through all groups for child in node.members: if child.kind == Kind.GROUP: keywords.append(child.name) path = os.path.join(index_path, child.refid + '.xml') xml_root = xml.etree.ElementTree.parse(path).getroot() compounddef = xml_root.find('compounddef') if compounddef is not None: briefdescription_paras = compounddef.find('briefdescription').findall('para') p = MdParagraph([]) name = compounddef.find('compoundname').text refid = compounddef.get('id') p.append(MdBold([MdLink([Text(name)], refid + '.md')])) modules[refid] = { 'name': name } p.append(Text(' ')) for para in briefdescription_paras: p.extend(convert_xml_para(para, cache)) lst.append(p) is_empty = False test_modules = {} test_inner_lst = make_groups_list(index_path, child, keywords, test_modules, cache) if test_inner_lst is not None: lst.append(test_inner_lst) name = modules[refid] modules[refid] = { 'name': name['name'], 'innergroups': test_modules } if is_empty: return None return lst
def paras(self, p: Element, italic: bool = False) -> [Md]: ret = [] if p is None: return ret if p.text: if italic: ret.append(MdItalic([Text(p.text.strip())])) ret.append(Text(' ')) else: ret.append(Text(p.text)) for item in p.getchildren(): # para if item.tag == 'para': ret.append(MdParagraph(self.paras(item))) ret.append(Text('\n')) # image elif item.tag == 'image': url = item.get('name') ret.append(MdImage(url)) # computeroutput elif item.tag == 'computeroutput': text = [] if item.text: text.append(item.text) for i in item.getchildren(): text.extend(self.plain(i)) ret.append(Code(' '.join(text))) # programlisting elif item.tag == 'programlisting': ret.extend(self.programlisting(item)) # table elif item.tag == 'table': t = MdTable() for row in item.findall('row'): r = MdTableRow([]) for cell in row.findall('entry'): for para in cell.findall('para'): r.append(MdTableCell(self.paras(para))) t.append(r) ret.append(t) # blockquote elif item.tag == 'blockquote': b = MdBlockQuote([]) for para in item.findall('para'): b.extend(self.paras(para)) ret.append(b) # heading elif item.tag == 'heading': ret.append(MdHeader(int(item.get('level')), self.paras(item))) # orderedlist elif item.tag == 'orderedlist' or item.tag == 'itemizedlist': lst = MdList([]) for listitem in item.findall('listitem'): i = MdParagraph([]) for para in listitem.findall('para'): i.extend(self.paras(para)) lst.append(i) ret.append(lst) # Reference elif item.tag == 'ref': refid = item.get('refid') try: ref = self.cache.get(refid) if italic: if item.text: ret.append( MdLink([MdItalic([MdBold([Text(item.text)])])], ref.url)) else: ret.append( MdLink([ MdItalic( [MdBold([Text(ref.get_full_name())])]) ], ref.url)) else: if item.text: ret.append( MdLink([MdBold([Text(item.text)])], ref.url)) else: ret.append( MdLink([MdBold([Text(ref.get_full_name())])], ref.url)) except: if item.text: ret.append(Text(item.text)) # sect1: elif item.tag == 'sect1': title = item.find('title').text ret.append(MdHeader(2, [Text(title)])) ret.extend(self.paras(item)) # sect2: elif item.tag == 'sect2': title = item.find('title').text ret.append(MdHeader(3, [Text(title)])) ret.extend(self.paras(item)) # sect3: elif item.tag == 'sect3': title = item.find('title').text ret.append(MdHeader(4, [Text(title)])) ret.extend(self.paras(item)) # sect4: elif item.tag == 'sect4': title = item.find('title').text ret.append(MdHeader(5, [Text(title)])) ret.extend(self.paras(item)) # sect5: elif item.tag == 'sect5': title = item.find('title').text ret.append(MdHeader(6, [Text(title)])) ret.extend(self.paras(item)) # variablelist elif item.tag == 'variablelist': varlistentry = item.find('varlistentry') ret.append(MdHeader(4, self.paras(varlistentry.find('term')))) term = varlistentry.find('term') for listitem in item.findall('listitem'): for para in listitem.findall('para'): ret.append(MdParagraph(self.paras(para))) # parameterlist elif item.tag == 'parameterlist': parameteritems = item.findall('parameteritem') lst = MdList([]) for parameteritem in parameteritems: name = parameteritem.find('parameternamelist').find( 'parametername') description = parameteritem.find( 'parameterdescription').findall('para') par = MdParagraph([]) if len(name) > 0: par.extend(self.paras(name)) else: par.append(Code(name.text)) par.append(Text(' ')) for ip in description: par.extend(self.paras(ip)) lst.append(par) ret.append(Br()) ret.append(MdBold([Text(SIMPLE_SECTIONS[item.get('kind')])])) ret.append(Br()) ret.append(lst) # simplesect elif item.tag == 'simplesect': kind = item.get('kind') if self.hints and self.target == 'vuepress' and kind in SIMPLE_SECTIONS_HINTS_VUEPRESS: ret.append(Br()) children = [] for sp in item.findall('para'): children.extend(self.paras(sp)) children.append(Br()) ret.append( MdHint(children, SIMPLE_SECTIONS_HINTS_VUEPRESS[kind], SIMPLE_SECTIONS[kind])) else: ret.append(Br()) ret.append(MdBold([Text(SIMPLE_SECTIONS[kind])])) if kind != 'see': ret.append(Br()) else: ret.append(Text(' ')) for sp, has_more in lookahead(item.findall('para')): ret.extend(self.paras(sp)) if kind == 'see': if has_more: ret.append(Text(', ')) else: ret.append(Br()) # xrefsect elif item.tag == 'xrefsect': xreftitle = item.find('xreftitle') xrefdescription = item.find('xrefdescription') kind = xreftitle.text.lower() if self.hints and self.target == 'vuepress' and kind in SIMPLE_SECTIONS_HINTS_VUEPRESS: children = [] for sp in xrefdescription.findall('para'): children.extend(self.paras(sp)) children.append(Br()) ret.append( MdHint(children, SIMPLE_SECTIONS_HINTS_VUEPRESS[kind], SIMPLE_SECTIONS[kind])) else: ret.append(Br()) ret.append(MdBold(self.paras(xreftitle))) ret.append(Br()) for sp in xrefdescription.findall('para'): ret.extend(self.paras(sp)) ret.append(Br()) # Hard link elif item.tag == 'ulink': ret.append(MdLink(self.paras(item), item.get('url'))) # Bold elif item.tag == 'bold': ret.append(MdBold(self.paras(item))) # Emphasis elif item.tag == 'emphasis': ret.append(MdItalic(self.paras(item))) # End of the item text if item.tail: if italic: ret.append(Text(' ')) ret.append(MdItalic([Text(item.tail.strip())])) else: ret.append(Text(item.tail)) return ret
def generateBriefRow(memberdef: xml.etree.ElementTree.Element, cache: Cache, reimplemented: List[str], ignore: List[str]) -> list: typ = MdTableCell([]) refid = memberdef.get('id') if refid in ignore: raise Exception('ignored') name = MdTableCell([ MdLink([MdBold([Text(memberdef.find('name').text)])], refid[:-35] + '.md#' + refid[-34:]) ]) kind = memberdef.get('kind') if kind == 'enum': typ.append(Text('enum')) name.append(Text(' { ')) isFirst = True for enumvalue in memberdef.findall('enumvalue'): if not isFirst: name.append(Text(', ')) isFirst = False name.append(MdBold([Text(enumvalue.find('name').text)])) initializer = enumvalue.find('initializer') if initializer is not None: name.append(Text(' ' + initializer.text)) name.append(Text(' } ')) else: if memberdef.get('static') == 'yes': typ.append(Text('static ')) virt = memberdef.get('virt') if virt == 'virtual' or virt == 'pure-virtual': typ.append(Text('virtual ')) if kind == 'typedef': typ.append(Text('typedef ')) typ.extend(convertXmlPara(memberdef.find('type'), cache)) if kind == 'function': name.append(Text(' (')) params = memberdef.findall('param') argsstring = memberdef.find('argsstring').text reimplements = memberdef.find('reimplements') if reimplements is not None: reimplemented.append(reimplements.get('refid')) isFirst = True for param in params: if not isFirst: name.append(Text(', ')) isFirst = False name.extend(convertXmlPara(param.find('type'), cache)) n = param.find('declname') if n is not None: name.append(Text(' ' + n.text)) d = param.find('defval') if d is not None: name.append(Text(' = ')) name.extend(convertXmlPara(d, cache)) name.append(Text(') ')) # Is deleted? if re.search('\\)\\s*=\\s*delete', argsstring): name.append(Text('= delete ')) # Is default? if re.search('\\)\\s*=\\s*default', argsstring): name.append(Text('= default ')) # Is noexcept if re.search('\\).*noexcept', argsstring): name.append(Text('noexcept ')) # Is override if re.search('\\).*override', argsstring): name.append(Text('override ')) # Is const? if memberdef.get('const') == 'yes': name.append(Text('const ')) # Is pure? if virt == 'pure-virtual': name.append(Text('= 0')) briefdescription = memberdef.find('briefdescription').findall('para') if len(briefdescription) > 0: name.append(Text('<br>')) for para in briefdescription: name.extend(convertXmlPara(para, cache)) return [typ, name]
def generateMember(indexDir: str, outputDir: str, refid: str, cache: Cache, noindex: bool): outputFile = os.path.join(outputDir, refid + '.md') print('Generating ' + outputFile) document = MdDocument() keywords = [] # Load XML xmlRoot = xml.etree.ElementTree.parse( os.path.join(indexDir, refid + '.xml')).getroot() if xmlRoot is None: IndexError('Root xml not found!') compounddef = xmlRoot.find('compounddef') if compounddef is None: IndexError('compounddef not found in xml!') compoundname = compounddef.find('compoundname').text keywords.append(compoundname) # Add title document.append( MdHeader(1, [Text(compounddef.get('kind') + ' ' + compoundname)])) if compounddef.get('kind') == 'file': document.append( MdParagraph([ MdBold([ MdLink([Text('Go to the source code of this file.')], refid + '_source.md') ]) ])) # Add brief description detaileddescriptionParas = compounddef.find('detaileddescription').findall( 'para') briefdescriptionParas = compounddef.find('briefdescription').findall( 'para') if len(briefdescriptionParas) > 0: p = MdParagraph([]) for para in briefdescriptionParas: p.extend(convertXmlPara(para, cache)) if len(detaileddescriptionParas) > 0: p.append(MdLink([Text('More...')], '#detailed-description')) document.append(p) # Add inheriance inheritanceRefids: List[str] = [] basecompoundrefs = compounddef.findall('basecompoundref') if len(basecompoundrefs) > 0: document.append(Br()) document.append(Text('Inherits the following classes: ')) isFirst = True for basecompoundref in basecompoundrefs: refid = basecompoundref.get('refid') if not isFirst: document.append(Text(', ')) isFirst = False if refid is not None: document.append( MdBold([ MdLink([Text(basecompoundref.text)], basecompoundref.get('refid') + '.md') ])) inheritanceRefids.append(basecompoundref.get('refid')) else: document.append(MdBold([Text(basecompoundref.text)])) document.append(Br()) # Add derivations derivedcompoundrefs = compounddef.findall('derivedcompoundref') if len(derivedcompoundrefs) > 0: document.append(Br()) document.append(Text('Inherited by the following classes: ')) isFirst = True for derivedcompoundref in derivedcompoundrefs: refid = derivedcompoundref.get('refid') if not isFirst: document.append(Text(', ')) isFirst = False if refid is not None: document.append( MdBold([ MdLink([Text(derivedcompoundref.text)], derivedcompoundref.get('refid') + '.md') ])) else: document.append(MdBold([Text(derivedcompoundref.text)])) document.append(Br()) # Find all inherited classes inheritanceCompounddefs: List[xml.etree.ElementTree.Element] = [] findInheritedClassesRecursively(inheritanceCompounddefs, indexDir, inheritanceRefids) #for refid in inheritanceRefids: # inheritanceCompounddefs.append(xml.etree.ElementTree.parse(os.path.join(indexDir, refid + '.xml')).getroot().find('compounddef')) # Add inner classes innerclasses = compounddef.findall('innerclass') if len(innerclasses) > 0: document.append(MdHeader(2, [Text('Classes')])) table = MdTable() header = MdTableRow([Text('Type'), Text('Name')]) table.append(header) for innerclass in innerclasses: typ = 'class' refid = innerclass.get('refid') if refid.startswith('struct'): typ = 'struct' if innerclass.text.startswith(compoundname): name = innerclass.text[len(compoundname) + 2:] else: name = innerclass.text keywords.append(name) row = MdTableRow( [Text(typ), MdLink([MdBold([Text(name)])], refid + '.md')]) table.append(row) document.append(table) # We will record which sections to skip skipSections = {} # We will also record which functions have been overwritten reimplemented = [] # Add sections sectiondefs = compounddef.findall('sectiondef') for sectiondef in sectiondefs: sectionKind = sectiondef.get('kind') if sectionKind.startswith('private'): continue document.append(MdHeader(2, [Text(SECTION_DEFS[sectionKind])])) table = makeSection(sectiondef, cache, reimplemented, []) document.append(table) for memberdef in sectiondef.findall('memberdef'): name = memberdef.find('name') if name is not None and name.text is not None: keywords.append(name.text) # Find inherited stuff for inheritanceCompounddef in inheritanceCompounddefs: inheritedSectiondefs = inheritanceCompounddef.findall('sectiondef') refid = inheritanceCompounddef.get('id') for sec in inheritedSectiondefs: if sec.get('kind') == sectionKind: inheritedName = inheritanceCompounddef.find( 'compoundname').text tmp = [] table = makeSection(sec, cache, tmp, reimplemented) if table is not None: document.append( MdHeader(4, [ Text(SECTION_DEFS[sectionKind] + ' inherited from '), MdLink([Text(inheritedName)], refid + '.md') ])) document.append(table) reimplemented.extend(tmp) for memberdef in sec.findall('memberdef'): name = memberdef.find('name') if name is not None and name.text is not None: keywords.append(name.text) if not refid in skipSections: skipSections[refid] = [sectionKind] else: skipSections[refid].append(sectionKind) missingSections = {} # Calculate if we need to create "Additional Inherited Members" section for inheritanceCompounddef in inheritanceCompounddefs: refid = inheritanceCompounddef.get('id') inheritedSectiondefs = inheritanceCompounddef.findall('sectiondef') for sec in inheritedSectiondefs: sectionKind = sec.get('kind') if sectionKind.startswith('private'): continue if refid in skipSections: if not sectionKind in skipSections[refid]: if not refid in missingSections: missingSections[refid] = [sectionKind] else: missingSections[refid].append(sectionKind) else: if not refid in missingSections: missingSections[refid] = [sectionKind] else: missingSections[refid].append(sectionKind) if missingSections: document.append(MdHeader(2, [Text('Additional Inherited Members')])) for inheritanceCompounddef in inheritanceCompounddefs: refid = inheritanceCompounddef.get('id') if refid in missingSections: inheritedSectiondefs = inheritanceCompounddef.findall( 'sectiondef') for sec in inheritedSectiondefs: sectionKind = sec.get('kind') if sectionKind.startswith('private'): continue if sectionKind in missingSections[refid]: inheritedName = inheritanceCompounddef.find( 'compoundname').text tmp = [] table = makeSection(sec, cache, tmp, reimplemented) if table is not None: document.append( MdHeader(4, [ Text(SECTION_DEFS[sectionKind] + ' inherited from '), MdLink([Text(inheritedName)], refid + '.md') ])) document.append(table) reimplemented.extend(tmp) # Add detailed description if len(detaileddescriptionParas) > 0: document.append(MdHeader(2, [Text('Detailed Description')])) document.extend( generateParagraph( compounddef.find('detaileddescription').findall('para'), cache)) # Add detailed sections sectiondefs = compounddef.findall('sectiondef') for sectiondef in sectiondefs: sectionKind = sectiondef.get('kind') if sectionKind.startswith('private'): continue document.append( MdHeader(2, [Text(SECTION_DEFS[sectionKind] + ' Documentation')])) for memberdef in sectiondef.findall('memberdef'): kind = memberdef.get('kind') document.append( MdHeader(3, [ Text(kind + ' <a id=\"' + memberdef.get('id')[-34:] + '\" href=\"#' + memberdef.get('id')[-34:] + '\">' + memberdef.find('name').text + '</a>') ])) code = [] if kind == 'function': code.extend(makeFunctionCode(compoundname, memberdef, False)) elif kind == 'friend': argsstring = memberdef.find('argsstring') if argsstring is not None and argsstring.text is not None and len( argsstring.text) > 0: code.extend(makeFunctionCode(compoundname, memberdef, True)) else: code.append(memberdef.find('definition').text + ';') elif kind == 'enum': code.append('enum ' + compoundname + '::' + memberdef.find('name').text + ' {') for enumvalue in memberdef.findall('enumvalue'): value = enumvalue.find('name').text initializer = enumvalue.find('initializer') if initializer is not None: value += ' ' + initializer.text code.append(' ' + value + ',') code.append('};') else: definition = memberdef.find('definition') if definition is None: code.append( memberdef.get('kind') + ' ' + memberdef.find('name').text + ';') else: code.append(definition.text + ';') document.append(MdCodeBlock(code)) # Add overrides reimplements = memberdef.find('reimplements') if reimplements is not None: try: found = cache.get(reimplements.get('refid')) document.append( MdParagraph([ Text('Overrides '), MdBold([ MdLink([Text(found.getFullName())], found.url) ]) ])) except: pass # Add descriptions detaileddescriptionParas = memberdef.find( 'detaileddescription').findall('para') briefdescriptionParas = memberdef.find('briefdescription').findall( 'para') document.extend(generateParagraph(briefdescriptionParas, cache)) document.append(Text('\n')) document.extend(generateParagraph(detaileddescriptionParas, cache)) document.append(Text('\n')) # Add location location = compounddef.find('location') if location is not None: document.append(Text('\n')) document.append(MdLine()) document.append( MdParagraph([ Text( 'The documentation for this class was generated from the following file: ' ), MdCode([Text(location.get('file'))]) ])) # Save if not noindex: document.setKeywords(keywords) with open(outputFile, 'w+') as f: document.render(MdRenderer(f))
def convertXmlPara(p: xml.etree.ElementTree.Element, cache: Cache) -> list: ret = [] if p is None: return ret if p.text: ret.append(Text(p.text)) for item in p.getchildren(): # para if item.tag == 'para': ret.append(MdParagraph(convertXmlPara(item, cache))) ret.append(Text('\n')) # image elif item.tag == 'image': url = item.get('name') ret.append(MdImage(url)) # computeroutput elif item.tag == 'computeroutput': ret.append(MdCode([Text(item.text)])) # programlisting elif item.tag == 'programlisting': gotLang = False code = MdCodeBlock([]) for codeline in item.findall('codeline'): line = '' for highlight in codeline.findall('highlight'): if not gotLang and len( highlight.getchildren() ) == 0 and highlight.text is not None and highlight.text.startswith( '{') and highlight.text.endswith('}'): lang = highlight.text[1:-1] code.setLang(lang) gotLang = True continue else: if highlight.text is not None: line += highlight.text for c in highlight.getchildren(): if c.tag == 'sp': line += ' ' if c.text: line += c.text if c.tail: line += c.tail code.append(line) ret.append(Text('\n')) ret.append(code) # table elif item.tag == 'table': t = MdTable() for row in item.findall('row'): r = MdTableRow([]) for cell in row.findall('entry'): for para in cell.findall('para'): r.append(MdTableCell(convertXmlPara(para, cache))) t.append(r) ret.append(t) # blockquote elif item.tag == 'blockquote': b = MdBlockQuote([]) for para in item.findall('para'): b.extend(convertXmlPara(para, cache)) ret.append(b) # heading elif item.tag == 'heading': ret.append( MdHeader(int(item.get('level')), convertXmlPara(item, cache))) # orderedlist elif item.tag == 'orderedlist' or item.tag == 'itemizedlist': lst = MdList([]) for listitem in item.findall('listitem'): i = MdParagraph([]) for para in listitem.findall('para'): i.extend(convertXmlPara(para, cache)) lst.append(i) ret.append(lst) # Reference elif item.tag == 'ref': refid = item.get('refid') try: ref = cache.get(refid) if item.text: ret.append(MdBold([MdLink([Text(item.text)], ref.url)])) else: ret.append( MdBold([MdLink([Text(ref.getFullName())], ref.url)])) except: pass # sect1: elif item.tag == 'sect1': title = item.find('title').text ret.append(MdHeader(2, [Text(title)])) ret.extend(convertXmlPara(item, cache)) # sect2: elif item.tag == 'sect2': title = item.find('title').text ret.append(MdHeader(3, [Text(title)])) ret.extend(convertXmlPara(item, cache)) # variablelist elif item.tag == 'variablelist': varlistentry = item.find('varlistentry') ret.append( MdHeader(4, convertXmlPara(varlistentry.find('term'), cache))) term = varlistentry.find('term') for listitem in item.findall('listitem'): for para in listitem.findall('para'): ret.append(MdParagraph(convertXmlPara(para, cache))) # parameterlist elif item.tag == 'parameterlist': parameteritems = item.findall('parameteritem') lst = MdList([]) for parameteritem in parameteritems: name = parameteritem.find('parameternamelist').find( 'parametername') description = parameteritem.find( 'parameterdescription').findall('para') par = MdParagraph([]) par.append(MdItalic(convertXmlPara(name, cache))) par.append(Text(' ')) for ip in description: par.extend(convertXmlPara(ip, cache)) lst.append(par) ret.append(Br()) ret.append(MdBold([Text(SIMPLE_SECTIONS[item.get('kind')])])) ret.append(Br()) ret.append(lst) # simplesect elif item.tag == 'simplesect': ret.append(Br()) ret.append(MdBold([Text(SIMPLE_SECTIONS[item.get('kind')])])) ret.append(Br()) for sp in item.findall('para'): ret.extend(convertXmlPara(sp, cache)) ret.append(Br()) # xrefsect elif item.tag == 'xrefsect': xreftitle = item.find('xreftitle') xrefdescription = item.find('xrefdescription') ret.append(Br()) ret.append(MdBold(convertXmlPara(xreftitle, cache))) ret.append(Br()) for sp in xrefdescription.findall('para'): ret.extend(convertXmlPara(sp, cache)) ret.append(Br()) # Hard link elif item.tag == 'ulink': ret.append(MdLink(convertXmlPara(item, cache), item.get('url'))) # Bold elif item.tag == 'bold': ret.append(MdBold(convertXmlPara(item, cache))) # Emphasis elif item.tag == 'emphasis': ret.append(MdItalic(convertXmlPara(item, cache))) # End of the item text if item.tail: ret.append(Text(item.tail)) return ret
def generate_member(index_path: str, output_path: str, refid: str, cache: Cache): output_file = os.path.join(output_path, refid + '.md') print('Generating ' + output_file) document = MdDocument() keywords = [] node = cache.get(refid) # Load XML xml_root = xml.etree.ElementTree.parse(os.path.join(index_path, refid + '.xml')).getroot() if xml_root is None: IndexError('Root xml not found!') compounddef = xml_root.find('compounddef') if compounddef is None: IndexError('compounddef not found in xml!') compoundname = compounddef.find('compoundname').text keywords.append(compoundname) # Add title title = compounddef.get('kind') + ' ' + compoundname document.append(MdHeader(1, [Text(title)])) if node.kind.is_parent(): document.append(generate_breadcrubs(node)) if compounddef.get('kind') == 'file': document.append(MdParagraph([MdBold([MdLink([Text('Go to the source code of this file.')], refid + '_source.md')])])) # Add brief description detaileddescription_paras = compounddef.find('detaileddescription').findall('para') briefdescription_paras = compounddef.find('briefdescription').findall('para') if len(briefdescription_paras) > 0: p = MdParagraph([]) for para in briefdescription_paras: p.extend(convert_xml_para(para, cache)) if len(detaileddescription_paras) > 0: p.append(MdLink([Text('More...')], '#detailed-description')) document.append(p) # Add inheriance inheritance_refids:List[str] = [] basecompoundrefs = compounddef.findall('basecompoundref') if len(basecompoundrefs) > 0: document.append(Br()) document.append(Text('Inherits the following classes: ')) is_first = True for basecompoundref in basecompoundrefs: refid = basecompoundref.get('refid') if not is_first: document.append(Text(', ')) is_first = False if refid is not None: document.append(MdBold([MdLink([Text(basecompoundref.text)], basecompoundref.get('refid') + '.md')])) inheritance_refids.append(basecompoundref.get('refid')) else: document.append(MdBold([Text(basecompoundref.text)])) document.append(Br()) # Add derivations derivedcompoundrefs = compounddef.findall('derivedcompoundref') if len(derivedcompoundrefs) > 0: document.append(Br()) document.append(Text('Inherited by the following classes: ')) is_first = True for derivedcompoundref in derivedcompoundrefs: refid = derivedcompoundref.get('refid') if not is_first: document.append(Text(', ')) is_first = False if refid is not None: document.append(MdBold([MdLink([Text(derivedcompoundref.text)], derivedcompoundref.get('refid') + '.md')])) else: document.append(MdBold([Text(derivedcompoundref.text)])) document.append(Br()) # Find all inherited classes inheritance_compounddefs:List[xml.etree.ElementTree.Element] = [] find_inherited_classes_recursively(inheritance_compounddefs, index_path, inheritance_refids) # Add inner groups innergroups = compounddef.findall('innergroup') if len(innergroups) > 0: document.append(MdHeader(2, [Text('Modules')])) lst = MdList([]) for innergroup in innergroups: refid = innergroup.get('refid') innergroup_root = xml.etree.ElementTree.parse(os.path.join(index_path, refid + '.xml')).getroot() compounddef = innergroup_root.find('compounddef') name = compounddef.find('title').text briefdescription_paras = compounddef.find('briefdescription').findall('para') link = MdLink([MdBold([Text(name)])], refid + '.md') link_with_brief = MdParagraph([link, Text(' ')]) link_with_brief.extend(generate_paragraph(briefdescription_paras, cache)) lst.append(link_with_brief) document.append(lst) document.append(Br()) # Add inner classes innerclasses = compounddef.findall('innerclass') if len(innerclasses) > 0: document.append(MdHeader(2, [Text('Classes')])) table = MdTable() header = MdTableRow([ Text('Type'), Text('Name') ]) table.append(header) for innerclass in innerclasses: typ = 'class' refid = innerclass.get('refid') if refid.startswith('struct'): typ = 'struct' if innerclass.text.startswith(compoundname): name = innerclass.text[len(compoundname)+2:] else: name = innerclass.text keywords.append(name) row = MdTableRow([ Text(typ), MdLink([MdBold([Text(name)])], refid + '.md') ]) table.append(row) document.append(table) # We will record which sections to skip skip_sections = {} # We will also record which functions have been overwritten reimplemented = [] # Add sections sectiondefs = compounddef.findall('sectiondef') for sectiondef in sectiondefs: section_kind = sectiondef.get('kind') if section_kind.startswith('private'): continue # Seems to work incorrectly, would print an empty "Functions" section, and then a populated "Functions Documentation" section below it. Only useful for classes. if section_kind not in "func" and section_kind not in "typedef": document.append(MdHeader(2, [Text(SECTION_DEFS[section_kind])])) table = make_section(sectiondef, cache, reimplemented, []) document.append(table) for memberdef in sectiondef.findall('memberdef'): name = memberdef.find('name') if name is not None and name.text is not None: keywords.append(name.text) # Find inherited stuff for inheritance_compounddefs in inheritance_compounddefs: inherited_sectiondefs = inheritance_compounddefs.findall('sectiondef') refid = inheritance_compounddefs.get('id') for sec in inherited_sectiondefs: if sec.get('kind') == skip_sections: inherited_name = inheritance_compounddefs.find('compoundname').text tmp = [] table = make_section(sec, cache, tmp, reimplemented) if table is not None: document.append(MdHeader(4, [Text(SECTION_DEFS[skip_sections] + ' inherited from '), MdLink([Text(inherited_name)], refid + '.md')])) document.append(table) reimplemented.extend(tmp) for memberdef in sec.findall('memberdef'): name = memberdef.find('name') if name is not None and name.text is not None: keywords.append(name.text) if not refid in skip_sections: skip_sections[refid] = [skip_sections] else: skip_sections[refid].append(skip_sections) missing_sections = {} # Calculate if we need to create "Additional Inherited Members" section for inheritance_compounddef in inheritance_compounddefs: refid = inheritance_compounddef.get('id') inherited_sectiondefs = inheritance_compounddef.findall('sectiondef') for sec in inherited_sectiondefs: section_kind = sec.get('kind') if section_kind.startswith('private'): continue if refid in skip_sections: if not section_kind in skip_sections[refid]: if not refid in missing_sections: missing_sections[refid] = [section_kind] else: missing_sections[refid].append(section_kind) else: if not refid in missing_sections: missing_sections[refid] = [section_kind] else: missing_sections[refid].append(section_kind) if missing_sections: document.append(MdHeader(2, [Text('Additional Inherited Members')])) for inheritance_compounddef in inheritance_compounddefs: refid = inheritance_compounddef.get('id') if refid in missing_sections: inherited_sectiondefs = inheritance_compounddef.findall('sectiondef') for sec in inherited_sectiondefs: section_kind = sec.get('kind') if section_kind.startswith('private'): continue if section_kind in missing_sections[refid]: inherited_name = inheritance_compounddef.find('compoundname').text tmp = [] table = make_section(sec, cache, tmp, reimplemented) if table is not None: document.append(MdHeader(4, [Text(SECTION_DEFS[section_kind] + ' inherited from '), MdLink([Text(inherited_name)], refid + '.md')])) document.append(table) reimplemented.extend(tmp) # Add detailed description if len(detaileddescription_paras) > 0: document.append(MdHeader(2, [Text('Detailed Description')])) document.extend(generate_paragraph(compounddef.find('detaileddescription').findall('para'), cache)) # Add detailed sections sectiondefs = compounddef.findall('sectiondef') for sectiondef in sectiondefs: section_kind = sectiondef.get('kind') if section_kind.startswith('private'): continue document.append(MdHeader(2, [Text(SECTION_DEFS[section_kind] + ' Documentation')])) memberdefs = sectiondef.findall('memberdef') for memberdef in memberdefs: kind = memberdef.get('kind') refid = memberdef.get('id') node = None try: node = cache.get(refid) except: pass name = memberdef.find('name').text if config.target == 'gitbook': if node is not None and node.overloaded: document.append(MdHeader(3, [Text(kind + ' <a id=\"' + refid[-34:] + '\" href=\"#' + refid[-34:] + '\">' + name + ' (' + str(node.overload_num) + '/' + str(node.overload_total) + ')</a>')])) else: document.append(MdHeader(3, [Text(kind + ' <a id=\"' + refid[-34:] + '\" href=\"#' + refid[-34:] + '\">' + name + '</a>')])) else: if node is not None and node.overloaded: document.append(MdHeader(3, [Text(kind + ' ' + name + ' (' + str(node.overload_num) + '/' + str(node.overload_total) + ')')])) else: document.append(MdHeader(3, [Text(kind + ' ' + name)])) code = [] if kind == 'function': code.extend(make_function_code(compoundname, memberdef, False)) elif kind == 'friend': argsstring = memberdef.find('argsstring') if argsstring is not None and argsstring.text is not None and len(argsstring.text) > 0: code.extend(make_function_code(compoundname, memberdef, True)) else: code.append(memberdef.find('definition').text + ';') elif kind == 'enum': code.append('enum ' + compoundname + '::' + memberdef.find('name').text + ' {') for enumvalue in memberdef.findall('enumvalue'): value = enumvalue.find('name').text initializer = enumvalue.find('initializer') if initializer is not None: value += ' ' + initializer.text code.append(' ' + value + ',') code.append('};') else: definition = memberdef.find('definition') if definition is None: code.append(memberdef.get('kind') + ' ' + memberdef.find('name').text + ';') else: code.append(definition.text + ';') document.append(MdCodeBlock(code)) # Add descriptions detaileddescription_paras = memberdef.find('detaileddescription').findall('para') briefdescription_paras = memberdef.find('briefdescription').findall('para') document.extend(generate_paragraph(briefdescription_paras, cache)) document.append(Text('\n')) document.extend(generate_paragraph(detaileddescription_paras, cache)) document.append(Text('\n')) # Add overrides reimplements = memberdef.find('reimplements') if reimplements is not None: try: found = cache.get(reimplements.get('refid')) document.append(MdParagraph([Text('Implements '), MdBold([MdLink([Text(found.get_full_name())], found.url)])])) document.append(Br()) except: pass # Add location location = compounddef.find('location') if location is not None: document.append(Text('\n')) document.append(MdLine()) document.append(MdParagraph([ Text('The documentation for this class was generated from the following file: '), MdCode([Text(location.get('file'))]) ])) # Save if not config.noindex: document.set_keywords(keywords) document.set_title(title) with open(output_file, 'w+') as f: document.render(MdRenderer(f))
def generate(path: str, root: Node, kind: Kind, filename: str, title: str, subtitle: str): output_file = os.path.join(path, filename + '.md') print('Generating ' + output_file) document = MdDocument() keywords = [] # Add title document.append(MdHeader(1, [Text(title)])) document.append(MdParagraph([Text(subtitle)])) # Sort dictionary = {} recursive_dictionary(kind, root, dictionary) for key in list(sorted(dictionary.keys())): document.append(MdHeader(2, [Text(key)])) mdl = MdList([]) # Remove overloads and sort into columns of classes class_dictionary = {} for member in dictionary[key]: if member.name not in class_dictionary: class_dictionary[member.name] = [] if len(class_dictionary[member.name]) > 0: if class_dictionary[member.name][-1].parent == member.parent: continue class_dictionary[member.name].append(member) for dict_key in list(sorted(class_dictionary.keys())): p = MdParagraph([]) first = class_dictionary[dict_key][-1] full_name = first.get_full_name(False) keywords.append(full_name) p.append(MdBold([Text(first.name)])) p.append(Text(' (')) for member, has_next in lookahead(class_dictionary[dict_key]): parent = member.parent p.append( MdLink([MdBold([Text(parent.get_full_name(True))])], parent.url + '#' + member.get_anchor_hash())) if has_next: p.append(Text(', ')) p.append(Text(')')) mdl.append(p) document.append(mdl) document.append(Br()) if not config.noindex: document.set_keywords(keywords) document.set_title(title) # Save with open(output_file, 'w') as f: document.render(MdRenderer(f))