/****************************************************************************** * * * * Copyright (C) 1997-2015 by Dimitri van Heesch. * * Permission to use, copy, modify, and distribute this software and its * documentation under the terms of the GNU General Public License is hereby * granted. No representations are made about the suitability of this software * for any purpose. It is provided "as is" without express or implied warranty. * See the GNU General Public License for more details. * * Documents produced by Doxygen are derivative works derived from the * input used in their production; they are not affected by this license. * */ /** @file * @brief This file contains functions for the various index pages. */ #include #include #include #include #include #include #include "message.h" #include "index.h" #include "doxygen.h" #include "config.h" #include "filedef.h" #include "outputlist.h" #include "util.h" #include "groupdef.h" #include "language.h" #include "htmlgen.h" #include "htmlhelp.h" #include "ftvhelp.h" #include "dot.h" #include "dotgfxhierarchytable.h" #include "dotlegendgraph.h" #include "pagedef.h" #include "dirdef.h" #include "vhdldocgen.h" #include "layout.h" #include "memberlist.h" #include "classlist.h" #include "namespacedef.h" #include "filename.h" #include "tooltip.h" #define MAX_ITEMS_BEFORE_MULTIPAGE_INDEX 200 #define MAX_ITEMS_BEFORE_QUICK_INDEX 30 int annotatedClasses; int annotatedClassesPrinted; int hierarchyClasses; int annotatedInterfaces; int annotatedInterfacesPrinted; int hierarchyInterfaces; int annotatedStructs; int annotatedStructsPrinted; int annotatedExceptions; int annotatedExceptionsPrinted; int hierarchyExceptions; int documentedFiles; int documentedGroups; int documentedNamespaces; int indexedPages; int documentedClassMembers[CMHL_Total]; int documentedFileMembers[FMHL_Total]; int documentedNamespaceMembers[NMHL_Total]; int documentedHtmlFiles; int documentedPages; int documentedDirs; static int countClassHierarchy(ClassDef::CompoundType ct); static void countFiles(int &htmlFiles,int &files); static int countGroups(); static int countDirs(); static int countNamespaces(); static int countAnnotatedClasses(int *cp,ClassDef::CompoundType ct); static void countRelatedPages(int &docPages,int &indexPages); void countDataStructures() { static bool sliceOpt = Config_getBool(OPTIMIZE_OUTPUT_SLICE); annotatedClasses = countAnnotatedClasses(&annotatedClassesPrinted, ClassDef::Class); // "classes" + "annotated" hierarchyClasses = countClassHierarchy(ClassDef::Class); // "hierarchy" // "interfaces" + "annotated" annotatedInterfaces = sliceOpt ? countAnnotatedClasses(&annotatedInterfacesPrinted, ClassDef::Interface) : 0; // "interfacehierarchy" hierarchyInterfaces = sliceOpt ? countClassHierarchy(ClassDef::Interface) : 0; // "structs" + "annotated" annotatedStructs = sliceOpt ? countAnnotatedClasses(&annotatedStructsPrinted, ClassDef::Struct) : 0; // "exceptions" + "annotated" annotatedExceptions = sliceOpt ? countAnnotatedClasses(&annotatedExceptionsPrinted, ClassDef::Exception) : 0; // "exceptionhierarchy" hierarchyExceptions = sliceOpt ? countClassHierarchy(ClassDef::Exception) : 0; countFiles(documentedHtmlFiles,documentedFiles); // "files" countRelatedPages(documentedPages,indexedPages); // "pages" documentedGroups = countGroups(); // "modules" documentedNamespaces = countNamespaces(); // "namespaces" documentedDirs = countDirs(); // "dirs" // "globals" // "namespacemembers" // "functions" } static void startIndexHierarchy(OutputList &ol,int level) { ol.pushGeneratorState(); ol.disable(OutputGenerator::Man); ol.disable(OutputGenerator::Html); if (level<6) ol.startIndexList(); ol.popGeneratorState(); ol.pushGeneratorState(); ol.disable(OutputGenerator::Latex); ol.disable(OutputGenerator::RTF); ol.disable(OutputGenerator::Docbook); ol.startItemList(); ol.popGeneratorState(); } static void endIndexHierarchy(OutputList &ol,int level) { ol.pushGeneratorState(); ol.disable(OutputGenerator::Man); ol.disable(OutputGenerator::Html); if (level<6) ol.endIndexList(); ol.popGeneratorState(); ol.pushGeneratorState(); ol.disable(OutputGenerator::Latex); ol.disable(OutputGenerator::Docbook); ol.disable(OutputGenerator::RTF); ol.endItemList(); ol.popGeneratorState(); } //---------------------------------------------------------------------------- class MemberIndexList : public QList { public: typedef const MemberDef ElementType; MemberIndexList(uint letter) : QList(), m_letter(letter) {} ~MemberIndexList() {} int compareValues(const MemberDef *md1, const MemberDef *md2) const { int result = qstricmp(md1->name(),md2->name()); if (result==0) { result = qstricmp(md1->qualifiedName(),md2->qualifiedName()); } return result; } uint letter() const { return m_letter; } private: uint m_letter; }; static LetterToIndexMap g_memberIndexLetterUsed[CMHL_Total]; static LetterToIndexMap g_fileIndexLetterUsed[FMHL_Total]; static LetterToIndexMap g_namespaceIndexLetterUsed[NMHL_Total]; const int maxItemsBeforeQuickIndex = MAX_ITEMS_BEFORE_QUICK_INDEX; //---------------------------------------------------------------------------- //---------------------------------------------------------------------------- static void startQuickIndexList(OutputList &ol,bool letterTabs=FALSE) { if (letterTabs) { ol.writeString("
\n"); } else { ol.writeString("
\n"); } ol.writeString("
    \n"); } static void endQuickIndexList(OutputList &ol) { ol.writeString("
