aboutsummaryrefslogtreecommitdiffstats
path: root/sources/shiboken2
diff options
context:
space:
mode:
authorAndreas Beckermann <beckermann@monument-software.de>2019-09-12 15:10:46 +0200
committerAndreas Beckermann <beckermann@monument-software.de>2019-10-25 07:37:34 +0200
commite52ebf296e8fcd84fa4055c80a3c489ae1431c9e (patch)
tree106510917095522f07c1f16d57b84f078cbfa9e3 /sources/shiboken2
parentb332456c38241d663d1eef3636129ea82fd00564 (diff)
Add support for __repr__ in QObject derived classes
Currently shiboken generates classes without __repr__ for QObject derived classes. However for all non-QObject classes that have an operator<<() for QDebug, it *does* add a valid repr implementation. Extend this behavior to QObject classes as well. In order for this to become more useful, also check for the indirection of operator<<(): If operator<<(QDebug, Foo*) is available, use the current non-value-type behavior, (i.e. provide cppSelf to operator<<()), but if operator<<(QDebug, const Foo&) is available instead, use the same behavior as for value-types, i.e. provide *cppSelf. This greatly increases the number of classes where operator<<() provides useful results. Also make sure to check for operator<<() in namespaces (recursively), not just at global scope. Change-Id: Ief9158455a25e332f07169f09692cafb8097078b Reviewed-by: Friedemann Kleint <Friedemann.Kleint@qt.io>
Diffstat (limited to 'sources/shiboken2')
-rw-r--r--sources/shiboken2/ApiExtractor/abstractmetabuilder.cpp17
-rw-r--r--sources/shiboken2/ApiExtractor/abstractmetabuilder_p.h1
-rw-r--r--sources/shiboken2/ApiExtractor/abstractmetalang.h9
-rw-r--r--sources/shiboken2/generator/shiboken2/cppgenerator.cpp11
-rw-r--r--sources/shiboken2/generator/shiboken2/cppgenerator.h2
5 files changed, 28 insertions, 12 deletions
diff --git a/sources/shiboken2/ApiExtractor/abstractmetabuilder.cpp b/sources/shiboken2/ApiExtractor/abstractmetabuilder.cpp
index 4b31dbb05..6aafe68be 100644
--- a/sources/shiboken2/ApiExtractor/abstractmetabuilder.cpp
+++ b/sources/shiboken2/ApiExtractor/abstractmetabuilder.cpp
@@ -248,6 +248,15 @@ void AbstractMetaBuilderPrivate::registerHashFunction(const FunctionModelItem &f
}
}
+void AbstractMetaBuilderPrivate::registerToStringCapabilityIn(const NamespaceModelItem &nsItem)
+{
+ const FunctionList &streamOps = nsItem->findFunctions(QLatin1String("operator<<"));
+ for (const FunctionModelItem &item : streamOps)
+ registerToStringCapability(item, nullptr);
+ for (const NamespaceModelItem &ni : nsItem->namespaces())
+ registerToStringCapabilityIn(ni);
+}
+
/**
* Check if a class has a debug stream operator that can be used as toString
*/
@@ -261,7 +270,7 @@ void AbstractMetaBuilderPrivate::registerToStringCapability(const FunctionModelI
const ArgumentModelItem &arg = arguments.at(1);
if (AbstractMetaClass *cls = argumentToClass(arg, currentClass)) {
if (arg->type().indirections() < 2)
- cls->setToStringCapability(true);
+ cls->setToStringCapability(true, arg->type().indirections());
}
}
}
@@ -591,11 +600,7 @@ void AbstractMetaBuilderPrivate::traverseDom(const FileModelItem &dom)
registerHashFunction(item, nullptr);
}
- {
- const FunctionList &streamOps = dom->findFunctions(QLatin1String("operator<<"));
- for (const FunctionModelItem &item : streamOps)
- registerToStringCapability(item, nullptr);
- }
+ registerToStringCapabilityIn(dom);
{
FunctionList binaryOperators = dom->findFunctions(QStringLiteral("operator=="));
diff --git a/sources/shiboken2/ApiExtractor/abstractmetabuilder_p.h b/sources/shiboken2/ApiExtractor/abstractmetabuilder_p.h
index fec2eddb9..9b1b181cc 100644
--- a/sources/shiboken2/ApiExtractor/abstractmetabuilder_p.h
+++ b/sources/shiboken2/ApiExtractor/abstractmetabuilder_p.h
@@ -106,6 +106,7 @@ public:
void checkFunctionModifications();
void registerHashFunction(const FunctionModelItem &functionItem,
AbstractMetaClass *currentClass);
+ void registerToStringCapabilityIn(const NamespaceModelItem &namespaceItem);
void registerToStringCapability(const FunctionModelItem &functionItem,
AbstractMetaClass *currentClass);
diff --git a/sources/shiboken2/ApiExtractor/abstractmetalang.h b/sources/shiboken2/ApiExtractor/abstractmetalang.h
index afb4e5fbd..91ca4d7a9 100644
--- a/sources/shiboken2/ApiExtractor/abstractmetalang.h
+++ b/sources/shiboken2/ApiExtractor/abstractmetalang.h
@@ -1691,9 +1691,10 @@ public:
return m_stream;
}
- void setToStringCapability(bool value)
+ void setToStringCapability(bool value, uint indirections = 0)
{
m_hasToStringCapability = value;
+ m_toStringCapabilityIndirections = indirections;
}
bool hasToStringCapability() const
@@ -1701,6 +1702,11 @@ public:
return m_hasToStringCapability;
}
+ uint toStringCapabilityIndirections() const
+ {
+ return m_toStringCapabilityIndirections;
+ }
+
bool deleteInMainThread() const;
static AbstractMetaClass *findClass(const AbstractMetaClassList &classes,
@@ -1753,6 +1759,7 @@ private:
// FunctionModelItem m_qDebugStreamFunction;
bool m_stream = false;
+ uint m_toStringCapabilityIndirections = 0;
};
Q_DECLARE_OPERATORS_FOR_FLAGS(AbstractMetaClass::FunctionQueryOptions)
diff --git a/sources/shiboken2/generator/shiboken2/cppgenerator.cpp b/sources/shiboken2/generator/shiboken2/cppgenerator.cpp
index 7de0cfc09..61429b383 100644
--- a/sources/shiboken2/generator/shiboken2/cppgenerator.cpp
+++ b/sources/shiboken2/generator/shiboken2/cppgenerator.cpp
@@ -3933,9 +3933,10 @@ void CppGenerator::writeClassDefinition(QTextStream &s,
m_tpFuncs[func->name()] = cpythonFunctionName(func);
}
if (m_tpFuncs.value(QLatin1String("__repr__")).isEmpty()
- && !metaClass->isQObject()
&& metaClass->hasToStringCapability()) {
- m_tpFuncs[QLatin1String("__repr__")] = writeReprFunction(s, classContext);
+ m_tpFuncs[QLatin1String("__repr__")] = writeReprFunction(s,
+ classContext,
+ metaClass->toStringCapabilityIndirections());
}
// class or some ancestor has multiple inheritance
@@ -6006,7 +6007,9 @@ void CppGenerator::writeIndexError(QTextStream &s, const QString &errorMsg)
s << INDENT << '}' << endl;
}
-QString CppGenerator::writeReprFunction(QTextStream &s, GeneratorContext &context)
+QString CppGenerator::writeReprFunction(QTextStream &s,
+ GeneratorContext &context,
+ uint indirections)
{
const AbstractMetaClass *metaClass = context.metaClass();
QString funcName = cpythonBaseName(metaClass) + QLatin1String("__repr__");
@@ -6019,7 +6022,7 @@ QString CppGenerator::writeReprFunction(QTextStream &s, GeneratorContext &contex
s << INDENT << "buffer.open(QBuffer::ReadWrite);" << endl;
s << INDENT << "QDebug dbg(&buffer);" << endl;
s << INDENT << "dbg << ";
- if (metaClass->typeEntry()->isValue())
+ if (metaClass->typeEntry()->isValue() || indirections == 0)
s << '*';
s << CPP_SELF_VAR << ';' << endl;
s << INDENT << "buffer.close();" << endl;
diff --git a/sources/shiboken2/generator/shiboken2/cppgenerator.h b/sources/shiboken2/generator/shiboken2/cppgenerator.h
index ae6da9582..005518f96 100644
--- a/sources/shiboken2/generator/shiboken2/cppgenerator.h
+++ b/sources/shiboken2/generator/shiboken2/cppgenerator.h
@@ -336,7 +336,7 @@ private:
/// Helper function for writeStdListWrapperMethods.
void writeIndexError(QTextStream &s, const QString &errorMsg);
- QString writeReprFunction(QTextStream &s, GeneratorContext &context);
+ QString writeReprFunction(QTextStream &s, GeneratorContext &context, uint indirections);
const AbstractMetaFunction *boolCast(const AbstractMetaClass *metaClass) const;
bool hasBoolCast(const AbstractMetaClass *metaClass) const