From 28401810fe9be0dafea604a50b4139d10f75873a Mon Sep 17 00:00:00 2001 From: Marcelo Lira Date: Mon, 28 Jun 2010 10:53:41 -0300 Subject: Class members are traversed after the classes themselves. To prevent a method that uses a type that was not ready at the moment of analysis, the classes are traversed separately and before the class members, namely fields and methods. --- abstractmetabuilder.cpp | 37 +++++++++++++++++++++++++++++++++---- 1 file changed, 33 insertions(+), 4 deletions(-) (limited to 'abstractmetabuilder.cpp') diff --git a/abstractmetabuilder.cpp b/abstractmetabuilder.cpp index e002b57ea..fe310cf1e 100644 --- a/abstractmetabuilder.cpp +++ b/abstractmetabuilder.cpp @@ -385,6 +385,11 @@ bool AbstractMetaBuilder::build(QIODevice* input) } ReportHandler::flush(); + foreach (ClassModelItem item, typeValues) + traverseClassMembers(model_dynamic_cast(item)); + foreach (NamespaceModelItem namespaceItem, namespaceMap.values()) + traverseClassMembers(model_dynamic_cast(namespaceItem)); + // Global functions foreach (FunctionModelItem func, m_dom->functions()) { if (func->accessPolicy() != CodeModel::Public || func->name().startsWith("operator")) @@ -629,8 +634,6 @@ AbstractMetaClass* AbstractMetaBuilder::traverseNamespace(NamespaceModelItem nam .arg(namespaceItem->name())); traverseEnums(model_dynamic_cast(namespaceItem), metaClass, namespaceItem->enumsDeclarations()); - traverseFunctions(model_dynamic_cast(namespaceItem), metaClass); -// traverseClasses(model_dynamic_cast(namespace_item)); pushScope(model_dynamic_cast(namespaceItem)); m_namespacePrefix = currentScope()->qualifiedName().join("::"); @@ -1070,8 +1073,6 @@ AbstractMetaClass* AbstractMetaBuilder::traverseClass(ClassModelItem classItem) parseQ_Property(metaClass, classItem->propertyDeclarations()); traverseEnums(model_dynamic_cast(classItem), metaClass, classItem->enumsDeclarations()); - traverseFields(model_dynamic_cast(classItem), metaClass); - traverseFunctions(model_dynamic_cast(classItem), metaClass); // Inner classes { @@ -1108,6 +1109,34 @@ AbstractMetaClass* AbstractMetaBuilder::traverseClass(ClassModelItem classItem) return metaClass; } +void AbstractMetaBuilder::traverseClassMembers(ScopeModelItem scopeItem) +{ + QString className = stripTemplateArgs(scopeItem->name()); + QString fullClassName = className; + + // This is an inner class + if (m_currentClass) + fullClassName = stripTemplateArgs(m_currentClass->typeEntry()->qualifiedCppName()) + "::" + fullClassName; + + AbstractMetaClass* metaClass = m_metaClasses.findClass(fullClassName); + if (!metaClass) + return; + + AbstractMetaClass* oldCurrentClass = m_currentClass; + m_currentClass = metaClass; + + traverseFields(scopeItem, metaClass); + traverseFunctions(scopeItem, metaClass); + + { + QList innerClasses = scopeItem->classMap().values(); + foreach (const ClassModelItem& ci, innerClasses) + traverseClassMembers(model_dynamic_cast(ci)); + } + + m_currentClass = oldCurrentClass; +} + AbstractMetaField* AbstractMetaBuilder::traverseField(VariableModelItem field, const AbstractMetaClass *cls) { QString fieldName = field->name(); -- cgit v1.2.3