\n"); ol.writeString("
\n"); } static void startQuickIndexItem(OutputList &ol,const char *l, bool hl,bool compact,bool &first) { first=FALSE; ol.writeString(" "); ol.writeString(""); } static void endQuickIndexItem(OutputList &ol) { ol.writeString(""); ol.writeString(""); ol.writeString("\n"); } // don't make this static as it is called from a template function and some // old compilers don't support calls to static functions from a template. QCString fixSpaces(const QCString &s) { return substitute(s," "," "); } void startTitle(OutputList &ol,const char *fileName,const DefinitionMutable *def) { ol.startHeaderSection(); if (def) def->writeSummaryLinks(ol); ol.startTitleHead(fileName); ol.pushGeneratorState(); ol.disable(OutputGenerator::Man); } void endTitle(OutputList &ol,const char *fileName,const char *name) { ol.popGeneratorState(); ol.endTitleHead(fileName,name); ol.endHeaderSection(); } void startFile(OutputList &ol,const char *name,const char *manName, const char *title,HighlightedItem hli,bool additionalIndices, const char *altSidebarName) { static bool disableIndex = Config_getBool(DISABLE_INDEX); ol.startFile(name,manName,title); ol.startQuickIndices(); if (!disableIndex) { ol.writeQuickLinks(TRUE,hli,name); } if (!additionalIndices) { ol.endQuickIndices(); } ol.writeSplitBar(altSidebarName ? altSidebarName : name); ol.writeSearchInfo(); } void endFile(OutputList &ol,bool skipNavIndex,bool skipEndContents, const QCString &navPath) { static bool generateTreeView = Config_getBool(GENERATE_TREEVIEW); ol.pushGeneratorState(); ol.disableAllBut(OutputGenerator::Html); if (!skipNavIndex) { if (!skipEndContents) ol.endContents(); if (generateTreeView) { ol.writeString("
\n"); } } ol.writeFooter(navPath); // write the footer ol.popGeneratorState(); ol.endFile(); } void endFileWithNavPath(const Definition *d,OutputList &ol) { static bool generateTreeView = Config_getBool(GENERATE_TREEVIEW); QCString navPath; if (generateTreeView) { ol.pushGeneratorState(); ol.disableAllBut(OutputGenerator::Html); ol.writeString("\n"); ol.popGeneratorState(); navPath = d->navigationPathAsString(); } endFile(ol,generateTreeView,TRUE,navPath); } //---------------------------------------------------------------------- static bool memberVisibleInIndex(const MemberDef *md) { bool isAnonymous = md->isAnonymous(); bool hideUndocMembers = Config_getBool(HIDE_UNDOC_MEMBERS); bool extractStatic = Config_getBool(EXTRACT_STATIC); return (!isAnonymous && (!hideUndocMembers || md->hasDocumentation()) && (!md->isStatic() || extractStatic) ); } static void writeMemberToIndex(const Definition *def,const MemberDef *md,bool addToIndex) { bool isAnonymous = md->isAnonymous(); bool hideUndocMembers = Config_getBool(HIDE_UNDOC_MEMBERS); const MemberList *enumList = md->enumFieldList(); bool isDir = enumList!=0 && md->isEnumerate(); if (md->getOuterScope()==def || md->getOuterScope()==Doxygen::globalScope) { Doxygen::indexList->addContentsItem(isDir, md->name(),md->getReference(),md->getOutputFileBase(),md->anchor(),FALSE,addToIndex); } else // inherited member { Doxygen::indexList->addContentsItem(isDir, md->name(),def->getReference(),def->getOutputFileBase(),md->anchor(),FALSE,addToIndex); } if (isDir) { if (!isAnonymous) { Doxygen::indexList->incContentsDepth(); } MemberListIterator emli(*enumList); MemberDef *emd; for (emli.toFirst();(emd=emli.current());++emli) { if (!hideUndocMembers || emd->hasDocumentation()) { if (emd->getOuterScope()==def || emd->getOuterScope()==Doxygen::globalScope) { Doxygen::indexList->addContentsItem(FALSE, emd->name(),emd->getReference(),emd->getOutputFileBase(),emd->anchor(),FALSE,addToIndex); } else // inherited member { Doxygen::indexList->addContentsItem(FALSE, emd->name(),def->getReference(),def->getOutputFileBase(),emd->anchor(),FALSE,addToIndex); } } } if (!isAnonymous) { Doxygen::indexList->decContentsDepth(); } } } //---------------------------------------------------------------------- template void addMembersToIndex(T *def,LayoutDocManager::LayoutPart part, const QCString &name,const QCString &anchor, bool addToIndex=TRUE,bool preventSeparateIndex=FALSE) { bool hasMembers = def->getMemberLists().count()>0 || def->getMemberGroupSDict()!=0; Doxygen::indexList->addContentsItem(hasMembers,name, def->getReference(),def->getOutputFileBase(),anchor, hasMembers && !preventSeparateIndex, addToIndex, def); int numClasses=0; for (const auto &cd : def->getClasses()) { if (cd->isLinkable()) numClasses++; } //printf("addMembersToIndex(def=%s hasMembers=%d numClasses=%d)\n",def->name().data(),hasMembers,numClasses); if (hasMembers || numClasses>0) { Doxygen::indexList->incContentsDepth(); QListIterator eli(LayoutDocManager::instance().docEntries(part)); LayoutDocEntry *lde; for (eli.toFirst();(lde=eli.current());++eli) { if (lde->kind()==LayoutDocEntry::MemberDef) { LayoutDocEntryMemberDef *lmd = (LayoutDocEntryMemberDef*)lde; MemberList *ml = def->getMemberList(lmd->type); if (ml) { MemberListIterator mi(*ml); MemberDef *md; for (mi.toFirst();(md=mi.current());++mi) { if (memberVisibleInIndex(md)) { writeMemberToIndex(def,md,addToIndex); } } } } else if (lde->kind()==LayoutDocEntry::NamespaceClasses || lde->kind()==LayoutDocEntry::FileClasses || lde->kind()==LayoutDocEntry::ClassNestedClasses ) { for (const auto &cd : def->getClasses()) { if (cd->isLinkable() && (cd->partOfGroups()==0 || def->definitionType()==Definition::TypeGroup)) { static bool inlineSimpleStructs = Config_getBool(INLINE_SIMPLE_STRUCTS); bool isNestedClass = def->definitionType()==Definition::TypeClass; addMembersToIndex(cd,LayoutDocManager::Class,cd->displayName(FALSE),cd->anchor(), addToIndex && (isNestedClass || (cd->isSimple() && inlineSimpleStructs)), preventSeparateIndex || cd->isEmbeddedInOuterScope()); } } } } Doxygen::indexList->decContentsDepth(); } } //---------------------------------------------------------------------------- /*! Generates HTML Help tree of classes */ static void writeClassTreeToOutput(OutputList &ol,const BaseClassList &bcl,int level,FTVHelp* ftv,bool addToIndex,ClassDefSet &visitedClasses) { if (bcl.empty()) return; bool started=FALSE; for (const auto &bcd : bcl) { ClassDef *cd=bcd.classDef; if (cd->getLanguage()==SrcLangExt_VHDL && (VhdlDocGen::VhdlClasses)cd->protection()!=VhdlDocGen::ENTITYCLASS) { continue; } bool b; if (cd->getLanguage()==SrcLangExt_VHDL) { b=hasVisibleRoot(cd->subClasses()); } else { b=hasVisibleRoot(cd->baseClasses()); } if (cd->isVisibleInHierarchy() && b) // hasVisibleRoot(cd->baseClasses())) { if (!started) { startIndexHierarchy(ol,level); if (addToIndex) { Doxygen::indexList->incContentsDepth(); } if (ftv) { ftv->incContentsDepth(); } started=TRUE; } ol.startIndexListItem(); //printf("Passed...\n"); bool hasChildren = visitedClasses.find(cd)==visitedClasses.end() && classHasVisibleChildren(cd); //printf("tree4: Has children %s: %d\n",cd->name().data(),hasChildren); if (cd->isLinkable()) { //printf("Writing class %s\n",cd->displayName().data()); ol.startIndexItem(cd->getReference(),cd->getOutputFileBase()); ol.parseText(cd->displayName()); ol.endIndexItem(cd->getReference(),cd->getOutputFileBase()); if (cd->isReference()) { ol.startTypewriter(); ol.docify(" [external]"); ol.endTypewriter(); } if (addToIndex) { Doxygen::indexList->addContentsItem(hasChildren,cd->displayName(),cd->getReference(),cd->getOutputFileBase(),cd->anchor()); } if (ftv) { if (cd->getLanguage()==SrcLangExt_VHDL) { ftv->addContentsItem(hasChildren,bcd.usedName,cd->getReference(),cd->getOutputFileBase(),cd->anchor(),FALSE,FALSE,cd); } else { ftv->addContentsItem(hasChildren,cd->displayName(),cd->getReference(),cd->getOutputFileBase(),cd->anchor(),FALSE,FALSE,cd); } } } else { ol.startIndexItem(0,0); ol.parseText(cd->name()); ol.endIndexItem(0,0); if (addToIndex) { Doxygen::indexList->addContentsItem(hasChildren,cd->displayName(),0,0,0); } if (ftv) { ftv->addContentsItem(hasChildren,cd->displayName(),0,0,0,FALSE,FALSE,cd); } } if (hasChildren) { //printf("Class %s at %p visited=%d\n",cd->name().data(),cd,cd->visited); visitedClasses.insert(cd); if (cd->getLanguage()==SrcLangExt_VHDL) { writeClassTreeToOutput(ol,cd->baseClasses(),level+1,ftv,addToIndex,visitedClasses); } else { writeClassTreeToOutput(ol,cd->subClasses(),level+1,ftv,addToIndex,visitedClasses); } } ol.endIndexListItem(); } } if (started) { endIndexHierarchy(ol,level); if (addToIndex) { Doxygen::indexList->decContentsDepth(); } if (ftv) { ftv->decContentsDepth(); } } } //---------------------------------------------------------------------------- static bool dirHasVisibleChildren(DirDef *dd) { if (dd->hasDocumentation()) return TRUE; QListIterator fli(*dd->getFiles()); FileDef *fd; for (fli.toFirst();(fd=fli.current());++fli) { bool genSourceFile; if (fileVisibleInIndex(fd,genSourceFile)) { return TRUE; } if (genSourceFile) { return TRUE; } } for(const auto subdd : dd->subDirs()) { if (dirHasVisibleChildren(subdd)) { return TRUE; } } return FALSE; } //---------------------------------------------------------------------------- static void writeDirTreeNode(OutputList &ol, DirDef *dd, int level, FTVHelp* ftv,bool addToIndex) { if (level>20) { warn(dd->getDefFileName(),dd->getDefLine(), "maximum nesting level exceeded for directory %s: " "check for possible recursive directory relation!\n",dd->name().data() ); return; } if (!dirHasVisibleChildren(dd)) { return; } static bool tocExpand = TRUE; //Config_getBool(TOC_EXPAND); bool isDir = dd->subDirs().size()>0 || // there are subdirs (tocExpand && // or toc expand and dd->getFiles() && dd->getFiles()->count()>0 // there are files ); //printf("gd='%s': pageDict=%d\n",gd->name().data(),gd->pageDict->count()); if (addToIndex) { Doxygen::indexList->addContentsItem(isDir,dd->shortName(),dd->getReference(),dd->getOutputFileBase(),0,TRUE,TRUE); Doxygen::indexList->incContentsDepth(); } if (ftv) { ftv->addContentsItem(isDir,dd->shortName(),dd->getReference(), dd->getOutputFileBase(),0,FALSE,TRUE,dd); ftv->incContentsDepth(); } ol.startIndexListItem(); ol.startIndexItem(dd->getReference(),dd->getOutputFileBase()); ol.parseText(dd->shortName()); ol.endIndexItem(dd->getReference(),dd->getOutputFileBase()); if (dd->isReference()) { ol.startTypewriter(); ol.docify(" [external]"); ol.endTypewriter(); } // write sub directories if (dd->subDirs().size()>0) { startIndexHierarchy(ol,level+1); for(const auto subdd : dd->subDirs()) { writeDirTreeNode(ol,subdd,level+1,ftv,addToIndex); } endIndexHierarchy(ol,level+1); } FileList *fileList=dd->getFiles(); int fileCount=0; if (fileList && fileList->count()>0) { QListIterator it(*fileList); FileDef *fd; for (;(fd=it.current());++it) { //static bool allExternals = Config_getBool(ALLEXTERNALS); //if ((allExternals && fd->isLinkable()) || fd->isLinkableInProject()) //{ // fileCount++; //} bool genSourceFile; if (fileVisibleInIndex(fd,genSourceFile)) { fileCount++; } else if (genSourceFile) { fileCount++; } } if (fileCount>0) { startIndexHierarchy(ol,level+1); for (it.toFirst();(fd=it.current());++it) { bool doc,src; doc = fileVisibleInIndex(fd,src); QCString reference; QCString outputBase; if (doc) { reference = fd->getReference(); outputBase = fd->getOutputFileBase(); } if (doc || src) { ol.startIndexListItem(); ol.startIndexItem(reference,outputBase); ol.parseText(fd->displayName()); ol.endIndexItem(reference,outputBase); ol.endIndexListItem(); if (ftv && (src || doc)) { ftv->addContentsItem(FALSE, fd->displayName(), reference,outputBase, 0,FALSE,FALSE,fd); } } } endIndexHierarchy(ol,level+1); } } if (tocExpand && addToIndex) { // write files of this directory if (fileCount>0) { QListIterator it(*fileList); FileDef *fd; for (;(fd=it.current());++it) { //static bool allExternals = Config_getBool(ALLEXTERNALS); //if ((allExternals && fd->isLinkable()) || fd->isLinkableInProject()) bool doc,src; doc = fileVisibleInIndex(fd,src); if (doc) { addMembersToIndex(fd,LayoutDocManager::File,fd->displayName(),QCString(),TRUE); } else if (src) { Doxygen::indexList->addContentsItem( FALSE, fd->name(), 0, fd->getSourceFileBase(), 0, FALSE, TRUE, fd); } } } } ol.endIndexListItem(); if (addToIndex) { Doxygen::indexList->decContentsDepth(); } if (ftv) { ftv->decContentsDepth(); } } static void writeDirHierarchy(OutputList &ol, FTVHelp* ftv,bool addToIndex) { if (ftv) { ol.pushGeneratorState(); ol.disable(OutputGenerator::Html); } bool fullPathNames = Config_getBool(FULL_PATH_NAMES); startIndexHierarchy(ol,0); if (fullPathNames) { SDict::Iterator dli(*Doxygen::directories); DirDef *dd; for (dli.toFirst();(dd=dli.current());++dli) { if (dd->getOuterScope()==Doxygen::globalScope) { writeDirTreeNode(ol,dd,0,ftv,addToIndex); } } } if (ftv) { for (const auto &fn : *Doxygen::inputNameLinkedMap) { for (const auto &fd : *fn) { if (!fullPathNames || fd->getDirDef()==0) // top level file { bool src; bool doc = fileVisibleInIndex(fd.get(),src); QCString reference, outputBase; if (doc) { reference = fd->getReference(); outputBase = fd->getOutputFileBase(); } if (doc || src) { ftv->addContentsItem(FALSE,fd->displayName(), reference, outputBase, 0, FALSE,FALSE,fd.get()); } if (addToIndex) { if (doc) { addMembersToIndex(fd.get(),LayoutDocManager::File,fd->displayName(),QCString(),TRUE); } else if (src) { Doxygen::indexList->addContentsItem( FALSE, fd->name(), 0, fd->getSourceFileBase(), 0, FALSE, TRUE, fd.get()); } } } } } } endIndexHierarchy(ol,0); if (ftv) { ol.popGeneratorState(); } } //---------------------------------------------------------------------------- static void writeClassTreeForList(OutputList &ol,const ClassLinkedMap &cl,bool &started,FTVHelp* ftv,bool addToIndex, ClassDef::CompoundType ct,ClassDefSet &visitedClasses) { static bool sliceOpt = Config_getBool(OPTIMIZE_OUTPUT_SLICE); for (const auto &cd : cl) { //printf("class %s hasVisibleRoot=%d isVisibleInHierarchy=%d\n", // cd->name().data(), // hasVisibleRoot(cd->baseClasses()), // cd->isVisibleInHierarchy() // ); bool b; if (cd->getLanguage()==SrcLangExt_VHDL) { if ((VhdlDocGen::VhdlClasses)cd->protection()!=VhdlDocGen::ENTITYCLASS) { continue; } b=!hasVisibleRoot(cd->subClasses()); } else if (sliceOpt && cd->compoundType() != ct) { continue; } else { b=!hasVisibleRoot(cd->baseClasses()); } if (b) //filter on root classes { if (cd->isVisibleInHierarchy()) // should it be visible { if (!started) { startIndexHierarchy(ol,0); if (addToIndex) { Doxygen::indexList->incContentsDepth(); } started=TRUE; } ol.startIndexListItem(); bool hasChildren = visitedClasses.find(cd.get())==visitedClasses.end() && classHasVisibleChildren(cd.get()); //printf("list: Has children %s: %d\n",cd->name().data(),hasChildren); if (cd->isLinkable()) { //printf("Writing class %s isLinkable()=%d isLinkableInProject()=%d cd->templateMaster()=%p\n", // cd->displayName().data(),cd->isLinkable(),cd->isLinkableInProject(),cd->templateMaster()); ol.startIndexItem(cd->getReference(),cd->getOutputFileBase()); ol.parseText(cd->displayName()); ol.endIndexItem(cd->getReference(),cd->getOutputFileBase()); if (cd->isReference()) { ol.startTypewriter(); ol.docify(" [external]"); ol.endTypewriter(); } if (addToIndex) { if (cd->getLanguage()!=SrcLangExt_VHDL) // prevents double insertion in Design Unit List Doxygen::indexList->addContentsItem(hasChildren,cd->displayName(),cd->getReference(),cd->getOutputFileBase(),cd->anchor(),FALSE,FALSE); } if (ftv) { ftv->addContentsItem(hasChildren,cd->displayName(),cd->getReference(),cd->getOutputFileBase(),cd->anchor(),FALSE,FALSE,cd.get()); } } else { ol.startIndexItem(0,0); ol.parseText(cd->displayName()); ol.endIndexItem(0,0); if (addToIndex) { Doxygen::indexList->addContentsItem(hasChildren,cd->displayName(),0,0,0,FALSE,FALSE); } if (ftv) { ftv->addContentsItem(hasChildren,cd->displayName(),0,0,0,FALSE,FALSE,cd.get()); } } if (cd->getLanguage()==SrcLangExt_VHDL && hasChildren) { writeClassTreeToOutput(ol,cd->baseClasses(),1,ftv,addToIndex,visitedClasses); visitedClasses.insert(cd.get()); } else if (hasChildren) { writeClassTreeToOutput(ol,cd->subClasses(),1,ftv,addToIndex,visitedClasses); visitedClasses.insert(cd.get()); } ol.endIndexListItem(); } } } } static void writeClassHierarchy(OutputList &ol, FTVHelp* ftv,bool addToIndex,ClassDef::CompoundType ct) { ClassDefSet visitedClasses; if (ftv) { ol.pushGeneratorState(); ol.disable(OutputGenerator::Html); } bool started=FALSE; writeClassTreeForList(ol,*Doxygen::classLinkedMap,started,ftv,addToIndex,ct,visitedClasses); writeClassTreeForList(ol,*Doxygen::hiddenClassLinkedMap,started,ftv,addToIndex,ct,visitedClasses); if (started) { endIndexHierarchy(ol,0); if (addToIndex) { Doxygen::indexList->decContentsDepth(); } } if (ftv) { ol.popGeneratorState(); } } //---------------------------------------------------------------------------- static int countClassesInTreeList(const ClassLinkedMap &cl, ClassDef::CompoundType ct) { static bool sliceOpt = Config_getBool(OPTIMIZE_OUTPUT_SLICE); int count=0; for (const auto &cd : cl) { if (sliceOpt && cd->compoundType() != ct) { continue; } if (!hasVisibleRoot(cd->baseClasses())) // filter on root classes { if (cd->isVisibleInHierarchy()) // should it be visible { if (!cd->subClasses().empty()) // should have sub classes { count++; } } } } return count; } static int countClassHierarchy(ClassDef::CompoundType ct) { int count=0; count+=countClassesInTreeList(*Doxygen::classLinkedMap, ct); count+=countClassesInTreeList(*Doxygen::hiddenClassLinkedMap, ct); return count; } //---------------------------------------------------------------------------- static void writeHierarchicalIndex(OutputList &ol) { if (hierarchyClasses==0) return; ol.pushGeneratorState(); //1.{ ol.disable(OutputGenerator::Man); ol.disable(OutputGenerator::Docbook); LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::ClassHierarchy); QCString title = lne ? lne->title() : theTranslator->trClassHierarchy(); bool addToIndex = lne==0 || lne->visible(); startFile(ol,"hierarchy",0, title, HLI_ClassHierarchy); startTitle(ol,0); ol.parseText(title); endTitle(ol,0,0); ol.startContents(); ol.startTextBlock(); if (Config_getBool(HAVE_DOT) && Config_getBool(GRAPHICAL_HIERARCHY)) { ol.pushGeneratorState(); ol.disable(OutputGenerator::Latex); ol.disable(OutputGenerator::RTF); ol.disable(OutputGenerator::Docbook); ol.startParagraph(); ol.startTextLink("inherits",0); ol.parseText(theTranslator->trGotoGraphicalHierarchy()); ol.endTextLink(); ol.endParagraph(); ol.popGeneratorState(); } ol.parseText(lne ? lne->intro() : theTranslator->trClassHierarchyDescription()); ol.endTextBlock(); // --------------- // Static class hierarchy for Latex/RTF // --------------- ol.pushGeneratorState(); //2.{ ol.disable(OutputGenerator::Html); Doxygen::indexList->disable(); writeClassHierarchy(ol,0,addToIndex,ClassDef::Class); Doxygen::indexList->enable(); ol.popGeneratorState(); //2.} // --------------- // Dynamic class hierarchical index for HTML // --------------- ol.pushGeneratorState(); //2.{ ol.disableAllBut(OutputGenerator::Html); { if (addToIndex) { Doxygen::indexList->addContentsItem(TRUE,title,0,"hierarchy",0,TRUE,TRUE); } FTVHelp* ftv = new FTVHelp(FALSE); writeClassHierarchy(ol,ftv,addToIndex,ClassDef::Class); QGString outStr; FTextStream t(&outStr); ftv->generateTreeViewInline(t); ol.pushGeneratorState(); ol.disableAllBut(OutputGenerator::Html); ol.writeString(outStr); ol.popGeneratorState(); delete ftv; } ol.popGeneratorState(); //2.} // ------ endFile(ol); ol.popGeneratorState(); //1.} } //---------------------------------------------------------------------------- static void writeGraphicalClassHierarchy(OutputList &ol) { if (hierarchyClasses==0) return; ol.disableAllBut(OutputGenerator::Html); LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::ClassHierarchy); QCString title = lne ? lne->title() : theTranslator->trClassHierarchy(); startFile(ol,"inherits",0,title,HLI_ClassHierarchy,FALSE,"hierarchy"); startTitle(ol,0); ol.parseText(title); endTitle(ol,0,0); ol.startContents(); ol.startTextBlock(); ol.startParagraph(); ol.startTextLink("hierarchy",0); ol.parseText(theTranslator->trGotoTextualHierarchy()); ol.endTextLink(); ol.endParagraph(); ol.endTextBlock(); DotGfxHierarchyTable g; ol.writeGraphicalHierarchy(g); endFile(ol); ol.enableAll(); } //---------------------------------------------------------------------------- static void writeHierarchicalInterfaceIndex(OutputList &ol) { if (hierarchyInterfaces==0) return; ol.pushGeneratorState(); //1.{ ol.disable(OutputGenerator::Man); LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::InterfaceHierarchy); QCString title = lne ? lne->title() : theTranslator->trInterfaceHierarchy(); bool addToIndex = lne==0 || lne->visible(); startFile(ol,"interfacehierarchy",0, title, HLI_InterfaceHierarchy); startTitle(ol,0); ol.parseText(title); endTitle(ol,0,0); ol.startContents(); ol.startTextBlock(); if (Config_getBool(HAVE_DOT) && Config_getBool(GRAPHICAL_HIERARCHY)) { ol.disable(OutputGenerator::Latex); ol.disable(OutputGenerator::RTF); ol.startParagraph(); ol.startTextLink("interfaceinherits",0); ol.parseText(theTranslator->trGotoGraphicalHierarchy()); ol.endTextLink(); ol.endParagraph(); ol.enable(OutputGenerator::Latex); ol.enable(OutputGenerator::RTF); } ol.parseText(lne ? lne->intro() : theTranslator->trInterfaceHierarchyDescription()); ol.endTextBlock(); // --------------- // Static interface hierarchy for Latex/RTF // --------------- ol.pushGeneratorState(); //2.{ ol.disable(OutputGenerator::Html); Doxygen::indexList->disable(); writeClassHierarchy(ol,0,addToIndex,ClassDef::Interface); Doxygen::indexList->enable(); ol.popGeneratorState(); //2.} // --------------- // Dynamic interface hierarchical index for HTML // --------------- ol.pushGeneratorState(); //2.{ ol.disableAllBut(OutputGenerator::Html); { if (addToIndex) { Doxygen::indexList->addContentsItem(TRUE,title,0,"interfacehierarchy",0,TRUE,TRUE); } FTVHelp* ftv = new FTVHelp(FALSE); writeClassHierarchy(ol,ftv,addToIndex,ClassDef::Interface); QGString outStr; FTextStream t(&outStr); ftv->generateTreeViewInline(t); ol.pushGeneratorState(); ol.disableAllBut(OutputGenerator::Html); ol.writeString(outStr); ol.popGeneratorState(); delete ftv; } ol.popGeneratorState(); //2.} // ------ endFile(ol); ol.popGeneratorState(); //1.} } //---------------------------------------------------------------------------- static void writeGraphicalInterfaceHierarchy(OutputList &ol) { if (hierarchyInterfaces==0) return; ol.disableAllBut(OutputGenerator::Html); LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::InterfaceHierarchy); QCString title = lne ? lne->title() : theTranslator->trInterfaceHierarchy(); startFile(ol,"interfaceinherits",0,title,HLI_InterfaceHierarchy,FALSE,"interfacehierarchy"); startTitle(ol,0); ol.parseText(title); endTitle(ol,0,0); ol.startContents(); ol.startTextBlock(); ol.startParagraph(); ol.startTextLink("interfacehierarchy",0); ol.parseText(theTranslator->trGotoTextualHierarchy()); ol.endTextLink(); ol.endParagraph(); ol.endTextBlock(); DotGfxHierarchyTable g("interface_",ClassDef::Interface); ol.writeGraphicalHierarchy(g); endFile(ol); ol.enableAll(); } //---------------------------------------------------------------------------- static void writeHierarchicalExceptionIndex(OutputList &ol) { if (hierarchyExceptions==0) return; ol.pushGeneratorState(); //1.{ ol.disable(OutputGenerator::Man); LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::ExceptionHierarchy); QCString title = lne ? lne->title() : theTranslator->trExceptionHierarchy(); bool addToIndex = lne==0 || lne->visible(); startFile(ol,"exceptionhierarchy",0, title, HLI_ExceptionHierarchy); startTitle(ol,0); ol.parseText(title); endTitle(ol,0,0); ol.startContents(); ol.startTextBlock(); if (Config_getBool(HAVE_DOT) && Config_getBool(GRAPHICAL_HIERARCHY)) { ol.disable(OutputGenerator::Latex); ol.disable(OutputGenerator::RTF); ol.startParagraph(); ol.startTextLink("exceptioninherits",0); ol.parseText(theTranslator->trGotoGraphicalHierarchy()); ol.endTextLink(); ol.endParagraph(); ol.enable(OutputGenerator::Latex); ol.enable(OutputGenerator::RTF); } ol.parseText(lne ? lne->intro() : theTranslator->trExceptionHierarchyDescription()); ol.endTextBlock(); // --------------- // Static exception hierarchy for Latex/RTF // --------------- ol.pushGeneratorState(); //2.{ ol.disable(OutputGenerator::Html); Doxygen::indexList->disable(); writeClassHierarchy(ol,0,addToIndex,ClassDef::Exception); Doxygen::indexList->enable(); ol.popGeneratorState(); //2.} // --------------- // Dynamic exception hierarchical index for HTML // --------------- ol.pushGeneratorState(); //2.{ ol.disableAllBut(OutputGenerator::Html); { if (addToIndex) { Doxygen::indexList->addContentsItem(TRUE,title,0,"exceptionhierarchy",0,TRUE,TRUE); } FTVHelp* ftv = new FTVHelp(FALSE); writeClassHierarchy(ol,ftv,addToIndex,ClassDef::Exception); QGString outStr; FTextStream t(&outStr); ftv->generateTreeViewInline(t); ol.pushGeneratorState(); ol.disableAllBut(OutputGenerator::Html); ol.writeString(outStr); ol.popGeneratorState(); delete ftv; } ol.popGeneratorState(); //2.} // ------ endFile(ol); ol.popGeneratorState(); //1.} } //---------------------------------------------------------------------------- static void writeGraphicalExceptionHierarchy(OutputList &ol) { if (hierarchyExceptions==0) return; ol.disableAllBut(OutputGenerator::Html); LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::ExceptionHierarchy); QCString title = lne ? lne->title() : theTranslator->trExceptionHierarchy(); startFile(ol,"exceptioninherits",0,title,HLI_ExceptionHierarchy,FALSE,"exceptionhierarchy"); startTitle(ol,0); ol.parseText(title); endTitle(ol,0,0); ol.startContents(); ol.startTextBlock(); ol.startParagraph(); ol.startTextLink("exceptionhierarchy",0); ol.parseText(theTranslator->trGotoTextualHierarchy()); ol.endTextLink(); ol.endParagraph(); ol.endTextBlock(); DotGfxHierarchyTable g("exception_",ClassDef::Exception); ol.writeGraphicalHierarchy(g); endFile(ol); ol.enableAll(); } //---------------------------------------------------------------------------- static void countFiles(int &htmlFiles,int &files) { htmlFiles=0; files=0; for (const auto &fn : *Doxygen::inputNameLinkedMap) { for (const auto &fd: *fn) { bool doc,src; doc = fileVisibleInIndex(fd.get(),src); if (doc || src) { htmlFiles++; } if (doc) { files++; } } } } static void writeSingleFileIndex(OutputList &ol,FileDef *fd) { //printf("Found filedef %s\n",fd->name().data()); bool doc = fd->isLinkableInProject(); bool src = fd->generateSourceFile(); bool nameOk = !fd->isDocumentationFile(); if (nameOk && (doc || src) && !fd->isReference()) { QCString path; if (Config_getBool(FULL_PATH_NAMES)) { path=stripFromPath(fd->getPath().copy()); } QCString fullName=fd->name(); if (!path.isEmpty()) { if (path.at(path.length()-1)!='/') fullName.prepend("/"); fullName.prepend(path); } ol.startIndexKey(); ol.docify(path); if (doc) { ol.writeObjectLink(0,fd->getOutputFileBase(),0,fd->name()); //if (addToIndex) //{ // addMembersToIndex(fd,LayoutDocManager::File,fullName,QCString()); //} } else { ol.startBold(); ol.docify(fd->name()); ol.endBold(); //if (addToIndex) //{ // Doxygen::indexList->addContentsItem(FALSE,fullName,0,0,0); //} } if (src) { ol.pushGeneratorState(); ol.disableAllBut(OutputGenerator::Html); ol.docify(" "); ol.startTextLink(fd->includeName(),0); ol.docify("["); ol.parseText(theTranslator->trCode()); ol.docify("]"); ol.endTextLink(); ol.popGeneratorState(); } ol.endIndexKey(); bool hasBrief = !fd->briefDescription().isEmpty(); ol.startIndexValue(hasBrief); if (hasBrief) { //ol.docify(" ("); ol.generateDoc( fd->briefFile(),fd->briefLine(), fd,0, fd->briefDescription(TRUE), FALSE, // index words FALSE, // isExample 0, // example name TRUE, // single line TRUE, // link from index Config_getBool(MARKDOWN_SUPPORT) ); //ol.docify(")"); } ol.endIndexValue(fd->getOutputFileBase(),hasBrief); //ol.popGeneratorState(); // -------------------------------------------------------- } } //---------------------------------------------------------------------------- static void writeFileIndex(OutputList &ol) { if (documentedHtmlFiles==0) return; ol.pushGeneratorState(); ol.disable(OutputGenerator::Man); ol.disable(OutputGenerator::Docbook); if (documentedFiles==0) ol.disableAllBut(OutputGenerator::Html); LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::FileList); if (lne==0) lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::Files); // fall back QCString title = lne ? lne->title() : theTranslator->trFileList(); bool addToIndex = lne==0 || lne->visible(); startFile(ol,"files",0,title,HLI_Files); startTitle(ol,0); //if (!Config_getString(PROJECT_NAME).isEmpty()) //{ // title.prepend(Config_getString(PROJECT_NAME)+" "); //} ol.parseText(title); endTitle(ol,0,0); ol.startContents(); ol.startTextBlock(); if (addToIndex) { Doxygen::indexList->addContentsItem(TRUE,title,0,"files",0,TRUE,TRUE); Doxygen::indexList->incContentsDepth(); } ol.parseText(lne ? lne->intro() : theTranslator->trFileListDescription(Config_getBool(EXTRACT_ALL))); ol.endTextBlock(); // --------------- // Flat file index // --------------- // 1. { ol.pushGeneratorState(); ol.disable(OutputGenerator::Html); OutputNameDict outputNameDict(1009); OutputNameList outputNameList; outputNameList.setAutoDelete(TRUE); if (Config_getBool(FULL_PATH_NAMES)) { // re-sort input files in (dir,file) output order instead of (file,dir) input order for (const auto &fn : *Doxygen::inputNameLinkedMap) { for (const auto &fd : *fn) { QCString path=fd->getPath(); if (path.isEmpty()) path="[external]"; FileList *fl = outputNameDict.find(path); if (fl) { fl->append(fd.get()); //printf("+ inserting %s---%s\n",fd->getPath().data(),fd->name().data()); } else { //printf("o inserting %s---%s\n",fd->getPath().data(),fd->name().data()); fl = new FileList(path); fl->append(fd.get()); outputNameList.append(fl); outputNameDict.insert(path,fl); } } } } ol.startIndexList(); if (Config_getBool(FULL_PATH_NAMES)) { outputNameList.sort(); QListIterator fnli(outputNameList); FileList *fl; for (fnli.toFirst();(fl=fnli.current());++fnli) { fl->sort(); QListIterator it(*fl); FileDef *fd; for (;(fd=it.current());++it) { writeSingleFileIndex(ol,fd); } } } else { for (const auto &fn : *Doxygen::inputNameLinkedMap) { for (const auto &fd : *fn) { writeSingleFileIndex(ol,fd.get()); } } } ol.endIndexList(); // 1. } ol.popGeneratorState(); // --------------- // Hierarchical file index for HTML // --------------- ol.pushGeneratorState(); ol.disableAllBut(OutputGenerator::Html); FTVHelp* ftv = new FTVHelp(FALSE); writeDirHierarchy(ol,ftv,addToIndex); QGString outStr; FTextStream t(&outStr); ftv->generateTreeViewInline(t); ol.writeString(outStr); delete ftv; ol.popGeneratorState(); // ------ if (addToIndex) { Doxygen::indexList->decContentsDepth(); } endFile(ol); ol.popGeneratorState(); } //---------------------------------------------------------------------------- static int countNamespaces() { int count=0; for (const auto &nd : *Doxygen::namespaceLinkedMap) { if (nd->isLinkableInProject()) count++; } return count; } //---------------------------------------------------------------------------- template const ClassDef *get_pointer(const Ptr &p); template<> const ClassDef *get_pointer(const ClassLinkedMap::Ptr &p) { return p.get(); } template<> const ClassDef *get_pointer(const ClassLinkedRefMap::Ptr &p) { return p; } template static void writeClassTree(const ListType &cl,FTVHelp *ftv,bool addToIndex,bool globalOnly,ClassDef::CompoundType ct) { static bool sliceOpt = Config_getBool(OPTIMIZE_OUTPUT_SLICE); for (const auto &cdi : cl) { const ClassDef *cd = get_pointer(cdi); ClassDefMutable *cdm = toClassDefMutable(cd); if (cdm && cd->getLanguage()==SrcLangExt_VHDL) { if ((VhdlDocGen::VhdlClasses)cd->protection()==VhdlDocGen::PACKAGECLASS || (VhdlDocGen::VhdlClasses)cd->protection()==VhdlDocGen::PACKBODYCLASS )// no architecture { continue; } if ((VhdlDocGen::VhdlClasses)cd->protection()==VhdlDocGen::ARCHITECTURECLASS) { QCString n=cd->name(); cdm->setClassName(n.data()); } } if (sliceOpt && cd->compoundType() != ct) { continue; } if (!globalOnly || cd->getOuterScope()==0 || cd->getOuterScope()==Doxygen::globalScope ) { int count=0; for (const auto &ccd : cd->getClasses()) { if (ccd->isLinkableInProject() && ccd->templateMaster()==0) { count++; } } if (classVisibleInIndex(cd) && cd->templateMaster()==0) { ftv->addContentsItem(count>0,cd->displayName(FALSE),cd->getReference(), cd->getOutputFileBase(),cd->anchor(),FALSE,TRUE,cd); if ((cd->getOuterScope()==0 || cd->getOuterScope()->definitionType()!=Definition::TypeClass ) ) { addMembersToIndex(cd,LayoutDocManager::Class, cd->displayName(FALSE), cd->anchor(), addToIndex && cd->partOfGroups()==0 && !cd->isSimple()); } if (count>0) { ftv->incContentsDepth(); writeClassTree(cd->getClasses(),ftv,addToIndex,FALSE,ct); ftv->decContentsDepth(); } } } } } static int countVisibleMembers(const NamespaceDef *nd) { int count=0; QListIterator eli(LayoutDocManager::instance().docEntries(LayoutDocManager::Namespace)); LayoutDocEntry *lde; for (eli.toFirst();(lde=eli.current());++eli) { if (lde->kind()==LayoutDocEntry::MemberDef) { LayoutDocEntryMemberDef *lmd = (LayoutDocEntryMemberDef*)lde; MemberList *ml = nd->getMemberList(lmd->type); if (ml) { MemberListIterator mi(*ml); MemberDef *md; for (mi.toFirst();(md=mi.current());++mi) { if (memberVisibleInIndex(md)) { count++; } } } } } return count; } static void writeNamespaceMembers(const NamespaceDef *nd,bool addToIndex) { QListIterator eli(LayoutDocManager::instance().docEntries(LayoutDocManager::Namespace)); LayoutDocEntry *lde; for (eli.toFirst();(lde=eli.current());++eli) { if (lde->kind()==LayoutDocEntry::MemberDef) { LayoutDocEntryMemberDef *lmd = (LayoutDocEntryMemberDef*)lde; MemberList *ml = nd->getMemberList(lmd->type); if (ml) { MemberListIterator mi(*ml); MemberDef *md; for (mi.toFirst();(md=mi.current());++mi) { //printf(" member %s visible=%d\n",md->name().data(),memberVisibleInIndex(md)); if (memberVisibleInIndex(md)) { writeMemberToIndex(nd,md,addToIndex); } } } } } } static void writeNamespaceTree(const NamespaceLinkedRefMap &nsLinkedMap,FTVHelp *ftv, bool rootOnly,bool addToIndex); static void writeNamespaceTreeElement(const NamespaceDef *nd,FTVHelp *ftv, bool rootOnly,bool addToIndex) { if (!nd->isAnonymous() && (!rootOnly || nd->getOuterScope()==Doxygen::globalScope)) { bool hasChildren = namespaceHasNestedNamespace(nd) || namespaceHasNestedClass(nd,false,ClassDef::Class); bool isLinkable = nd->isLinkableInProject(); int visibleMembers = countVisibleMembers(nd); //printf("namespace %s hasChildren=%d visibleMembers=%d\n",nd->name().data(),hasChildren,visibleMembers); QCString ref; QCString file; if (isLinkable) { ref = nd->getReference(); file = nd->getOutputFileBase(); if (nd->getLanguage()==SrcLangExt_VHDL) // UGLY HACK { file=file.replace(0,qstrlen("namespace"),"class"); } } bool isDir = hasChildren || visibleMembers>0; if ((isLinkable) || isDir) { ftv->addContentsItem(hasChildren,nd->localName(),ref,file,0,FALSE,TRUE,nd); if (addToIndex) { Doxygen::indexList->addContentsItem(isDir,nd->localName(),ref,file,QCString(), hasChildren && !file.isEmpty(),addToIndex); } if (addToIndex && isDir) { Doxygen::indexList->incContentsDepth(); } //printf("*** writeNamespaceTree count=%d addToIndex=%d false=%d classCount=%d\n", // count,addToIndex,false,classCount); if (isDir) { ftv->incContentsDepth(); writeNamespaceTree(nd->getNamespaces(),ftv,FALSE,addToIndex); writeClassTree(nd->getClasses(),ftv,FALSE,FALSE,ClassDef::Class); writeNamespaceMembers(nd,addToIndex); ftv->decContentsDepth(); } if (addToIndex && isDir) { Doxygen::indexList->decContentsDepth(); } } } } static void writeNamespaceTree(const NamespaceLinkedRefMap &nsLinkedMap,FTVHelp *ftv, bool rootOnly,bool addToIndex) { for (const auto &nd : nsLinkedMap) { writeNamespaceTreeElement(nd,ftv,rootOnly,addToIndex); } } static void writeNamespaceTree(const NamespaceLinkedMap &nsLinkedMap,FTVHelp *ftv, bool rootOnly,bool addToIndex) { for (const auto &nd : nsLinkedMap) { writeNamespaceTreeElement(nd.get(),ftv,rootOnly,addToIndex); } } static void writeClassTreeInsideNamespace(const NamespaceLinkedRefMap &nsLinkedMap,FTVHelp *ftv, bool rootOnly,bool addToIndex,ClassDef::CompoundType ct); static void writeClassTreeInsideNamespaceElement(const NamespaceDef *nd,FTVHelp *ftv, bool rootOnly,bool addToIndex,ClassDef::CompoundType ct) { static bool sliceOpt = Config_getBool(OPTIMIZE_OUTPUT_SLICE); if (!nd->isAnonymous() && (!rootOnly || nd->getOuterScope()==Doxygen::globalScope)) { bool isDir = namespaceHasNestedClass(nd,sliceOpt,ct); bool isLinkable = nd->isLinkableInProject(); //printf("namespace %s isDir=%d\n",nd->name().data(),isDir); QCString ref; QCString file; if (isLinkable) { ref = nd->getReference(); file = nd->getOutputFileBase(); if (nd->getLanguage()==SrcLangExt_VHDL) // UGLY HACK { file=file.replace(0,qstrlen("namespace"),"class"); } } if (isDir) { ftv->addContentsItem(isDir,nd->localName(),ref,file,0,FALSE,TRUE,nd); if (addToIndex) { // the namespace entry is already shown under the namespace list so don't // add it to the nav index and don't create a separate index file for it otherwise // it will overwrite the one written for the namespace list. Doxygen::indexList->addContentsItem(isDir,nd->localName(),ref,file,QCString(), false, // separateIndex false // addToNavIndex ); } if (addToIndex) { Doxygen::indexList->incContentsDepth(); } ftv->incContentsDepth(); writeClassTreeInsideNamespace(nd->getNamespaces(),ftv,FALSE,addToIndex,ct); ClassLinkedRefMap d = nd->getClasses(); if (sliceOpt) { if (ct == ClassDef::Interface) { d = nd->getInterfaces(); } else if (ct == ClassDef::Struct) { d = nd->getStructs(); } else if (ct == ClassDef::Exception) { d = nd->getExceptions(); } } writeClassTree(d,ftv,addToIndex,FALSE,ct); ftv->decContentsDepth(); if (addToIndex) { Doxygen::indexList->decContentsDepth(); } } } } static void writeClassTreeInsideNamespace(const NamespaceLinkedRefMap &nsLinkedMap,FTVHelp *ftv, bool rootOnly,bool addToIndex,ClassDef::CompoundType ct) { for (const auto &nd : nsLinkedMap) { writeClassTreeInsideNamespaceElement(nd,ftv,rootOnly,addToIndex,ct); } } static void writeClassTreeInsideNamespace(const NamespaceLinkedMap &nsLinkedMap,FTVHelp *ftv, bool rootOnly,bool addToIndex,ClassDef::CompoundType ct) { for (const auto &nd : nsLinkedMap) { writeClassTreeInsideNamespaceElement(nd.get(),ftv,rootOnly,addToIndex,ct); } } static void writeNamespaceIndex(OutputList &ol) { if (documentedNamespaces==0) return; ol.pushGeneratorState(); ol.disable(OutputGenerator::Man); ol.disable(OutputGenerator::Docbook); LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::NamespaceList); if (lne==0) lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::Namespaces); // fall back QCString title = lne ? lne->title() : theTranslator->trNamespaceList(); bool addToIndex = lne==0 || lne->visible(); startFile(ol,"namespaces",0,title,HLI_Namespaces); startTitle(ol,0); ol.parseText(title); endTitle(ol,0,0); ol.startContents(); ol.startTextBlock(); ol.parseText(lne ? lne->intro() : theTranslator->trNamespaceListDescription(Config_getBool(EXTRACT_ALL))); ol.endTextBlock(); bool first=TRUE; // --------------- // Linear namespace index for Latex/RTF // --------------- ol.pushGeneratorState(); ol.disable(OutputGenerator::Html); for (const auto &nd : *Doxygen::namespaceLinkedMap) { if (nd->isLinkableInProject()) { if (first) { ol.startIndexList(); first=FALSE; } //ol.writeStartAnnoItem("namespace",nd->getOutputFileBase(),0,nd->name()); ol.startIndexKey(); if (nd->getLanguage()==SrcLangExt_VHDL) { ol.writeObjectLink(0, nd->getOutputFileBase().replace(0,qstrlen("namespace"),"class"),0,nd->displayName()); } else { ol.writeObjectLink(0,nd->getOutputFileBase(),0,nd->displayName()); } ol.endIndexKey(); bool hasBrief = !nd->briefDescription().isEmpty(); ol.startIndexValue(hasBrief); if (hasBrief) { //ol.docify(" ("); ol.generateDoc( nd->briefFile(),nd->briefLine(), nd.get(),0, nd->briefDescription(TRUE), FALSE, // index words FALSE, // isExample 0, // example name TRUE, // single line TRUE, // link from index Config_getBool(MARKDOWN_SUPPORT) ); //ol.docify(")"); } ol.endIndexValue(nd->getOutputFileBase(),hasBrief); } } if (!first) ol.endIndexList(); ol.popGeneratorState(); // --------------- // Hierarchical namespace index for HTML // --------------- ol.pushGeneratorState(); ol.disableAllBut(OutputGenerator::Html); { if (addToIndex) { Doxygen::indexList->addContentsItem(TRUE,title,0,"namespaces",0,TRUE,TRUE); Doxygen::indexList->incContentsDepth(); } FTVHelp* ftv = new FTVHelp(FALSE); writeNamespaceTree(*Doxygen::namespaceLinkedMap,ftv,TRUE,addToIndex); QGString outStr; FTextStream t(&outStr); ftv->generateTreeViewInline(t); ol.writeString(outStr); delete ftv; if (addToIndex) { Doxygen::indexList->decContentsDepth(); } } ol.popGeneratorState(); // ------ endFile(ol); ol.popGeneratorState(); } //---------------------------------------------------------------------------- static int countAnnotatedClasses(int *cp, ClassDef::CompoundType ct) { static bool sliceOpt = Config_getBool(OPTIMIZE_OUTPUT_SLICE); int count=0; int countPrinted=0; for (const auto &cd : *Doxygen::classLinkedMap) { if (sliceOpt && cd->compoundType() != ct) { continue; } if (cd->isLinkableInProject() && cd->templateMaster()==0) { if (!cd->isEmbeddedInOuterScope()) { countPrinted++; } count++; } } *cp = countPrinted; return count; } static void writeAnnotatedClassList(OutputList &ol,ClassDef::CompoundType ct) { //LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::ClassList); //bool addToIndex = lne==0 || lne->visible(); bool first=TRUE; static bool sliceOpt = Config_getBool(OPTIMIZE_OUTPUT_SLICE); for (const auto &cd : *Doxygen::classLinkedMap) { if (cd->getLanguage()==SrcLangExt_VHDL && ((VhdlDocGen::VhdlClasses)cd->protection()==VhdlDocGen::PACKAGECLASS || (VhdlDocGen::VhdlClasses)cd->protection()==VhdlDocGen::PACKBODYCLASS) ) // no architecture { continue; } if (first) { ol.startIndexList(); first=FALSE; } if (sliceOpt && cd->compoundType() != ct) { continue; } ol.pushGeneratorState(); if (cd->isEmbeddedInOuterScope()) { ol.disable(OutputGenerator::Latex); ol.disable(OutputGenerator::Docbook); ol.disable(OutputGenerator::RTF); } if (cd->isLinkableInProject() && cd->templateMaster()==0) { ol.startIndexKey(); if (cd->getLanguage()==SrcLangExt_VHDL) { QCString prot= VhdlDocGen::getProtectionName((VhdlDocGen::VhdlClasses)cd->protection()); ol.docify(prot.data()); ol.writeString(" "); } ol.writeObjectLink(0,cd->getOutputFileBase(),cd->anchor(),cd->displayName()); ol.endIndexKey(); bool hasBrief = !cd->briefDescription().isEmpty(); ol.startIndexValue(hasBrief); if (hasBrief) { ol.generateDoc( cd->briefFile(),cd->briefLine(), cd.get(),0, cd->briefDescription(TRUE), FALSE, // indexWords FALSE, // isExample 0, // example name TRUE, // single line TRUE, // link from index Config_getBool(MARKDOWN_SUPPORT) ); } ol.endIndexValue(cd->getOutputFileBase(),hasBrief); //if (addToIndex) //{ // addMembersToIndex(cd,LayoutDocManager::Class,cd->displayName(),cd->anchor()); //} } ol.popGeneratorState(); } if (!first) ol.endIndexList(); } inline bool isId1(int c) { return (c<127 && c>31); // printable ASCII character } static QCString letterToString(uint letter) { return QString(QChar(letter)).utf8(); } static QCString letterToLabel(const char *startLetter) { const char *p = startLetter; if (startLetter==0 || *startLetter==0) return ""; char c = *p; QCString result; if (isId1(c)) { result+=c; } else { result="0x"; const char hex[]="0123456789abcdef"; while ((c=*p++)) { result+=hex[((unsigned char)c)>>4]; result+=hex[((unsigned char)c)&0xf]; } } return result; } static QCString letterToLabel(uint startLetter) { char s[11]; // max 0x12345678 + '\0' if (isId1(startLetter)) // printable ASCII character { s[0]=(char)startLetter; s[1]=0; } else { const char hex[]="0123456789abcdef"; int i=0; s[i++]='0'; s[i++]='x'; if (startLetter>(1<<24)) // 4 byte character { s[i++]=hex[(startLetter>>28)&0xf]; s[i++]=hex[(startLetter>>24)&0xf]; } if (startLetter>(1<<16)) // 3 byte character { s[i++]=hex[(startLetter>>20)&0xf]; s[i++]=hex[(startLetter>>16)&0xf]; } if (startLetter>(1<<8)) // 2 byte character { s[i++]=hex[(startLetter>>12)&0xf]; s[i++]=hex[(startLetter>>8)&0xf]; } // one byte character s[i++]=hex[(startLetter>>4)&0xf]; s[i++]=hex[(startLetter>>0)&0xf]; s[i++]=0; } return s; } //---------------------------------------------------------------------------- /** Class representing a cell in the alphabetical class index. */ class AlphaIndexTableCell { public: AlphaIndexTableCell(int row,int col,const std::string &letter,const ClassDef *cd) : m_letter(letter), m_class(cd), m_row(row), m_col(col) { } const ClassDef *classDef() const { return m_class; } std::string letter() const { return m_letter; } int row() const { return m_row; } int column() const { return m_col; } private: std::string m_letter; const ClassDef *m_class; int m_row; int m_col; }; using UsedIndexLetters = std::set; // write an alphabetical index of all class with a header for each letter static void writeAlphabeticalClassList(OutputList &ol, ClassDef::CompoundType ct, int annotatedCount) { static bool sliceOpt = Config_getBool(OPTIMIZE_OUTPUT_SLICE); // What starting letters are used UsedIndexLetters indexLettersUsed; // first count the number of headers for (const auto &cd : *Doxygen::classLinkedMap) { if (sliceOpt && cd->compoundType() != ct) continue; if (cd->isLinkableInProject() && cd->templateMaster()==0) { if (cd->getLanguage()==SrcLangExt_VHDL && !((VhdlDocGen::VhdlClasses)cd->protection()==VhdlDocGen::ENTITYCLASS ))// no architecture continue; int index = getPrefixIndex(cd->className()); //printf("name=%s index=%d %d\n",cd->className().data(),index,cd->protection()); char charStr[MAX_UTF8_CHAR_SIZE]; if (getUtf8Char(cd->className().data()+index,charStr,CaseModifier::ToUpper)>0) // get the first UTF8 character (after the part that should be ignored) { indexLettersUsed.insert(charStr); } } } // write quick link index (row of letters) QCString alphaLinks = "
"; bool first=true; for (const auto &letter : indexLettersUsed) { if (!first) alphaLinks += " | "; first=false; QCString li = letterToLabel(letter.c_str()); alphaLinks += (QCString)"" + letter + ""; } alphaLinks += "
\n"; ol.writeString(alphaLinks); std::map > classesByLetter; // fill the columns with the class list (row elements in each column, // expect for the columns with number >= itemsInLastRow, which get one // item less. for (const auto &cd : *Doxygen::classLinkedMap) { if (sliceOpt && cd->compoundType() != ct) continue; if (cd->getLanguage()==SrcLangExt_VHDL && !((VhdlDocGen::VhdlClasses)cd->protection()==VhdlDocGen::ENTITYCLASS ))// no architecture continue; if (cd->isLinkableInProject() && cd->templateMaster()==0) { int index = getPrefixIndex(cd->className()); char charStr[MAX_UTF8_CHAR_SIZE]; if (getUtf8Char(cd->className().data()+index,charStr,CaseModifier::ToUpper)>0) // get the first UTF8 character (after the part that should be ignored) { auto it = classesByLetter.find(charStr); if (it!=classesByLetter.end()) // add class to the existing list { it->second.push_back(cd.get()); } else // new entry { classesByLetter.insert( std::make_pair(std::string(charStr), std::vector({ cd.get() }))); } } } } // sort the class lists per letter while ignoring the prefix for (auto &kv : classesByLetter) { std::sort(kv.second.begin(), kv.second.end(), [](const auto &c1,const auto &c2) { QCString n1 = c1->className(); QCString n2 = c2->className(); return qstricmp(n1.data()+getPrefixIndex(n1), n2.data()+getPrefixIndex(n2))<0; }); } // generate table if (!classesByLetter.empty()) { ol.writeString("
\n"); int counter=0; for (const auto &cl : classesByLetter) { QCString parity = (counter++%2)==0 ? "even" : "odd"; ol.writeString("
\n"); // write character heading ol.writeString("
"); QCString s = letterToLabel(cl.first.c_str()); ol.writeString(""); ol.writeString(cl.first.c_str()); ol.writeString(""); ol.writeString("
\n"); // write class links for (const auto &cd : cl.second) { ol.writeString("
"); QCString namesp,cname; extractNamespaceName(cd->name(),cname,namesp); QCString nsDispName; SrcLangExt lang = cd->getLanguage(); QCString sep = getLanguageSpecificSeparator(lang); if (sep!="::") { nsDispName=substitute(namesp,"::",sep); cname=substitute(cname,"::",sep); } else { nsDispName=namesp; } ol.writeObjectLink(cd->getReference(), cd->getOutputFileBase(),cd->anchor(),cname); if (!namesp.isEmpty()) { ol.writeString(" ("); NamespaceDef *nd = getResolvedNamespace(namesp); if (nd && nd->isLinkable()) { ol.writeObjectLink(nd->getReference(), nd->getOutputFileBase(),0,nsDispName); } else { ol.docify(nsDispName); } ol.writeString(")"); } ol.writeString("
"); } ol.writeString("
\n"); } ol.writeString("
\n"); } } //---------------------------------------------------------------------------- static void writeAlphabeticalIndex(OutputList &ol) { if (annotatedClasses==0) return; ol.pushGeneratorState(); ol.disableAllBut(OutputGenerator::Html); LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::ClassIndex); QCString title = lne ? lne->title() : theTranslator->trCompoundIndex(); bool addToIndex = lne==0 || lne->visible(); startFile(ol,"classes",0,title,HLI_Classes); startTitle(ol,0); ol.parseText(title); endTitle(ol,0,0); if (addToIndex) { Doxygen::indexList->addContentsItem(FALSE,title,0,"classes",0,FALSE,TRUE); } ol.startContents(); writeAlphabeticalClassList(ol, ClassDef::Class, annotatedClasses); endFile(ol); // contains ol.endContents() ol.popGeneratorState(); } //---------------------------------------------------------------------------- static void writeAlphabeticalInterfaceIndex(OutputList &ol) { if (annotatedInterfaces==0) return; ol.pushGeneratorState(); ol.disableAllBut(OutputGenerator::Html); LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::InterfaceIndex); QCString title = lne ? lne->title() : theTranslator->trInterfaceIndex(); bool addToIndex = lne==0 || lne->visible(); startFile(ol,"interfaces",0,title,HLI_Interfaces); startTitle(ol,0); ol.parseText(title); endTitle(ol,0,0); if (addToIndex) { Doxygen::indexList->addContentsItem(FALSE,title,0,"interfaces",0,FALSE,TRUE); } ol.startContents(); writeAlphabeticalClassList(ol, ClassDef::Interface, annotatedInterfaces); endFile(ol); // contains ol.endContents() ol.popGeneratorState(); } //---------------------------------------------------------------------------- static void writeAlphabeticalStructIndex(OutputList &ol) { if (annotatedStructs==0) return; ol.pushGeneratorState(); ol.disableAllBut(OutputGenerator::Html); LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::StructIndex); QCString title = lne ? lne->title() : theTranslator->trStructIndex(); bool addToIndex = lne==0 || lne->visible(); startFile(ol,"structs",0,title,HLI_Structs); startTitle(ol,0); ol.parseText(title); endTitle(ol,0,0); if (addToIndex) { Doxygen::indexList->addContentsItem(FALSE,title,0,"structs",0,FALSE,TRUE); } ol.startContents(); writeAlphabeticalClassList(ol, ClassDef::Struct, annotatedStructs); endFile(ol); // contains ol.endContents() ol.popGeneratorState(); } //---------------------------------------------------------------------------- static void writeAlphabeticalExceptionIndex(OutputList &ol) { if (annotatedExceptions==0) return; ol.pushGeneratorState(); ol.disableAllBut(OutputGenerator::Html); LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::ExceptionIndex); QCString title = lne ? lne->title() : theTranslator->trExceptionIndex(); bool addToIndex = lne==0 || lne->visible(); startFile(ol,"exceptions",0,title,HLI_Exceptions); startTitle(ol,0); ol.parseText(title); endTitle(ol,0,0); if (addToIndex) { Doxygen::indexList->addContentsItem(FALSE,title,0,"exceptions",0,FALSE,TRUE); } ol.startContents(); writeAlphabeticalClassList(ol, ClassDef::Exception, annotatedExceptions); endFile(ol); // contains ol.endContents() ol.popGeneratorState(); } //---------------------------------------------------------------------------- struct AnnotatedIndexContext { AnnotatedIndexContext(int numAnno,int numPrint, LayoutNavEntry::Kind lk,LayoutNavEntry::Kind fk, const QCString &title,const QCString &intro, ClassDef::CompoundType ct, const QCString &fn, HighlightedItem hi) : numAnnotated(numAnno), numPrinted(numPrint), listKind(lk), fallbackKind(fk), listDefaultTitleText(title), listDefaultIntroText(intro), compoundType(ct),fileBaseName(fn), hiItem(hi) { } const int numAnnotated; const int numPrinted; const LayoutNavEntry::Kind listKind; const LayoutNavEntry::Kind fallbackKind; const QCString listDefaultTitleText; const QCString listDefaultIntroText; const ClassDef::CompoundType compoundType; const QCString fileBaseName; const HighlightedItem hiItem; }; static void writeAnnotatedIndexGeneric(OutputList &ol,const AnnotatedIndexContext ctx) { //printf("writeAnnotatedIndex: count=%d printed=%d\n", // annotatedClasses,annotatedClassesPrinted); if (ctx.numAnnotated==0) return; ol.pushGeneratorState(); ol.disable(OutputGenerator::Man); if (ctx.numPrinted==0) { ol.disable(OutputGenerator::Latex); ol.disable(OutputGenerator::RTF); } LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(ctx.listKind); if (lne==0) lne = LayoutDocManager::instance().rootNavEntry()->find(ctx.fallbackKind); // fall back QCString title = lne ? lne->title() : ctx.listDefaultTitleText; bool addToIndex = lne==0 || lne->visible(); startFile(ol,ctx.fileBaseName,0,title,ctx.hiItem); startTitle(ol,0); ol.parseText(title); endTitle(ol,0,0); ol.startContents(); ol.startTextBlock(); ol.parseText(lne ? lne->intro() : ctx.listDefaultIntroText); ol.endTextBlock(); // --------------- // Linear class index for Latex/RTF // --------------- ol.pushGeneratorState(); ol.disable(OutputGenerator::Html); Doxygen::indexList->disable(); writeAnnotatedClassList(ol, ctx.compoundType); Doxygen::indexList->enable(); ol.popGeneratorState(); // --------------- // Hierarchical class index for HTML // --------------- ol.pushGeneratorState(); ol.disableAllBut(OutputGenerator::Html); { if (addToIndex) { Doxygen::indexList->addContentsItem(TRUE,title,0,ctx.fileBaseName,0,TRUE,TRUE); Doxygen::indexList->incContentsDepth(); } FTVHelp ftv(false); writeClassTreeInsideNamespace(*Doxygen::namespaceLinkedMap,&ftv,TRUE,addToIndex,ctx.compoundType); writeClassTree(*Doxygen::classLinkedMap,&ftv,addToIndex,TRUE,ctx.compoundType); QGString outStr; FTextStream t(&outStr); ftv.generateTreeViewInline(t); ol.writeString(outStr); if (addToIndex) { Doxygen::indexList->decContentsDepth(); } } ol.popGeneratorState(); // ------ endFile(ol); // contains ol.endContents() ol.popGeneratorState(); } //---------------------------------------------------------------------------- static void writeAnnotatedIndex(OutputList &ol) { writeAnnotatedIndexGeneric(ol, AnnotatedIndexContext(annotatedClasses,annotatedClassesPrinted, LayoutNavEntry::ClassList,LayoutNavEntry::Classes, theTranslator->trCompoundList(),theTranslator->trCompoundListDescription(), ClassDef::Class, "annotated", HLI_AnnotatedClasses)); } //---------------------------------------------------------------------------- static void writeAnnotatedInterfaceIndex(OutputList &ol) { writeAnnotatedIndexGeneric(ol, AnnotatedIndexContext(annotatedInterfaces,annotatedInterfacesPrinted, LayoutNavEntry::InterfaceList,LayoutNavEntry::Interfaces, theTranslator->trInterfaceList(),theTranslator->trInterfaceListDescription(), ClassDef::Interface, "annotatedinterfaces", HLI_AnnotatedInterfaces)); } //---------------------------------------------------------------------------- static void writeAnnotatedStructIndex(OutputList &ol) { writeAnnotatedIndexGeneric(ol, AnnotatedIndexContext(annotatedStructs,annotatedStructsPrinted, LayoutNavEntry::StructList,LayoutNavEntry::Structs, theTranslator->trStructList(),theTranslator->trStructListDescription(), ClassDef::Struct, "annotatedstructs", HLI_AnnotatedStructs)); } //---------------------------------------------------------------------------- static void writeAnnotatedExceptionIndex(OutputList &ol) { writeAnnotatedIndexGeneric(ol, AnnotatedIndexContext(annotatedExceptions,annotatedExceptionsPrinted, LayoutNavEntry::ExceptionList,LayoutNavEntry::Exceptions, theTranslator->trExceptionList(),theTranslator->trExceptionListDescription(), ClassDef::Exception, "annotatedexceptions", HLI_AnnotatedExceptions)); } //---------------------------------------------------------------------------- static void writeClassLinkForMember(OutputList &ol,MemberDef *md,const char *separator, QCString &prevClassName) { const ClassDef *cd=md->getClassDef(); if ( cd && prevClassName!=cd->displayName()) { ol.docify(separator); ol.writeObjectLink(md->getReference(),md->getOutputFileBase(),md->anchor(), cd->displayName()); ol.writeString("\n"); prevClassName = cd->displayName(); } } static void writeFileLinkForMember(OutputList &ol,MemberDef *md,const char *separator, QCString &prevFileName) { const FileDef *fd=md->getFileDef(); if (fd && prevFileName!=fd->name()) { ol.docify(separator); ol.writeObjectLink(md->getReference(),md->getOutputFileBase(),md->anchor(), fd->name()); ol.writeString("\n"); prevFileName = fd->name(); } } static void writeNamespaceLinkForMember(OutputList &ol,MemberDef *md,const char *separator, QCString &prevNamespaceName) { const NamespaceDef *nd=md->getNamespaceDef(); if (nd && prevNamespaceName!=nd->displayName()) { ol.docify(separator); ol.writeObjectLink(md->getReference(),md->getOutputFileBase(),md->anchor(), nd->displayName()); ol.writeString("\n"); prevNamespaceName = nd->displayName(); } } static void writeMemberList(OutputList &ol,bool useSections,int page, const LetterToIndexMap &memberLists, Definition::DefType type) { int index = (int)type; ASSERT(index<3); typedef void (*writeLinkForMember_t)(OutputList &ol,MemberDef *md,const char *separator, QCString &prevNamespaceName); // each index tab has its own write function static writeLinkForMember_t writeLinkForMemberMap[3] = { &writeClassLinkForMember, &writeFileLinkForMember, &writeNamespaceLinkForMember }; QCString prevName; QCString prevDefName; bool first=TRUE; bool firstSection=TRUE; bool firstItem=TRUE; MemberIndexList *ml; SIntDict::Iterator it(memberLists); for (it.toFirst();(ml=it.current());++it) { if (page!=-1) { ml = memberLists[page]; it.toLast(); } if (ml==0 || ml->count()==0) continue; ml->sort(); QListIterator mli(*ml); MemberDef *md; for (mli.toFirst();(md=mli.current());++mli) { const char *sep; bool isFunc=!md->isObjCMethod() && (md->isFunction() || md->isSlot() || md->isSignal()); QCString name=md->name(); int startIndex = getPrefixIndex(name); if (QCString(name.data()+startIndex)!=prevName) // new entry { if ((prevName.isEmpty() || tolower(name.at(startIndex))!=tolower(prevName.at(0))) && useSections) // new section { if (!firstItem) ol.endItemListItem(); if (!firstSection) ol.endItemList(); QCString cs = letterToLabel(ml->letter()); QCString cl = letterToString(ml->letter()); QCString anchor=(QCString)"index_"+convertToId(cs); QCString title=(QCString)"- "+cl+" -"; ol.startSection(anchor,title,SectionType::Subsection); ol.docify(title); ol.endSection(anchor,SectionType::Subsection); ol.startItemList(); firstSection=FALSE; firstItem=TRUE; } else if (!useSections && first) { ol.startItemList(); first=FALSE; } // member name if (!firstItem) ol.endItemListItem(); ol.startItemListItem(); firstItem=FALSE; ol.docify(name); if (isFunc) ol.docify("()"); ol.writeString("\n"); // link to class prevDefName=""; sep = ": "; prevName = name.data()+startIndex; } else // same entry { sep = ", "; // link to class for other members with the same name } if (index<3) { // write the link for the specific list type writeLinkForMemberMap[index](ol,md,sep,prevDefName); } } } if (!firstItem) ol.endItemListItem(); ol.endItemList(); } //---------------------------------------------------------------------------- void initClassMemberIndices() { int j=0; for (j=0;jisLinkableInProject() && (cd=md->getClassDef()) && cd->isLinkableInProject() && cd->templateMaster()==0) { QCString n = md->name(); int index = getPrefixIndex(n); uint letter = getUtf8CodeToLower(n,index); if (!n.isEmpty()) { bool isFriendToHide = hideFriendCompounds && (QCString(md->typeString())=="friend class" || QCString(md->typeString())=="friend struct" || QCString(md->typeString())=="friend union"); if (!(md->isFriend() && isFriendToHide) && (!md->isEnumValue() || (md->getEnumScope() && !md->getEnumScope()->isStrong())) ) { g_memberIndexLetterUsed[CMHL_All].append(letter,md); documentedClassMembers[CMHL_All]++; } if (md->isFunction() || md->isSlot() || md->isSignal()) { g_memberIndexLetterUsed[CMHL_Functions].append(letter,md); documentedClassMembers[CMHL_Functions]++; } else if (md->isVariable()) { g_memberIndexLetterUsed[CMHL_Variables].append(letter,md); documentedClassMembers[CMHL_Variables]++; } else if (md->isTypedef()) { g_memberIndexLetterUsed[CMHL_Typedefs].append(letter,md); documentedClassMembers[CMHL_Typedefs]++; } else if (md->isEnumerate()) { g_memberIndexLetterUsed[CMHL_Enums].append(letter,md); documentedClassMembers[CMHL_Enums]++; } else if (md->isEnumValue() && md->getEnumScope() && !md->getEnumScope()->isStrong()) { g_memberIndexLetterUsed[CMHL_EnumValues].append(letter,md); documentedClassMembers[CMHL_EnumValues]++; } else if (md->isProperty()) { g_memberIndexLetterUsed[CMHL_Properties].append(letter,md); documentedClassMembers[CMHL_Properties]++; } else if (md->isEvent()) { g_memberIndexLetterUsed[CMHL_Events].append(letter,md); documentedClassMembers[CMHL_Events]++; } else if (md->isRelated() || md->isForeign() || (md->isFriend() && !isFriendToHide)) { g_memberIndexLetterUsed[CMHL_Related].append(letter,md); documentedClassMembers[CMHL_Related]++; } } } } //---------------------------------------------------------------------------- void initNamespaceMemberIndices() { int j=0; for (j=0;jgetNamespaceDef(); if (nd && nd->isLinkableInProject() && md->isLinkableInProject()) { QCString n = md->name(); int index = getPrefixIndex(n); uint letter = getUtf8CodeToLower(n,index); if (!n.isEmpty()) { if (!md->isEnumValue() || (md->getEnumScope() && !md->getEnumScope()->isStrong())) { g_namespaceIndexLetterUsed[NMHL_All].append(letter,md); documentedNamespaceMembers[NMHL_All]++; } if (md->isFunction()) { g_namespaceIndexLetterUsed[NMHL_Functions].append(letter,md); documentedNamespaceMembers[NMHL_Functions]++; } else if (md->isVariable()) { g_namespaceIndexLetterUsed[NMHL_Variables].append(letter,md); documentedNamespaceMembers[NMHL_Variables]++; } else if (md->isTypedef()) { g_namespaceIndexLetterUsed[NMHL_Typedefs].append(letter,md); documentedNamespaceMembers[NMHL_Typedefs]++; } else if (md->isSequence()) { g_namespaceIndexLetterUsed[NMHL_Sequences].append(letter,md); documentedNamespaceMembers[NMHL_Sequences]++; } else if (md->isDictionary()) { g_namespaceIndexLetterUsed[NMHL_Dictionaries].append(letter,md); documentedNamespaceMembers[NMHL_Dictionaries]++; } else if (md->isEnumerate()) { g_namespaceIndexLetterUsed[NMHL_Enums].append(letter,md); documentedNamespaceMembers[NMHL_Enums]++; } else if (md->isEnumValue() && md->getEnumScope() && !md->getEnumScope()->isStrong()) { g_namespaceIndexLetterUsed[NMHL_EnumValues].append(letter,md); documentedNamespaceMembers[NMHL_EnumValues]++; } } } } //---------------------------------------------------------------------------- void initFileMemberIndices() { int j=0; for (j=0;jgetFileDef(); if (fd && fd->isLinkableInProject() && md->isLinkableInProject()) { QCString n = md->name(); int index = getPrefixIndex(n); uint letter = getUtf8CodeToLower(n,index); if (!n.isEmpty()) { if (!md->isEnumValue() || (md->getEnumScope() && !md->getEnumScope()->isStrong())) { g_fileIndexLetterUsed[FMHL_All].append(letter,md); documentedFileMembers[FMHL_All]++; } if (md->isFunction()) { g_fileIndexLetterUsed[FMHL_Functions].append(letter,md); documentedFileMembers[FMHL_Functions]++; } else if (md->isVariable()) { g_fileIndexLetterUsed[FMHL_Variables].append(letter,md); documentedFileMembers[FMHL_Variables]++; } else if (md->isTypedef()) { g_fileIndexLetterUsed[FMHL_Typedefs].append(letter,md); documentedFileMembers[FMHL_Typedefs]++; } else if (md->isSequence()) { g_fileIndexLetterUsed[FMHL_Sequences].append(letter,md); documentedFileMembers[FMHL_Sequences]++; } else if (md->isDictionary()) { g_fileIndexLetterUsed[FMHL_Dictionaries].append(letter,md); documentedFileMembers[FMHL_Dictionaries]++; } else if (md->isEnumerate()) { g_fileIndexLetterUsed[FMHL_Enums].append(letter,md); documentedFileMembers[FMHL_Enums]++; } else if (md->isEnumValue() && md->getEnumScope() && !md->getEnumScope()->isStrong()) { g_fileIndexLetterUsed[FMHL_EnumValues].append(letter,md); documentedFileMembers[FMHL_EnumValues]++; } else if (md->isDefine()) { g_fileIndexLetterUsed[FMHL_Defines].append(letter,md); documentedFileMembers[FMHL_Defines]++; } } } } //---------------------------------------------------------------------------- static void writeQuickMemberIndex(OutputList &ol, const LetterToIndexMap &charUsed,uint page, QCString fullName,bool multiPage) { bool first=TRUE; startQuickIndexList(ol,TRUE); SIntDict::Iterator it(charUsed); MemberIndexList *ml; for (it.toFirst();(ml=it.current());++it) { uint i = ml->letter(); QCString is = letterToLabel(i); QCString ci = letterToString(i); QCString anchor; QCString extension=Doxygen::htmlFileExtension; if (!multiPage) anchor="#index_"; else if (first) anchor=fullName+extension+"#index_"; else anchor=fullName+"_"+letterToLabel(i)+extension+"#index_"; startQuickIndexItem(ol,anchor+convertToId(is),i==page,TRUE,first); ol.writeString(ci); endQuickIndexItem(ol); first=FALSE; } endQuickIndexList(ol); } //---------------------------------------------------------------------------- /** Helper class representing a class member in the navigation menu. */ struct CmhlInfo { CmhlInfo(const char *fn,const char *t) : fname(fn), title(t) {} const char *fname; QCString title; }; static const CmhlInfo *getCmhlInfo(int hl) { static bool fortranOpt = Config_getBool(OPTIMIZE_FOR_FORTRAN); static bool vhdlOpt = Config_getBool(OPTIMIZE_OUTPUT_VHDL); static CmhlInfo cmhlInfo[] = { CmhlInfo("functions", theTranslator->trAll()), CmhlInfo("functions_func", fortranOpt ? theTranslator->trSubprograms() : vhdlOpt ? theTranslator->trFunctionAndProc() : theTranslator->trFunctions()), CmhlInfo("functions_vars",theTranslator->trVariables()), CmhlInfo("functions_type",theTranslator->trTypedefs()), CmhlInfo("functions_enum",theTranslator->trEnumerations()), CmhlInfo("functions_eval",theTranslator->trEnumerationValues()), CmhlInfo("functions_prop",theTranslator->trProperties()), CmhlInfo("functions_evnt",theTranslator->trEvents()), CmhlInfo("functions_rela",theTranslator->trRelatedFunctions()) }; return &cmhlInfo[hl]; } static void writeClassMemberIndexFiltered(OutputList &ol, ClassMemberHighlight hl) { if (documentedClassMembers[hl]==0) return; static bool disableIndex = Config_getBool(DISABLE_INDEX); bool multiPageIndex=FALSE; if (documentedClassMembers[hl]>MAX_ITEMS_BEFORE_MULTIPAGE_INDEX) { multiPageIndex=TRUE; } ol.pushGeneratorState(); ol.disableAllBut(OutputGenerator::Html); QCString extension=Doxygen::htmlFileExtension; LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::ClassMembers); QCString title = lne ? lne->title() : theTranslator->trCompoundMembers(); if (hl!=CMHL_All) title+=(QCString)" - "+getCmhlInfo(hl)->title; bool addToIndex = lne==0 || lne->visible(); if (addToIndex) { Doxygen::indexList->addContentsItem(multiPageIndex,getCmhlInfo(hl)->title,0, getCmhlInfo(hl)->fname,0,multiPageIndex,TRUE); if (multiPageIndex) Doxygen::indexList->incContentsDepth(); } bool first=TRUE; SIntDict::Iterator it(g_memberIndexLetterUsed[hl]); MemberIndexList *ml; for (it.toFirst();(ml=it.current());++it) { uint page = ml->letter(); QCString fileName = getCmhlInfo(hl)->fname; if (multiPageIndex) { if (!first) { fileName+="_"+letterToLabel(page); } QCString cs = letterToString(page); if (addToIndex) { Doxygen::indexList->addContentsItem(FALSE,cs,0,fileName,0,FALSE,TRUE); } } bool quickIndex = documentedClassMembers[hl]>maxItemsBeforeQuickIndex; ol.startFile(fileName+extension,0,title); ol.startQuickIndices(); if (!disableIndex) { ol.writeQuickLinks(TRUE,HLI_Functions,0); if (!Config_getBool(HTML_DYNAMIC_MENUS)) { startQuickIndexList(ol); // index item for global member list startQuickIndexItem(ol, getCmhlInfo(0)->fname+Doxygen::htmlFileExtension,hl==CMHL_All,TRUE,first); ol.writeString(fixSpaces(getCmhlInfo(0)->title)); endQuickIndexItem(ol); int i; // index items per category member lists for (i=1;i0) { startQuickIndexItem(ol,getCmhlInfo(i)->fname+Doxygen::htmlFileExtension,hl==i,TRUE,first); ol.writeString(fixSpaces(getCmhlInfo(i)->title)); //printf("multiPageIndex=%d first=%d fileName=%s file=%s title=%s\n", // multiPageIndex,first,fileName.data(),getCmhlInfo(i)->fname,getCmhlInfo(i)->title.data()); endQuickIndexItem(ol); } } endQuickIndexList(ol); // quick alphabetical index if (quickIndex) { writeQuickMemberIndex(ol,g_memberIndexLetterUsed[hl],page, getCmhlInfo(hl)->fname,multiPageIndex); } } } ol.endQuickIndices(); ol.writeSplitBar(fileName); ol.writeSearchInfo(); ol.startContents(); if (hl==CMHL_All) { ol.startTextBlock(); ol.parseText(lne ? lne->intro() : theTranslator->trCompoundMembersDescription(Config_getBool(EXTRACT_ALL))); ol.endTextBlock(); } else { // hack to work around a mozilla bug, which refuses to switch to // normal lists otherwise ol.writeString(" "); } writeMemberList(ol,quickIndex, multiPageIndex?page:-1, g_memberIndexLetterUsed[hl], Definition::TypeClass); endFile(ol); first=FALSE; } if (multiPageIndex && addToIndex) Doxygen::indexList->decContentsDepth(); ol.popGeneratorState(); } static void writeClassMemberIndex(OutputList &ol) { LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::ClassMembers); bool addToIndex = lne==0 || lne->visible(); if (documentedClassMembers[CMHL_All]>0 && addToIndex) { Doxygen::indexList->addContentsItem(TRUE,lne ? lne->title() : theTranslator->trCompoundMembers(),0,"functions",0); Doxygen::indexList->incContentsDepth(); } writeClassMemberIndexFiltered(ol,CMHL_All); writeClassMemberIndexFiltered(ol,CMHL_Functions); writeClassMemberIndexFiltered(ol,CMHL_Variables); writeClassMemberIndexFiltered(ol,CMHL_Typedefs); writeClassMemberIndexFiltered(ol,CMHL_Enums); writeClassMemberIndexFiltered(ol,CMHL_EnumValues); writeClassMemberIndexFiltered(ol,CMHL_Properties); writeClassMemberIndexFiltered(ol,CMHL_Events); writeClassMemberIndexFiltered(ol,CMHL_Related); if (documentedClassMembers[CMHL_All]>0 && addToIndex) { Doxygen::indexList->decContentsDepth(); } } //---------------------------------------------------------------------------- /** Helper class representing a file member in the navigation menu. */ struct FmhlInfo { FmhlInfo(const char *fn,const char *t) : fname(fn), title(t) {} const char *fname; QCString title; }; static const FmhlInfo *getFmhlInfo(int hl) { static bool fortranOpt = Config_getBool(OPTIMIZE_FOR_FORTRAN); static bool vhdlOpt = Config_getBool(OPTIMIZE_OUTPUT_VHDL); static bool sliceOpt = Config_getBool(OPTIMIZE_OUTPUT_SLICE); static FmhlInfo fmhlInfo[] = { FmhlInfo("globals", theTranslator->trAll()), FmhlInfo("globals_func", fortranOpt ? theTranslator->trSubprograms() : vhdlOpt ? theTranslator->trFunctionAndProc() : theTranslator->trFunctions()), FmhlInfo("globals_vars",sliceOpt ? theTranslator->trConstants() : theTranslator->trVariables()), FmhlInfo("globals_type",theTranslator->trTypedefs()), FmhlInfo("globals_sequ",theTranslator->trSequences()), FmhlInfo("globals_dict",theTranslator->trDictionaries()), FmhlInfo("globals_enum",theTranslator->trEnumerations()), FmhlInfo("globals_eval",theTranslator->trEnumerationValues()), FmhlInfo("globals_defs",theTranslator->trDefines()) }; return &fmhlInfo[hl]; } static void writeFileMemberIndexFiltered(OutputList &ol, FileMemberHighlight hl) { if (documentedFileMembers[hl]==0) return; static bool disableIndex = Config_getBool(DISABLE_INDEX); bool multiPageIndex=FALSE; if (documentedFileMembers[hl]>MAX_ITEMS_BEFORE_MULTIPAGE_INDEX) { multiPageIndex=TRUE; } ol.pushGeneratorState(); ol.disableAllBut(OutputGenerator::Html); QCString extension=Doxygen::htmlFileExtension; LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::FileGlobals); QCString title = lne ? lne->title() : theTranslator->trFileMembers(); bool addToIndex = lne==0 || lne->visible(); if (addToIndex) { Doxygen::indexList->addContentsItem(multiPageIndex,getFmhlInfo(hl)->title,0, getFmhlInfo(hl)->fname,0,multiPageIndex,TRUE); if (multiPageIndex) Doxygen::indexList->incContentsDepth(); } bool first=TRUE; SIntDict::Iterator it(g_fileIndexLetterUsed[hl]); MemberIndexList *ml; for (it.toFirst();(ml=it.current());++it) { uint page = ml->letter(); QCString fileName = getFmhlInfo(hl)->fname; if (multiPageIndex) { if (!first) { fileName+="_"+letterToLabel(page); } QCString cs = letterToString(page); if (addToIndex) { Doxygen::indexList->addContentsItem(FALSE,cs,0,fileName,0,FALSE,TRUE); } } bool quickIndex = documentedFileMembers[hl]>maxItemsBeforeQuickIndex; ol.startFile(fileName+extension,0,title); ol.startQuickIndices(); if (!disableIndex) { ol.writeQuickLinks(TRUE,HLI_Globals,0); if (!Config_getBool(HTML_DYNAMIC_MENUS)) { startQuickIndexList(ol); // index item for all file member lists startQuickIndexItem(ol, getFmhlInfo(0)->fname+Doxygen::htmlFileExtension,hl==FMHL_All,TRUE,first); ol.writeString(fixSpaces(getFmhlInfo(0)->title)); endQuickIndexItem(ol); int i; // index items for per category member lists for (i=1;i0) { startQuickIndexItem(ol, getFmhlInfo(i)->fname+Doxygen::htmlFileExtension,hl==i,TRUE,first); ol.writeString(fixSpaces(getFmhlInfo(i)->title)); endQuickIndexItem(ol); } } endQuickIndexList(ol); if (quickIndex) { writeQuickMemberIndex(ol,g_fileIndexLetterUsed[hl],page, getFmhlInfo(hl)->fname,multiPageIndex); } } } ol.endQuickIndices(); ol.writeSplitBar(fileName); ol.writeSearchInfo(); ol.startContents(); if (hl==FMHL_All) { ol.startTextBlock(); ol.parseText(lne ? lne->intro() : theTranslator->trFileMembersDescription(Config_getBool(EXTRACT_ALL))); ol.endTextBlock(); } else { // hack to work around a mozilla bug, which refuses to switch to // normal lists otherwise ol.writeString(" "); } writeMemberList(ol,quickIndex, multiPageIndex?page:-1, g_fileIndexLetterUsed[hl], Definition::TypeFile); endFile(ol); first=FALSE; } if (multiPageIndex && addToIndex) Doxygen::indexList->decContentsDepth(); ol.popGeneratorState(); } static void writeFileMemberIndex(OutputList &ol) { LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::FileGlobals); bool addToIndex = lne==0 || lne->visible(); if (documentedFileMembers[FMHL_All]>0 && addToIndex) { Doxygen::indexList->addContentsItem(FALSE,lne ? lne->title() : theTranslator->trFileMembers(),0,"globals",0); Doxygen::indexList->incContentsDepth(); } writeFileMemberIndexFiltered(ol,FMHL_All); writeFileMemberIndexFiltered(ol,FMHL_Functions); writeFileMemberIndexFiltered(ol,FMHL_Variables); writeFileMemberIndexFiltered(ol,FMHL_Typedefs); writeFileMemberIndexFiltered(ol,FMHL_Sequences); writeFileMemberIndexFiltered(ol,FMHL_Dictionaries); writeFileMemberIndexFiltered(ol,FMHL_Enums); writeFileMemberIndexFiltered(ol,FMHL_EnumValues); writeFileMemberIndexFiltered(ol,FMHL_Defines); if (documentedFileMembers[FMHL_All]>0 && addToIndex) { Doxygen::indexList->decContentsDepth(); } } //---------------------------------------------------------------------------- /** Helper class representing a namespace member in the navigation menu. */ struct NmhlInfo { NmhlInfo(const char *fn,const char *t) : fname(fn), title(t) {} const char *fname; QCString title; }; static const NmhlInfo *getNmhlInfo(int hl) { static bool fortranOpt = Config_getBool(OPTIMIZE_FOR_FORTRAN); static bool vhdlOpt = Config_getBool(OPTIMIZE_OUTPUT_VHDL); static bool sliceOpt = Config_getBool(OPTIMIZE_OUTPUT_SLICE); static NmhlInfo nmhlInfo[] = { NmhlInfo("namespacemembers", theTranslator->trAll()), NmhlInfo("namespacemembers_func", fortranOpt ? theTranslator->trSubprograms() : vhdlOpt ? theTranslator->trFunctionAndProc() : theTranslator->trFunctions()), NmhlInfo("namespacemembers_vars",sliceOpt ? theTranslator->trConstants() : theTranslator->trVariables()), NmhlInfo("namespacemembers_type",theTranslator->trTypedefs()), NmhlInfo("namespacemembers_sequ",theTranslator->trSequences()), NmhlInfo("namespacemembers_dict",theTranslator->trDictionaries()), NmhlInfo("namespacemembers_enum",theTranslator->trEnumerations()), NmhlInfo("namespacemembers_eval",theTranslator->trEnumerationValues()) }; return &nmhlInfo[hl]; } //---------------------------------------------------------------------------- static void writeNamespaceMemberIndexFiltered(OutputList &ol, NamespaceMemberHighlight hl) { if (documentedNamespaceMembers[hl]==0) return; static bool disableIndex = Config_getBool(DISABLE_INDEX); bool multiPageIndex=FALSE; if (documentedNamespaceMembers[hl]>MAX_ITEMS_BEFORE_MULTIPAGE_INDEX) { multiPageIndex=TRUE; } ol.pushGeneratorState(); ol.disableAllBut(OutputGenerator::Html); QCString extension=Doxygen::htmlFileExtension; LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::NamespaceMembers); QCString title = lne ? lne->title() : theTranslator->trNamespaceMembers(); bool addToIndex = lne==0 || lne->visible(); if (addToIndex) { Doxygen::indexList->addContentsItem(multiPageIndex,getNmhlInfo(hl)->title,0, getNmhlInfo(hl)->fname,0,multiPageIndex,TRUE); if (multiPageIndex) Doxygen::indexList->incContentsDepth(); } bool first=TRUE; SIntDict::Iterator it(g_namespaceIndexLetterUsed[hl]); MemberIndexList *ml; for (it.toFirst();(ml=it.current());++it) { uint page = ml->letter(); QCString fileName = getNmhlInfo(hl)->fname; if (multiPageIndex) { if (!first) { fileName+="_"+letterToLabel(page); } QCString cs = letterToString(page); if (addToIndex) { Doxygen::indexList->addContentsItem(FALSE,cs,0,fileName,0,FALSE,TRUE); } } bool quickIndex = documentedNamespaceMembers[hl]>maxItemsBeforeQuickIndex; ol.startFile(fileName+extension,0,title); ol.startQuickIndices(); if (!disableIndex) { ol.writeQuickLinks(TRUE,HLI_NamespaceMembers,0); if (!Config_getBool(HTML_DYNAMIC_MENUS)) { startQuickIndexList(ol); // index item for all namespace member lists startQuickIndexItem(ol, getNmhlInfo(0)->fname+Doxygen::htmlFileExtension,hl==NMHL_All,TRUE,first); ol.writeString(fixSpaces(getNmhlInfo(0)->title)); endQuickIndexItem(ol); int i; // index items per category member lists for (i=1;i0) { startQuickIndexItem(ol, getNmhlInfo(i)->fname+Doxygen::htmlFileExtension,hl==i,TRUE,first); ol.writeString(fixSpaces(getNmhlInfo(i)->title)); endQuickIndexItem(ol); } } endQuickIndexList(ol); if (quickIndex) { writeQuickMemberIndex(ol,g_namespaceIndexLetterUsed[hl],page, getNmhlInfo(hl)->fname,multiPageIndex); } } } ol.endQuickIndices(); ol.writeSplitBar(fileName); ol.writeSearchInfo(); ol.startContents(); if (hl==NMHL_All) { ol.startTextBlock(); ol.parseText(lne ? lne->intro() : theTranslator->trNamespaceMemberDescription(Config_getBool(EXTRACT_ALL))); ol.endTextBlock(); } else { // hack to work around a mozilla bug, which refuses to switch to // normal lists otherwise ol.writeString(" "); } writeMemberList(ol,quickIndex, multiPageIndex?page:-1, g_namespaceIndexLetterUsed[hl], Definition::TypeNamespace); endFile(ol); first=FALSE; } if (multiPageIndex && addToIndex) Doxygen::indexList->decContentsDepth(); ol.popGeneratorState(); } static void writeNamespaceMemberIndex(OutputList &ol) { LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::NamespaceMembers); bool addToIndex = lne==0 || lne->visible(); if (documentedNamespaceMembers[NMHL_All]>0 && addToIndex) { Doxygen::indexList->addContentsItem(FALSE,lne ? lne->title() : theTranslator->trNamespaceMembers(),0,"namespacemembers",0); Doxygen::indexList->incContentsDepth(); } //bool fortranOpt = Config_getBool(OPTIMIZE_FOR_FORTRAN); writeNamespaceMemberIndexFiltered(ol,NMHL_All); writeNamespaceMemberIndexFiltered(ol,NMHL_Functions); writeNamespaceMemberIndexFiltered(ol,NMHL_Variables); writeNamespaceMemberIndexFiltered(ol,NMHL_Typedefs); writeNamespaceMemberIndexFiltered(ol,NMHL_Sequences); writeNamespaceMemberIndexFiltered(ol,NMHL_Dictionaries); writeNamespaceMemberIndexFiltered(ol,NMHL_Enums); writeNamespaceMemberIndexFiltered(ol,NMHL_EnumValues); if (documentedNamespaceMembers[NMHL_All]>0 && addToIndex) { Doxygen::indexList->decContentsDepth(); } } //---------------------------------------------------------------------------- //---------------------------------------------------------------------------- static void writeExampleIndex(OutputList &ol) { if (Doxygen::exampleSDict->count()==0) return; ol.pushGeneratorState(); ol.disable(OutputGenerator::Man); ol.disable(OutputGenerator::Docbook); LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::Examples); QCString title = lne ? lne->title() : theTranslator->trExamples(); bool addToIndex = lne==0 || lne->visible(); startFile(ol,"examples",0,title,HLI_Examples); startTitle(ol,0); ol.parseText(title); endTitle(ol,0,0); ol.startContents(); if (addToIndex) { Doxygen::indexList->addContentsItem(TRUE,title,0,"examples",0,TRUE,TRUE); Doxygen::indexList->incContentsDepth(); } ol.startTextBlock(); ol.parseText(lne ? lne->intro() : theTranslator->trExamplesDescription()); ol.endTextBlock(); ol.startItemList(); PageSDict::Iterator pdi(*Doxygen::exampleSDict); PageDef *pd=0; for (pdi.toFirst();(pd=pdi.current());++pdi) { ol.startItemListItem(); QCString n=pd->getOutputFileBase(); if (!pd->title().isEmpty()) { ol.writeObjectLink(0,n,0,pd->title()); if (addToIndex) { Doxygen::indexList->addContentsItem(FALSE,filterTitle(pd->title()),pd->getReference(),n,0,FALSE,TRUE); } } else { ol.writeObjectLink(0,n,0,pd->name()); if (addToIndex) { Doxygen::indexList->addContentsItem(FALSE,pd->name(),pd->getReference(),n,0,FALSE,TRUE); } } ol.endItemListItem(); ol.writeString("\n"); } ol.endItemList(); if (addToIndex) { Doxygen::indexList->decContentsDepth(); } endFile(ol); ol.popGeneratorState(); } //---------------------------------------------------------------------------- static void countRelatedPages(int &docPages,int &indexPages) { docPages=indexPages=0; PageSDict::Iterator pdi(*Doxygen::pageSDict); PageDef *pd=0; for (pdi.toFirst();(pd=pdi.current());++pdi) { if ( pd->visibleInIndex()) { indexPages++; } if ( pd->documentedPage()) { docPages++; } } } //---------------------------------------------------------------------------- static bool mainPageHasOwnTitle() { static QCString projectName = Config_getString(PROJECT_NAME); QCString title; if (Doxygen::mainPage) { title = filterTitle(Doxygen::mainPage->title()); } return !projectName.isEmpty() && mainPageHasTitle() && qstricmp(title,projectName)!=0; } static void writePages(PageDef *pd,FTVHelp *ftv) { //printf("writePages()=%s pd=%p mainpage=%p\n",pd->name().data(),pd,Doxygen::mainPage); LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::Pages); bool addToIndex = lne==0 || lne->visible(); if (!addToIndex) return; bool hasSubPages = pd->hasSubPages(); bool hasSections = pd->hasSections(); if (pd->visibleInIndex()) { QCString pageTitle; if (pd->title().isEmpty()) pageTitle=pd->name(); else pageTitle=filterTitle(pd->title()); if (ftv) { //printf("*** adding %s hasSubPages=%d hasSections=%d\n",pageTitle.data(),hasSubPages,hasSections); ftv->addContentsItem( hasSubPages,pageTitle, pd->getReference(),pd->getOutputFileBase(), 0,hasSubPages,TRUE,pd); } if (addToIndex && pd!=Doxygen::mainPage) { Doxygen::indexList->addContentsItem( hasSubPages || hasSections,pageTitle, pd->getReference(),pd->getOutputFileBase(), 0,hasSubPages,TRUE); } } if (hasSubPages && ftv) ftv->incContentsDepth(); bool doIndent = (hasSections || hasSubPages) && (pd!=Doxygen::mainPage || mainPageHasOwnTitle()); if (doIndent) { Doxygen::indexList->incContentsDepth(); } if (hasSections) { pd->addSectionsToIndex(); } PageSDict *subPages = pd->getSubPages(); if (subPages) { PageSDict::Iterator pi(*subPages); PageDef *subPage; for (pi.toFirst();(subPage=pi.current());++pi) { writePages(subPage,ftv); } } if (hasSubPages && ftv) ftv->decContentsDepth(); if (doIndent) { Doxygen::indexList->decContentsDepth(); } //printf("end writePages()=%s\n",pd->title().data()); } //---------------------------------------------------------------------------- static void writePageIndex(OutputList &ol) { if (indexedPages==0) return; ol.pushGeneratorState(); ol.disableAllBut(OutputGenerator::Html); LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::Pages); QCString title = lne ? lne->title() : theTranslator->trRelatedPages(); startFile(ol,"pages",0,title,HLI_Pages); startTitle(ol,0); ol.parseText(title); endTitle(ol,0,0); ol.startContents(); ol.startTextBlock(); ol.parseText(lne ? lne->intro() : theTranslator->trRelatedPagesDescription()); ol.endTextBlock(); { FTVHelp* ftv = new FTVHelp(FALSE); PageSDict::Iterator pdi(*Doxygen::pageSDict); PageDef *pd=0; for (pdi.toFirst();(pd=pdi.current());++pdi) { if ((pd->getOuterScope()==0 || pd->getOuterScope()->definitionType()!=Definition::TypePage) && // not a sub page !pd->isReference() // not an external page ) { writePages(pd,ftv); } } QGString outStr; FTextStream t(&outStr); ftv->generateTreeViewInline(t); ol.writeString(outStr); delete ftv; } // ol.popGeneratorState(); // ------ endFile(ol); ol.popGeneratorState(); } //---------------------------------------------------------------------------- static int countGroups() { int count=0; GroupSDict::Iterator gli(*Doxygen::groupSDict); GroupDef *gd; for (gli.toFirst();(gd=gli.current());++gli) { if (!gd->isReference()) { //gd->visited=FALSE; count++; } } return count; } //---------------------------------------------------------------------------- static int countDirs() { int count=0; SDict::Iterator dli(*Doxygen::directories); DirDef *dd; for (dli.toFirst();(dd=dli.current());++dli) { if (dd->isLinkableInProject()) { count++; } } return count; } //---------------------------------------------------------------------------- void writeGraphInfo(OutputList &ol) { if (!Config_getBool(HAVE_DOT) || !Config_getBool(GENERATE_HTML)) return; ol.pushGeneratorState(); ol.disableAllBut(OutputGenerator::Html); DotLegendGraph gd; gd.writeGraph(Config_getString(HTML_OUTPUT)); bool stripCommentsStateRef = Config_getBool(STRIP_CODE_COMMENTS); bool oldStripCommentsState = stripCommentsStateRef; bool createSubdirs = Config_getBool(CREATE_SUBDIRS); bool oldCreateSubdirs = createSubdirs; // temporarily disable the stripping of comments for our own code example! stripCommentsStateRef = Config_updateBool(STRIP_CODE_COMMENTS,FALSE); // temporarily disable create subdirs for linking to our example createSubdirs = Config_updateBool(CREATE_SUBDIRS,FALSE); startFile(ol,"graph_legend",0,theTranslator->trLegendTitle().data()); startTitle(ol,0); ol.parseText(theTranslator->trLegendTitle()); endTitle(ol,0,0); ol.startContents(); QCString legendDocs = theTranslator->trLegendDocs(); int s = legendDocs.find("
"); int e = legendDocs.find("
"); QCString imgExt = getDotImageExtension(); if (imgExt=="svg" && s!=-1 && e!=-1) { legendDocs = legendDocs.left(s+8) + "[!-- SVG 0 --]\n" + legendDocs.mid(e); //printf("legendDocs=%s\n",legendDocs.data()); } FileDef *fd = createFileDef("","graph_legend.dox"); ol.generateDoc("graph_legend",1,fd,0,legendDocs,FALSE,FALSE, 0,FALSE,FALSE,FALSE); delete fd; // restore config settings Config_updateBool(STRIP_CODE_COMMENTS,oldStripCommentsState); Config_updateBool(CREATE_SUBDIRS,oldCreateSubdirs); endFile(ol); ol.popGeneratorState(); } //---------------------------------------------------------------------------- /*! * write groups as hierarchical trees */ static void writeGroupTreeNode(OutputList &ol, GroupDef *gd, int level, FTVHelp* ftv, bool addToIndex) { //bool fortranOpt = Config_getBool(OPTIMIZE_FOR_FORTRAN); //bool vhdlOpt = Config_getBool(OPTIMIZE_OUTPUT_VHDL); if (level>20) { warn(gd->getDefFileName(),gd->getDefLine(), "maximum nesting level exceeded for group %s: check for possible recursive group relation!\n",gd->name().data() ); return; } /* Some groups should appear twice under different parent-groups. * That is why we should not check if it was visited */ if (/*!gd->visited &&*/ (!gd->isASubGroup() || level>0) && gd->isVisible() && (!gd->isReference() || Config_getBool(EXTERNAL_GROUPS)) // hide external groups by default ) { //printf("gd->name()=%s #members=%d\n",gd->name().data(),gd->countMembers()); // write group info bool hasSubGroups = gd->getSubGroups()->count()>0; bool hasSubPages = gd->getPages()->count()>0; size_t numSubItems = 0; if (1 /*Config_getBool(TOC_EXPAND)*/) { QListIterator mli(gd->getMemberLists()); MemberList *ml; for (mli.toFirst();(ml=mli.current());++mli) { if (ml->listType()&MemberListType_documentationLists) { numSubItems += ml->count(); } } numSubItems += gd->getNamespaces().size(); numSubItems += gd->getClasses().size(); numSubItems += gd->getFiles()->count(); numSubItems += gd->getDirs().size(); numSubItems += gd->getPages()->count(); } bool isDir = hasSubGroups || hasSubPages || numSubItems>0; //printf("gd='%s': pageDict=%d\n",gd->name().data(),gd->pageDict->count()); if (addToIndex) { Doxygen::indexList->addContentsItem(isDir,gd->groupTitle(),gd->getReference(),gd->getOutputFileBase(),0,isDir,TRUE); Doxygen::indexList->incContentsDepth(); } if (ftv) { ftv->addContentsItem(hasSubGroups,gd->groupTitle(), gd->getReference(),gd->getOutputFileBase(),0, FALSE,FALSE,gd); ftv->incContentsDepth(); } //ol.writeListItem(); //ol.startTextLink(gd->getOutputFileBase(),0); //parseText(ol,gd->groupTitle()); //ol.endTextLink(); ol.startIndexListItem(); ol.startIndexItem(gd->getReference(),gd->getOutputFileBase()); ol.parseText(gd->groupTitle()); ol.endIndexItem(gd->getReference(),gd->getOutputFileBase()); if (gd->isReference()) { ol.startTypewriter(); ol.docify(" [external]"); ol.endTypewriter(); } QListIterator eli(LayoutDocManager::instance().docEntries(LayoutDocManager::Group)); LayoutDocEntry *lde; for (eli.toFirst();(lde=eli.current());++eli) { if (lde->kind()==LayoutDocEntry::MemberDef && addToIndex) { LayoutDocEntryMemberDef *lmd = (LayoutDocEntryMemberDef*)lde; MemberList *ml = gd->getMemberList(lmd->type); if (ml) { MemberListIterator mi(*ml); MemberDef *md; for (mi.toFirst();(md=mi.current());++mi) { const MemberList *enumList = md->enumFieldList(); isDir = enumList!=0 && md->isEnumerate(); if (md->isVisible() && !md->isAnonymous()) { Doxygen::indexList->addContentsItem(isDir, md->name(),md->getReference(), md->getOutputFileBase(),md->anchor(),FALSE,addToIndex); } if (isDir) { Doxygen::indexList->incContentsDepth(); MemberListIterator emli(*enumList); MemberDef *emd; for (emli.toFirst();(emd=emli.current());++emli) { if (emd->isVisible()) { Doxygen::indexList->addContentsItem(FALSE, emd->name(),emd->getReference(),emd->getOutputFileBase(), emd->anchor(),FALSE,addToIndex); } } Doxygen::indexList->decContentsDepth(); } } } } else if (lde->kind()==LayoutDocEntry::GroupClasses && addToIndex) { for (const auto &cd : gd->getClasses()) { //bool nestedClassInSameGroup = // cd->getOuterScope() && cd->getOuterScope()->definitionType()==Definition::TypeClass && // cd->getOuterScope()->partOfGroups()!=0 && cd->getOuterScope()->partOfGroups()->contains(gd); //printf("===== GroupClasses: %s visible=%d nestedClassInSameGroup=%d\n",cd->name().data(),cd->isVisible(),nestedClassInSameGroup); if (cd->isVisible() /*&& !nestedClassInSameGroup*/) { //if (cd->isEmbeddedInOuterScope()) //{ //printf("add class & members %d\n",addToIndex); addMembersToIndex(cd,LayoutDocManager::Class,cd->displayName(FALSE),cd->anchor(),addToIndex,TRUE); //} //else // only index the class, not its members //{ // printf("%s: add class only\n",cd->name().data()); // Doxygen::indexList->addContentsItem(FALSE, // cd->displayName(TRUE),cd->getReference(), // cd->getOutputFileBase(),cd->anchor(),addToIndex,TRUE); //} } } } else if (lde->kind()==LayoutDocEntry::GroupNamespaces && addToIndex) { for (const auto &nd : gd->getNamespaces()) { if (nd->isVisible()) { Doxygen::indexList->addContentsItem(FALSE, nd->localName(),nd->getReference(), nd->getOutputFileBase(),0,FALSE,FALSE); } } } else if (lde->kind()==LayoutDocEntry::GroupFiles && addToIndex) { QListIterator it(*gd->getFiles()); FileDef *fd; for (;(fd=it.current());++it) { if (fd->isVisible()) { Doxygen::indexList->addContentsItem(FALSE, fd->displayName(),fd->getReference(), fd->getOutputFileBase(),0,FALSE,FALSE); } } } else if (lde->kind()==LayoutDocEntry::GroupDirs && addToIndex) { for (const auto &dd : gd->getDirs()) { if (dd->isVisible()) { Doxygen::indexList->addContentsItem(FALSE, dd->shortName(),dd->getReference(), dd->getOutputFileBase(),0,FALSE,FALSE); } } } else if (lde->kind()==LayoutDocEntry::GroupPageDocs && addToIndex) { SDict::Iterator it(*gd->getPages()); PageDef *pd; for (;(pd=it.current());++it) { const SectionInfo *si=0; if (!pd->name().isEmpty()) si=SectionManager::instance().find(pd->name()); hasSubPages = pd->hasSubPages(); bool hasSections = pd->hasSections(); Doxygen::indexList->addContentsItem( hasSubPages || hasSections, pd->title(), gd->getReference(), gd->getOutputFileBase(), si ? si->label().data() : 0, hasSubPages || hasSections, TRUE); // addToNavIndex if (hasSections || hasSubPages) { Doxygen::indexList->incContentsDepth(); } if (hasSections) { pd->addSectionsToIndex(); } writePages(pd,0); if (hasSections || hasSubPages) { Doxygen::indexList->decContentsDepth(); } } } else if (lde->kind()==LayoutDocEntry::GroupNestedGroups) { if (gd->getSubGroups()->count()>0) { startIndexHierarchy(ol,level+1); QListIterator gli(*gd->getSubGroups()); GroupDef *subgd = 0; for (gli.toFirst();(subgd=gli.current());++gli) { writeGroupTreeNode(ol,subgd,level+1,ftv,addToIndex); } endIndexHierarchy(ol,level+1); } } } ol.endIndexListItem(); if (addToIndex) { Doxygen::indexList->decContentsDepth(); } if (ftv) { ftv->decContentsDepth(); } //gd->visited=TRUE; } } static void writeGroupHierarchy(OutputList &ol, FTVHelp* ftv,bool addToIndex) { if (ftv) { ol.pushGeneratorState(); ol.disable(OutputGenerator::Html); } startIndexHierarchy(ol,0); GroupSDict::Iterator gli(*Doxygen::groupSDict); GroupDef *gd; for (gli.toFirst();(gd=gli.current());++gli) { writeGroupTreeNode(ol,gd,0,ftv,addToIndex); } endIndexHierarchy(ol,0); if (ftv) { ol.popGeneratorState(); } } #if 0 static void writeGroupTree(GroupDef *gd,FTVHelp *ftv,int level,bool addToIndex) { static bool externalGroups = Config_getBool(EXTERNAL_GROUPS); /* Some groups should appear twice under different parent-groups. * That is why we should not check if it was visited */ if ((!gd->isASubGroup() || level>0) && gd->isVisible() && (!gd->isReference() || externalGroups) // hide external groups by default ) { if (ftv) { ftv->addContentsItem(hasSubGroups,gd->groupTitle(),gd->getReference(),gd->getOutputFileBase(),0); ftv->incContentsDepth(); } if (ftv) { ftv->decContentsDepth(); } } } static void writeGroupTree(FTVHelp *ftv,bool addToIndex) { GroupSDict::Iterator gli(*Doxygen::groupSDict); GroupDef *gd; for (gli.toFirst();(gd=gli.current());++gli) { writeGroupTree(gd,ftv,0,addToIndex); } } #endif //---------------------------------------------------------------------------- static void writeGroupIndex(OutputList &ol) { if (documentedGroups==0) return; ol.pushGeneratorState(); // 1.{ ol.disable(OutputGenerator::Man); ol.disable(OutputGenerator::Docbook); LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::Modules); QCString title = lne ? lne->title() : theTranslator->trModules(); bool addToIndex = lne==0 || lne->visible(); startFile(ol,"modules",0,title,HLI_Modules); startTitle(ol,0); ol.parseText(title); endTitle(ol,0,0); ol.startContents(); ol.startTextBlock(); ol.parseText(lne ? lne->intro() : theTranslator->trModulesDescription()); ol.endTextBlock(); // --------------- // Normal group index for Latex/RTF // --------------- // 2.{ ol.pushGeneratorState(); ol.disable(OutputGenerator::Html); Doxygen::indexList->disable(); writeGroupHierarchy(ol,0,FALSE); Doxygen::indexList->enable(); ol.popGeneratorState(); // 2.} // --------------- // interactive group index for HTML // --------------- // 2.{ ol.pushGeneratorState(); ol.disableAllBut(OutputGenerator::Html); { if (addToIndex) { Doxygen::indexList->addContentsItem(TRUE,title,0,"modules",0,TRUE,TRUE); Doxygen::indexList->incContentsDepth(); } FTVHelp* ftv = new FTVHelp(FALSE); writeGroupHierarchy(ol,ftv,addToIndex); QGString outStr; FTextStream t(&outStr); ftv->generateTreeViewInline(t); ol.disableAllBut(OutputGenerator::Html); ol.writeString(outStr); delete ftv; if (addToIndex) { Doxygen::indexList->decContentsDepth(); } } ol.popGeneratorState(); // 2.} endFile(ol); ol.popGeneratorState(); // 1.} } //---------------------------------------------------------------------------- #if 0 static void writeDirIndex(OutputList &ol) { if (documentedDirs==0) return; ol.pushGeneratorState(); ol.disable(OutputGenerator::Man); LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::Dirs); QCString title = lne ? lne->title() : theTranslator->trDirectories(); bool addToIndex=FALSE; //lne==0 || lne->visible(); startFile(ol,"dirs",0,title,HLI_Directories); startTitle(ol,0); ol.parseText(title); endTitle(ol,0,0); ol.startContents(); ol.startTextBlock(); if (addToIndex) { Doxygen::indexList->addContentsItem(TRUE,title,0,"dirs",0,TRUE,TRUE); Doxygen::indexList->incContentsDepth(); } ol.parseText(lne ? lne->intro() : theTranslator->trDirDescription()); ol.endTextBlock(); FTVHelp* ftv = 0; bool treeView=Config_getBool(USE_INLINE_TREES); if (treeView) { ftv = new FTVHelp(FALSE); } writeDirHierarchy(ol,ftv,addToIndex); if (ftv) { QGString outStr; FTextStream t(&outStr); ftv->generateTreeViewInline(t); ol.pushGeneratorState(); ol.disableAllBut(OutputGenerator::Html); ol.writeString(outStr); ol.popGeneratorState(); delete ftv; } if (addToIndex) { Doxygen::indexList->decContentsDepth(); } endFile(ol); ol.popGeneratorState(); } #endif //---------------------------------------------------------------------------- static void writeUserGroupStubPage(OutputList &ol,LayoutNavEntry *lne) { if (lne->baseFile().left(9)=="usergroup") { ol.pushGeneratorState(); ol.disableAllBut(OutputGenerator::Html); startFile(ol,lne->baseFile(),0,lne->title(),HLI_UserGroup); startTitle(ol,0); ol.parseText(lne->title()); endTitle(ol,0,0); ol.startContents(); QListIterator li(lne->children()); LayoutNavEntry *entry; int count=0; for (li.toFirst();(entry=li.current());++li) { if (entry->visible()) count++; } if (count>0) { ol.writeString("\n"); } endFile(ol); ol.popGeneratorState(); } } //---------------------------------------------------------------------------- static void writeIndex(OutputList &ol) { static bool fortranOpt = Config_getBool(OPTIMIZE_FOR_FORTRAN); static bool vhdlOpt = Config_getBool(OPTIMIZE_OUTPUT_VHDL); static QCString projectName = Config_getString(PROJECT_NAME); // save old generator state ol.pushGeneratorState(); QCString projPrefix; if (!projectName.isEmpty()) { projPrefix=projectName+" "; } //-------------------------------------------------------------------- // write HTML index //-------------------------------------------------------------------- ol.disableAllBut(OutputGenerator::Html); QCString defFileName = Doxygen::mainPage ? Doxygen::mainPage->docFile().data() : "[generated]"; int defLine = Doxygen::mainPage ? Doxygen::mainPage->docLine() : -1; QCString title; if (!mainPageHasTitle()) { title = theTranslator->trMainPage(); } else if (Doxygen::mainPage) { title = filterTitle(Doxygen::mainPage->title()); } QCString indexName="index"; ol.startFile(indexName,0,title); if (Doxygen::mainPage) { if ( (!projectName.isEmpty() && mainPageHasTitle() && qstricmp(title,projectName)!=0) ) // to avoid duplicate entries in the treeview { Doxygen::indexList->addContentsItem(Doxygen::mainPage->hasSubPages(),title,0,indexName,0,Doxygen::mainPage->hasSubPages(),TRUE); } if (Doxygen::mainPage->hasSubPages() || Doxygen::mainPage->hasSections()) { writePages(Doxygen::mainPage,0); } } ol.startQuickIndices(); if (!Config_getBool(DISABLE_INDEX)) { ol.writeQuickLinks(TRUE,HLI_Main,0); } ol.endQuickIndices(); ol.writeSplitBar(indexName); ol.writeSearchInfo(); bool headerWritten=FALSE; if (Doxygen::mainPage) { if (!Doxygen::mainPage->title().isEmpty()) { if (Doxygen::mainPage->title().lower() != "notitle") ol.startPageDoc(Doxygen::mainPage->title()); else ol.startPageDoc(""); } else ol.startPageDoc(projectName); } if (Doxygen::mainPage && !Doxygen::mainPage->title().isEmpty()) { if (Doxygen::mainPage->title().lower()!="notitle") { ol.startHeaderSection(); ol.startTitleHead(0); ol.generateDoc(Doxygen::mainPage->docFile(),Doxygen::mainPage->getStartBodyLine(), Doxygen::mainPage,0,Doxygen::mainPage->title(),TRUE,FALSE, 0,TRUE,FALSE,Config_getBool(MARKDOWN_SUPPORT)); headerWritten = TRUE; } } else { if (!projectName.isEmpty()) { ol.startHeaderSection(); ol.startTitleHead(0); ol.parseText(projPrefix+theTranslator->trDocumentation()); headerWritten = TRUE; } } if (headerWritten) { ol.endTitleHead(0,0); ol.endHeaderSection(); } ol.startContents(); if (Config_getBool(DISABLE_INDEX) && Doxygen::mainPage==0) { ol.writeQuickLinks(FALSE,HLI_Main,0); } if (Doxygen::mainPage) { Doxygen::insideMainPage=TRUE; if (Doxygen::mainPage->localToc().isHtmlEnabled() && Doxygen::mainPage->hasSections()) { Doxygen::mainPage->writeToc(ol,Doxygen::mainPage->localToc()); } ol.startTextBlock(); ol.generateDoc(defFileName,defLine,Doxygen::mainPage,0, Doxygen::mainPage->documentation(),TRUE,FALSE, 0,FALSE,FALSE,Config_getBool(MARKDOWN_SUPPORT)); ol.endTextBlock(); ol.endPageDoc(); Doxygen::insideMainPage=FALSE; } endFile(ol); ol.disable(OutputGenerator::Html); //-------------------------------------------------------------------- // write LaTeX/RTF index //-------------------------------------------------------------------- ol.enable(OutputGenerator::Latex); ol.enable(OutputGenerator::Docbook); ol.enable(OutputGenerator::RTF); ol.startFile("refman",0,0); ol.startIndexSection(isTitlePageStart); if (!Config_getString(LATEX_HEADER).isEmpty()) { ol.disable(OutputGenerator::Latex); } ol.disable(OutputGenerator::Docbook); if (projPrefix.isEmpty()) { ol.parseText(theTranslator->trReferenceManual()); } else { ol.parseText(projPrefix); } if (!Config_getString(PROJECT_NUMBER).isEmpty()) { ol.startProjectNumber(); ol.generateDoc(defFileName,defLine,Doxygen::mainPage,0,Config_getString(PROJECT_NUMBER),FALSE,FALSE, 0,FALSE,FALSE,Config_getBool(MARKDOWN_SUPPORT)); ol.endProjectNumber(); } ol.endIndexSection(isTitlePageStart); ol.startIndexSection(isTitlePageAuthor); ol.parseText(theTranslator->trGeneratedBy()); ol.endIndexSection(isTitlePageAuthor); ol.enable(OutputGenerator::Latex); ol.enable(OutputGenerator::Docbook); ol.lastIndexPage(); if (Doxygen::mainPage) { ol.startIndexSection(isMainPage); if (mainPageHasTitle()) { ol.parseText(Doxygen::mainPage->title()); } else { ol.parseText(/*projPrefix+*/theTranslator->trMainPage()); } ol.endIndexSection(isMainPage); } if (documentedPages>0) { //ol.parseText(projPrefix+theTranslator->trPageDocumentation()); //ol.endIndexSection(isPageDocumentation); PageSDict::Iterator pdi(*Doxygen::pageSDict); PageDef *pd=pdi.toFirst(); bool first=Doxygen::mainPage==0; for (pdi.toFirst();(pd=pdi.current());++pdi) { if (!pd->getGroupDef() && !pd->isReference() && (!pd->hasParentPage() || // not inside other page (Doxygen::mainPage==pd->getOuterScope())) // or inside main page ) { bool isCitationPage = pd->name()=="citelist"; if (isCitationPage) { // For LaTeX the bibliograph is already written by \bibliography ol.pushGeneratorState(); ol.disable(OutputGenerator::Latex); } title = pd->title(); if (title.isEmpty()) title=pd->name(); ol.disable(OutputGenerator::Docbook); ol.startIndexSection(isPageDocumentation); ol.parseText(title); ol.endIndexSection(isPageDocumentation); ol.enable(OutputGenerator::Docbook); ol.pushGeneratorState(); // write TOC title (RTF only) ol.disableAllBut(OutputGenerator::RTF); ol.startIndexSection(isPageDocumentation2); ol.parseText(title); ol.endIndexSection(isPageDocumentation2); ol.popGeneratorState(); ol.writeAnchor(0,pd->getOutputFileBase()); ol.writePageLink(pd->getOutputFileBase(),first); first=FALSE; if (isCitationPage) { ol.popGeneratorState(); } } } } ol.disable(OutputGenerator::Docbook); if (!Config_getBool(LATEX_HIDE_INDICES)) { //if (indexedPages>0) //{ // ol.startIndexSection(isPageIndex); // ol.parseText(/*projPrefix+*/ theTranslator->trPageIndex()); // ol.endIndexSection(isPageIndex); //} if (documentedGroups>0) { ol.startIndexSection(isModuleIndex); ol.parseText(/*projPrefix+*/ theTranslator->trModuleIndex()); ol.endIndexSection(isModuleIndex); } if (Config_getBool(SHOW_NAMESPACES) && (documentedNamespaces>0)) { ol.startIndexSection(isNamespaceIndex); ol.parseText(/*projPrefix+*/(fortranOpt?theTranslator->trModulesIndex():theTranslator->trNamespaceIndex())); ol.endIndexSection(isNamespaceIndex); } if (hierarchyInterfaces>0) { ol.startIndexSection(isClassHierarchyIndex); ol.parseText(/*projPrefix+*/theTranslator->trHierarchicalIndex()); ol.endIndexSection(isClassHierarchyIndex); } if (hierarchyClasses>0) { ol.startIndexSection(isClassHierarchyIndex); ol.parseText(/*projPrefix+*/ (fortranOpt ? theTranslator->trCompoundIndexFortran() : vhdlOpt ? theTranslator->trHierarchicalIndex() : theTranslator->trHierarchicalIndex() )); ol.endIndexSection(isClassHierarchyIndex); } if (hierarchyExceptions>0) { ol.startIndexSection(isClassHierarchyIndex); ol.parseText(/*projPrefix+*/theTranslator->trHierarchicalIndex()); ol.endIndexSection(isClassHierarchyIndex); } if (annotatedInterfacesPrinted>0) { ol.startIndexSection(isCompoundIndex); ol.parseText(/*projPrefix+*/theTranslator->trInterfaceIndex()); ol.endIndexSection(isCompoundIndex); } if (annotatedClassesPrinted>0) { ol.startIndexSection(isCompoundIndex); ol.parseText(/*projPrefix+*/ (fortranOpt ? theTranslator->trCompoundIndexFortran() : vhdlOpt ? theTranslator->trDesignUnitIndex() : theTranslator->trCompoundIndex() )); ol.endIndexSection(isCompoundIndex); } if (annotatedStructsPrinted>0) { ol.startIndexSection(isCompoundIndex); ol.parseText(/*projPrefix+*/theTranslator->trStructIndex()); ol.endIndexSection(isCompoundIndex); } if (annotatedExceptionsPrinted>0) { ol.startIndexSection(isCompoundIndex); ol.parseText(/*projPrefix+*/theTranslator->trExceptionIndex()); ol.endIndexSection(isCompoundIndex); } if (Config_getBool(SHOW_FILES) && (documentedFiles>0)) { ol.startIndexSection(isFileIndex); ol.parseText(/*projPrefix+*/theTranslator->trFileIndex()); ol.endIndexSection(isFileIndex); } } ol.enable(OutputGenerator::Docbook); if (documentedGroups>0) { ol.startIndexSection(isModuleDocumentation); ol.parseText(/*projPrefix+*/theTranslator->trModuleDocumentation()); ol.endIndexSection(isModuleDocumentation); } if (documentedNamespaces>0) { ol.startIndexSection(isNamespaceDocumentation); ol.parseText(/*projPrefix+*/(fortranOpt?theTranslator->trModuleDocumentation():theTranslator->trNamespaceDocumentation())); ol.endIndexSection(isNamespaceDocumentation); } if (annotatedInterfacesPrinted>0) { ol.startIndexSection(isClassDocumentation); ol.parseText(/*projPrefix+*/theTranslator->trInterfaceDocumentation()); ol.endIndexSection(isClassDocumentation); } if (annotatedClassesPrinted>0) { ol.startIndexSection(isClassDocumentation); ol.parseText(/*projPrefix+*/(fortranOpt?theTranslator->trTypeDocumentation():theTranslator->trClassDocumentation())); ol.endIndexSection(isClassDocumentation); } if (annotatedStructsPrinted>0) { ol.startIndexSection(isClassDocumentation); ol.parseText(/*projPrefix+*/theTranslator->trStructDocumentation()); ol.endIndexSection(isClassDocumentation); } if (annotatedExceptionsPrinted>0) { ol.startIndexSection(isClassDocumentation); ol.parseText(/*projPrefix+*/theTranslator->trExceptionDocumentation()); ol.endIndexSection(isClassDocumentation); } if (documentedFiles>0) { ol.startIndexSection(isFileDocumentation); ol.parseText(/*projPrefix+*/theTranslator->trFileDocumentation()); ol.endIndexSection(isFileDocumentation); } if (Doxygen::exampleSDict->count()>0) { ol.startIndexSection(isExampleDocumentation); ol.parseText(/*projPrefix+*/theTranslator->trExampleDocumentation()); ol.endIndexSection(isExampleDocumentation); } ol.endIndexSection(isEndIndex); endFile(ol); if (Doxygen::mainPage) { Doxygen::insideMainPage=TRUE; ol.disable(OutputGenerator::Man); startFile(ol,Doxygen::mainPage->name(),0,Doxygen::mainPage->title()); ol.startContents(); ol.startTextBlock(); ol.generateDoc(defFileName,defLine,Doxygen::mainPage,0, Doxygen::mainPage->documentation(),FALSE,FALSE, 0,FALSE,FALSE,Config_getBool(MARKDOWN_SUPPORT) ); ol.endTextBlock(); endFile(ol); ol.enable(OutputGenerator::Man); Doxygen::insideMainPage=FALSE; } ol.popGeneratorState(); } static QArray indexWritten; static void writeIndexHierarchyEntries(OutputList &ol,const QList &entries) { static bool sliceOpt = Config_getBool(OPTIMIZE_OUTPUT_SLICE); QListIterator li(entries); LayoutNavEntry *lne; for (li.toFirst();(lne=li.current());++li) { LayoutNavEntry::Kind kind = lne->kind(); uint index = (uint)kind; if (index>=indexWritten.size()) { uint i; uint oldSize = indexWritten.size(); uint newSize = index+1; indexWritten.resize(newSize); for (i=oldSize;ititle().data(),lne->kind()); bool addToIndex=lne->visible(); bool needsClosing=FALSE; if (!indexWritten.at(index)) { switch(kind) { case LayoutNavEntry::MainPage: msg("Generating index page...\n"); writeIndex(ol); break; case LayoutNavEntry::Pages: msg("Generating page index...\n"); writePageIndex(ol); break; case LayoutNavEntry::Modules: msg("Generating module index...\n"); writeGroupIndex(ol); break; case LayoutNavEntry::Namespaces: { static bool showNamespaces = Config_getBool(SHOW_NAMESPACES); if (showNamespaces) { if (documentedNamespaces>0 && addToIndex) { Doxygen::indexList->addContentsItem(TRUE,lne->title(),0,lne->baseFile(),0); Doxygen::indexList->incContentsDepth(); needsClosing=TRUE; } if (LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::Namespaces)!=lne) // for backward compatibility with old layout file { msg("Generating namespace index...\n"); writeNamespaceIndex(ol); } } } break; case LayoutNavEntry::NamespaceList: { static bool showNamespaces = Config_getBool(SHOW_NAMESPACES); if (showNamespaces) { msg("Generating namespace index...\n"); writeNamespaceIndex(ol); } } break; case LayoutNavEntry::NamespaceMembers: msg("Generating namespace member index...\n"); writeNamespaceMemberIndex(ol); break; case LayoutNavEntry::Classes: if (annotatedClasses>0 && addToIndex) { Doxygen::indexList->addContentsItem(TRUE,lne->title(),0,lne->baseFile(),0); Doxygen::indexList->incContentsDepth(); needsClosing=TRUE; } if (LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::Classes)!=lne) // for backward compatibility with old layout file { msg("Generating annotated compound index...\n"); writeAnnotatedIndex(ol); } break; case LayoutNavEntry::ClassList: msg("Generating annotated compound index...\n"); writeAnnotatedIndex(ol); break; case LayoutNavEntry::ClassIndex: msg("Generating alphabetical compound index...\n"); writeAlphabeticalIndex(ol); break; case LayoutNavEntry::ClassHierarchy: msg("Generating hierarchical class index...\n"); writeHierarchicalIndex(ol); if (Config_getBool(HAVE_DOT) && Config_getBool(GRAPHICAL_HIERARCHY)) { msg("Generating graphical class hierarchy...\n"); writeGraphicalClassHierarchy(ol); } break; case LayoutNavEntry::ClassMembers: if (!sliceOpt) { msg("Generating member index...\n"); writeClassMemberIndex(ol); } break; case LayoutNavEntry::Interfaces: if (sliceOpt && annotatedInterfaces>0 && addToIndex) { Doxygen::indexList->addContentsItem(TRUE,lne->title(),0,lne->baseFile(),0); Doxygen::indexList->incContentsDepth(); needsClosing=TRUE; } break; case LayoutNavEntry::InterfaceList: if (sliceOpt) { msg("Generating annotated interface index...\n"); writeAnnotatedInterfaceIndex(ol); } break; case LayoutNavEntry::InterfaceIndex: if (sliceOpt) { msg("Generating alphabetical interface index...\n"); writeAlphabeticalInterfaceIndex(ol); } break; case LayoutNavEntry::InterfaceHierarchy: if (sliceOpt) { msg("Generating hierarchical interface index...\n"); writeHierarchicalInterfaceIndex(ol); if (Config_getBool(HAVE_DOT) && Config_getBool(GRAPHICAL_HIERARCHY)) { msg("Generating graphical interface hierarchy...\n"); writeGraphicalInterfaceHierarchy(ol); } } break; case LayoutNavEntry::Structs: if (sliceOpt && annotatedStructs>0 && addToIndex) { Doxygen::indexList->addContentsItem(TRUE,lne->title(),0,lne->baseFile(),0); Doxygen::indexList->incContentsDepth(); needsClosing=TRUE; } break; case LayoutNavEntry::StructList: if (sliceOpt) { msg("Generating annotated struct index...\n"); writeAnnotatedStructIndex(ol); } break; case LayoutNavEntry::StructIndex: if (sliceOpt) { msg("Generating alphabetical struct index...\n"); writeAlphabeticalStructIndex(ol); } break; case LayoutNavEntry::Exceptions: if (sliceOpt && annotatedExceptions>0 && addToIndex) { Doxygen::indexList->addContentsItem(TRUE,lne->title(),0,lne->baseFile(),0); Doxygen::indexList->incContentsDepth(); needsClosing=TRUE; } break; case LayoutNavEntry::ExceptionList: if (sliceOpt) { msg("Generating annotated exception index...\n"); writeAnnotatedExceptionIndex(ol); } break; case LayoutNavEntry::ExceptionIndex: if (sliceOpt) { msg("Generating alphabetical exception index...\n"); writeAlphabeticalExceptionIndex(ol); } break; case LayoutNavEntry::ExceptionHierarchy: if (sliceOpt) { msg("Generating hierarchical exception index...\n"); writeHierarchicalExceptionIndex(ol); if (Config_getBool(HAVE_DOT) && Config_getBool(GRAPHICAL_HIERARCHY)) { msg("Generating graphical exception hierarchy...\n"); writeGraphicalExceptionHierarchy(ol); } } break; case LayoutNavEntry::Files: { static bool showFiles = Config_getBool(SHOW_FILES); if (showFiles) { if (documentedHtmlFiles>0 && addToIndex) { Doxygen::indexList->addContentsItem(TRUE,lne->title(),0,lne->baseFile(),0); Doxygen::indexList->incContentsDepth(); needsClosing=TRUE; } if (LayoutDocManager::instance().rootNavEntry()->find(LayoutNavEntry::Files)!=lne) // for backward compatibility with old layout file { msg("Generating file index...\n"); writeFileIndex(ol); } } } break; case LayoutNavEntry::FileList: { static bool showFiles = Config_getBool(SHOW_FILES); if (showFiles) { msg("Generating file index...\n"); writeFileIndex(ol); } } break; case LayoutNavEntry::FileGlobals: msg("Generating file member index...\n"); writeFileMemberIndex(ol); break; case LayoutNavEntry::Examples: msg("Generating example index...\n"); writeExampleIndex(ol); break; case LayoutNavEntry::User: { // prepend a ! or ^ marker to the URL to avoid tampering with it QCString url = correctURL(lne->url(),"!"); // add ! to relative URL bool isRelative=url.at(0)=='!'; if (!url.isEmpty() && !isRelative) // absolute URL { url.prepend("^"); // prepend ^ to absolute URL } bool isRef = lne->baseFile().left(4)=="@ref" || lne->baseFile().left(4)=="\\ref"; Doxygen::indexList->addContentsItem(TRUE,lne->title(),0,url,0,FALSE,isRef || isRelative); } break; case LayoutNavEntry::UserGroup: if (addToIndex) { QCString url = correctURL(lne->url(),"!"); // add ! to relative URL if (!url.isEmpty()) { if (url=="![none]") { Doxygen::indexList->addContentsItem(TRUE,lne->title(),0,0,0,FALSE,FALSE); } else { bool isRelative=url.at(0)=='!'; if (!isRelative) // absolute URL { url.prepend("^"); // prepend ^ to absolute URL } bool isRef = lne->baseFile().left(4)=="@ref" || lne->baseFile().left(4)=="\\ref"; Doxygen::indexList->addContentsItem(TRUE,lne->title(),0,url,0,FALSE,isRef || isRelative); } } else { Doxygen::indexList->addContentsItem(TRUE,lne->title(),0,lne->baseFile(),0,TRUE,TRUE); } Doxygen::indexList->incContentsDepth(); needsClosing=TRUE; } writeUserGroupStubPage(ol,lne); break; case LayoutNavEntry::None: assert(kind != LayoutNavEntry::None); // should never happen, means not properly initialized break; } if (kind!=LayoutNavEntry::User && kind!=LayoutNavEntry::UserGroup) // User entry may appear multiple times { indexWritten.at(index)=TRUE; } } writeIndexHierarchyEntries(ol,lne->children()); if (needsClosing) { switch(kind) { case LayoutNavEntry::Namespaces: case LayoutNavEntry::Classes: case LayoutNavEntry::Files: case LayoutNavEntry::UserGroup: Doxygen::indexList->decContentsDepth(); break; default: break; } } //printf("ending %s kind=%d\n",lne->title().data(),lne->kind()); } } static bool quickLinkVisible(LayoutNavEntry::Kind kind) { static bool showFiles = Config_getBool(SHOW_FILES); static bool showNamespaces = Config_getBool(SHOW_NAMESPACES); static bool sliceOpt = Config_getBool(OPTIMIZE_OUTPUT_SLICE); switch (kind) { case LayoutNavEntry::MainPage: return TRUE; case LayoutNavEntry::User: return TRUE; case LayoutNavEntry::UserGroup: return TRUE; case LayoutNavEntry::Pages: return indexedPages>0; case LayoutNavEntry::Modules: return documentedGroups>0; case LayoutNavEntry::Namespaces: return documentedNamespaces>0 && showNamespaces; case LayoutNavEntry::NamespaceList: return documentedNamespaces>0 && showNamespaces; case LayoutNavEntry::NamespaceMembers: return documentedNamespaceMembers[NMHL_All]>0; case LayoutNavEntry::Classes: return annotatedClasses>0; case LayoutNavEntry::ClassList: return annotatedClasses>0; case LayoutNavEntry::ClassIndex: return annotatedClasses>0; case LayoutNavEntry::ClassHierarchy: return hierarchyClasses>0; case LayoutNavEntry::ClassMembers: return documentedClassMembers[CMHL_All]>0 && !sliceOpt; case LayoutNavEntry::Interfaces: return annotatedInterfaces>0; case LayoutNavEntry::InterfaceList: return annotatedInterfaces>0; case LayoutNavEntry::InterfaceIndex: return annotatedInterfaces>0; case LayoutNavEntry::InterfaceHierarchy: return hierarchyInterfaces>0; case LayoutNavEntry::Structs: return annotatedStructs>0; case LayoutNavEntry::StructList: return annotatedStructs>0; case LayoutNavEntry::StructIndex: return annotatedStructs>0; case LayoutNavEntry::Exceptions: return annotatedExceptions>0; case LayoutNavEntry::ExceptionList: return annotatedExceptions>0; case LayoutNavEntry::ExceptionIndex: return annotatedExceptions>0; case LayoutNavEntry::ExceptionHierarchy: return hierarchyExceptions>0; case LayoutNavEntry::Files: return documentedHtmlFiles>0 && showFiles; case LayoutNavEntry::FileList: return documentedHtmlFiles>0 && showFiles; case LayoutNavEntry::FileGlobals: return documentedFileMembers[FMHL_All]>0; case LayoutNavEntry::Examples: return Doxygen::exampleSDict->count()>0; case LayoutNavEntry::None: // should never happen, means not properly initialized assert(kind != LayoutNavEntry::None); return FALSE; } return FALSE; } template void renderMemberIndicesAsJs(FTextStream &t, int total,const int *numDocumented,const LetterToIndexMap *memberLists, const T *(*getInfo)(int hl)) { // index items per category member lists bool firstMember=TRUE; for (int i=0;i0) { t << ","; if (firstMember) { t << "children:["; firstMember=FALSE; } t << endl << "{text:\"" << convertToJSString(getInfo(i)->title) << "\",url:\"" << convertToJSString(getInfo(i)->fname+Doxygen::htmlFileExtension, false) << "\""; // Check if we have many members, then add sub entries per letter... // quick alphabetical index bool quickIndex = numDocumented[i]>maxItemsBeforeQuickIndex; if (quickIndex) { bool multiPageIndex=FALSE; if (numDocumented[i]>MAX_ITEMS_BEFORE_MULTIPAGE_INDEX) { multiPageIndex=TRUE; } t << ",children:[" << endl; bool firstLetter=TRUE; SIntDict::Iterator it(memberLists[i]); MemberIndexList *ml; for (it.toFirst();(ml=it.current());++it) { if (!firstLetter) t << "," << endl; uint letter = ml->letter(); QCString is = letterToLabel(letter); QCString ci = letterToString(letter); QCString anchor; QCString extension=Doxygen::htmlFileExtension; QCString fullName = getInfo(i)->fname; if (!multiPageIndex || firstLetter) anchor=fullName+extension+"#index_"; else // other pages of multi page index anchor=fullName+"_"+is+extension+"#index_"; t << "{text:\"" << convertToJSString(ci) << "\",url:\"" << convertToJSString(anchor+convertToId(is), false) << "\"}"; firstLetter=FALSE; } t << "]"; } t << "}"; } } if (!firstMember) { t << "]"; } } static bool renderQuickLinksAsJs(FTextStream &t,LayoutNavEntry *root,bool first) { QListIterator li(root->children()); LayoutNavEntry *entry; int count=0; for (li.toFirst();(entry=li.current());++li) { if (entry->visible() && quickLinkVisible(entry->kind())) count++; } if (count>0) // at least one item is visible { bool firstChild = TRUE; if (!first) t << ","; t << "children:[" << endl; for (li.toFirst();(entry=li.current());++li) { if (entry->visible() && quickLinkVisible(entry->kind())) { if (!firstChild) t << "," << endl; firstChild=FALSE; QCString url = entry->url(); t << "{text:\"" << convertToJSString(entry->title()) << "\",url:\"" << convertToJSString(url, false) << "\""; bool hasChildren=FALSE; if (entry->kind()==LayoutNavEntry::NamespaceMembers) { renderMemberIndicesAsJs(t,NMHL_Total,documentedNamespaceMembers, g_namespaceIndexLetterUsed,getNmhlInfo); } else if (entry->kind()==LayoutNavEntry::ClassMembers) { renderMemberIndicesAsJs(t,CMHL_Total,documentedClassMembers, g_memberIndexLetterUsed,getCmhlInfo); } else if (entry->kind()==LayoutNavEntry::FileGlobals) { renderMemberIndicesAsJs(t,FMHL_Total,documentedFileMembers, g_fileIndexLetterUsed,getFmhlInfo); } else // recursive into child list { hasChildren = renderQuickLinksAsJs(t,entry,FALSE); } if (hasChildren) t << "]"; t << "}"; } } } return count>0; } static void writeMenuData() { if (!Config_getBool(GENERATE_HTML) || Config_getBool(DISABLE_INDEX)) return; QCString outputDir = Config_getBool(HTML_OUTPUT); QFile f(outputDir+"/menudata.js"); LayoutNavEntry *root = LayoutDocManager::instance().rootNavEntry(); if (f.open(IO_WriteOnly)) { FTextStream t(&f); t << JAVASCRIPT_LICENSE_TEXT; t << "var menudata={"; bool hasChildren = renderQuickLinksAsJs(t,root,TRUE); if (hasChildren) t << "]"; t << "}" << endl; } } void writeIndexHierarchy(OutputList &ol) { writeMenuData(); LayoutNavEntry *lne = LayoutDocManager::instance().rootNavEntry(); if (lne) { writeIndexHierarchyEntries(ol,lne->children()); } }