summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorDimitri van Heesch <dimitri@stack.nl>2013-12-29 08:47:51 (GMT)
committerDimitri van Heesch <dimitri@stack.nl>2013-12-29 08:47:51 (GMT)
commit744d1ca52e25dfa9e3d656056d87ed7cb6320585 (patch)
tree4829b62cf252449983b94d46c0cf167d3442c62e /src
parent2912829ca5bced897a2c063d1883b9cfd39d3bd9 (diff)
downloadDoxygen-744d1ca52e25dfa9e3d656056d87ed7cb6320585.zip
Doxygen-744d1ca52e25dfa9e3d656056d87ed7cb6320585.tar.gz
Doxygen-744d1ca52e25dfa9e3d656056d87ed7cb6320585.tar.bz2
More work on the template and context mechanisms
Diffstat (limited to 'src')
-rw-r--r--src/classdef.cpp22
-rw-r--r--src/classdef.h8
-rw-r--r--src/context.cpp928
-rw-r--r--src/context.h42
-rw-r--r--src/filedef.cpp20
-rw-r--r--src/filedef.h4
-rw-r--r--src/memberdef.cpp27
-rw-r--r--src/memberdef.h3
-rw-r--r--src/message.cpp9
-rw-r--r--src/message.h2
-rw-r--r--src/namespacedef.cpp56
-rw-r--r--src/namespacedef.h1
-rw-r--r--src/template.cpp388
-rw-r--r--src/template.h80
14 files changed, 1284 insertions, 306 deletions
diff --git a/src/classdef.cpp b/src/classdef.cpp
index 6404431..7e8b331 100644
--- a/src/classdef.cpp
+++ b/src/classdef.cpp
@@ -1767,20 +1767,24 @@ void ClassDef::writeMoreLink(OutputList &ol,const QCString &anchor)
}
}
+bool ClassDef::visibleInParentsDeclList() const
+{
+ static bool extractPrivate = Config_getBool("EXTRACT_PRIVATE");
+ static bool hideUndocClasses = Config_getBool("HIDE_UNDOC_CLASSES");
+ static bool extractLocalClasses = Config_getBool("EXTRACT_LOCAL_CLASSES");
+ bool linkable = isLinkable();
+ return (name().find('@')==-1 && !isExtension() &&
+ (protection()!=::Private || extractPrivate) &&
+ (linkable || (!hideUndocClasses && (!isLocal() || extractLocalClasses)))
+ );
+}
void ClassDef::writeDeclarationLink(OutputList &ol,bool &found,const char *header,bool localNames)
{
//static bool fortranOpt = Config_getBool("OPTIMIZE_FOR_FORTRAN");
//static bool vhdlOpt = Config_getBool("OPTIMIZE_OUTPUT_VHDL");
- static bool hideUndocClasses = Config_getBool("HIDE_UNDOC_CLASSES");
- static bool extractLocalClasses = Config_getBool("EXTRACT_LOCAL_CLASSES");
- bool isLink = isLinkable();
SrcLangExt lang = getLanguage();
- if (isLink ||
- (!hideUndocClasses &&
- (!isLocal() || extractLocalClasses)
- )
- )
+ if (visibleInParentsDeclList())
{
if (!found) // first class
{
@@ -1820,7 +1824,7 @@ void ClassDef::writeDeclarationLink(OutputList &ol,bool &found,const char *heade
ol.writeString(" ");
ol.insertMemberAlign();
}
- if (isLink)
+ if (isLinkable())
{
ol.writeObjectLink(getReference(),
getOutputFileBase(),
diff --git a/src/classdef.h b/src/classdef.h
index 4e76117..6ce1e73 100644
--- a/src/classdef.h
+++ b/src/classdef.h
@@ -168,6 +168,9 @@ class ClassDef : public Definition
/** the class is visible in a class diagram, or class hierarchy */
bool isVisibleInHierarchy();
+ /** show this class in the declaration section of its parent? */
+ bool visibleInParentsDeclList() const;
+
/** Returns the template arguments of this class
* Will return 0 if not applicable.
*/
@@ -310,14 +313,13 @@ class ClassDef : public Definition
QCString generatedFromFiles() const;
const FileList &usedFiles() const;
- QCString includeStatement() const;
-
const ArgumentList *typeConstraints() const;
const ExampleSDict *exampleList() const;
bool hasExamples() const;
QCString getMemberListFileName() const;
bool subGrouping() const;
+
//-----------------------------------------------------------------------------------
// --- setters ----
//-----------------------------------------------------------------------------------
@@ -432,6 +434,8 @@ class ClassDef : public Definition
QPtrDict<void> *visitedClasses);
void getTitleForMemberListType(MemberListType type,
QCString &title,QCString &subtitle);
+ QCString includeStatement() const;
+
ClassDefImpl *m_impl;
diff --git a/src/context.cpp b/src/context.cpp
index e573dde..02a5212 100644
--- a/src/context.cpp
+++ b/src/context.cpp
@@ -27,6 +27,8 @@
// TODO: pass the current file to Dot*::writeGraph, so the user can put dot graphs in other
// files as well
+#define ADD_PROPERTY(name) addProperty(#name,this,&Private::name);
+
struct ContextGlobals
{
enum OutputFormat
@@ -453,6 +455,18 @@ class TranslateContext::Private : public PropertyMapper
}
return TemplateVariant();
}
+ TemplateVariant handleIncludeDependencyGraph(const QValueList<TemplateVariant> &args) const
+ {
+ if (args.count()==1)
+ {
+ return theTranslator->trInclDepGraph(args[0].toString());
+ }
+ else
+ {
+ err("tr.includeDependencyGraph should take one string argument, got %d\n",args.count());
+ }
+ return TemplateVariant();
+ }
@@ -483,6 +497,8 @@ class TranslateContext::Private : public PropertyMapper
TemplateVariant classes() const
{
return theTranslator->trClasses();
+ // TODO: VHDL: trVhdlType(VhdlDocGen::ENTITY,FALSE)
+ // TODO: Fortran: trDataTypes()
}
TemplateVariant classList() const
{
@@ -669,6 +685,34 @@ class TranslateContext::Private : public PropertyMapper
{
return theTranslator->trAdditionalInheritedMembers();
}
+ TemplateVariant includeDependencyGraph() const
+ {
+ return TemplateVariant::Delegate::fromMethod<Private,&Private::handleIncludeDependencyGraph>(this);
+ }
+ TemplateVariant includedByDependencyGraph() const
+ {
+ return theTranslator->trInclByDepGraph();
+ }
+ TemplateVariant gotoSourceCode() const
+ {
+ return theTranslator->trGotoSourceCode();
+ }
+ TemplateVariant gotoDocumentation() const
+ {
+ return theTranslator->trGotoDocumentation();
+ }
+ TemplateVariant constantgroups() const
+ {
+ return theTranslator->trConstantGroups();
+ }
+ TemplateVariant classDocumentation() const
+ {
+ return theTranslator->trClassDocumentation();
+ }
+ TemplateVariant compoundMembers() const
+ {
+ return theTranslator->trCompoundMembers();
+ }
Private()
{
//%% string generatedBy
@@ -761,6 +805,20 @@ class TranslateContext::Private : public PropertyMapper
addProperty("inheritedFrom", this,&Private::inheritedFrom);
//%% string addtionalInheritedMembers
addProperty("additionalInheritedMembers",this,&Private::additionalInheritedMembers);
+ //%% string includeDependencyGraph:container_name
+ addProperty("includeDependencyGraph",this,&Private::includeDependencyGraph);
+ //%% string includedByDependencyGraph
+ addProperty("includedByDependencyGraph",this,&Private::includedByDependencyGraph);
+ //%% string gotoSourceCode
+ addProperty("gotoSourceCode", this,&Private::gotoSourceCode);
+ //%% string gotoDocumentation
+ addProperty("gotoDocumentation", this,&Private::gotoDocumentation);
+ //%% string constantgroups
+ addProperty("constantgroups", this,&Private::constantgroups);
+ //%% string classDocumentation
+ addProperty("classDocumentation", this,&Private::classDocumentation);
+ //%% string compoundMembers
+ addProperty("compoundMembers", this,&Private::compoundMembers);
m_javaOpt = Config_getBool("OPTIMIZE_OUTPUT_JAVA");
m_fortranOpt = Config_getBool("OPTIMIZE_FOR_FORTRAN");
@@ -823,6 +881,31 @@ static TemplateVariant parseCode(MemberDef *md,const QCString &scopeName,const Q
return TemplateVariant(s.data(),TRUE);
}
+static TemplateVariant parseCode(FileDef *fd,const QCString &relPath)
+{
+ static bool filterSourceFiles = Config_getBool("FILTER_SOURCE_FILES");
+ ParserInterface *pIntf = Doxygen::parserManager->getParser(fd->getDefFileExtension());
+ pIntf->resetCodeParserState();
+ QGString s;
+ FTextStream t(&s);
+ HtmlCodeGenerator codeGen(t,relPath);
+ pIntf->parseCode(codeGen,0,
+ fileToString(fd->absFilePath(),filterSourceFiles,TRUE), // the sources
+ fd->getLanguage(), // lang
+ FALSE, // isExampleBlock
+ 0, // exampleName
+ fd, // fileDef
+ -1, // startLine
+ -1, // endLine
+ FALSE, // inlineFragment
+ 0, // memberDef
+ TRUE, // showLineNumbers
+ 0, // searchCtx
+ TRUE // collectXRefs, TODO: should become FALSE
+ );
+ return TemplateVariant(s.data(),TRUE);
+}
+
//------------------------------------------------------------------------
//%% struct Symbol: shared info for all symbols
@@ -1027,7 +1110,10 @@ class DefinitionContext : public PropertyMapper
if (!m_cache.navPath)
{
TemplateList *list = new TemplateList;
- fillPath(m_def,list);
+ if (m_def->getOuterScope() && m_def->getOuterScope()!=Doxygen::globalScope)
+ {
+ fillPath(m_def->getOuterScope(),list);
+ }
m_cache.navPath.reset(list);
}
return m_cache.navPath.get();
@@ -1058,7 +1144,7 @@ class DefinitionContext : public PropertyMapper
class IncludeInfoContext::Private : public PropertyMapper
{
public:
- Private(IncludeInfo *info,SrcLangExt lang) :
+ Private(const IncludeInfo *info,SrcLangExt lang) :
m_info(info),
m_fileContext(info && info->fileDef ? info->fileDef : 0),
m_lang(lang)
@@ -1096,12 +1182,12 @@ class IncludeInfoContext::Private : public PropertyMapper
return m_info->includeName;
}
private:
- IncludeInfo *m_info;
+ const IncludeInfo *m_info;
FileContext m_fileContext;
SrcLangExt m_lang;
};
-IncludeInfoContext::IncludeInfoContext(IncludeInfo *info,SrcLangExt lang)
+IncludeInfoContext::IncludeInfoContext(const IncludeInfo *info,SrcLangExt lang)
{
p = new Private(info,lang);
}
@@ -1119,14 +1205,59 @@ TemplateVariant IncludeInfoContext::get(const char *n) const
//------------------------------------------------------------------------
+//%% list IncludeInfoList[Class] : list of nested classes
+class IncludeInfoListContext::Private : public GenericNodeListContext<IncludeInfoContext>
+{
+ public:
+ Private(const QList<IncludeInfo> &list,SrcLangExt lang)
+ {
+ QListIterator<IncludeInfo> li(list);
+ IncludeInfo *ii;
+ for (li.toFirst();(ii=li.current());++li)
+ {
+ if (!ii->indirect)
+ {
+ append(new IncludeInfoContext(ii,lang));
+ }
+ }
+ }
+};
+
+IncludeInfoListContext::IncludeInfoListContext(const QList<IncludeInfo> &list,SrcLangExt lang)
+{
+ p = new Private(list,lang);
+}
+
+IncludeInfoListContext::~IncludeInfoListContext()
+{
+ delete p;
+}
+
+// TemplateListIntf
+int IncludeInfoListContext::count() const
+{
+ return p->count();
+}
+
+TemplateVariant IncludeInfoListContext::at(int index) const
+{
+ return p->at(index);
+}
+
+TemplateListIntf::ConstIterator *IncludeInfoListContext::createIterator() const
+{
+ return p->createIterator();
+}
+
+//------------------------------------------------------------------------
+
//%% struct Class(Symbol): class information
//%% {
class ClassContext::Private : public DefinitionContext<ClassContext::Private>
{
public:
- Private(ClassDef *cd) : DefinitionContext<ClassContext::Private>(cd) ,
- m_classDef(cd), m_usedFiles(cd),
- m_includeInfo(cd ? cd->includeInfo() : 0, cd ? cd->getLanguage() : SrcLangExt_Unknown)
+ Private(ClassDef *cd) : DefinitionContext<ClassContext::Private>(cd),
+ m_classDef(cd), m_usedFiles(cd)
{
addProperty("title", this,&Private::title);
addProperty("highlight", this,&Private::highlight);
@@ -1139,7 +1270,6 @@ class ClassContext::Private : public DefinitionContext<ClassContext::Private>
addProperty("hasCollaborationDiagram", this,&Private::hasCollaborationDiagram);
addProperty("collaborationDiagram", this,&Private::collaborationDiagram);
addProperty("includeInfo", this,&Private::includeInfo);
- addProperty("includeStatement", this,&Private::includeStatement);
addProperty("inherits", this,&Private::inherits);
addProperty("inheritedBy", this,&Private::inheritedBy);
addProperty("unoIDLServices", this,&Private::unoIDLServices);
@@ -1182,7 +1312,7 @@ class ClassContext::Private : public DefinitionContext<ClassContext::Private>
addProperty("detailedVariables", this,&Private::detailedVariables);
addProperty("detailedProperties", this,&Private::detailedProperties);
addProperty("detailedEvents", this,&Private::detailedEvents);
- addProperty("nestedClasses", this,&Private::nestedClasses);
+ addProperty("classes", this,&Private::classes);
addProperty("compoundType", this,&Private::compoundType);
addProperty("templateDecls", this,&Private::templateDecls);
addProperty("typeConstraints", this,&Private::typeConstraints);
@@ -1317,19 +1447,19 @@ class ClassContext::Private : public DefinitionContext<ClassContext::Private>
TemplateVariant includeInfo() const
{
- if (m_classDef->includeInfo())
+ if (!m_cache.includeInfo && m_classDef->includeInfo())
+ {
+ m_cache.includeInfo.reset(new IncludeInfoContext(m_classDef->includeInfo(),m_classDef->getLanguage()));
+ }
+ if (m_cache.includeInfo)
{
- return TemplateVariant(&m_includeInfo);
+ return m_cache.includeInfo.get();
}
else
{
return TemplateVariant(FALSE);
}
}
- TemplateVariant includeStatement() const
- {
- return m_classDef->includeStatement();
- }
TemplateVariant inherits() const
{
if (!m_cache.inheritsList)
@@ -1530,12 +1660,9 @@ class ClassContext::Private : public DefinitionContext<ClassContext::Private>
{
return getMemberList(m_cache.detailedEvents,MemberListType_eventMembers,theTranslator->trEventDocumentation(),TRUE);
}
- TemplateVariant nestedClasses() const
+ TemplateVariant classes() const
{
- static bool extractPrivate = Config_getBool("EXTRACT_PRIVATE");
- static bool hideUndocClasses = Config_getBool("HIDE_UNDOC_CLASSES");
- static bool extractLocalClasses = Config_getBool("EXTRACT_LOCAL_CLASSES");
- if (!m_cache.nestedClasses)
+ if (!m_cache.classes)
{
NestedClassListContext *classList = new NestedClassListContext;
if (m_classDef->getClassSDict())
@@ -1544,20 +1671,15 @@ class ClassContext::Private : public DefinitionContext<ClassContext::Private>
ClassDef *cd;
for (sdi.toFirst();(cd=sdi.current());++sdi)
{
- bool linkable = cd->isLinkable();
- if (cd->name().find('@')==-1 && !cd->isExtension() &&
- (cd->protection()!=::Private || extractPrivate) &&
- (linkable ||
- (!hideUndocClasses && (!cd->isLocal() || extractLocalClasses)))
- )
+ if (cd->visibleInParentsDeclList())
{
classList->append(cd);
}
}
}
- m_cache.nestedClasses.reset(classList);
+ m_cache.classes.reset(classList);
}
- return m_cache.nestedClasses.get();
+ return m_cache.classes.get();
}
TemplateVariant compoundType() const
{
@@ -1764,71 +1886,70 @@ class ClassContext::Private : public DefinitionContext<ClassContext::Private>
private:
ClassDef *m_classDef;
UsedFilesContext m_usedFiles;
- IncludeInfoContext m_includeInfo;
struct Cachable
{
Cachable() : inheritanceNodes(-1)
{
templateArgList.setAutoDelete(TRUE);
exampleList.setAutoDelete(TRUE);
- allMembers.setAutoDelete(TRUE);
}
+ ScopedPtr<IncludeInfoContext> includeInfo;
ScopedPtr<InheritanceListContext> inheritsList;
ScopedPtr<InheritanceListContext> inheritedByList;
ScopedPtr<DotClassGraph> classGraph;
ScopedPtr<DotClassGraph> collaborationGraph;
- ScopedPtr<NestedClassListContext> nestedClasses;
- ScopedPtr<MemberListInfoContext> publicTypes;
- ScopedPtr<MemberListInfoContext> publicMethods;
- ScopedPtr<MemberListInfoContext> publicStaticMethods;
- ScopedPtr<MemberListInfoContext> publicAttributes;
- ScopedPtr<MemberListInfoContext> publicStaticAttributes;
- ScopedPtr<MemberListInfoContext> publicSlots;
- ScopedPtr<MemberListInfoContext> protectedTypes;
- ScopedPtr<MemberListInfoContext> protectedMethods;
- ScopedPtr<MemberListInfoContext> protectedStaticMethods;
- ScopedPtr<MemberListInfoContext> protectedAttributes;
- ScopedPtr<MemberListInfoContext> protectedStaticAttributes;
- ScopedPtr<MemberListInfoContext> protectedSlots;
- ScopedPtr<MemberListInfoContext> privateTypes;
- ScopedPtr<MemberListInfoContext> privateMethods;
- ScopedPtr<MemberListInfoContext> privateStaticMethods;
- ScopedPtr<MemberListInfoContext> privateAttributes;
- ScopedPtr<MemberListInfoContext> privateStaticAttributes;
- ScopedPtr<MemberListInfoContext> privateSlots;
- ScopedPtr<MemberListInfoContext> packageTypes;
- ScopedPtr<MemberListInfoContext> packageMethods;
- ScopedPtr<MemberListInfoContext> packageStaticMethods;
- ScopedPtr<MemberListInfoContext> packageAttributes;
- ScopedPtr<MemberListInfoContext> packageStaticAttributes;
- ScopedPtr<MemberListInfoContext> unoIDLServices;
- ScopedPtr<MemberListInfoContext> unoIDLInterfaces;
- ScopedPtr<MemberListInfoContext> signals;
- ScopedPtr<MemberListInfoContext> properties;
- ScopedPtr<MemberListInfoContext> events;
- ScopedPtr<MemberListInfoContext> friends;
- ScopedPtr<MemberListInfoContext> related;
- ScopedPtr<MemberListInfoContext> detailedTypedefs;
- ScopedPtr<MemberListInfoContext> detailedEnums;
- ScopedPtr<MemberListInfoContext> detailedServices;
- ScopedPtr<MemberListInfoContext> detailedInterfaces;
- ScopedPtr<MemberListInfoContext> detailedConstructors;
- ScopedPtr<MemberListInfoContext> detailedMethods;
- ScopedPtr<MemberListInfoContext> detailedRelated;
- ScopedPtr<MemberListInfoContext> detailedVariables;
- ScopedPtr<MemberListInfoContext> detailedProperties;
- ScopedPtr<MemberListInfoContext> detailedEvents;
+ ScopedPtr<NestedClassListContext> classes;
+ ScopedPtr<MemberListInfoContext> publicTypes;
+ ScopedPtr<MemberListInfoContext> publicMethods;
+ ScopedPtr<MemberListInfoContext> publicStaticMethods;
+ ScopedPtr<MemberListInfoContext> publicAttributes;
+ ScopedPtr<MemberListInfoContext> publicStaticAttributes;
+ ScopedPtr<MemberListInfoContext> publicSlots;
+ ScopedPtr<MemberListInfoContext> protectedTypes;
+ ScopedPtr<MemberListInfoContext> protectedMethods;
+ ScopedPtr<MemberListInfoContext> protectedStaticMethods;
+ ScopedPtr<MemberListInfoContext> protectedAttributes;
+ ScopedPtr<MemberListInfoContext> protectedStaticAttributes;
+ ScopedPtr<MemberListInfoContext> protectedSlots;
+ ScopedPtr<MemberListInfoContext> privateTypes;
+ ScopedPtr<MemberListInfoContext> privateMethods;
+ ScopedPtr<MemberListInfoContext> privateStaticMethods;
+ ScopedPtr<MemberListInfoContext> privateAttributes;
+ ScopedPtr<MemberListInfoContext> privateStaticAttributes;
+ ScopedPtr<MemberListInfoContext> privateSlots;
+ ScopedPtr<MemberListInfoContext> packageTypes;
+ ScopedPtr<MemberListInfoContext> packageMethods;
+ ScopedPtr<MemberListInfoContext> packageStaticMethods;
+ ScopedPtr<MemberListInfoContext> packageAttributes;
+ ScopedPtr<MemberListInfoContext> packageStaticAttributes;
+ ScopedPtr<MemberListInfoContext> unoIDLServices;
+ ScopedPtr<MemberListInfoContext> unoIDLInterfaces;
+ ScopedPtr<MemberListInfoContext> signals;
+ ScopedPtr<MemberListInfoContext> properties;
+ ScopedPtr<MemberListInfoContext> events;
+ ScopedPtr<MemberListInfoContext> friends;
+ ScopedPtr<MemberListInfoContext> related;
+ ScopedPtr<MemberListInfoContext> detailedTypedefs;
+ ScopedPtr<MemberListInfoContext> detailedEnums;
+ ScopedPtr<MemberListInfoContext> detailedServices;
+ ScopedPtr<MemberListInfoContext> detailedInterfaces;
+ ScopedPtr<MemberListInfoContext> detailedConstructors;
+ ScopedPtr<MemberListInfoContext> detailedMethods;
+ ScopedPtr<MemberListInfoContext> detailedRelated;
+ ScopedPtr<MemberListInfoContext> detailedVariables;
+ ScopedPtr<MemberListInfoContext> detailedProperties;
+ ScopedPtr<MemberListInfoContext> detailedEvents;
ScopedPtr<MemberGroupListContext> memberGroups;
- ScopedPtr<AllMembersListContext> allMembersList;
- ScopedPtr<ArgumentListContext> typeConstraints;
- ScopedPtr<TemplateList> examples;
- ScopedPtr<TemplateList> templateDecls;
+ ScopedPtr<AllMembersListContext> allMembersList;
+ ScopedPtr<ArgumentListContext> typeConstraints;
+ ScopedPtr<TemplateList> examples;
+ ScopedPtr<TemplateList> templateDecls;
ScopedPtr<InheritedMemberInfoListContext> additionalInheritedMembers;
- ScopedPtr<MemberListContext> members;
- QList<ArgumentListContext> templateArgList;
- int inheritanceNodes;
- QList<TemplateStruct> exampleList;
- MemberList allMembers;
+ ScopedPtr<MemberListContext> members;
+ QList<ArgumentListContext> templateArgList;
+ int inheritanceNodes;
+ QList<TemplateStruct> exampleList;
+ MemberList allMembers;
};
mutable Cachable m_cache;
};
@@ -1862,6 +1983,7 @@ class NamespaceContext::Private : public DefinitionContext<NamespaceContext::Pri
addProperty("title",this,&Private::title);
addProperty("highlight",this,&Private::highlight);
addProperty("subhighlight",this,&Private::subHighlight);
+ addProperty("compoundType",this,&Private::compoundType);
}
TemplateVariant title() const
{
@@ -1875,6 +1997,10 @@ class NamespaceContext::Private : public DefinitionContext<NamespaceContext::Pri
{
return TemplateVariant("");
}
+ TemplateVariant compoundType() const
+ {
+ return m_namespaceDef->compoundTypeString();
+ }
private:
NamespaceDef *m_namespaceDef;
};
@@ -1904,10 +2030,34 @@ class FileContext::Private : public DefinitionContext<FileContext::Private>
public:
Private(FileDef *fd) : DefinitionContext<FileContext::Private>(fd) , m_fileDef(fd)
{
- addProperty("title",this,&Private::title);
- addProperty("highlight",this,&Private::highlight);
- addProperty("subhighlight",this,&Private::subHighlight);
- addProperty("versionInfo",this,&Private::versionInfo);
+ addProperty("title", this,&Private::title);
+ addProperty("highlight", this,&Private::highlight);
+ addProperty("subhighlight", this,&Private::subHighlight);
+ addProperty("versionInfo", this,&Private::versionInfo);
+ addProperty("includeList", this,&Private::includeList);
+ addProperty("hasIncludeGraph", this,&Private::hasIncludeGraph);
+ addProperty("hasIncludedByGraph", this,&Private::hasIncludedByGraph);
+ addProperty("includeGraph", this,&Private::includeGraph);
+ addProperty("includedByGraph", this,&Private::includedByGraph);
+ addProperty("hasDetails", this,&Private::hasDetails);
+ addProperty("hasSourceFile", this,&Private::hasSourceFile);
+ addProperty("sources", this,&Private::sources);
+ addProperty("version", this,&Private::version);
+ addProperty("classes", this,&Private::classes);
+ addProperty("namespaces", this,&Private::namespaces);
+ addProperty("constantgroups", this,&Private::constantgroups);
+ addProperty("macros", this,&Private::macros);
+ addProperty("typedefs", this,&Private::typedefs);
+ addProperty("enums", this,&Private::enums);
+ addProperty("functions", this,&Private::functions);
+ addProperty("variables", this,&Private::variables);
+ addProperty("memberGroups", this,&Private::memberGroups);
+ addProperty("detailedMacros", this,&Private::detailedMacros);
+ addProperty("detailedTypedefs", this,&Private::detailedTypedefs);
+ addProperty("detailedEnums", this,&Private::detailedEnums);
+ addProperty("detailedFunctions", this,&Private::detailedFunctions);
+ addProperty("detailedVariables", this,&Private::detailedVariables);
+ addProperty("inlineClasses", this,&Private::inlineClasses);
}
TemplateVariant title() const
{
@@ -1925,8 +2075,302 @@ class FileContext::Private : public DefinitionContext<FileContext::Private>
{
return m_fileDef->getVersion();
}
+ TemplateVariant includeList() const
+ {
+ if (!m_cache.includeInfoList && m_fileDef->includeFileList())
+ {
+ m_cache.includeInfoList.reset(new IncludeInfoListContext(
+ *m_fileDef->includeFileList(),m_fileDef->getLanguage()));
+ }
+ if (m_cache.includeInfoList)
+ {
+ return m_cache.includeInfoList.get();
+ }
+ else
+ {
+ return TemplateVariant(FALSE);
+ }
+ }
+ DotInclDepGraph *getIncludeGraph() const
+ {
+ if (!m_cache.includeGraph)
+ {
+ m_cache.includeGraph.reset(new DotInclDepGraph(m_fileDef,FALSE));
+ }
+ return m_cache.includeGraph.get();
+ }
+ TemplateVariant hasIncludeGraph() const
+ {
+ static bool haveDot = Config_getBool("HAVE_DOT");
+ DotInclDepGraph *incGraph = getIncludeGraph();
+ return (haveDot && !incGraph->isTooBig() && !incGraph->isTrivial());
+ }
+ TemplateVariant includeGraph() const
+ {
+ static bool haveDot = Config_getBool("HAVE_DOT");
+ QGString result;
+ if (haveDot)
+ {
+ DotInclDepGraph *cg = getIncludeGraph();
+ FTextStream t(&result);
+ cg->writeGraph(t,BITMAP,
+ g_globals.outputDir,
+ g_globals.outputDir+portable_pathSeparator()+m_fileDef->getOutputFileBase()+Doxygen::htmlFileExtension,
+ relPathAsString(),TRUE,g_globals.dynSectionId
+ );
+ }
+ g_globals.dynSectionId++;
+ return TemplateVariant(result.data(),TRUE);
+ }
+ DotInclDepGraph *getIncludedByGraph() const
+ {
+ if (!m_cache.includedByGraph)
+ {
+ m_cache.includedByGraph.reset(new DotInclDepGraph(m_fileDef,TRUE));
+ }
+ return m_cache.includedByGraph.get();
+ }
+ TemplateVariant hasIncludedByGraph() const
+ {
+ static bool haveDot = Config_getBool("HAVE_DOT");
+ DotInclDepGraph *incGraph = getIncludedByGraph();
+ return (haveDot && !incGraph->isTooBig() && !incGraph->isTrivial());
+ }
+ TemplateVariant includedByGraph() const
+ {
+ static bool haveDot = Config_getBool("HAVE_DOT");
+ QGString result;
+ if (haveDot)
+ {
+ DotInclDepGraph *cg = getIncludedByGraph();
+ FTextStream t(&result);
+ cg->writeGraph(t,BITMAP,
+ g_globals.outputDir,
+ g_globals.outputDir+portable_pathSeparator()+m_fileDef->getOutputFileBase()+Doxygen::htmlFileExtension,
+ relPathAsString(),TRUE,g_globals.dynSectionId
+ );
+ }
+ g_globals.dynSectionId++;
+ return TemplateVariant(result.data(),TRUE);
+ }
+ TemplateVariant hasDetails() const
+ {
+ return m_fileDef->hasDetailedDescription();
+ }
+ TemplateVariant hasSourceFile() const
+ {
+ return m_fileDef->generateSourceFile();
+ }
+ TemplateVariant sources() const
+ {
+ if (!m_cache.sources)
+ {
+ if (m_fileDef->generateSourceFile())
+ {
+ m_cache.sources.reset(new TemplateVariant(parseCode(m_fileDef,relPathAsString())));
+ }
+ else
+ {
+ m_cache.sources.reset(new TemplateVariant(""));
+ }
+ }
+ return *m_cache.sources;
+ }
+ TemplateVariant version() const
+ {
+ return m_fileDef->fileVersion();
+ }
+ TemplateVariant classes() const
+ {
+ if (!m_cache.classes)
+ {
+ NestedClassListContext *classList = new NestedClassListContext;
+ if (m_fileDef->getClassSDict())
+ {
+ ClassSDict::Iterator sdi(*m_fileDef->getClassSDict());
+ ClassDef *cd;
+ for (sdi.toFirst();(cd=sdi.current());++sdi)
+ {
+ if (cd->visibleInParentsDeclList())
+ {
+ classList->append(cd);
+ }
+ }
+ }
+ m_cache.classes.reset(classList);
+ }
+ return m_cache.classes.get();
+ }
+ TemplateVariant namespaces() const
+ {
+ if (!m_cache.namespaces)
+ {
+ NestedNamespaceListContext *namespaceList = new NestedNamespaceListContext;
+ if (m_fileDef->getNamespaceSDict())
+ {
+ NamespaceSDict::Iterator sdi(*m_fileDef->getNamespaceSDict());
+ NamespaceDef *nd;
+ for (sdi.toFirst();(nd=sdi.current());++sdi)
+ {
+ if (nd->isLinkable() && !nd->isConstantGroup())
+ {
+ namespaceList->append(nd);
+ }
+ }
+ }
+ m_cache.namespaces.reset(namespaceList);
+ }
+ return m_cache.namespaces.get();
+ }
+ TemplateVariant constantgroups() const
+ {
+ if (!m_cache.constantgroups)
+ {
+ NestedNamespaceListContext *namespaceList = new NestedNamespaceListContext;
+ if (m_fileDef->getNamespaceSDict())
+ {
+ NamespaceSDict::Iterator sdi(*m_fileDef->getNamespaceSDict());
+ NamespaceDef *nd;
+ for (sdi.toFirst();(nd=sdi.current());++sdi)
+ {
+ if (nd->isLinkable() && nd->isConstantGroup())
+ {
+ namespaceList->append(nd);
+ }
+ }
+ }
+ m_cache.constantgroups.reset(namespaceList);
+ }
+ return m_cache.constantgroups.get();
+ }
+ TemplateVariant getMemberList(ScopedPtr<MemberListInfoContext> &list,
+ MemberListType type,const char *title,bool detailed=FALSE) const
+ {
+ if (!list)
+ {
+ MemberList *ml = m_fileDef->getMemberList(type);
+ if (ml)
+ {
+ list.reset(new MemberListInfoContext(m_fileDef,relPathAsString(),ml,title,detailed));
+ }
+ }
+ if (list)
+ {
+ return list.get();
+ }
+ else
+ {
+ return TemplateVariant(FALSE);
+ }
+ }
+ TemplateVariant macros() const
+ {
+ return getMemberList(m_cache.macros,MemberListType_decDefineMembers,theTranslator->trDefines());
+ }
+ TemplateVariant typedefs() const
+ {
+ return getMemberList(m_cache.typedefs,MemberListType_decTypedefMembers,theTranslator->trTypedefs());
+ }
+ TemplateVariant enums() const
+ {
+ return getMemberList(m_cache.enums,MemberListType_decEnumMembers,theTranslator->trEnumerations());
+ }
+ TemplateVariant functions() const
+ {
+ // TODO: Fortran: trSubprograms()
+ // TODO: VHDL: VhdlDocGen::trFunctionAndProc()
+ return getMemberList(m_cache.functions,MemberListType_decFuncMembers,theTranslator->trFunctions());
+ }
+ TemplateVariant variables() const
+ {
+ return getMemberList(m_cache.variables,MemberListType_decVarMembers,theTranslator->trVariables());
+ }
+ TemplateVariant memberGroups() const
+ {
+ if (!m_cache.memberGroups)
+ {
+ if (m_fileDef->getMemberGroupSDict())
+ {
+ m_cache.memberGroups.reset(new MemberGroupListContext(m_fileDef,relPathAsString(),m_fileDef->getMemberGroupSDict(),m_fileDef->subGrouping()));
+ }
+ else
+ {
+ m_cache.memberGroups.reset(new MemberGroupListContext);
+ }
+ }
+ return m_cache.memberGroups.get();
+ }
+ TemplateVariant detailedMacros() const
+ {
+ return getMemberList(m_cache.detailedMacros,MemberListType_docDefineMembers,theTranslator->trDefineDocumentation());
+ }
+ TemplateVariant detailedTypedefs() const
+ {
+ return getMemberList(m_cache.detailedTypedefs,MemberListType_docTypedefMembers,theTranslator->trTypedefDocumentation());
+ }
+ TemplateVariant detailedEnums() const
+ {
+ return getMemberList(m_cache.detailedEnums,MemberListType_docEnumMembers,theTranslator->trEnumerationTypeDocumentation());
+ }
+ TemplateVariant detailedFunctions() const
+ {
+ // TODO: Fortran: trSubprogramDocumentation()
+ return getMemberList(m_cache.detailedFunctions,MemberListType_docFuncMembers,theTranslator->trFunctionDocumentation());
+ }
+ TemplateVariant detailedVariables() const
+ {
+ return getMemberList(m_cache.detailedVariables,MemberListType_docVarMembers,theTranslator->trVariableDocumentation());
+ }
+ TemplateVariant inlineClasses() const
+ {
+ if (!m_cache.inlineClasses)
+ {
+ NestedClassListContext *classList = new NestedClassListContext;
+ if (m_fileDef->getClassSDict())
+ {
+ ClassSDict::Iterator sdi(*m_fileDef->getClassSDict());
+ ClassDef *cd;
+ for (sdi.toFirst();(cd=sdi.current());++sdi)
+ {
+ if (cd->name().find('@')==-1 &&
+ cd->isLinkableInProject() &&
+ cd->isEmbeddedInOuterScope() &&
+ cd->partOfGroups()==0)
+ {
+ classList->append(cd);
+ }
+ }
+ }
+ m_cache.inlineClasses.reset(classList);
+ }
+ return m_cache.inlineClasses.get();
+ }
+
private:
FileDef *m_fileDef;
+ struct Cachable
+ {
+ ScopedPtr<IncludeInfoListContext> includeInfoList;
+ ScopedPtr<DotInclDepGraph> includeGraph;
+ ScopedPtr<DotInclDepGraph> includedByGraph;
+ ScopedPtr<TemplateVariant> sources;
+ ScopedPtr<NestedClassListContext> classes;
+ ScopedPtr<NestedNamespaceListContext> namespaces;
+ ScopedPtr<NestedNamespaceListContext> constantgroups;
+ ScopedPtr<MemberListInfoContext> macros;
+ ScopedPtr<MemberListInfoContext> typedefs;
+ ScopedPtr<MemberListInfoContext> enums;
+ ScopedPtr<MemberListInfoContext> functions;
+ ScopedPtr<MemberListInfoContext> variables;
+ ScopedPtr<MemberGroupListContext> memberGroups;
+ ScopedPtr<MemberListInfoContext> detailedMacros;
+ ScopedPtr<MemberListInfoContext> detailedTypedefs;
+ ScopedPtr<MemberListInfoContext> detailedEnums;
+ ScopedPtr<MemberListInfoContext> detailedFunctions;
+ ScopedPtr<MemberListInfoContext> detailedVariables;
+ ScopedPtr<NestedClassListContext> inlineClasses;
+ };
+ mutable Cachable m_cache;
};
//%% }
@@ -2160,21 +2604,70 @@ class MemberContext::Private : public DefinitionContext<MemberContext::Private>
public:
Private(MemberDef *md) : DefinitionContext<MemberContext::Private>(md) , m_memberDef(md)
{
- addProperty("declType", this,&Private::declType);
- addProperty("declArgs", this,&Private::declArgs);
+ addProperty("isSignal", this,&Private::isSignal);
+ addProperty("isSlot", this,&Private::isSlot);
+ addProperty("isVariable", this,&Private::isVariable);
+ addProperty("isEnumeration", this,&Private::isEnumeration);
+ addProperty("isEnumValue", this,&Private::isEnumValue);
+ addProperty("isTypedef", this,&Private::isTypedef);
+ addProperty("isFunction", this,&Private::isFunction);
+ addProperty("isFunctionPtr", this,&Private::isFunctionPtr);
+ addProperty("isDefine", this,&Private::isDefine);
+ addProperty("isFriend", this,&Private::isFriend);
+ addProperty("isProperty", this,&Private::isProperty);
+ addProperty("isEvent", this,&Private::isEvent);
+ addProperty("isRelated", this,&Private::isRelated);
+ addProperty("isForeign", this,&Private::isForeign);
addProperty("isStatic", this,&Private::isStatic);
+ addProperty("isInline", this,&Private::isInline);
+ addProperty("isExplicit", this,&Private::isExplicit);
+ addProperty("isMutable", this,&Private::isMutable);
+ addProperty("isGettable", this,&Private::isGettable);
+ addProperty("isSettable", this,&Private::isSettable);
+ addProperty("isReadable", this,&Private::isReadable);
+ addProperty("isWritable", this,&Private::isWritable);
+ addProperty("isAddable", this,&Private::isAddable);
+ addProperty("isRemovable", this,&Private::isRemovable);
+ addProperty("isRaisable", this,&Private::isRaisable);
+ addProperty("isFinal", this,&Private::isFinal);
+ addProperty("isAbstract", this,&Private::isAbstract);
+ addProperty("isOverride", this,&Private::isOverride);
+ addProperty("isInitonly", this,&Private::isInitonly);
+ addProperty("isOptional", this,&Private::isOptional);
+ addProperty("isRequired", this,&Private::isRequired);
+ addProperty("isNonAtomic", this,&Private::isNonAtomic);
+ addProperty("isCopy", this,&Private::isCopy);
+ addProperty("isAssign", this,&Private::isAssign);
+ addProperty("isRetain", this,&Private::isRetain);
+ addProperty("isWeak", this,&Private::isWeak);
+ addProperty("isStrong", this,&Private::isStrong);
+ addProperty("isUnretained", this,&Private::isUnretained);
+ addProperty("isNew", this,&Private::isNew);
+ addProperty("isSealed", this,&Private::isSealed);
+ addProperty("isImplementation", this,&Private::isImplementation);
+ addProperty("isExternal", this,&Private::isExternal);
+ addProperty("isAlias", this,&Private::isAlias);
+ addProperty("isDefault", this,&Private::isDefault);
+ addProperty("isDelete", this,&Private::isDelete);
+ addProperty("isNoExcept", this,&Private::isNoExcept);
+ addProperty("isAttribute", this,&Private::isAttribute);
+ addProperty("isUNOProperty", this,&Private::isUNOProperty);
+ addProperty("isReadonly", this,&Private::isReadonly);
+ addProperty("isBound", this,&Private::isBound);
+ addProperty("isConstrained", this,&Private::isConstrained);
+ addProperty("isTransient", this,&Private::isTransient);
+ addProperty("isMaybeVoid", this,&Private::isMaybeVoid);
+ addProperty("isMaybeDefault", this,&Private::isMaybeDefault);
+ addProperty("isMaybeAmbiguous", this,&Private::isMaybeAmbiguous);
+ addProperty("isPublished", this,&Private::isPublished);
+ addProperty("isTemplateSpecialization",this,&Private::isTemplateSpecialization);
addProperty("isObjCMethod", this,&Private::isObjCMethod);
addProperty("isObjCProperty", this,&Private::isObjCProperty);
- addProperty("isDefine", this,&Private::isDefine);
- addProperty("isImplementation", this,&Private::isImplementation);
- addProperty("isEvent", this,&Private::isEvent);
- addProperty("isProperty", this,&Private::isProperty);
- addProperty("isEnumeration", this,&Private::isEnumeration);
- addProperty("isEnumValue", this,&Private::isEnumValue);
addProperty("isAnonymous", this,&Private::isAnonymous);
+ addProperty("declType", this,&Private::declType);
+ addProperty("declArgs", this,&Private::declArgs);
addProperty("anonymousType", this,&Private::anonymousType);
addProperty("anonymousMember", this,&Private::anonymousMember);
- addProperty("isRelated", this,&Private::isRelated);
addProperty("hasDetails", this,&Private::hasDetails);
addProperty("exception", this,&Private::exception);
addProperty("bitfields", this,&Private::bitfields);
@@ -2214,6 +2707,7 @@ class MemberContext::Private : public DefinitionContext<MemberContext::Private>
addProperty("callGraph", this,&Private::callGraph);
addProperty("hasCallerGraph", this,&Private::hasCallerGraph);
addProperty("callerGraph", this,&Private::callerGraph);
+ addProperty("fieldType", this,&Private::fieldType);
if (md && md->isProperty())
{
@@ -2227,6 +2721,10 @@ class MemberContext::Private : public DefinitionContext<MemberContext::Private>
if (md->isRaisable()) m_eventAttrs.append("raise");
}
}
+ TemplateVariant fieldType() const
+ {
+ return createLinkedText(m_memberDef,relPathAsString(),m_memberDef->fieldType());
+ }
TemplateVariant declType() const
{
return createLinkedText(m_memberDef,relPathAsString(),m_memberDef->getDeclType());
@@ -2259,10 +2757,202 @@ class MemberContext::Private : public DefinitionContext<MemberContext::Private>
{
return m_memberDef->isImplementation();
}
+ TemplateVariant isSignal() const
+ {
+ return m_memberDef->isSignal();
+ }
+ TemplateVariant isSlot() const
+ {
+ return m_memberDef->isSlot();
+ }
+ TemplateVariant isTypedef() const
+ {
+ return m_memberDef->isTypedef();
+ }
+ TemplateVariant isFunction() const
+ {
+ return m_memberDef->isFunction();
+ }
+ TemplateVariant isFunctionPtr() const
+ {
+ return m_memberDef->isFunctionPtr();
+ }
+ TemplateVariant isFriend() const
+ {
+ return m_memberDef->isFriend();
+ }
+ TemplateVariant isForeign() const
+ {
+ return m_memberDef->isForeign();
+ }
TemplateVariant isEvent() const
{
return m_memberDef->isEvent();
}
+ TemplateVariant isInline() const
+ {
+ return m_memberDef->isInline();
+ }
+ TemplateVariant isExplicit() const
+ {
+ return m_memberDef->isExplicit();
+ }
+ TemplateVariant isMutable() const
+ {
+ return m_memberDef->isMutable();
+ }
+ TemplateVariant isGettable() const
+ {
+ return m_memberDef->isSettable();
+ }
+ TemplateVariant isSettable() const
+ {
+ return m_memberDef->isSettable();
+ }
+ TemplateVariant isReadable() const
+ {
+ return m_memberDef->isReadable();
+ }
+ TemplateVariant isWritable() const
+ {
+ return m_memberDef->isWritable();
+ }
+ TemplateVariant isAddable() const
+ {
+ return m_memberDef->isAddable();
+ }
+ TemplateVariant isRemovable() const
+ {
+ return m_memberDef->isRemovable();
+ }
+ TemplateVariant isRaisable() const
+ {
+ return m_memberDef->isRaisable();
+ }
+ TemplateVariant isFinal() const
+ {
+ return m_memberDef->isFinal();
+ }
+ TemplateVariant isAbstract() const
+ {
+ return m_memberDef->isAbstract();
+ }
+ TemplateVariant isOverride() const
+ {
+ return m_memberDef->isOverride();
+ }
+ TemplateVariant isInitonly() const
+ {
+ return m_memberDef->isInitonly();
+ }
+ TemplateVariant isOptional() const
+ {
+ return m_memberDef->isOptional();
+ }
+ TemplateVariant isRequired() const
+ {
+ return m_memberDef->isRequired();
+ }
+ TemplateVariant isNonAtomic() const
+ {
+ return m_memberDef->isNonAtomic();
+ }
+ TemplateVariant isCopy() const
+ {
+ return m_memberDef->isCopy();
+ }
+ TemplateVariant isAssign() const
+ {
+ return m_memberDef->isAssign();
+ }
+ TemplateVariant isRetain() const
+ {
+ return m_memberDef->isRetain();
+ }
+ TemplateVariant isWeak() const
+ {
+ return m_memberDef->isWeak();
+ }
+ TemplateVariant isStrong() const
+ {
+ return m_memberDef->isStrong();
+ }
+ TemplateVariant isUnretained() const
+ {
+ return m_memberDef->isUnretained();
+ }
+ TemplateVariant isNew() const
+ {
+ return m_memberDef->isNew();
+ }
+ TemplateVariant isSealed() const
+ {
+ return m_memberDef->isSealed();
+ }
+ TemplateVariant isExternal() const
+ {
+ return m_memberDef->isExternal();
+ }
+ TemplateVariant isAlias() const
+ {
+ return m_memberDef->isAlias();
+ }
+ TemplateVariant isDefault() const
+ {
+ return m_memberDef->isDefault();
+ }
+ TemplateVariant isDelete() const
+ {
+ return m_memberDef->isDelete();
+ }
+ TemplateVariant isNoExcept() const
+ {
+ return m_memberDef->isNoExcept();
+ }
+ TemplateVariant isAttribute() const
+ {
+ return m_memberDef->isAttribute();
+ }
+ TemplateVariant isUNOProperty() const
+ {
+ return m_memberDef->isUNOProperty();
+ }
+ TemplateVariant isReadonly() const
+ {
+ return m_memberDef->isReadonly();
+ }
+ TemplateVariant isBound() const
+ {
+ return m_memberDef->isBound();
+ }
+ TemplateVariant isConstrained() const
+ {
+ return m_memberDef->isConstrained();
+ }
+ TemplateVariant isTransient() const
+ {
+ return m_memberDef->isTransient();
+ }
+ TemplateVariant isMaybeVoid() const
+ {
+ return m_memberDef->isMaybeVoid();
+ }
+ TemplateVariant isMaybeDefault() const
+ {
+ return m_memberDef->isMaybeDefault();
+ }
+ TemplateVariant isMaybeAmbiguous() const
+ {
+ return m_memberDef->isMaybeAmbiguous();
+ }
+ TemplateVariant isPublished() const
+ {
+ return m_memberDef->isPublished();
+ }
+ TemplateVariant isTemplateSpecialization() const
+ {
+ return m_memberDef->isTemplateSpecialization();
+ }
TemplateVariant isProperty() const
{
return m_memberDef->isProperty();
@@ -2271,6 +2961,10 @@ class MemberContext::Private : public DefinitionContext<MemberContext::Private>
{
return m_memberDef->isEnumValue();
}
+ TemplateVariant isVariable() const
+ {
+ return m_memberDef->isVariable();
+ }
TemplateVariant isEnumeration() const
{
return m_memberDef->isEnumerate();
@@ -2717,10 +3411,10 @@ class MemberContext::Private : public DefinitionContext<MemberContext::Private>
TemplateVariant functionQualifier() const
{
if (!m_memberDef->isObjCMethod() &&
- (m_memberDef->isFunction() || m_memberDef->isSlot() ||
+ (m_memberDef->isFunction() || m_memberDef->isSlot() ||
m_memberDef->isPrototype() || m_memberDef->isSignal()
)
- )
+ )
{
return "()";
}
@@ -3007,6 +3701,47 @@ void NestedClassListContext::append(ClassDef *cd)
//------------------------------------------------------------------------
+//%% list NestedClassList[Class] : list of nested namespaces
+class NestedNamespaceListContext::Private : public GenericNodeListContext<NamespaceContext>
+{
+};
+
+NestedNamespaceListContext::NestedNamespaceListContext()
+{
+ p = new Private;
+}
+
+NestedNamespaceListContext::~NestedNamespaceListContext()
+{
+ delete p;
+}
+
+// TemplateListIntf
+int NestedNamespaceListContext::count() const
+{
+ return p->count();
+}
+
+TemplateVariant NestedNamespaceListContext::at(int index) const
+{
+ return p->at(index);
+}
+
+TemplateListIntf::ConstIterator *NestedNamespaceListContext::createIterator() const
+{
+ return p->createIterator();
+}
+
+void NestedNamespaceListContext::append(NamespaceDef *cd)
+{
+ if (cd)
+ {
+ p->append(new NamespaceContext(cd));
+ }
+}
+
+//------------------------------------------------------------------------
+
//%% list ClassList[Class] : list of classes
class ClassListContext::Private : public GenericNodeListContext<ClassContext>
{
@@ -5744,7 +6479,7 @@ void generateOutputViaTemplate()
ctx->set("exampleList",&exampleList);
// render HTML output
- Template *tpl = e.loadByName("htmllayout.tpl");
+ Template *tpl = e.loadByName("htmllayout.tpl",1);
if (tpl)
{
g_globals.outputFormat = ContextGlobals::Html;
@@ -5758,6 +6493,7 @@ void generateOutputViaTemplate()
FTextStream ts;
tpl->render(ts,ctx);
}
+ e.unload(tpl);
// TODO: render other outputs
}
diff --git a/src/context.h b/src/context.h
index f027749..7506471 100644
--- a/src/context.h
+++ b/src/context.h
@@ -3,6 +3,7 @@
#include "types.h"
#include "template.h"
+#include <qlist.h>
class Definition;
class ClassDef;
@@ -108,7 +109,7 @@ class UsedFilesContext : public TemplateListIntf
class IncludeInfoContext : public TemplateStructIntf
{
public:
- IncludeInfoContext(IncludeInfo *,SrcLangExt lang);
+ IncludeInfoContext(const IncludeInfo *,SrcLangExt lang);
~IncludeInfoContext();
// TemplateStructIntf methods
@@ -121,6 +122,25 @@ class IncludeInfoContext : public TemplateStructIntf
//----------------------------------------------------
+class IncludeInfoListContext : public TemplateListIntf
+{
+ public:
+ IncludeInfoListContext(const QList<IncludeInfo> &list,SrcLangExt lang);
+ ~IncludeInfoListContext();
+
+ // TemplateListIntf
+ virtual int count() const;
+ virtual TemplateVariant at(int index) const;
+ virtual TemplateListIntf::ConstIterator *createIterator() const;
+
+ private:
+ class Private;
+ Private *p;
+};
+
+
+//----------------------------------------------------
+
class ClassContext : public TemplateStructIntf
{
public:
@@ -254,6 +274,26 @@ class NestedClassListContext : public TemplateListIntf
//----------------------------------------------------
+class NestedNamespaceListContext : public TemplateListIntf
+{
+ public:
+ NestedNamespaceListContext();
+ ~NestedNamespaceListContext();
+
+ // TemplateListIntf
+ virtual int count() const;
+ virtual TemplateVariant at(int index) const;
+ virtual TemplateListIntf::ConstIterator *createIterator() const;
+
+ void append(NamespaceDef *cd);
+
+ private:
+ class Private;
+ Private *p;
+};
+
+//----------------------------------------------------
+
class ClassListContext : public TemplateListIntf
{
public:
diff --git a/src/filedef.cpp b/src/filedef.cpp
index e286284..1368628 100644
--- a/src/filedef.cpp
+++ b/src/filedef.cpp
@@ -170,12 +170,18 @@ void FileDef::findSectionsInDocumentation()
}
}
+bool FileDef::hasDetailedDescription() const
+{
+ static bool sourceBrowser = Config_getBool("SOURCE_BROWSER");
+ return ((!briefDescription().isEmpty() && Config_getBool("REPEAT_BRIEF")) ||
+ !documentation().stripWhiteSpace().isEmpty() || // avail empty section
+ (sourceBrowser && getStartBodyLine()!=-1 && getBodyDef())
+ );
+}
+
void FileDef::writeDetailedDescription(OutputList &ol,const QCString &title)
{
- if ((!briefDescription().isEmpty() && Config_getBool("REPEAT_BRIEF")) ||
- !documentation().stripWhiteSpace().isEmpty() || // avail empty section
- (Config_getBool("SOURCE_BROWSER") && getStartBodyLine()!=-1 && getBodyDef())
- )
+ if (hasDetailedDescription())
{
ol.pushGeneratorState();
ol.disable(OutputGenerator::Html);
@@ -379,7 +385,7 @@ void FileDef::writeIncludedByGraph(OutputList &ol)
{
warn_uncond("Included by graph for '%s' not generated, too many nodes. Consider increasing DOT_GRAPH_MAX_NODES.\n",name().data());
}
- if (!incDepGraph.isTrivial())
+ else if (!incDepGraph.isTrivial())
{
ol.startTextBlock();
ol.disable(OutputGenerator::Man);
@@ -1800,3 +1806,7 @@ QCString FileDef::title() const
return theTranslator->trFileReference(name());
}
+QCString FileDef::fileVersion() const
+{
+ return m_fileVersion;
+}
diff --git a/src/filedef.h b/src/filedef.h
index d1d7496..58b17bd 100644
--- a/src/filedef.h
+++ b/src/filedef.h
@@ -133,6 +133,10 @@ class FileDef : public Definition
ClassSDict *getClassSDict() const { return m_classSDict; }
QCString title() const;
+ bool hasDetailedDescription() const;
+ QCString fileVersion() const;
+
+ bool subGrouping() const { return m_subGrouping; }
//---------------------------------
diff --git a/src/memberdef.cpp b/src/memberdef.cpp
index 4d7ea9f..d2964d4 100644
--- a/src/memberdef.cpp
+++ b/src/memberdef.cpp
@@ -3036,6 +3036,18 @@ static Definition *getClassFromType(Definition *scope,const QCString &type,SrcLa
}
#endif
+QCString MemberDef::fieldType() const
+{
+ QCString type = m_impl->accessorType;
+ if (type.isEmpty())
+ {
+ type = m_impl->type;
+ }
+
+ if (isTypedef()) type.prepend("typedef ");
+ return simplifyTypeForTable(type);
+}
+
void MemberDef::writeMemberDocSimple(OutputList &ol, Definition *container)
{
Definition *scope = getOuterScope();
@@ -3056,15 +3068,7 @@ void MemberDef::writeMemberDocSimple(OutputList &ol, Definition *container)
ol.startInlineMemberType();
ol.startDoxyAnchor(cfname,cname,memAnchor,doxyName,doxyArgs);
- QCString type = m_impl->accessorType;
- if (type.isEmpty())
- {
- type = m_impl->type;
- }
-
- if (isTypedef()) type.prepend("typedef ");
-
- QCString ts = simplifyTypeForTable(type);
+ QCString ts = fieldType();
if (cd) // cd points to an anonymous struct pointed to by this member
// so we add a link to it from the type column.
@@ -3855,6 +3859,11 @@ void MemberDef::setAccessorType(ClassDef *cd,const char *t)
m_impl->accessorType = t;
}
+ClassDef *MemberDef::accessorClass() const
+{
+ return m_impl->accessorClass;
+}
+
void MemberDef::findSectionsInDocumentation()
{
docFindSections(documentation(),this,0,docFile());
diff --git a/src/memberdef.h b/src/memberdef.h
index 47912b8..dffd53c 100644
--- a/src/memberdef.h
+++ b/src/memberdef.h
@@ -81,6 +81,7 @@ class MemberDef : public Definition
ClassDef *getClassDef() const;
FileDef *getFileDef() const;
NamespaceDef* getNamespaceDef() const;
+ ClassDef *accessorClass() const;
// grabbing the property read/write accessor names
const char *getReadAccessor() const;
@@ -251,7 +252,7 @@ class MemberDef : public Definition
// overrules
QCString documentation() const;
QCString briefDescription(bool abbr=FALSE) const;
-
+ QCString fieldType() const;
//-----------------------------------------------------------------------------------
diff --git a/src/message.cpp b/src/message.cpp
index dd3549a..ff5dac2 100644
--- a/src/message.cpp
+++ b/src/message.cpp
@@ -13,7 +13,6 @@
*
*/
-#include <stdarg.h>
#include <stdio.h>
#include <qdatetime.h>
#include "config.h"
@@ -22,6 +21,7 @@
#include "doxygen.h"
#include "portable.h"
#include "filedef.h"
+#include "message.h"
static QCString outputFormat;
static const char *warning_str = "warning: ";
@@ -110,7 +110,7 @@ void msg(const char *fmt, ...)
va_list args;
va_start(args, fmt);
vfprintf(stdout, fmt, args);
- va_end(args);
+ va_end(args);
}
}
@@ -172,6 +172,11 @@ void warn(const char *file,int line,const char *fmt, ...)
va_end(args);
}
+void warn(const char *file,int line,const char *fmt,va_list args)
+{
+ do_warn("WARNINGS", file, line, warning_str, fmt, args);
+}
+
void warn_simple(const char *file,int line,const char *text)
{
if (!Config_getBool("WARNINGS")) return; // warning type disabled
diff --git a/src/message.h b/src/message.h
index b7bdfe4..2875e81 100644
--- a/src/message.h
+++ b/src/message.h
@@ -19,9 +19,11 @@
#define MESSAGE_H
#include <stdio.h>
+#include <stdarg.h>
extern void msg(const char *fmt, ...);
extern void warn(const char *file,int line,const char *fmt, ...);
+extern void warn(const char *file,int line,const char *fmt, va_list args);
extern void warn_simple(const char *file,int line,const char *text);
extern void warn_undoc(const char *file,int line,const char *fmt, ...);
extern void warn_doc_error(const char *file,int line,const char *fmt, ...);
diff --git a/src/namespacedef.cpp b/src/namespacedef.cpp
index d00d845..c39b38f 100644
--- a/src/namespacedef.cpp
+++ b/src/namespacedef.cpp
@@ -916,29 +916,9 @@ void NamespaceSDict::writeDeclaration(OutputList &ol,const char *title,
continue; // will be output in another pass, see layout_default.xml
ol.startMemberDeclaration();
ol.startMemberItem(nd->getOutputFileBase(),0);
- if (lang==SrcLangExt_Java || lang==SrcLangExt_CSharp)
- {
- ol.docify("package ");
- }
- else if (lang==SrcLangExt_Fortran)
- {
- ol.docify("module ");
- }
- else if (lang==SrcLangExt_IDL)
- {
- if (nd->isModule())
- {
- ol.docify("module ");
- }
- else if (nd->isConstantGroup())
- {
- ol.docify("constants");
- }
- else
- {
- err("Internal inconsistency: namespace in IDL not module or cg\n");
- }
- }
+ QCString ct = nd->compoundTypeString();
+ ol.docify(ct);
+ ol.docify(" ");
ol.insertMemberAlign();
QCString name;
if (localName)
@@ -1103,3 +1083,33 @@ QCString NamespaceDef::title() const
}
return pageTitle;
}
+
+QCString NamespaceDef::compoundTypeString() const
+{
+ SrcLangExt lang = getLanguage();
+ if (lang==SrcLangExt_Java || lang==SrcLangExt_CSharp)
+ {
+ return "package";
+ }
+ else if (lang==SrcLangExt_Fortran)
+ {
+ return "module";
+ }
+ else if (lang==SrcLangExt_IDL)
+ {
+ if (isModule())
+ {
+ return "module";
+ }
+ else if (isConstantGroup())
+ {
+ return "constants";
+ }
+ else
+ {
+ err("Internal inconsistency: namespace in IDL not module or constant group\n");
+ }
+ }
+ return "";
+}
+
diff --git a/src/namespacedef.h b/src/namespacedef.h
index 2037d23..2fe5e4a 100644
--- a/src/namespacedef.h
+++ b/src/namespacedef.h
@@ -94,6 +94,7 @@ class NamespaceDef : public Definition
NamespaceSDict *getNamespaceSDict() const { return namespaceSDict; }
QCString title() const;
+ QCString compoundTypeString() const;
bool visited;
diff --git a/src/template.cpp b/src/template.cpp
index 8144afd..af15a47 100644
--- a/src/template.cpp
+++ b/src/template.cpp
@@ -29,7 +29,8 @@ class TemplateToken;
//-------------------------------------------------------------------
-static QValueList<QCString> split(const QCString &str,const QCString &sep,bool allowEmptyEntries=FALSE,bool cleanup=TRUE)
+static QValueList<QCString> split(const QCString &str,const QCString &sep,
+ bool allowEmptyEntries=FALSE,bool cleanup=TRUE)
{
QValueList<QCString> lst;
@@ -561,7 +562,7 @@ class TemplateBlockContext
class TemplateContextImpl : public TemplateContext
{
public:
- TemplateContextImpl();
+ TemplateContextImpl(const TemplateEngine *e);
virtual ~TemplateContextImpl();
// TemplateContext methods
@@ -589,8 +590,10 @@ class TemplateContextImpl : public TemplateContext
TemplateSpacelessIntf *spacelessIntf() const { return m_spacelessIntf; }
void enableSpaceless(bool b) { m_spacelessEnabled=b; }
bool spacelessEnabled() const { return m_spacelessEnabled && m_spacelessIntf; }
+ void warn(const char *fileName,int line,const char *fmt,...) const;
private:
+ const TemplateEngine *m_engine;
QCString m_templateName;
int m_line;
QCString m_outputDir;
@@ -874,7 +877,7 @@ class ExprAstVariable : public ExprAst
TemplateVariant v = c->get(m_name);
if (!v.isValid())
{
- warn(ci->templateName(),ci->line(),"undefined variable '%s' in expression",m_name.data());
+ ci->warn(ci->templateName(),ci->line(),"undefined variable '%s' in expression",m_name.data());
}
return v;
}
@@ -928,7 +931,7 @@ class ExprAstFilter : public ExprAst
TemplateVariant result = TemplateFilterFactory::instance()->apply(m_name,v,arg,ok);
if (!ok)
{
- warn(ci->templateName(),ci->line(),"unknown filter '%s'",m_name.data());
+ ci->warn(ci->templateName(),ci->line(),"unknown filter '%s'",m_name.data());
}
return result;
}
@@ -1047,6 +1050,46 @@ class ExprAstBinary : public ExprAst
ExprAst *m_rhs;
};
+//----------------------------------------------------------
+
+/** @brief Base class of all nodes in a template's AST */
+class TemplateNode
+{
+ public:
+ TemplateNode(TemplateNode *parent) : m_parent(parent) {}
+ virtual ~TemplateNode() {}
+
+ virtual void render(FTextStream &ts, TemplateContext *c) = 0;
+
+ TemplateNode *parent() { return m_parent; }
+
+ private:
+ TemplateNode *m_parent;
+};
+
+//----------------------------------------------------------
+
+/** @brief Parser for templates */
+class TemplateParser
+{
+ public:
+ TemplateParser(const TemplateEngine *engine,
+ const QCString &templateName,QList<TemplateToken> &tokens);
+ void parse(TemplateNode *parent,int line,const QStrList &stopAt,
+ QList<TemplateNode> &nodes);
+ bool hasNextToken() const;
+ TemplateToken *takeNextToken();
+ void removeNextToken();
+ void prependToken(const TemplateToken *token);
+ const TemplateToken *currentToken() const;
+ QCString templateName() const { return m_templateName; }
+ void warn(const char *fileName,int line,const char *fmt,...) const;
+ private:
+ const TemplateEngine *m_engine;
+ QCString m_templateName;
+ QList<TemplateToken> &m_tokens;
+};
+
//--------------------------------------------------------------------
/** @brief Recursive decent parser for Django style template expressions.
@@ -1054,8 +1097,8 @@ class ExprAstBinary : public ExprAst
class ExpressionParser
{
public:
- ExpressionParser(const QCString &templateName,int line)
- : m_templateName(templateName), m_line(line), m_tokenStream(0)
+ ExpressionParser(const TemplateParser *parser,int line)
+ : m_parser(parser), m_line(line), m_tokenStream(0)
{
}
virtual ~ExpressionParser()
@@ -1153,7 +1196,7 @@ class ExpressionParser
ExprAst *expr = parseCompareExpression();
if (expr==0)
{
- warn(m_templateName,m_line,"argument missing for not operator");
+ warn(m_parser->templateName(),m_line,"argument missing for not operator");
return 0;
}
result = new ExprAstNegate(expr);
@@ -1210,12 +1253,12 @@ class ExpressionParser
default:
if (m_curToken.type==ExprToken::Operator)
{
- warn(m_templateName,m_line,"unexpected operator '%s' in expression",
+ warn(m_parser->templateName(),m_line,"unexpected operator '%s' in expression",
Operator::toString(m_curToken.op));
}
else
{
- warn(m_templateName,m_line,"unexpected token in expression");
+ warn(m_parser->templateName(),m_line,"unexpected token in expression");
}
}
TRACE(("}parsePrimary(%s)\n",m_tokenStream));
@@ -1461,7 +1504,7 @@ class ExpressionParser
char s[2];
s[0]=c;
s[1]=0;
- warn(m_templateName,m_line,"Found unknown token %s while parsing %s",s,m_tokenStream);
+ warn(m_parser->templateName(),m_line,"Found unknown token %s while parsing %s",s,m_tokenStream);
m_curToken.id = s;
p++;
}
@@ -1472,51 +1515,14 @@ class ExpressionParser
return TRUE;
}
+ const TemplateParser *m_parser;
ExprToken m_curToken;
- QCString m_templateName;
int m_line;
const char *m_tokenStream;
};
//----------------------------------------------------------
-/** @brief Base class of all nodes in a template's AST */
-class TemplateNode
-{
- public:
- TemplateNode(TemplateNode *parent) : m_parent(parent) {}
- virtual ~TemplateNode() {}
-
- virtual void render(FTextStream &ts, TemplateContext *c) = 0;
-
- TemplateNode *parent() { return m_parent; }
-
- private:
- TemplateNode *m_parent;
-};
-
-//----------------------------------------------------------
-
-/** @brief Parser for templates */
-class TemplateParser
-{
- public:
- TemplateParser(const QCString &templateName,QList<TemplateToken> &tokens);
- void parse(TemplateNode *parent,int line,const QStrList &stopAt,
- QList<TemplateNode> &nodes);
- bool hasNextToken() const;
- TemplateToken *takeNextToken();
- void removeNextToken();
- void prependToken(const TemplateToken *token);
- const TemplateToken *currentToken() const;
- QCString templateName() const { return m_templateName; }
- private:
- QCString m_templateName;
- QList<TemplateToken> &m_tokens;
-};
-
-//----------------------------------------------------------
-
/** @brief Class representing a lexical token in a template */
class TemplateToken
{
@@ -1558,24 +1564,23 @@ class TemplateImpl : public TemplateNode, public Template
{
public:
TemplateImpl(TemplateEngine *e,const QCString &name,const QCString &data);
- ~TemplateImpl() {}
void render(FTextStream &ts, TemplateContext *c);
TemplateEngine *engine() const { return m_engine; }
TemplateBlockContext *blockContext() { return &m_blockContext; }
private:
+ TemplateEngine *m_engine;
QCString m_name;
TemplateNodeList m_nodes;
- TemplateEngine *m_engine;
TemplateBlockContext m_blockContext;
};
//----------------------------------------------------------
-TemplateContextImpl::TemplateContextImpl()
- : m_templateName("<unknown>"), m_line(1), m_escapeIntf(0),
+TemplateContextImpl::TemplateContextImpl(const TemplateEngine *e)
+ : m_engine(e), m_templateName("<unknown>"), m_line(1), m_escapeIntf(0),
m_spacelessIntf(0), m_spacelessEnabled(FALSE)
{
m_contextStack.setAutoDelete(TRUE);
@@ -1704,6 +1709,15 @@ TemplateBlockContext *TemplateContextImpl::blockContext()
return &m_blockContext;
}
+void TemplateContextImpl::warn(const char *fileName,int line,const char *fmt,...) const
+{
+ va_list args;
+ va_start(args,fmt);
+ ::warn(fileName,line,fmt,args);
+ va_end(args);
+ m_engine->printIncludeContext(fileName,line);
+}
+
//----------------------------------------------------------
/** @brief Class representing a piece of plain text in a template */
@@ -1743,7 +1757,7 @@ class TemplateNodeVariable : public TemplateNode
: TemplateNode(parent), m_templateName(parser->templateName()), m_line(line)
{
TRACE(("TemplateNodeVariable(%s)\n",var.data()));
- ExpressionParser expParser(m_templateName,line);
+ ExpressionParser expParser(parser,line);
m_var = expParser.parseVariable(var);
}
~TemplateNodeVariable()
@@ -1821,14 +1835,14 @@ class TemplateNodeIf : public TemplateNodeCreator<TemplateNodeIf>
TRACE(("{TemplateNodeIf(%s)\n",data.data()));
if (data.isEmpty())
{
- warn(m_templateName,line,"missing argument for if tag");
+ parser->warn(m_templateName,line,"missing argument for if tag");
}
QStrList stopAt;
stopAt.append("endif");
stopAt.append("else");
parser->parse(this,line,stopAt,m_trueNodes);
TemplateToken *tok = parser->takeNextToken();
- ExpressionParser ex(parser->templateName(),line);
+ ExpressionParser ex(parser,line);
m_guardAst = ex.parse(data);
if (tok && tok->data=="else")
@@ -1847,7 +1861,8 @@ class TemplateNodeIf : public TemplateNodeCreator<TemplateNodeIf>
void render(FTextStream &ts, TemplateContext *c)
{
- dynamic_cast<TemplateContextImpl*>(c)->setLocation(m_templateName,m_line);
+ TemplateContextImpl* ci = dynamic_cast<TemplateContextImpl*>(c);
+ ci->setLocation(m_templateName,m_line);
//printf("TemplateNodeIf::render #trueNodes=%d #falseNodes=%d\n",m_trueNodes.count(),m_falseNodes.count());
if (m_guardAst)
{
@@ -1877,7 +1892,7 @@ class TemplateNodeRepeat : public TemplateNodeCreator<TemplateNodeRepeat>
: TemplateNodeCreator<TemplateNodeRepeat>(parser,parent,line)
{
TRACE(("{TemplateNodeRepeat(%s)\n",data.data()));
- ExpressionParser expParser(parser->templateName(),line);
+ ExpressionParser expParser(parser,line);
m_expr = expParser.parseVariable(data);
QStrList stopAt;
stopAt.append("endrepeat");
@@ -1891,7 +1906,8 @@ class TemplateNodeRepeat : public TemplateNodeCreator<TemplateNodeRepeat>
}
void render(FTextStream &ts, TemplateContext *c)
{
- dynamic_cast<TemplateContextImpl*>(c)->setLocation(m_templateName,m_line);
+ TemplateContextImpl* ci = dynamic_cast<TemplateContextImpl*>(c);
+ ci->setLocation(m_templateName,m_line);
TemplateVariant v;
if (m_expr && (v=m_expr->resolve(c)).type()==TemplateVariant::Integer)
{
@@ -1912,7 +1928,7 @@ class TemplateNodeRepeat : public TemplateNodeCreator<TemplateNodeRepeat>
}
else // simple type...
{
- warn(m_templateName,m_line,"for requires a variable of list type!");
+ ci->warn(m_templateName,m_line,"for requires a variable of list type!");
}
}
private:
@@ -1936,15 +1952,15 @@ class TemplateNodeFor : public TemplateNodeCreator<TemplateNodeFor>
{
if (data.right(3)==" in")
{
- warn(m_templateName,line,"for is missing container after 'in' keyword");
+ parser->warn(m_templateName,line,"for is missing container after 'in' keyword");
}
else if (data=="in")
{
- warn(m_templateName,line,"for needs at least one iterator variable");
+ parser->warn(m_templateName,line,"for needs at least one iterator variable");
}
else
{
- warn(m_templateName,line,"for is missing 'in' keyword");
+ parser->warn(m_templateName,line,"for is missing 'in' keyword");
}
}
else
@@ -1952,7 +1968,7 @@ class TemplateNodeFor : public TemplateNodeCreator<TemplateNodeFor>
m_vars = split(data.left(i),",");
if (m_vars.count()==0)
{
- warn(m_templateName,line,"for needs at least one iterator variable");
+ parser->warn(m_templateName,line,"for needs at least one iterator variable");
}
int j = data.find(" reversed",i);
@@ -1965,10 +1981,10 @@ class TemplateNodeFor : public TemplateNodeCreator<TemplateNodeFor>
}
if (exprStr.isEmpty())
{
- warn(m_templateName,line,"for is missing container after 'in' keyword");
+ parser->warn(m_templateName,line,"for is missing container after 'in' keyword");
}
}
- ExpressionParser expParser(parser->templateName(),line);
+ ExpressionParser expParser(parser,line);
m_expr = expParser.parseVariable(exprStr);
QStrList stopAt;
@@ -1993,7 +2009,8 @@ class TemplateNodeFor : public TemplateNodeCreator<TemplateNodeFor>
void render(FTextStream &ts, TemplateContext *c)
{
- dynamic_cast<TemplateContextImpl*>(c)->setLocation(m_templateName,m_line);
+ TemplateContextImpl* ci = dynamic_cast<TemplateContextImpl*>(c);
+ ci->setLocation(m_templateName,m_line);
//printf("TemplateNodeFor::render #loopNodes=%d #emptyNodes=%d\n",
// m_loopNodes.count(),m_emptyNodes.count());
if (m_expr)
@@ -2058,7 +2075,7 @@ class TemplateNodeFor : public TemplateNodeCreator<TemplateNodeFor>
}
else // simple type...
{
- warn(m_templateName,m_line,"for requires a variable of list type!");
+ ci->warn(m_templateName,m_line,"for requires a variable of list type!");
}
}
}
@@ -2090,6 +2107,7 @@ class TemplateNodeMsg : public TemplateNodeCreator<TemplateNodeMsg>
void render(FTextStream &, TemplateContext *c)
{
TemplateContextImpl* ci = dynamic_cast<TemplateContextImpl*>(c);
+ ci->setLocation(m_templateName,m_line);
TemplateEscapeIntf *escIntf = ci->escapeIntf();
ci->setEscapeIntf(0); // avoid escaping things we send to standard out
bool enable = ci->spacelessEnabled();
@@ -2118,7 +2136,7 @@ class TemplateNodeBlock : public TemplateNodeCreator<TemplateNodeBlock>
m_blockName = data;
if (m_blockName.isEmpty())
{
- warn(parser->templateName(),line,"block tag without name");
+ parser->warn(parser->templateName(),line,"block tag without name");
}
QStrList stopAt;
stopAt.append("endblock");
@@ -2156,14 +2174,18 @@ class TemplateNodeBlock : public TemplateNodeCreator<TemplateNodeBlock>
superBlock.set("super",TemplateVariant(super.data(),TRUE));
ci->set("block",&superBlock);
// render the overruled block contents
+ t->engine()->enterBlock(nb->m_templateName,nb->m_blockName,nb->m_line);
nb->m_nodes.render(ts,c);
+ t->engine()->leaveBlock();
ci->pop();
// re-add block to the context
ci->blockContext()->push(nb);
}
else // block has no overrule
{
+ t->engine()->enterBlock(m_templateName,m_blockName,m_line);
m_nodes.render(ts,c);
+ t->engine()->leaveBlock();
}
}
}
@@ -2188,10 +2210,10 @@ class TemplateNodeExtend : public TemplateNodeCreator<TemplateNodeExtend>
: TemplateNodeCreator<TemplateNodeExtend>(parser,parent,line)
{
TRACE(("{TemplateNodeExtend(%s)\n",data.data()));
- ExpressionParser ep(m_templateName,line);
+ ExpressionParser ep(parser,line);
if (data.isEmpty())
{
- warn(m_templateName,line,"extend tag is missing template file argument");
+ parser->warn(m_templateName,line,"extend tag is missing template file argument");
}
m_extendExpr = ep.parsePrimary(data);
QStrList stopAt;
@@ -2205,20 +2227,21 @@ class TemplateNodeExtend : public TemplateNodeCreator<TemplateNodeExtend>
void render(FTextStream &ts, TemplateContext *c)
{
- dynamic_cast<TemplateContextImpl*>(c)->setLocation(m_templateName,m_line);
+ TemplateContextImpl* ci = dynamic_cast<TemplateContextImpl*>(c);
+ ci->setLocation(m_templateName,m_line);
if (m_extendExpr==0) return;
QCString extendFile = m_extendExpr->resolve(c).toString();
if (extendFile.isEmpty())
{
- warn(m_templateName,m_line,"invalid parameter for extend command");
+ ci->warn(m_templateName,m_line,"invalid parameter for extend command");
}
// goto root of tree (template node)
TemplateImpl *t = getTemplate();
if (t)
{
- Template *bt = t->engine()->loadByName(extendFile);
+ Template *bt = t->engine()->loadByName(extendFile,m_line);
TemplateImpl *baseTemplate = bt ? dynamic_cast<TemplateImpl*>(bt) : 0;
if (baseTemplate)
{
@@ -2248,11 +2271,11 @@ class TemplateNodeExtend : public TemplateNodeCreator<TemplateNodeExtend>
// clean up
bc->clear();
- //delete baseTemplate;
+ t->engine()->unload(t);
}
else
{
- warn(m_templateName,m_line,"failed to load template %s for extend",extendFile.data());
+ ci->warn(m_templateName,m_line,"failed to load template %s for extend",extendFile.data());
}
}
}
@@ -2270,10 +2293,10 @@ class TemplateNodeInclude : public TemplateNodeCreator<TemplateNodeInclude>
: TemplateNodeCreator<TemplateNodeInclude>(parser,parent,line)
{
TRACE(("TemplateNodeInclude(%s)\n",data.data()));
- ExpressionParser ep(m_templateName,line);
+ ExpressionParser ep(parser,line);
if (data.isEmpty())
{
- warn(m_templateName,line,"include tag is missing template file argument");
+ parser->warn(m_templateName,line,"include tag is missing template file argument");
}
m_includeExpr = ep.parsePrimary(data);
}
@@ -2283,28 +2306,30 @@ class TemplateNodeInclude : public TemplateNodeCreator<TemplateNodeInclude>
}
void render(FTextStream &ts, TemplateContext *c)
{
- dynamic_cast<TemplateContextImpl*>(c)->setLocation(m_templateName,m_line);
+ TemplateContextImpl* ci = dynamic_cast<TemplateContextImpl*>(c);
+ ci->setLocation(m_templateName,m_line);
if (m_includeExpr)
{
QCString includeFile = m_includeExpr->resolve(c).toString();
if (includeFile.isEmpty())
{
- warn(m_templateName,m_line,"invalid parameter for include command\n");
+ ci->warn(m_templateName,m_line,"invalid parameter for include command\n");
}
else
{
TemplateImpl *t = getTemplate();
if (t)
{
- Template *it = t->engine()->loadByName(includeFile);
+ Template *it = t->engine()->loadByName(includeFile,m_line);
TemplateImpl *incTemplate = it ? dynamic_cast<TemplateImpl*>(it) : 0;
if (incTemplate)
{
incTemplate->render(ts,c);
+ t->engine()->unload(t);
}
else
{
- warn(m_templateName,m_line,"failed to load template '%s' for include",includeFile.data()?includeFile.data():"");
+ ci->warn(m_templateName,m_line,"failed to load template '%s' for include",includeFile.data()?includeFile.data():"");
}
}
}
@@ -2325,30 +2350,30 @@ class TemplateNodeCreate : public TemplateNodeCreator<TemplateNodeCreate>
: TemplateNodeCreator<TemplateNodeCreate>(parser,parent,line)
{
TRACE(("TemplateNodeCreate(%s)\n",data.data()));
- ExpressionParser ep(m_templateName,line);
+ ExpressionParser ep(parser,line);
if (data.isEmpty())
{
- warn(m_templateName,line,"create tag is missing arguments");
+ parser->warn(m_templateName,line,"create tag is missing arguments");
}
int i = data.find(" from ");
if (i==-1)
{
if (data.right(3)==" from")
{
- warn(m_templateName,line,"create is missing template name after 'from' keyword");
+ parser->warn(m_templateName,line,"create is missing template name after 'from' keyword");
}
else if (data=="from")
{
- warn(m_templateName,line,"create needs a file name and a template name");
+ parser->warn(m_templateName,line,"create needs a file name and a template name");
}
else
{
- warn(m_templateName,line,"create is missing 'from' keyword");
+ parser->warn(m_templateName,line,"create is missing 'from' keyword");
}
}
else
{
- ExpressionParser ep(m_templateName,line);
+ ExpressionParser ep(parser,line);
m_fileExpr = ep.parsePrimary(data.left(i).stripWhiteSpace());
m_templateExpr = ep.parsePrimary(data.mid(i+6).stripWhiteSpace());
}
@@ -2368,18 +2393,18 @@ class TemplateNodeCreate : public TemplateNodeCreator<TemplateNodeCreate>
QCString outputFile = m_fileExpr->resolve(c).toString();
if (templateFile.isEmpty())
{
- warn(m_templateName,m_line,"empty template name parameter for create command\n");
+ ci->warn(m_templateName,m_line,"empty template name parameter for create command\n");
}
else if (outputFile.isEmpty())
{
- warn(m_templateName,m_line,"empty file name parameter for create command\n");
+ ci->warn(m_templateName,m_line,"empty file name parameter for create command\n");
}
else
{
TemplateImpl *t = getTemplate();
if (t)
{
- Template *ct = t->engine()->loadByName(templateFile);
+ Template *ct = t->engine()->loadByName(templateFile,m_line);
TemplateImpl *createTemplate = ct ? dynamic_cast<TemplateImpl*>(ct) : 0;
if (createTemplate)
{
@@ -2392,16 +2417,16 @@ class TemplateNodeCreate : public TemplateNodeCreator<TemplateNodeCreate>
{
FTextStream ts(&f);
createTemplate->render(ts,c);
- //delete createTemplate;
+ t->engine()->unload(t);
}
else
{
- warn(m_templateName,m_line,"failed to open output file '%s' for create command",outputFile.data());
+ ci->warn(m_templateName,m_line,"failed to open output file '%s' for create command",outputFile.data());
}
}
else
{
- warn(m_templateName,m_line,"failed to load template '%s' for include",templateFile.data());
+ ci->warn(m_templateName,m_line,"failed to load template '%s' for include",templateFile.data());
}
}
}
@@ -2431,10 +2456,10 @@ class TemplateNodeTree : public TemplateNodeCreator<TemplateNodeTree>
: TemplateNodeCreator<TemplateNodeTree>(parser,parent,line)
{
TRACE(("{TemplateNodeTree(%s)\n",data.data()));
- ExpressionParser ep(m_templateName,line);
+ ExpressionParser ep(parser,line);
if (data.isEmpty())
{
- warn(m_templateName,line,"recursetree tag is missing data argument");
+ parser->warn(m_templateName,line,"recursetree tag is missing data argument");
}
m_treeExpr = ep.parsePrimary(data);
QStrList stopAt;
@@ -2508,7 +2533,7 @@ class TemplateNodeTree : public TemplateNodeCreator<TemplateNodeTree>
}
else
{
- warn(m_templateName,m_line,"recursetree's argument should be a list type");
+ ci->warn(m_templateName,m_line,"recursetree's argument should be a list type");
}
}
@@ -2535,7 +2560,7 @@ class TemplateNodeWith : public TemplateNodeCreator<TemplateNodeWith>
{
TRACE(("{TemplateNodeWith(%s)\n",data.data()));
m_args.setAutoDelete(TRUE);
- ExpressionParser expParser(parser->templateName(),line);
+ ExpressionParser expParser(parser,line);
QValueList<QCString> args = split(data," ");
QValueListIterator<QCString> it = args.begin();
while (it!=args.end())
@@ -2552,7 +2577,7 @@ class TemplateNodeWith : public TemplateNodeCreator<TemplateNodeWith>
}
else
{
- warn(parser->templateName(),line,"invalid argument '%s' for with tag",arg.data());
+ parser->warn(parser->templateName(),line,"invalid argument '%s' for with tag",arg.data());
}
++it;
}
@@ -2568,6 +2593,7 @@ class TemplateNodeWith : public TemplateNodeCreator<TemplateNodeWith>
void render(FTextStream &ts, TemplateContext *c)
{
TemplateContextImpl *ci = dynamic_cast<TemplateContextImpl*>(c);
+ ci->setLocation(m_templateName,m_line);
c->push();
QListIterator<Mapping> it(m_args);
Mapping *mapping;
@@ -2596,7 +2622,7 @@ class TemplateNodeCycle : public TemplateNodeCreator<TemplateNodeCycle>
TRACE(("{TemplateNodeCycle(%s)\n",data.data()));
m_args.setAutoDelete(TRUE);
m_index=0;
- ExpressionParser expParser(parser->templateName(),line);
+ ExpressionParser expParser(parser,line);
QValueList<QCString> args = split(data," ");
QValueListIterator<QCString> it = args.begin();
while (it!=args.end())
@@ -2610,13 +2636,14 @@ class TemplateNodeCycle : public TemplateNodeCreator<TemplateNodeCycle>
}
if (m_args.count()<2)
{
- warn(parser->templateName(),line,"expected at least two arguments for cycle command, got %d",m_args.count());
+ parser->warn(parser->templateName(),line,"expected at least two arguments for cycle command, got %d",m_args.count());
}
TRACE(("}TemplateNodeCycle(%s)\n",data.data()));
}
void render(FTextStream &ts, TemplateContext *c)
{
TemplateContextImpl *ci = dynamic_cast<TemplateContextImpl*>(c);
+ ci->setLocation(m_templateName,m_line);
if (m_index<m_args.count())
{
TemplateVariant v = m_args.at(m_index)->resolve(c);
@@ -2661,7 +2688,7 @@ class TemplateNodeSet : public TemplateNodeCreator<TemplateNodeSet>
{
TRACE(("{TemplateNodeSet(%s)\n",data.data()));
m_args.setAutoDelete(TRUE);
- ExpressionParser expParser(parser->templateName(),line);
+ ExpressionParser expParser(parser,line);
QValueList<QCString> args = split(data," ");
QValueListIterator<QCString> it = args.begin();
while (it!=args.end())
@@ -2678,7 +2705,7 @@ class TemplateNodeSet : public TemplateNodeCreator<TemplateNodeSet>
}
else
{
- warn(parser->templateName(),line,"invalid argument '%s' for with tag",arg.data());
+ parser->warn(parser->templateName(),line,"invalid argument '%s' for with tag",arg.data());
}
++it;
}
@@ -2687,6 +2714,7 @@ class TemplateNodeSet : public TemplateNodeCreator<TemplateNodeSet>
void render(FTextStream &, TemplateContext *c)
{
TemplateContextImpl *ci = dynamic_cast<TemplateContextImpl*>(c);
+ ci->setLocation(m_templateName,m_line);
QListIterator<Mapping> it(m_args);
Mapping *mapping;
for (it.toFirst();(mapping=it.current());++it)
@@ -2718,6 +2746,7 @@ class TemplateNodeSpaceless : public TemplateNodeCreator<TemplateNodeSpaceless>
void render(FTextStream &ts, TemplateContext *c)
{
TemplateContextImpl *ci = dynamic_cast<TemplateContextImpl*>(c);
+ ci->setLocation(m_templateName,m_line);
bool wasSpaceless = ci->spacelessEnabled();
ci->enableSpaceless(TRUE);
m_nodes.render(ts,c);
@@ -2741,11 +2770,11 @@ class TemplateNodeMarkers : public TemplateNodeCreator<TemplateNodeMarkers>
int w = data.find(" with ");
if (i==-1 || w==-1 || w<i)
{
- warn(m_templateName,line,"markers tag as wrong format. Expected: markers <var> in <list> with <string_with_markers>");
+ parser->warn(m_templateName,line,"markers tag as wrong format. Expected: markers <var> in <list> with <string_with_markers>");
}
else
{
- ExpressionParser expParser(parser->templateName(),line);
+ ExpressionParser expParser(parser,line);
m_var = data.left(i);
m_listExpr = expParser.parseVariable(data.mid(i+4,w-i-4));
m_patternExpr = expParser.parseVariable(data.right(data.length()-w-6));
@@ -2796,11 +2825,11 @@ class TemplateNodeMarkers : public TemplateNodeCreator<TemplateNodeMarkers>
}
else if (!ok)
{
- warn(m_templateName,m_line,"markers pattern string has invalid markers '%s'",str.data());
+ ci->warn(m_templateName,m_line,"markers pattern string has invalid markers '%s'",str.data());
}
else if (i<entryIndex)
{
- warn(m_templateName,m_line,"markers list does not an element for marker position %d",i);
+ ci->warn(m_templateName,m_line,"markers list does not an element for marker position %d",i);
}
index=newIndex+matchLen; // set index just after marker
}
@@ -2809,12 +2838,12 @@ class TemplateNodeMarkers : public TemplateNodeCreator<TemplateNodeMarkers>
}
else
{
- warn(m_templateName,m_line,"markers requires a parameter of string type after 'with'!");
+ ci->warn(m_templateName,m_line,"markers requires a parameter of string type after 'with'!");
}
}
else
{
- warn(m_templateName,m_line,"markers requires a parameter of list type after 'in'!");
+ ci->warn(m_templateName,m_line,"markers requires a parameter of list type after 'in'!");
}
}
}
@@ -2970,19 +2999,20 @@ void TemplateBlockContext::push(TemplateNodeBlock *block)
class TemplateLexer
{
public:
- TemplateLexer(const QCString &fileName,const QCString &data);
+ TemplateLexer(const TemplateEngine *engine,const QCString &fileName,const QCString &data);
void tokenize(QList<TemplateToken> &tokens);
private:
void addToken(QList<TemplateToken> &tokens,
const char *data,int line,int startPos,int endPos,
TemplateToken::Type type);
void reset();
+ const TemplateEngine *m_engine;
QCString m_fileName;
QCString m_data;
};
-TemplateLexer::TemplateLexer(const QCString &fileName,const QCString &data) :
- m_fileName(fileName), m_data(data)
+TemplateLexer::TemplateLexer(const TemplateEngine *engine,const QCString &fileName,const QCString &data) :
+ m_engine(engine), m_fileName(fileName), m_data(data)
{
}
@@ -3049,6 +3079,7 @@ void TemplateLexer::tokenize(QList<TemplateToken> &tokens)
if (c=='\n')
{
warn(m_fileName,line,"unexpected new line inside {%%...%%} block");
+ m_engine->printIncludeContext(m_fileName,line);
}
else if (c=='%') // %} or something else
{
@@ -3072,6 +3103,7 @@ void TemplateLexer::tokenize(QList<TemplateToken> &tokens)
if (c=='\n')
{
warn(m_fileName,line,"unexpected new line inside {%%...%%} block");
+ m_engine->printIncludeContext(m_fileName,line);
}
state=StateTag;
}
@@ -3080,6 +3112,7 @@ void TemplateLexer::tokenize(QList<TemplateToken> &tokens)
if (c=='\n')
{
warn(m_fileName,line,"unexpected new line inside {#...#} block");
+ m_engine->printIncludeContext(m_fileName,line);
}
else if (c=='#') // #} or something else
{
@@ -3101,6 +3134,7 @@ void TemplateLexer::tokenize(QList<TemplateToken> &tokens)
if (c=='\n')
{
warn(m_fileName,line,"unexpected new line inside {#...#} block");
+ m_engine->printIncludeContext(m_fileName,line);
}
state=StateComment;
}
@@ -3125,6 +3159,7 @@ void TemplateLexer::tokenize(QList<TemplateToken> &tokens)
if (c=='\n')
{
warn(m_fileName,line,"unexpected new line inside {{...}} block");
+ m_engine->printIncludeContext(m_fileName,line);
}
else if (c=='}') // }} or something else
{
@@ -3148,6 +3183,7 @@ void TemplateLexer::tokenize(QList<TemplateToken> &tokens)
if (c=='\n')
{
warn(m_fileName,line,"unexpected new line inside {{...}} block");
+ m_engine->printIncludeContext(m_fileName,line);
}
state=StateVariable;
}
@@ -3192,9 +3228,10 @@ void TemplateLexer::addToken(QList<TemplateToken> &tokens,
//----------------------------------------------------------
-TemplateParser::TemplateParser(const QCString &templateName,
+TemplateParser::TemplateParser(const TemplateEngine *engine,
+ const QCString &templateName,
QList<TemplateToken> &tokens) :
- m_templateName(templateName), m_tokens(tokens)
+ m_engine(engine), m_templateName(templateName), m_tokens(tokens)
{
}
@@ -3214,10 +3251,10 @@ void TemplateParser::parse(
case TemplateToken::Text:
nodes.append(new TemplateNodeText(this,parent,tok->line,tok->data));
break;
- case TemplateToken::Variable:
+ case TemplateToken::Variable: // {{ var }}
nodes.append(new TemplateNodeVariable(this,parent,tok->line,tok->data));
break;
- case TemplateToken::Block:
+ case TemplateToken::Block: // {% tag %}
{
QCString command = tok->data;
int sep = command.find(' ');
@@ -3301,6 +3338,15 @@ void TemplateParser::prependToken(const TemplateToken *token)
m_tokens.prepend(token);
}
+void TemplateParser::warn(const char *fileName,int line,const char *fmt,...) const
+{
+ va_list args;
+ va_start(args,fmt);
+ ::warn(fileName,line,fmt,args);
+ va_end(args);
+ m_engine->printIncludeContext(fileName,line);
+}
+
//----------------------------------------------------------
@@ -3311,11 +3357,11 @@ TemplateImpl::TemplateImpl(TemplateEngine *engine,const QCString &name,const QCS
{
m_name = name;
m_engine = engine;
- TemplateLexer lexer(name,data);
+ TemplateLexer lexer(engine,name,data);
QList<TemplateToken> tokens;
tokens.setAutoDelete(TRUE);
lexer.tokenize(tokens);
- TemplateParser parser(name,tokens);
+ TemplateParser parser(engine,name,tokens);
parser.parse(this,1,QStrList(),m_nodes);
}
@@ -3348,11 +3394,35 @@ void TemplateImpl::render(FTextStream &ts, TemplateContext *c)
/** @brief Private data of the template engine */
class TemplateEngine::Private
{
+ class IncludeEntry
+ {
+ public:
+ enum Type { Template, Block };
+ IncludeEntry(Type type,const QCString &fileName,const QCString &blockName,int line)
+ : m_type(type), m_fileName(fileName), m_blockName(blockName), m_line(line) {}
+ Type type() const { return m_type; }
+ QCString fileName() const { return m_fileName; }
+ QCString blockName() const { return m_blockName; }
+ int line() const { return m_line; }
+
+ private:
+ Type m_type;
+ QCString m_fileName;
+ QCString m_blockName;
+ int m_line;
+ };
public:
- Private(TemplateEngine *engine) : m_templateCache(17), m_engine(engine)
- { m_templateCache.setAutoDelete(TRUE); }
- Template *loadByName(const QCString &fileName) const
+ Private(TemplateEngine *engine) : m_templateCache(17) /*, m_indent(0)*/, m_engine(engine)
{
+ m_templateCache.setAutoDelete(TRUE);
+ m_includeStack.setAutoDelete(TRUE);
+ }
+ Template *loadByName(const QCString &fileName,int line)
+ {
+ //for (int i=0;i<m_indent;i++) printf(" ");
+ //m_indent++;
+ //printf("loadByName(%s,%d) {\n",fileName.data(),line);
+ m_includeStack.append(new IncludeEntry(IncludeEntry::Template,fileName,QCString(),line));
Template *templ = m_templateCache.find(fileName);
if (templ==0)
{
@@ -3379,10 +3449,60 @@ class TemplateEngine::Private
}
return templ;
}
+ void unload(Template * /*t*/)
+ {
+ //(void)t;
+ //m_indent--;
+ //for (int i=0;i<m_indent;i++) printf(" ");
+ //printf("}\n");
+ m_includeStack.removeLast();
+ }
+
+ void enterBlock(const QCString &fileName,const QCString &blockName,int line)
+ {
+ //for (int i=0;i<m_indent;i++) printf(" ");
+ //m_indent++;
+ //printf("enterBlock(%s,%s,%d) {\n",fileName.data(),blockName.data(),line);
+ m_includeStack.append(new IncludeEntry(IncludeEntry::Block,fileName,blockName,line));
+ }
+
+ void leaveBlock()
+ {
+ //m_indent--;
+ //for (int i=0;i<m_indent;i++) printf(" ");
+ //printf("}\n");
+ m_includeStack.removeLast();
+ }
+
+ void printIncludeContext(const char *fileName,int line) const
+ {
+ QListIterator<IncludeEntry> li(m_includeStack);
+ li.toLast();
+ IncludeEntry *ie=li.current();
+ while ((ie=li.current()))
+ {
+ --li;
+ IncludeEntry *next=li.current();
+ if (ie->type()==IncludeEntry::Template)
+ {
+ if (next)
+ {
+ warn(fileName,line," inside template '%s' included from template '%s' at line %d",ie->fileName().data(),next->fileName().data(),ie->line());
+ }
+ }
+ else // ie->type()==IncludeEntry::Block
+ {
+ warn(fileName,line," included by block '%s' inside template '%s' at line %d",ie->blockName().data(),
+ ie->fileName().data(),ie->line());
+ }
+ }
+ }
private:
- mutable QDict<Template> m_templateCache;
+ QDict<Template> m_templateCache;
+ //mutable int m_indent;
TemplateEngine *m_engine;
+ QList<IncludeEntry> m_includeStack;
};
TemplateEngine::TemplateEngine()
@@ -3397,11 +3517,31 @@ TemplateEngine::~TemplateEngine()
TemplateContext *TemplateEngine::createContext() const
{
- return new TemplateContextImpl;
+ return new TemplateContextImpl(this);
+}
+
+Template *TemplateEngine::loadByName(const QCString &fileName,int line)
+{
+ return p->loadByName(fileName,line);
+}
+
+void TemplateEngine::unload(Template *t)
+{
+ p->unload(t);
+}
+
+void TemplateEngine::enterBlock(const QCString &fileName,const QCString &blockName,int line)
+{
+ p->enterBlock(fileName,blockName,line);
+}
+
+void TemplateEngine::leaveBlock()
+{
+ p->leaveBlock();
}
-Template *TemplateEngine::loadByName(const QCString &fileName)
+void TemplateEngine::printIncludeContext(const char *fileName,int line) const
{
- return p->loadByName(fileName);
+ p->printIncludeContext(fileName,line);
}
diff --git a/src/template.h b/src/template.h
index 9e3b106..62cea34 100644
--- a/src/template.h
+++ b/src/template.h
@@ -10,32 +10,32 @@ class TemplateListIntf;
class TemplateStructIntf;
class TemplateEngine;
-/** @defgroup template_api Template API
+/** @defgroup template_api Template API
*
- * This is the API for a
- * <a href="https://docs.djangoproject.com/en/1.6/topics/templates/">Django</a>
+ * This is the API for a
+ * <a href="https://docs.djangoproject.com/en/1.6/topics/templates/">Django</a>
* compatible template system written in C++.
- * It is somewhat inspired by Stephen Kelly's
+ * It is somewhat inspired by Stephen Kelly's
* <a href="http://www.gitorious.org/grantlee/pages/Home">Grantlee</a>.
*
- * A template is simply a text file.
- * A template contains \b variables, which get replaced with values when the
+ * A template is simply a text file.
+ * A template contains \b variables, which get replaced with values when the
* template is evaluated, and \b tags, which control the logic of the template.
*
* Variables look like this: `{{ variable }}`
- * When the template engine encounters a variable, it evaluates that variable and
- * replaces it with the result. Variable names consist of any combination of
+ * When the template engine encounters a variable, it evaluates that variable and
+ * replaces it with the result. Variable names consist of any combination of
* alphanumeric characters and the underscore ("_").
* Use a dot (.) to access attributes of a structured variable.
- *
+ *
* One can modify variables for display by using \b filters, for example:
* `{{ value|default:"nothing" }}`
*
- * Tags look like this: `{% tag %}`. Tags are more complex than variables:
- * Some create text in the output, some control flow by performing loops or logic,
+ * Tags look like this: `{% tag %}`. Tags are more complex than variables:
+ * Some create text in the output, some control flow by performing loops or logic,
* and some load external information into the template to be used by later variables.
*
- * To comment-out part of a line in a template, use the comment syntax:
+ * To comment-out part of a line in a template, use the comment syntax:
* `{# comment text #}`.
*
* Supported Django tags:
@@ -144,13 +144,13 @@ class TemplateVariant
/** Constructs a new variant with a string value \a s. */
TemplateVariant(const QCString &s,bool raw=FALSE);
- /** Constructs a new variant with a struct value \a s.
+ /** Constructs a new variant with a struct value \a s.
* @note. Only a pointer to the struct is stored. The caller
* is responsible to manage the memory for the struct object.
*/
TemplateVariant(const TemplateStructIntf *s);
- /** Constructs a new variant with a list value \a l.
+ /** Constructs a new variant with a list value \a l.
* @note. Only a pointer to the struct is stored. The caller
* is responsible to manage the memory for the list object.
*/
@@ -168,7 +168,7 @@ class TemplateVariant
/** Destroys the Variant object */
~TemplateVariant();
- /** Constructs a copy of the variant, \a v,
+ /** Constructs a copy of the variant, \a v,
* passed as the argument to this constructor.
*/
TemplateVariant(const TemplateVariant &v);
@@ -176,7 +176,7 @@ class TemplateVariant
/** Assigns the value of the variant \a v to this variant. */
TemplateVariant &operator=(const TemplateVariant &v);
- /** Compares this QVariant with v and returns true if they are equal;
+ /** Compares this QVariant with v and returns true if they are equal;
* otherwise returns false.
*/
bool operator==(TemplateVariant &other);
@@ -190,13 +190,13 @@ class TemplateVariant
/** Returns the variant as an integer. */
int toInt() const;
- /** Returns the pointer to list referenced by this variant
- * or 0 if this variant does not have list type.
+ /** Returns the pointer to list referenced by this variant
+ * or 0 if this variant does not have list type.
*/
const TemplateListIntf *toList() const;
- /** Returns the pointer to struct referenced by this variant
- * or 0 if this variant does not have struct type.
+ /** Returns the pointer to struct referenced by this variant
+ * or 0 if this variant does not have struct type.
*/
const TemplateStructIntf *toStruct() const;
@@ -205,7 +205,7 @@ class TemplateVariant
*/
TemplateVariant call(const QValueList<TemplateVariant> &args);
- /** Sets whether or not the value of the Variant should be
+ /** Sets whether or not the value of the Variant should be
* escaped or written as-is (raw).
* @param[in] b TRUE means write as-is, FALSE means apply escaping.
*/
@@ -223,7 +223,7 @@ class TemplateVariant
//------------------------------------------------------------------------
-/** @brief Abstract read-only interface for a context value of type list.
+/** @brief Abstract read-only interface for a context value of type list.
* @note The values of the list are TemplateVariants.
*/
class TemplateListIntf
@@ -245,7 +245,7 @@ class TemplateListIntf
virtual void toPrev() = 0;
/* Returns TRUE if the iterator points to a valid element
* in the list, or FALSE otherwise.
- * If TRUE is returned, the value pointed to be the
+ * If TRUE is returned, the value pointed to be the
* iterator is assigned to \a v.
*/
virtual bool current(TemplateVariant &v) const = 0;
@@ -260,7 +260,7 @@ class TemplateListIntf
/** Returns the element at index position \a index. */
virtual TemplateVariant at(int index) const = 0;
- /** Creates a new iterator for this list.
+ /** Creates a new iterator for this list.
* @note the user should call delete on the returned pointer.
*/
virtual TemplateListIntf::ConstIterator *createIterator() const = 0;
@@ -279,7 +279,7 @@ class TemplateList : public TemplateListIntf
virtual int count() const;
virtual TemplateVariant at(int index) const;
virtual TemplateListIntf::ConstIterator *createIterator() const;
-
+
/** Appends element \a v to the end of the list */
virtual void append(const TemplateVariant &v);
@@ -350,8 +350,8 @@ class TemplateSpacelessIntf
//------------------------------------------------------------------------
-/** @brief Abstract interface for a template context.
- *
+/** @brief Abstract interface for a template context.
+ *
* A Context consists of a stack of dictionaries.
* A dictionary consists of a mapping of string keys onto TemplateVariant values.
* A key is searched starting with the dictionary at the top of the stack
@@ -370,10 +370,10 @@ class TemplateContext
/** Pop the current scope from the stack. */
virtual void pop() = 0;
- /** Sets a value in the current scope.
+ /** Sets a value in the current scope.
* @param[in] name The name of the value; the key in the dictionary.
* @param[in] v The value associated with the key.
- * @note When a given key is already present,
+ * @note When a given key is already present,
* its value will be replaced by \a v
*/
virtual void set(const char *name,const TemplateVariant &v) = 0;
@@ -409,8 +409,8 @@ class TemplateContext
//------------------------------------------------------------------------
-/** @brief Abstract interface for a template.
- * @note Must be created by TemplateEngine
+/** @brief Abstract interface for a template.
+ * @note Must be created and is deleted by the TemplateEngine
*/
class Template
{
@@ -418,7 +418,7 @@ class Template
/** Destructor */
virtual ~Template() {}
- /** Renders a template instance to a stream.
+ /** Renders a template instance to a stream.
* @param[in] ts The text stream to write the results to.
* @param[in] c The context containing data that can be used
* when instantiating the template.
@@ -444,13 +444,25 @@ class TemplateEngine
TemplateContext *createContext() const;
/** Creates a new template whole contents are in a file.
- * @param[in] fileName The name of the file containing the
+ * @param[in] fileName The name of the file containing the
* template data
+ * @param[in] fromLine The line number of the statement that triggered the load
* @return the new template, the caller will be the owner.
*/
- Template *loadByName(const QCString &fileName);
+ Template *loadByName(const QCString &fileName,int fromLine);
+
+ /** Indicates that template \a t is no longer needed. The engine
+ * may decide to delete it.
+ */
+ void unload(Template *t);
+
+ void printIncludeContext(const char *fileName,int line) const;
private:
+ friend class TemplateNodeBlock;
+ void enterBlock(const QCString &fileName,const QCString &blockName,int line);
+ void leaveBlock();
+
class Private;
Private *p;
};