From 1079b1066cb60995da4913cdf3b25fb258334600 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Thu, 25 Nov 2010 19:39:42 -0200 Subject: [PATCH 001/703] Fix doc generation after the refactor for v1.0. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewer: Renato Araújo Marcelo Lira --- doc/inheritance_diagram.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/doc/inheritance_diagram.py b/doc/inheritance_diagram.py index 0f9be08..fcbed55 100644 --- a/doc/inheritance_diagram.py +++ b/doc/inheritance_diagram.py @@ -148,7 +148,7 @@ class InheritanceGraph(object): def recurse(cls): all_classes[cls] = None for c in cls.__bases__: - if c not in all_classes and c.__name__ != "BaseWrapper": + if c not in all_classes and not (c.__name__ == "Object" and c.__module__ == "Shiboken"): recurse(c) for cls in classes: @@ -246,7 +246,7 @@ class InheritanceGraph(object): # Write the edges for base in cls.__bases__: - if base.__name__ == "BaseWrapper": + if base.__name__ == "Object" and base.__module__ == "Shiboken": continue if not self.show_builtins and base in __builtins__.values(): continue From 52c2a2cd0d2571e5447f3c20c48626b685fc83d0 Mon Sep 17 00:00:00 2001 From: Luciano Wolf Date: Tue, 30 Nov 2010 10:30:55 -0300 Subject: [PATCH 002/703] Add needed cast to compile using python versions <2.6 Reviewer: Hugo Parente Lima Marcelo Lira --- PySide/phonon/typesystem_phonon.xml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/PySide/phonon/typesystem_phonon.xml b/PySide/phonon/typesystem_phonon.xml index 16dd72c..226560e 100644 --- a/PySide/phonon/typesystem_phonon.xml +++ b/PySide/phonon/typesystem_phonon.xml @@ -87,11 +87,11 @@ signal_item = PySide::Signal::newObject("capabilitiesChanged", "void", NULL); PyDict_SetItemString(Sbk_Phonon_BackendCapabilities_NotifierWrapper_Type.super.ht_type.tp_dict, "capabilitiesChanged", (PyObject*)signal_item); - Py_DECREF(signal_item); + Py_DECREF((PyObject*)signal_item); signal_item = PySide::Signal::newObject("availableAudioOutputDevicesChanged", "void", NULL); PyDict_SetItemString( Sbk_Phonon_BackendCapabilities_NotifierWrapper_Type.super.ht_type.tp_dict, "availableAudioOutputDevicesChanged", (PyObject*)signal_item); - Py_DECREF(signal_item); + Py_DECREF((PyObject*)signal_item); From ec7b01c24f903925494fe21cc08b5c5111435daa Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Wed, 1 Dec 2010 15:34:44 -0200 Subject: [PATCH 003/703] Fixed dynamic meta object to avoid empty meta method. Empty meta methods cause a assert failure on QtDeclarative module. Also removed the scoped pointer to avoid heap allocation when it's not needed, as QByteArray is already implicity shared. --- libpyside/dynamicqmetaobject.cpp | 93 ++++++++++++++++---------------- libpyside/dynamicqmetaobject_p.h | 14 +++-- libpyside/globalreceiver.cpp | 2 +- libpyside/pysideslot.cpp | 1 + 4 files changed, 58 insertions(+), 52 deletions(-) diff --git a/libpyside/dynamicqmetaobject.cpp b/libpyside/dynamicqmetaobject.cpp index 43aeae6..0622bcb 100644 --- a/libpyside/dynamicqmetaobject.cpp +++ b/libpyside/dynamicqmetaobject.cpp @@ -43,7 +43,7 @@ #define MAX_GLOBAL_SIGNALS_COUNT 500 #define MAX_GLOBAL_SLOTS_COUNT 500 -#define GLOBAL_RECEIVER_CLASS_NAME "__GlobalReceiver__" +#define EMPTY_META_METHOD "0()" using namespace PySide; @@ -79,7 +79,7 @@ public: QByteArray m_className; void updateMetaObject(QMetaObject* metaObj); - void writeMethodsData(QList& methods, unsigned int** data, QList* strings, int* prtIndex, int maxCount, int nullIndex, int flags); + void writeMethodsData(const QList& methods, unsigned int** data, QList* strings, int* prtIndex, int maxCount, int nullIndex, int flags); }; static int registerString(const QByteArray& s, QList* strings) @@ -135,12 +135,12 @@ static bool isQRealType(const char *type) /* * Avoid API break keep this on cpp */ -static int maxSlotsCount(const QByteArray& className) +static inline int maxSlotsCount(const QByteArray& className) { return className == GLOBAL_RECEIVER_CLASS_NAME ? MAX_GLOBAL_SIGNALS_COUNT : MAX_SLOTS_COUNT; } -static int maxSignalsCount(const QByteArray& className) +static inline int maxSignalsCount(const QByteArray& className) { return className == GLOBAL_RECEIVER_CLASS_NAME ? MAX_GLOBAL_SIGNALS_COUNT : MAX_SIGNALS_COUNT; } @@ -198,50 +198,48 @@ uint PropertyData::flags() const return flags; } -MethodData::MethodData(const char* signature, const char* type) +// const QByteArray with EMPTY_META_METHOD, used to save some memory +const QByteArray MethodData::m_emptySig(EMPTY_META_METHOD); + +MethodData::MethodData() : m_signature(m_emptySig) +{ +} + +MethodData::MethodData(const char* signature, const char* type) : m_signature(signature), m_type(type) { - m_signature = QSharedPointer(new QByteArray(signature)); - m_type = QSharedPointer(new QByteArray(type)); } void MethodData::clear() { - m_signature->clear(); - m_type->clear(); + m_signature = m_emptySig; + m_type.clear(); } bool MethodData::operator==(const MethodData& other) const { - return *m_signature == other.signature(); + return m_signature == other.signature(); } bool MethodData::operator==(const char* other) const { - return *m_signature == other; + return m_signature == other; } QByteArray MethodData::signature() const { - if (!m_signature.isNull()) - return *m_signature; - else - return QByteArray(); + return m_signature; } QByteArray MethodData::type() const { - if (!m_type.isNull()) { - if (*m_type == "void") - return QByteArray(); - return *m_type; - } else { + if (m_type == "void") return QByteArray(); - } + return m_type; } bool MethodData::isValid() const { - return m_signature->size(); + return m_signature.size(); } PropertyData::PropertyData() @@ -334,29 +332,27 @@ void DynamicQMetaObject::addSlot(const char* slot, const char* type) if (index != -1) return; - int maxSlots = maxSlotsCount(m_d->m_className); - if (m_d->m_slots.size() >= maxSlots) { - qWarning() << "Fail to add dynamic slot to QObject. PySide support at most" << maxSlots << "dynamic slots."; - return; - } - //search for a empty space MethodData blank; index = m_d->m_slots.indexOf(blank); if (index != -1) { m_d->m_slots[index] = MethodData(slot, type); - } else { + } else if (m_d->m_slots.size() < maxSlotsCount(m_d->m_className)) { m_d->m_slots << MethodData(slot, type); + } else { + qWarning() << "Fail to add dynamic slot to QObject. PySide support at most" << maxSlotsCount(m_d->m_className) << "dynamic slots."; + return; } m_d->updateMetaObject(this); } void DynamicQMetaObject::removeSlot(uint index) { - QMetaMethod m = method(index); - foreach(MethodData md, m_d->m_slots) { - if (md.signature() == m.signature()) { - md.clear(); + const char* methodSig = method(index).signature(); + QList::iterator it = m_d->m_slots.begin(); + for (; it != m_d->m_slots.end(); ++it) { + if (it->signature() == methodSig) { + it->clear(); m_d->updateMetaObject(this); break; } @@ -460,7 +456,7 @@ void DynamicQMetaObject::removeSignal(uint index) } } -void DynamicQMetaObject::DynamicQMetaObjectPrivate::writeMethodsData(QList& methods, +void DynamicQMetaObject::DynamicQMetaObjectPrivate::writeMethodsData(const QList& methods, unsigned int** data, QList* strings, int* prtIndex, @@ -470,23 +466,28 @@ void DynamicQMetaObject::DynamicQMetaObjectPrivate::writeMethodsData(QList::iterator iMethod = methods.begin(); - for(int i=0; i < maxCount; i++) { - QByteArray mType; - if (iMethod != methods.end() && ((*iMethod).signature().size() > 0) ) { - (*data)[index++] = registerString((*iMethod).signature(), strings); // func name - mType = (*iMethod).type(); - } else { - (*data)[index++] = nullIndex; // func name - } + int emptyIndex = registerString(EMPTY_META_METHOD, strings); + + QList::const_iterator it = methods.begin(); + + for (; it != methods.end(); ++it) { + if (it->signature() != EMPTY_META_METHOD) + (*data)[index++] = registerString(it->signature(), strings); // func name + else + (*data)[index++] = emptyIndex; // func name (*data)[index++] = nullIndex; // arguments - (*data)[index++] = (mType.size() > 0 ? registerString(mType, strings) : nullIndex); // normalized type + (*data)[index++] = (it->type().size() > 0 ? registerString(it->type(), strings) : nullIndex); // normalized type (*data)[index++] = nullIndex; // tags (*data)[index++] = flags; - if (iMethod != methods.end()) - iMethod++; } + for (int i = methods.count(); i < maxCount; ++i) { + (*data)[index++] = emptyIndex; // func name + (*data)[index++] = nullIndex; // arguments + (*data)[index++] = nullIndex; // normalized type + (*data)[index++] = nullIndex; // tags + (*data)[index++] = flags; + } *prtIndex = index; } diff --git a/libpyside/dynamicqmetaobject_p.h b/libpyside/dynamicqmetaobject_p.h index e692700..d31e908 100644 --- a/libpyside/dynamicqmetaobject_p.h +++ b/libpyside/dynamicqmetaobject_p.h @@ -25,9 +25,9 @@ #include #include -#include #define PYSIDE_SLOT_LIST_ATTR "_slots" +#define GLOBAL_RECEIVER_CLASS_NAME "__GlobalReceiver__" struct PySideProperty; namespace PySide @@ -35,7 +35,11 @@ namespace PySide class MethodData { public: - MethodData(){} + MethodData(); + /** + * \param signature method signature + * \param type method return type + */ MethodData(const char* signature, const char* type = 0); void clear(); bool isValid() const; @@ -43,11 +47,11 @@ namespace PySide QByteArray type() const; bool operator==(const MethodData& other) const; bool operator==(const char* other) const; - operator const char*() { return m_signature->data(); } private: - QSharedPointer m_signature; - QSharedPointer m_type; + QByteArray m_signature; + QByteArray m_type; + static const QByteArray m_emptySig; }; class PropertyData diff --git a/libpyside/globalreceiver.cpp b/libpyside/globalreceiver.cpp index d63ebdf..e1cf4ed 100644 --- a/libpyside/globalreceiver.cpp +++ b/libpyside/globalreceiver.cpp @@ -21,6 +21,7 @@ */ #include "globalreceiver.h" +#include "dynamicqmetaobject_p.h" #include #include @@ -32,7 +33,6 @@ #include "signalmanager.h" #define RECEIVER_DESTROYED_SLOT_NAME "__receiverDestroyed__(QObject*)" -#define GLOBAL_RECEIVER_CLASS_NAME "__GlobalReceiver__" namespace PySide { diff --git a/libpyside/pysideslot.cpp b/libpyside/pysideslot.cpp index 538a258..acd0bb9 100644 --- a/libpyside/pysideslot.cpp +++ b/libpyside/pysideslot.cpp @@ -25,6 +25,7 @@ #include #include +#include #define SLOT_DEC_NAME "Slot" From 9edc8a3834c9ba067b255b9996d59a473df6ef18 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Wed, 1 Dec 2010 18:09:09 -0200 Subject: [PATCH 004/703] Fixed qt_metacall, now everything works as it should. Reviewer: Luciano Wolf Lauro Moura --- PySide/QtCore/qvariant_conversions.h | 66 ++++++++++++---------------- libpyside/pysidemetafunction.cpp | 27 +++++------- libpyside/signalmanager.cpp | 30 ++++++++----- libpyside/signalmanager.h | 1 + 4 files changed, 59 insertions(+), 65 deletions(-) diff --git a/PySide/QtCore/qvariant_conversions.h b/PySide/QtCore/qvariant_conversions.h index 68b6e8f..0b89534 100644 --- a/PySide/QtCore/qvariant_conversions.h +++ b/PySide/QtCore/qvariant_conversions.h @@ -14,26 +14,26 @@ struct Converter return true; } - static QByteArray resolveMetaType(PyTypeObject* type, int &typeId) + static const char* resolveMetaType(PyTypeObject* type, int* typeId) { if (PyObject_TypeCheck(type, &SbkObjectType_Type)) { SbkObjectType* sbkType = reinterpret_cast(type); - QByteArray typeName(Shiboken::ObjectType::getOriginalName(sbkType)); - bool valueType = !typeName.endsWith("*"); + const char* typeName = Shiboken::ObjectType::getOriginalName(sbkType); + bool valueType = '*' != typeName[qstrlen(typeName) - 1]; // Do not convert user type of value if (valueType && Shiboken::ObjectType::isUserType(type)) - return QByteArray(); + return 0; int obTypeId = QMetaType::type(typeName); if (obTypeId) { - typeId = obTypeId; - return QByteArray(typeName); + *typeId = obTypeId; + return typeName; } // Do not resolve types to value type if (valueType) - return QByteArray(); + return 0; // find in base types if (type->tp_base) { @@ -41,14 +41,14 @@ struct Converter } else if (type->tp_bases) { int size = PyTuple_GET_SIZE(type->tp_bases); for(int i=0; i < size; i++){ - QByteArray derivedName = resolveMetaType(reinterpret_cast(PyTuple_GET_ITEM(type->tp_bases, i)), typeId); - if (!derivedName.isEmpty()) + const char* derivedName = resolveMetaType(reinterpret_cast(PyTuple_GET_ITEM(type->tp_bases, i)), typeId); + if (derivedName) return derivedName; } } } - typeId = 0; - return QByteArray(); + *typeId = 0; + return 0; } static QVariant toCpp(PyObject* pyObj) @@ -87,22 +87,15 @@ struct Converter } else { // a class supported by QVariant? if (Shiboken::Object::checkType(pyObj)) { - SbkObjectType* objType = reinterpret_cast(pyObj->ob_type); - int typeCode = 0; - QByteArray typeName = resolveMetaType(reinterpret_cast(objType), typeCode); - if (typeCode) { + int typeCode; + const char* typeName = resolveMetaType(pyObj->ob_type, &typeCode); + + if (typeCode && typeName) { Shiboken::TypeResolver* tr = Shiboken::TypeResolver::get(typeName); - void* data = 0; - data = tr->toCpp(pyObj, &data, true); - if (typeName.endsWith("*")) { - QVariant var(typeCode, &data); - tr->deleteObject(data); - return var; - } else { - QVariant var(typeCode, data); - tr->deleteObject(data); - return var; - } + QVariant var(typeCode, (void*)0); + void* args[] = { var.data() }; + tr->toCpp(pyObj, args); + return var; } } // Is a shiboken type not known by Qt @@ -140,28 +133,25 @@ struct Converter return QVariant(); Shiboken::AutoDecRef element(PySequence_GetItem(list, 0)); - int typeId = 0; - QByteArray typeName = resolveMetaType(element.cast(), typeId); - if (!typeName.isEmpty()) { - QByteArray listTypeName = QByteArray("QList<"+typeName+">"); + int typeId; + const char* typeName = resolveMetaType(element.cast(), &typeId); + if (typeName) { + QByteArray listTypeName("QList<"); + listTypeName += typeName; + listTypeName += '>'; typeId = QMetaType::type(listTypeName); if (typeId > 0) { Shiboken::TypeResolver* tr = Shiboken::TypeResolver::get(listTypeName); if (!tr) { qWarning() << "TypeResolver for :" << listTypeName << "not registered."; - return QVariant(); } else { - void *data = 0; - data = tr->toCpp(list, &data, true); - QVariant var(typeId, data); - tr->deleteObject(data); + QVariant var(typeId, (void*)0); + void* args[] = { var.data(), 0 }; + tr->toCpp(list, args); return var; } - } else { - return QVariant(); } } - return QVariant(); } diff --git a/libpyside/pysidemetafunction.cpp b/libpyside/pysidemetafunction.cpp index bcccbb8..bee793c 100644 --- a/libpyside/pysidemetafunction.cpp +++ b/libpyside/pysidemetafunction.cpp @@ -98,29 +98,26 @@ void functionFree(void *self) PyObject* functionCall(PyObject* self, PyObject* args, PyObject* kw) { - QGenericArgument gArgs[10]; - PySideMetaFunction* function = reinterpret_cast(self); - QList vArgs; - QMetaMethod method = function->d->method; - QList pTypes = method.parameterTypes(); - int numArgs = pTypes.size(); - - Shiboken::TypeResolver* typeResolver = Shiboken::TypeResolver::get("QVariant"); + static Shiboken::TypeResolver* typeResolver = Shiboken::TypeResolver::get("QVariant"); Q_ASSERT(typeResolver); - for(int i=0; i < numArgs; i++) { - QVariant *vArg; + + QGenericArgument gArgs[10]; + QVariant vArgs[10]; + PySideMetaFunction* function = reinterpret_cast(self); + QMetaMethod method = function->d->method; + int argsGiven = method.parameterTypes().size(); + + for (int i = 0; i < argsGiven; ++i) { Shiboken::AutoDecRef pyArg(PySequence_GetItem(args, i)); - typeResolver->toCpp(pyArg, (void**)&vArg, true); - vArgs.append(vArg); - gArgs[i] = Q_ARG(QVariant, *vArg); + gArgs[i] = Q_ARG(QVariant, vArgs[i]); + void* v[1] = { &vArgs[i] }; + typeResolver->toCpp(pyArg, v); } QVariant retVariant; QGenericReturnArgument returnValue = Q_RETURN_ARG(QVariant, retVariant); method.invoke(function->d->qobject, returnValue, gArgs[0], gArgs[1], gArgs[2], gArgs[3], gArgs[4], gArgs[5], gArgs[6], gArgs[7], gArgs[8], gArgs[9]); - while(!vArgs.isEmpty()) - delete vArgs.takeFirst(); if (retVariant.isValid()) return typeResolver->toPython(&retVariant); diff --git a/libpyside/signalmanager.cpp b/libpyside/signalmanager.cpp index d4b0cb7..5ff62be 100644 --- a/libpyside/signalmanager.cpp +++ b/libpyside/signalmanager.cpp @@ -70,9 +70,17 @@ PyObjectWrapper::PyObjectWrapper(const PyObjectWrapper &other) PyObjectWrapper::~PyObjectWrapper() { + Shiboken::GilState gil; Py_DECREF(m_me); } +PyObjectWrapper& PyObjectWrapper::operator=(const PySide::PyObjectWrapper& other) +{ + Py_INCREF(other.m_me); + Py_DECREF(m_me); + m_me = other.m_me; + return *this; +} PyObjectWrapper::operator PyObject*() const { @@ -179,24 +187,26 @@ static bool emitNormalSignal(QObject* source, int signalIndex, const char* signa { Shiboken::AutoDecRef sequence(PySequence_Fast(args, 0)); int argsGiven = PySequence_Fast_GET_SIZE(sequence.object()); + if (argsGiven > argTypes.count()) { PyErr_Format(PyExc_TypeError, "%s only accepts %d arguments, %d given!", signal, argTypes.count(), argsGiven); return false; } - void** signalArgs = new void*[argsGiven+1]; - void** signalValues = new void*[argsGiven]; + QVariant* signalValues = new QVariant[argsGiven]; + void** signalArgs = new void*[argsGiven + 1]; signalArgs[0] = 0; int i; for (i = 0; i < argsGiven; ++i) { - Shiboken::TypeResolver* typeResolver = Shiboken::TypeResolver::get(qPrintable(argTypes[i])); + const char* typeName = argTypes[i].toAscii().constData(); + Shiboken::TypeResolver* typeResolver = Shiboken::TypeResolver::get(typeName); if (typeResolver) { - typeResolver->toCpp(PySequence_Fast_GET_ITEM(sequence.object(), i), &signalValues[i], true); - if (Shiboken::TypeResolver::getType(qPrintable(argTypes[i])) == Shiboken::TypeResolver::ObjectType) - signalArgs[i+1] = &signalValues[i]; - else - signalArgs[i+1] = signalValues[i]; + int typeId = QMetaType::type(typeName); + if (Shiboken::TypeResolver::getType(typeName) == Shiboken::TypeResolver::ValueType) + signalValues[i] = QVariant(typeId, (void*) 0); + signalArgs[i+1] = signalValues[i].data(); + typeResolver->toCpp(PySequence_Fast_GET_ITEM(sequence.object(), i), &signalArgs[i+1]); } else { PyErr_Format(PyExc_TypeError, "Unknown type used to emit a signal: %s", qPrintable(argTypes[i])); break; @@ -207,10 +217,6 @@ static bool emitNormalSignal(QObject* source, int signalIndex, const char* signa if (ok) QMetaObject::activate(source, signalIndex, signalArgs); - //cleanup memory - for (int j = 0; j < i; ++j) - Shiboken::TypeResolver::get(qPrintable(argTypes[j]))->deleteObject(signalArgs[j+1]); - delete[] signalArgs; delete[] signalValues; diff --git a/libpyside/signalmanager.h b/libpyside/signalmanager.h index 91c86e0..f6ce1fb 100644 --- a/libpyside/signalmanager.h +++ b/libpyside/signalmanager.h @@ -43,6 +43,7 @@ public: PyObjectWrapper(const PyObjectWrapper &other); ~PyObjectWrapper(); operator PyObject*() const; + PyObjectWrapper& operator=(const PyObjectWrapper &other); private: PyObject* m_me; void* m_data; //future From 0220d7d1768353f062ef7af10845686f1327923e Mon Sep 17 00:00:00 2001 From: Marcelo Lira Date: Thu, 2 Dec 2010 16:18:29 -0300 Subject: [PATCH 005/703] Updated a lot of code snippets on documentation concerning QtCore module. Reviewed by Hugo Parente Reviewed by Luciano Wolf --- .../src/snippets/code/doc_src_unicode.qdoc | 8 +-- .../code/src_corelib_codecs_qtextcodec.cpp | 22 ++++---- .../src_corelib_concurrent_qthreadpool.cpp | 2 +- .../code/src_corelib_global_qglobal.cpp | 50 +++++++++---------- .../src_corelib_io_qabstractfileengine.cpp | 12 ++--- .../code/src_corelib_io_qdatastream.cpp | 46 ++++++++--------- .../src/snippets/code/src_corelib_io_qdir.cpp | 8 +-- .../code/src_corelib_io_qfileinfo.cpp | 12 ++--- .../code/src_corelib_io_qiodevice.cpp | 24 ++++----- .../snippets/code/src_corelib_io_qprocess.cpp | 5 +- .../code/src_corelib_io_qsettings.cpp | 8 +-- .../code/src_corelib_io_qtemporaryfile.cpp | 6 +-- .../code/src_corelib_io_qtextstream.cpp | 22 ++++---- .../src/snippets/code/src_corelib_io_qurl.cpp | 8 +-- .../src_corelib_kernel_qcoreapplication.cpp | 18 ++----- .../code/src_corelib_kernel_qmetaobject.cpp | 8 +-- .../code/src_corelib_kernel_qtimer.cpp | 2 +- .../code/src_corelib_thread_qthread.cpp | 2 +- .../code/src_corelib_tools_qbitarray.cpp | 2 +- .../code/src_corelib_tools_qbytearray.cpp | 14 +++--- .../code/src_corelib_tools_qdatetime.cpp | 2 +- .../code/src_corelib_tools_qlocale.cpp | 13 +++-- .../code/src_corelib_tools_qtimeline.cpp | 4 +- .../doc/src/snippets/process/process.cpp | 2 +- .../src/snippets/qdir-namefilters/main.cpp | 33 +++++------- .../snippets/qprocess-environment/main.cpp | 9 +++- .../qprocess/qprocess-simpleexecution.cpp | 5 +- .../doc/src/snippets/timers/timers.cpp | 8 +-- .../doc/src/snippets/whatsthis/whatsthis.cpp | 4 +- 29 files changed, 172 insertions(+), 187 deletions(-) diff --git a/doc/codesnippets/doc/src/snippets/code/doc_src_unicode.qdoc b/doc/codesnippets/doc/src/snippets/code/doc_src_unicode.qdoc index 30a3710..526c755 100644 --- a/doc/codesnippets/doc/src/snippets/code/doc_src_unicode.qdoc +++ b/doc/codesnippets/doc/src/snippets/code/doc_src_unicode.qdoc @@ -1,18 +1,18 @@ //! [0] -label->setText("Password:"); +label.setText("Password:") //! [0] //! [1] -label->setText(tr("Password:")); +label.setText(QObject.tr("Password:")) //! [1] //! [2] -QFile file(QString::fromLatin1("appicon.png")); +file_ = QFile("appicon.png") //! [2] //! [3] -QFile file(QLatin1String("appicon.png")); +file_= QFile("appicon.png") //! [3] diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_codecs_qtextcodec.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_codecs_qtextcodec.cpp index f1c839d..47a5c7a 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_codecs_qtextcodec.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_codecs_qtextcodec.cpp @@ -1,25 +1,25 @@ //! [0] encodedString = QByteArray("...") -codec = QTextCodec::codecForName("KOI8-R") -string = codec->toUnicode(encodedString) +codec = QTextCodec.codecForName("KOI8-R") +string = codec.toUnicode(encodedString) //! [0] //! [1] -string = QString("...") -codec = QTextCodec::codecForName("KOI8-R") -encodedString = codec->fromUnicode(string) +string = u"..." +codec = QTextCodec.codecForName("KOI8-R") +encodedString = codec.fromUnicode(string) //! [1] //! [2] -codec = QTextCodec::codecForName("Shift-JIS") -decoder = codec->makeDecoder() +codec = QTextCodec.codecForName("Shift-JIS") +decoder = codec.makeDecoder() -string = QString() +string = u'' while new_data_available(): - chunk = get_new_data(); - string += decoder->toUnicode(chunk) + chunk = get_new_data() + string += decoder.toUnicode(chunk) //! [2] @@ -27,6 +27,6 @@ while new_data_available(): //! [3] def main(): app = QApplication([]) - QTextCodec::setCodecForTr(QTextCodec::codecForName("eucKR")) + QTextCodec.setCodecForTr(QTextCodec.codecForName("eucKR")) ... //! [3] diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_concurrent_qthreadpool.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_concurrent_qthreadpool.cpp index 174b878..ecbfe23 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_concurrent_qthreadpool.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_concurrent_qthreadpool.cpp @@ -5,5 +5,5 @@ class HelloWorldTask(QRunnable): hello = HelloWorldTask() # QThreadPool takes ownership and deletes 'hello' automatically -QThreadPool.globalInstance()->start(hello) +QThreadPool.globalInstance().start(hello) //! [0] diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_global_qglobal.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_global_qglobal.cpp index 287181a..4c12049 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_global_qglobal.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_global_qglobal.cpp @@ -1,5 +1,5 @@ //! [0] -label->setAlignment(Qt::AlignLeft | Qt::AlignTop); +label.setAlignment(Qt.AlignLeft | Qt.AlignTop) //! [0] @@ -73,60 +73,58 @@ quint64 value = Q_UINT64_C(932838457459459); //! [10] -int absoluteValue; -int myValue = -4; - -absoluteValue = qAbs(myValue); +myValue = -4 +absoluteValue = qAbs(myValue) // absoluteValue == 4 //! [10] //! [11] -qreal valueA = 2.3; -qreal valueB = 2.7; +valueA = 2.3 +valueB = 2.7 -int roundedValueA = qRound(valueA); +roundedValueA = qRound(valueA) // roundedValueA = 2 -int roundedValueB = qRound(valueB); +roundedValueB = qRound(valueB) // roundedValueB = 3 //! [11] //! [12] -qreal valueA = 42949672960.3; -qreal valueB = 42949672960.7; +valueA = 42949672960.3 +valueB = 42949672960.7 -int roundedValueA = qRound(valueA); +roundedValueA = qRound(valueA) // roundedValueA = 42949672960 -int roundedValueB = qRound(valueB); +roundedValueB = qRound(valueB) // roundedValueB = 42949672961 //! [12] //! [13] -int myValue = 6; -int yourValue = 4; +myValue = 6 +yourValue = 4 -int minValue = qMin(myValue, yourValue); +minValue = qMin(myValue, yourValue) // minValue == yourValue //! [13] //! [14] -int myValue = 6; -int yourValue = 4; +myValue = 6 +yourValue = 4 -int maxValue = qMax(myValue, yourValue); +maxValue = qMax(myValue, yourValue) // maxValue == myValue //! [14] //! [15] -int myValue = 10; -int minValue = 2; -int maxValue = 6; +myValue = 10 +minValue = 2 +maxValue = 6 -int boundedValue = qBound(minValue, myValue, maxValue); +boundedValue = qBound(minValue, myValue, maxValue) // boundedValue == 6 //! [15] @@ -436,7 +434,7 @@ namespace QT_NAMESPACE { //! [43] class MyClass : public QObject { - + private: Q_DISABLE_COPY(MyClass) }; @@ -446,7 +444,7 @@ class MyClass : public QObject //! [44] class MyClass : public QObject { - + private: MyClass(const MyClass &); MyClass &operator=(const MyClass &); @@ -454,7 +452,7 @@ class MyClass : public QObject //! [44] //! [45] - QWidget w = QWidget(); + w = QWidget() //! [45] //! [46] diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qabstractfileengine.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qabstractfileengine.cpp index 5984b62..de0fd50 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qabstractfileengine.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qabstractfileengine.cpp @@ -1,6 +1,6 @@ //! [0] -class ZipEngineHandler(QAbstractFileEngineHandler) - def create(fileName): +class ZipEngineHandler(QAbstractFileEngineHandler): + def create(self, fileName): # ZipEngineHandler returns a ZipEngine for all .zip files if fileName.toLower().endsWith(".zip"): return ZipEngine(fileName) @@ -22,7 +22,7 @@ def main(): //! [1] def create(fileName): # ZipEngineHandler returns a ZipEngine for all .zip files - if fileName.toLower().endsWith(".zip"): + if fileName.lower().endswith(".zip"): return ZipEngine(fileName) else return None @@ -52,9 +52,9 @@ class CustomIterator(QAbstractFileEngineIterator): return self.index < self.entries.size() - 1 def next(self): - if !self.hasNext(): - return QString() - index++ + if not self.hasNext(): + return None + index += 1 return currentFilePath() def currentFileName(self): diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qdatastream.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qdatastream.cpp index 6b66276..033a54c 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qdatastream.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qdatastream.cpp @@ -2,27 +2,27 @@ void wrapInFunction() { //! [0] -file = QFile("file.dat") -file.open(QIODevice.WriteOnly) +file_ = QFile("file.dat") +file_.open(QIODevice.WriteOnly) # we will serialize the data into the file -out = QDataStream(file) +out = QDataStream(file_) # serialize a string -out << "the answer is" +out.writeQString("the answer is") # serialize an integer out.writeInt32(42) //! [0] //! [1] -file = QFile("file.dat") -file.open(QIODevice.ReadOnly) +file_ = QFile("file.dat") +file_.open(QIODevice.ReadOnly) # read the data serialized from the file -i = QDataStream(file) -str = QString() +i = QDataStream(file_) +string = '' a = 0 # extract "the answer is" and 42 -i >> str -a = i.readInt32() +string = i.readQString() +a = i.readInt32() //! [1] @@ -32,15 +32,15 @@ stream.setVersion(QDataStream.Qt_4_0) //! [3] -file = QFile("file.xxx") -file.open(QIODevice.WriteOnly) -out = QDataStream(file) +file_ = QFile("file.xxx") +file_.open(QIODevice.WriteOnly) +out = QDataStream(file_) # Write a header with a "magic number" and a version out.writeInt32(0xA0B0C0D0) out.writeInt32(123) -out.setVersion(QDataStream.Qt_4_0); +out.setVersion(QDataStream.Qt_4_0) // Write the data out << lots_of_interesting_data @@ -48,9 +48,9 @@ out << lots_of_interesting_data //! [4] -file = QFile("file.xxx") -file.open(QIODevice.ReadOnly) -i = QDataStream(file) +file_ = QFile("file.xxx") +file_.open(QIODevice.ReadOnly) +i = QDataStream(file_) // Read and check the header magic = i.readInt32() @@ -65,20 +65,20 @@ if version > 123: return XXX_BAD_FILE_TOO_NEW if version <= 110: - in.setVersion(QDataStream.Qt_3_2) + in_.setVersion(QDataStream.Qt_3_2) else: - in.setVersion(QDataStream.Qt_4_0) + in_.setVersion(QDataStream.Qt_4_0) // Read the data -in >> lots_of_interesting_data +in_ >> lots_of_interesting_data if version >= 120: - in >> data_new_in_XXX_version_1_2 -in >> other_interesting_data + in_ >> data_new_in_XXX_version_1_2 +in_ >> other_interesting_data //! [4] //! [5] -out = QDataStream(file) +out = QDataStream(file_) out.setVersion(QDataStream.Qt_4_0) //! [5] diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qdir.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qdir.cpp index 5bb0b07..a849e48 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qdir.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qdir.cpp @@ -28,14 +28,14 @@ absolutePath = directory.absoluteFilePath("contents.txt") //! [4] dir = QDir("example") -if !dir.exists(): +if not dir.exists(): print "Cannot find the example directory" //! [4] //! [5] dir = QDir.root() # "/" -if !dir.cd("tmp"): # "/tmp" +if not dir.cd("tmp"): # "/tmp" print "Cannot find the \"/tmp\" directory" else: file = QFile(dir.filePath("ex1.txt")) # "/tmp/ex1.txt" @@ -83,7 +83,7 @@ if dir.isRoot(): //! [10] -// The current directory is "/usr/local" +# The current directory is "/usr/local" d1 = QDir("/usr/local/bin") d2 = QDir("bin") if d1 == d2: @@ -112,7 +112,7 @@ Q_INIT_RESOURCE(myapp); //! [14] -def initMyResource(): +def initMyResource(): Q_INIT_RESOURCE(myapp) class MyNamespace diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qfileinfo.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qfileinfo.cpp index fb0e1c8..c021c3b 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qfileinfo.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qfileinfo.cpp @@ -11,7 +11,7 @@ info1.size() # returns 56201 info1.symLinkTarget() # returns "/opt/pretty++/bin/untabify" info2 = QFileInfo(info1.symLinkTarget()) -info1.isSymLink() # returns false +info1.isSymLink() # returns False info1.absoluteFilePath() # returns "/opt/pretty++/bin/untabify" info1.size() # returns 56201 @@ -20,25 +20,25 @@ info1.size() # returns 56201 //! [1] info1 = QFileInfo("C:\\Documents and Settings\\Bob\\untabify.lnk") -info1.isSymLink() # returns true +info1.isSymLink() # returns True info1.absoluteFilePath() # returns "C:/Documents and Settings/Bob/untabify.lnk" info1.size() # returns 743 info1.symLinkTarget() # returns "C:/Pretty++/untabify" info2 = QFileInfo(info1.symLinkTarget()) -info1.isSymLink() # returns false +info1.isSymLink() # returns False info1.absoluteFilePath() # returns "C:/Pretty++/untabify" info1.size() # returns 63942 //! [1] //! [2] -absolute = QString("/local/bin") -relative = QString("local/bin") +absolute = "/local/bin" +relative = "local/bin" absFile = QFileInfo(absolute) relFile = QFileInfo(relative) -QDir.setCurrent(QDir::rootPath()) +QDir.setCurrent(QDir.rootPath()) # absFile and relFile now point to the same file QDir.setCurrent("/tmp") diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qiodevice.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qiodevice.cpp index 44bd197..6b791bf 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qiodevice.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qiodevice.cpp @@ -1,10 +1,10 @@ //! [0] gzip = QProcess() -gzip.start("gzip", QStringList() << "-c") -if !gzip.waitForStarted(): - return false +gzip.start("gzip", ["-c"]) +if not gzip.waitForStarted(): + return False -gzip.write("uncompressed data"); +gzip.write("uncompressed data") compressed = QByteArray() while gzip.waitForReadyRead(): @@ -21,7 +21,7 @@ def bytesAvailable(self): //! [2] file = QFile("box.txt") if file.open(QFile.ReadOnly): - buf = file.readLine(1024); + buf = file.readLine(1024) if buf.size(): # the line is available in buf //! [2] @@ -29,20 +29,20 @@ if file.open(QFile.ReadOnly): //! [3] def canReadLine(self): - return buffer.contains('\n') || QIODevice.canReadLine() + return buffer.contains('\n') or QIODevice.canReadLine() //! [3] //! [4] -def isExeFile(file): - buf = file->peek(2); +def isExeFile(file_): + buf = file_.peek(2) if buf.size() == 2: - return (buf[0] == 'M' && buf[1] == 'Z') - return false + return buf[0] == 'M' and buf[1] == 'Z' + return False //! [4] //! [5] -def isExeFile(file): - return file->peek(2) == "MZ" +def isExeFile(file_): + return file_.peek(2) == "MZ" //! [5] diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qprocess.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qprocess.cpp index 7f4bd7a..228a24c 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qprocess.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qprocess.cpp @@ -6,10 +6,11 @@ builder = QProcess() builder.setProcessChannelMode(QProcess.MergedChannels) builder.start("make", QStringList() << "-j2") +import sys if !builder.waitForFinished(): - qDebug() << "Make failed:" << builder.errorString() + sys.stderr.write("Make failed:" + builder.errorString()) else - qDebug() << "Make output:" << builder.readAll() + sys.stderr.write("Make output:" + builder.readAll()) //! [0] diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qsettings.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qsettings.cpp index 71745fa..f07dc8b 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qsettings.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qsettings.cpp @@ -106,8 +106,8 @@ settings.endGroup() //! [15] class Login: - userName = QString() - password = QString() + userName = '' + password = '' logins = [] ... @@ -127,8 +127,8 @@ class Login: //! [16] class Login: - userName = QString() - password = QString() + userName = '' + password = '' logins = [] ... diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qtemporaryfile.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qtemporaryfile.cpp index 8ebbd9e..77d394e 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qtemporaryfile.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qtemporaryfile.cpp @@ -2,9 +2,9 @@ //! [0] # Within a function/method... - file = QTemporaryFile() - if file.open(): - # file.fileName() returns the unique file name + file_ = QTemporaryFile() + if file_.open(): + # file_.fileName() returns the unique file name # The QTemporaryFile destructor removes the temporary file # as it goes out of scope. diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qtextstream.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qtextstream.cpp index 6988af4..18e1f69 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qtextstream.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qtextstream.cpp @@ -1,6 +1,6 @@ //! [0] data = QFile("output.txt") -if data.open(QFile.WriteOnly | QFile::Truncate): +if data.open(QFile.WriteOnly | QFile.Truncate): out = QTextStream(&data) out << "Result: " << qSetFieldWidth(10) << left << 3.14 << 2.7 # writes "Result: 3.14 2.7 " @@ -19,15 +19,15 @@ while(True): //! [2] -in = QTextStream("0x50 0x20") +in_ = QTextStream("0x50 0x20") firstNumber = 0 secondNumber = 0 -in >> firstNumber # firstNumber == 80 -in >> dec >> secondNumber # secondNumber == 0 +in_ >> firstNumber # firstNumber == 80 +in_ >> dec >> secondNumber # secondNumber == 0 ch = None -in >> ch # ch == 'x' +in_ >> ch # ch == 'x' //! [2] @@ -36,16 +36,16 @@ def main(): # read numeric arguments (123, 0x20, 4.5...) for i in sys.argv(): number = None - QTextStream in(i) - in >> number + QTextStream in_(i) + in_ >> number ... //! [3] //! [4] str = QString() -in = QTextStream(sys.stdin.fileno()) -in >> str +in_ = QTextStream(sys.stdin.fileno()) +in_ >> str //! [4] @@ -65,11 +65,11 @@ out << "Qt" << "rocks!" //! [7] -in = QTextStream(file) +in_ = QTextStream(file) ch1 = QChar() ch2 = QChar() ch3 = QChar() -in >> ch1 >> ch2 >> ch3; +in_ >> ch1 >> ch2 >> ch3; //! [7] diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qurl.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qurl.cpp index a568438..c0a4fca 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qurl.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qurl.cpp @@ -12,10 +12,10 @@ url = QUrl.fromEncoded("http://qtsoftware.com/List%20of%20holidays.xml") //! [2] def checkUrl(url): if !url.isValid(): - print QString("Invalid URL: %1").arg(url.toString()) - return false + print "Invalid URL: %s" % url.toString() + return False - return true + return True //! [2] @@ -41,6 +41,6 @@ print baseUrl.resolved(relativeUrl).toString() //! [6] ba = QUrl.toPercentEncoding("{a fishy string?}", "{}", "s") -print ba.constData() +print ba # prints "{a fi%73hy %73tring%3F}" //! [6] diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_kernel_qcoreapplication.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_kernel_qcoreapplication.cpp index f9cc001..48d3a24 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_kernel_qcoreapplication.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_kernel_qcoreapplication.cpp @@ -6,7 +6,7 @@ QApplication.sendEvent(mainWindow, event) //! [1] quitButton = QPushButton("Quit") -QObject.connect(quitButton, SIGNAL("clicked()"), app, SLOT("quit()")) +quitButton.clicked.connect(app.quit) //! [1] @@ -22,19 +22,11 @@ myEventFilter(message, result) //! [4] -static int *global_ptr = 0; +def cleanup_stuff(): + # do the cleanup stuff -static void cleanup_ptr() -{ - delete [] global_ptr; - global_ptr = 0; -} - -void init_ptr() -{ - global_ptr = new int[100]; // allocate data - qAddPostRoutine(cleanup_ptr); // delete later -} +def init_stuff(): + qAddPostRoutine(cleanup_stuff) //! [4] diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_kernel_qmetaobject.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_kernel_qmetaobject.cpp index 5676f13..046b40c 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_kernel_qmetaobject.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_kernel_qmetaobject.cpp @@ -48,17 +48,13 @@ class MyClass: //! [propertyCount] metaObject = obj.metaObject() -properties = QStringList() -for i in range(metaObject.propertyOffset(), metaObject.propertyCount()): - properties << QString.fromLatin1(metaObject.property(i).name()) +properties = [metaObject.property(i).name() for i in range(metaObject.propertyOffset(), metaObject.propertyCount())] //! [propertyCount] //! [methodCount] metaObject = obj.metaObject() -methods = QStringList() -for i in rang(metaObject.methodOffset(), metaObject->methodCount()): - methods << QString.fromLatin1(metaObject.method(i).signature()) +methods = [metaObject.method(i).signature() for i in range(metaObject.methodOffset(), metaObject.methodCount())] //! [methodCount] //! [6] diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_kernel_qtimer.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_kernel_qtimer.cpp index 1b7ea4e..bb646a1 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_kernel_qtimer.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_kernel_qtimer.cpp @@ -6,5 +6,5 @@ def main(): app = QApplication([]) QTimer.singleShot(600000, app, SLOT('quit()')) ... - return app.exec() + return app.exec_() //! [0] diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_thread_qthread.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_thread_qthread.cpp index a100127..768f96f 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_thread_qthread.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_thread_qthread.cpp @@ -5,5 +5,5 @@ class MyThread (QThread): # connect QTcpSocket's signals somewhere meaningful # ... socket.connectToHost(hostName, portNumber) - exec_() + self.exec_() //! [0] diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_tools_qbitarray.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_tools_qbitarray.cpp index 19be88f..d794676 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_tools_qbitarray.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_tools_qbitarray.cpp @@ -173,7 +173,7 @@ c = a | b //! [14] a = QBitArray(3) -QBitArray b(2) +b = QBitArray(2) c = QBitArray() a[0] = 1 a[1] = 0 diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_tools_qbytearray.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_tools_qbytearray.cpp index c097a26..c563df4 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_tools_qbytearray.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_tools_qbytearray.cpp @@ -327,15 +327,13 @@ ba = QByteArray.number(12.3456, 'E', 3) //! [43] - static const char mydata[] = { - 0x00, 0x00, 0x03, 0x84, 0x78, 0x9c, 0x3b, 0x76, - 0xec, 0x18, 0xc3, 0x31, 0x0a, 0xf1, 0xcc, 0x99, - ... - 0x6d, 0x5b -}; +mydata = '\x00\x00\x03\x84\x78\x9c\x3b\x76'\ + '\xec\x18\xc3\x31\x0a\xf1\xcc\x99'\ + ... + '\x6d\x5b' -QByteArray data = QByteArray::fromRawData(mydata, sizeof(mydata)); -QDataStream in(&data, QIODevice::ReadOnly); +data = QByteArray.fromRawData(mydata) +in_ = QDataStream(data, QIODevice.ReadOnly) ... //! [43] diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_tools_qdatetime.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_tools_qdatetime.cpp index b935e34..ccd4380 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_tools_qdatetime.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_tools_qdatetime.cpp @@ -36,7 +36,7 @@ QDate.isValid(1202, 6, 6) # True (even though 1202 is pre-Gregorian) //! [5] -n = QTime(14, 0, 0) # n == 14:00:00 +n = QTime(14, 0, 0) # n == 14:00:00 t = QTime() t = n.addSecs(70) # t == 14:01:10 t = n.addSecs(-70) # t == 13:58:50 diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_tools_qlocale.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_tools_qlocale.cpp index 6fedb1f..c1b8468 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_tools_qlocale.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_tools_qlocale.cpp @@ -14,15 +14,18 @@ hebrew = QLocale() # Constructs a default QLocale s1 = hebrew.toString(15714.3, 'e') QLocale.setDefault(QLocale(QLocale.C)) -(d, ok) = QString("1234,56").toDouble() # ok == false -(d, ok) = QString("1234.56").toDouble() # ok == true, d == 1234.56 +c = QLocale() +(d, ok) = c.toDouble("1234,56") # ok == false +(d, ok) = c.toDouble("1234.56") # ok == true, d == 1234.56 QLocale.setDefault(QLocale(QLocale.German)) -(d, ok) = QString("1234,56").toDouble() # ok == true, d == 1234.56 -(d, ok) = QString("1234.56").toDouble() # ok == true, d == 1234.56 +german = QLocale() +(d, ok) = german.toDouble("1234,56") # ok == true, d == 1234.56 +(d, ok) = german.toDouble("1234.56") # ok == true, d == 1234.56 QLocale.setDefault(QLocale(QLocale.English, QLocale.UnitedStates)) -string = QString("%1 %L2 %L3").arg(12345).arg(12345).arg(12345, 0, 16) +english = QLocale() +string = '%s %s %10x' % (12345, english.toString(12345), 12345) # string == "12345 12,345 3039" //! [1] diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_tools_qtimeline.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_tools_qtimeline.cpp index 5f2e978..5b0d16e 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_tools_qtimeline.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_tools_qtimeline.cpp @@ -6,10 +6,10 @@ progressBar.setRange(0, 100) # Construct a 1-second timeline with a frame range of 0 - 100 timeLine = QTimeLine(1000, self) timeLine.setFrameRange(0, 100) -QObject.connect(timeLine, SIGNAL("frameChanged(int)"), progressBar, SLOT("setValue(int)")) +timeLine.frameChanged[int].connect(progressBar.setValue) # Clicking the push button will start the progress bar animation pushButton = QPushButton(QObject.tr("Start animation"), self) -QObject.connect(pushButton, SIGNAL("clicked()"), timeLine, SLOT("start()")) +pushButton.clicked.connect(timeLine.start) ... //! [0] diff --git a/doc/codesnippets/doc/src/snippets/process/process.cpp b/doc/codesnippets/doc/src/snippets/process/process.cpp index 3baeb58..7201bdb 100644 --- a/doc/codesnippets/doc/src/snippets/process/process.cpp +++ b/doc/codesnippets/doc/src/snippets/process/process.cpp @@ -45,7 +45,7 @@ bool zip() { //! [0] gzip = QProcess() - gzip.start("gzip", QStringList() << "-c") + gzip.start("gzip", ["-c"]) if not gzip.waitForStarted(): return False diff --git a/doc/codesnippets/doc/src/snippets/qdir-namefilters/main.cpp b/doc/codesnippets/doc/src/snippets/qdir-namefilters/main.cpp index d34fdf3..259821f 100644 --- a/doc/codesnippets/doc/src/snippets/qdir-namefilters/main.cpp +++ b/doc/codesnippets/doc/src/snippets/qdir-namefilters/main.cpp @@ -39,28 +39,21 @@ ** ****************************************************************************/ -#include -#include +from PySide.QtCore import * -int main(int argc, char *argv[]) -{ - QDir dir; - dir.setFilter(QDir::Files | QDir::Hidden | QDir::NoSymLinks); - dir.setSorting(QDir::Size | QDir::Reversed); +def main(): + dir_ = QDir() + dir_.setFilter(QDir.Files | QDir.Hidden | QDir.NoSymLinks) + dir_.setSorting(QDir.Size | QDir.Reversed) //! [0] - filters = QStringList() - filters << "*.cpp" << "*.cxx" << "*.cc" - dir.setNameFilters(filters) + filters = ["*.cpp", "*.cxx", "*.cc"] + dir_.setNameFilters(filters) //! [0] +// + lst = d.entryInfoList() + + print " Bytes Filename" + for fileInfo in lst: + print '%d %s' % (fileInfo.size(), fileInfo.fileName()) - QFileInfoList list = dir.entryInfoList(); - std::cout << " Bytes Filename" << std::endl; - for (int i = 0; i < list.size(); ++i) { - QFileInfo fileInfo = list.at(i); - std::cout << qPrintable(QString("%1 %2").arg(fileInfo.size(), 10) - .arg(fileInfo.fileName())); - std::cout << std::endl; - } - return 0; -} diff --git a/doc/codesnippets/doc/src/snippets/qprocess-environment/main.cpp b/doc/codesnippets/doc/src/snippets/qprocess-environment/main.cpp index ed49da3..696daeb 100644 --- a/doc/codesnippets/doc/src/snippets/qprocess-environment/main.cpp +++ b/doc/codesnippets/doc/src/snippets/qprocess-environment/main.cpp @@ -44,10 +44,15 @@ void startProcess() { //! [0] +import re +from PySide.QtCore import QProcess + process = QProcess() + env = QProcess.systemEnvironment() -env << "TMPDIR=C:\\MyApp\\temp" # Add an environment variable -env.replaceInStrings(QRegExp("^PATH=(.*)", Qt.CaseInsensitive), "PATH=\\1;C:\\Bin") +env.append("TMPDIR=C:\\MyApp\\temp") # Add an environment variable +regex = re.compile(r'^PATH=(.*)', re.IGNORECASE) +env = [regex.sub(r'PATH=\1;C:\\Bin', var) for var in env] process.setEnvironment(env) process.start("myapp") //! [0] diff --git a/doc/codesnippets/doc/src/snippets/qprocess/qprocess-simpleexecution.cpp b/doc/codesnippets/doc/src/snippets/qprocess/qprocess-simpleexecution.cpp index 09bb7ca..b17f9ef 100644 --- a/doc/codesnippets/doc/src/snippets/qprocess/qprocess-simpleexecution.cpp +++ b/doc/codesnippets/doc/src/snippets/qprocess/qprocess-simpleexecution.cpp @@ -51,13 +51,12 @@ int main(int argc, char *argv[]) parent = &app; //! [1] - program = QString("./path/to/Qt/examples/widgets/analogclock") + program = "./path/to/Qt/examples/widgets/analogclock" //! [1] program = "./../../../../examples/widgets/analogclock/analogclock"; //! [2] - arguments = QStringList() - arguments << "-style" << "motif" + arguments ["-style", "motif"] myProcess = QProcess(parent) myProcess.start(program, arguments) diff --git a/doc/codesnippets/doc/src/snippets/timers/timers.cpp b/doc/codesnippets/doc/src/snippets/timers/timers.cpp index 3e5e1ac..9a05870 100644 --- a/doc/codesnippets/doc/src/snippets/timers/timers.cpp +++ b/doc/codesnippets/doc/src/snippets/timers/timers.cpp @@ -39,7 +39,7 @@ ** ****************************************************************************/ -#include +from PySide.QtCore import QTimer class Foo : public QObject { @@ -52,7 +52,7 @@ Foo::Foo() //! [0] timer = QTimer(self) //! [0] //! [1] - self.connect(timer, SIGNAL("timeout()"), self.updateCaption) + timer.timeout.connect(self.updateCaption) //! [1] //! [2] timer.start(1000) //! [2] @@ -66,7 +66,7 @@ Foo::Foo() //! [4] timer = QTimer(self) //! [4] //! [5] - self.connect(timer, SIGNAL("timeout()"), self.processOneThing) + timer.timeout.connect(self.processOneThing) //! [5] //! [6] timer.start() //! [6] @@ -75,5 +75,5 @@ Foo::Foo() int main() { - + } diff --git a/doc/codesnippets/doc/src/snippets/whatsthis/whatsthis.cpp b/doc/codesnippets/doc/src/snippets/whatsthis/whatsthis.cpp index 4bd1961..871254b 100644 --- a/doc/codesnippets/doc/src/snippets/whatsthis/whatsthis.cpp +++ b/doc/codesnippets/doc/src/snippets/whatsthis/whatsthis.cpp @@ -42,7 +42,7 @@ //! [0] Act = QAction(tr("&New"), self) Act.setShortcut(tr("Ctrl+N")) - Act.setStatusTip(tr("Create a new file")) - Act.setWhatsThis(tr("Click self option to create a new file.")) + Act.setStatusTip(QObject.tr("Create a new file")) + Act.setWhatsThis(QObject.tr("Click self option to create a new file.")) //! [0] From 885386fdba018286912d7f3efb3da347e4c80a83 Mon Sep 17 00:00:00 2001 From: Marcelo Lira Date: Fri, 3 Dec 2010 10:48:08 -0300 Subject: [PATCH 006/703] Updates to more code snippets on documentation concerning QtCore module. Reviewed by Hugo Parente Reviewed by Luciano Wolf --- .../src_corelib_io_qabstractfileengine.cpp | 2 +- .../src/snippets/code/src_corelib_io_qdir.cpp | 4 +- .../snippets/code/src_corelib_io_qprocess.cpp | 10 +- .../src_corelib_kernel_qabstractitemmodel.cpp | 20 ++++ ...src_corelib_statemachine_qstatemachine.cpp | 55 +++++++++ .../doc/src/snippets/qelapsedtimer/main.cpp | 109 ++++++++++++++++++ .../snippets/qelapsedtimer/qelapsedtimer.pro | 2 + .../snippets/qprocess-environment/main.cpp | 70 ++++++----- .../qprocess/qprocess-simpleexecution.cpp | 2 +- 9 files changed, 236 insertions(+), 38 deletions(-) create mode 100644 doc/codesnippets/doc/src/snippets/code/src_corelib_statemachine_qstatemachine.cpp create mode 100644 doc/codesnippets/doc/src/snippets/qelapsedtimer/main.cpp create mode 100644 doc/codesnippets/doc/src/snippets/qelapsedtimer/qelapsedtimer.pro diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qabstractfileengine.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qabstractfileengine.cpp index de0fd50..98c9303 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qabstractfileengine.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qabstractfileengine.cpp @@ -31,7 +31,7 @@ def create(fileName): //! [2] # @arg filters QDir.Filters -# @arg filterNames QStringList +# @arg filterNames [str, ...] # @return QAbstractFileEngineIterator def beginEntryList(filters, filterNames): return CustomFileEngineIterator(filters, filterNames) diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qdir.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qdir.cpp index a849e48..1de2168 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qdir.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qdir.cpp @@ -66,8 +66,8 @@ s = dir.relativeFilePath("/home/mary/file.txt") # s is "../mary/file.txt" //! [8] -QDir.setSearchPaths("icons", QStringList(QDir.homePath() + "/images")) -QDir.setSearchPaths("docs", QStringList(":/embeddedDocuments")) +QDir.setSearchPaths("icons", [QDir.homePath() + "/images"]) +QDir.setSearchPaths("docs", [":/embeddedDocuments"]) ... pixmap = QPixmap("icons:undo.png") # will look for undo.png in QDir::homePath() + "/images" file = QFile("docs:design.odf") # will look in the :/embeddedDocuments resource path diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qprocess.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qprocess.cpp index 228a24c..6b97e37 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qprocess.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_io_qprocess.cpp @@ -4,10 +4,10 @@ def wrapInFunction(): //! [0] builder = QProcess() builder.setProcessChannelMode(QProcess.MergedChannels) -builder.start("make", QStringList() << "-j2") +builder.start("make", ["-j2"]) import sys -if !builder.waitForFinished(): +if not builder.waitForFinished(): sys.stderr.write("Make failed:" + builder.errorString()) else sys.stderr.write("Make output:" + builder.readAll()) @@ -57,7 +57,7 @@ class SandboxProcess(QProcess): //! [5] process = QProcess() process.start("del /s *.txt") -# same as process.start("del", QStringList() << "/s" << "*.txt") +# same as process.start("del", ["/s", "*.txt"]) ... //! [5] @@ -76,8 +76,8 @@ process.start("dir \"\"\"My Documents\"\"\"") //! [8] environment = QProcess.systemEnvironment() -# environment = {"PATH=/usr/bin:/usr/local/bin", -# "USER=greg", "HOME=/home/greg"} +# environment = [PATH=/usr/bin:/usr/local/bin", +# "USER=greg", "HOME=/home/greg"] //! [8] diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_kernel_qabstractitemmodel.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_kernel_qabstractitemmodel.cpp index 61ea362..1f20c3b 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_corelib_kernel_qabstractitemmodel.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_kernel_qabstractitemmodel.cpp @@ -26,3 +26,23 @@ beginInsertColumns(parent, 6, 8) //! [5] beginRemoveColumns(parent, 4, 6) //! [5] + + +//! [6] +beginMoveRows(sourceParent, 2, 4, destinationParent, 2) +//! [6] + + +//! [7] +beginMoveRows(sourceParent, 2, 4, destinationParent, 6) +//! [7] + + +//! [8] +beginMoveRows(parent, 2, 2, parent, 0) +//! [8] + + +//! [9] +beginMoveRows(parent, 2, 2, parent, 4) +//! [9] diff --git a/doc/codesnippets/doc/src/snippets/code/src_corelib_statemachine_qstatemachine.cpp b/doc/codesnippets/doc/src/snippets/code/src_corelib_statemachine_qstatemachine.cpp new file mode 100644 index 0000000..e768081 --- /dev/null +++ b/doc/codesnippets/doc/src/snippets/code/src_corelib_statemachine_qstatemachine.cpp @@ -0,0 +1,55 @@ +/**************************************************************************** +** +** Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies). +** All rights reserved. +** Contact: Nokia Corporation (qt-info@nokia.com) +** +** This file is part of the documentation of the Qt Toolkit. +** +** $QT_BEGIN_LICENSE:BSD$ +** You may use this file under the terms of the BSD license as follows: +** +** "Redistribution and use in source and binary forms, with or without +** modification, are permitted provided that the following conditions are +** met: +** * Redistributions of source code must retain the above copyright +** notice, this list of conditions and the following disclaimer. +** * Redistributions in binary form must reproduce the above copyright +** notice, this list of conditions and the following disclaimer in +** the documentation and/or other materials provided with the +** distribution. +** * Neither the name of Nokia Corporation and its Subsidiary(-ies) nor +** the names of its contributors may be used to endorse or promote +** products derived from this software without specific prior written +** permission. +** +** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE." +** $QT_END_LICENSE$ +** +****************************************************************************/ + +//! [simple state machine] +button = QPushButton() + +machine = QStateMachine() +s1 = QState() +s1.assignProperty(button, "text", "Click me") + +s2 = QFinalState() +s1.addTransition(button, SIGNAL('clicked()'), s2) + +machine.addState(s1) +machine.addState(s2) +machine.setInitialState(s1) +machine.start() +//! [simple state machine] diff --git a/doc/codesnippets/doc/src/snippets/qelapsedtimer/main.cpp b/doc/codesnippets/doc/src/snippets/qelapsedtimer/main.cpp new file mode 100644 index 0000000..cae84e7 --- /dev/null +++ b/doc/codesnippets/doc/src/snippets/qelapsedtimer/main.cpp @@ -0,0 +1,109 @@ +/**************************************************************************** +** +** Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies). +** All rights reserved. +** Contact: Nokia Corporation (qt-info@nokia.com) +** +** This file is part of the QtNetwork module of the Qt Toolkit. +** +** $QT_BEGIN_LICENSE:BSD$ +** You may use this file under the terms of the BSD license as follows: +** +** "Redistribution and use in source and binary forms, with or without +** modification, are permitted provided that the following conditions are +** met: +** * Redistributions of source code must retain the above copyright +** notice, this list of conditions and the following disclaimer. +** * Redistributions in binary form must reproduce the above copyright +** notice, this list of conditions and the following disclaimer in +** the documentation and/or other materials provided with the +** distribution. +** * Neither the name of Nokia Corporation and its Subsidiary(-ies) nor +** the names of its contributors may be used to endorse or promote +** products derived from this software without specific prior written +** permission. +** +** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE." +** $QT_END_LICENSE$ +** +****************************************************************************/ +#include + +void slowOperation1() +{ + static char buf[256]; + for (int i = 0; i < (1<<20); ++i) + buf[i % sizeof buf] = i; +} + +void slowOperation2(int) { slowOperation1(); } + +void startExample() +{ +//![0] + timer = QElapsedTimer() + timer.start() + + slowOperation1() + + sys.stderr.write("The slow operation took" + timer.elapsed() + "milliseconds") +//![0] +} + +//![1] +def executeSlowOperations(timeout): + timer = QElapsedTimer() + timer.start() + slowOperation1() + + remainingTime = timeout - timer.elapsed() + if remainingTime > 0: + slowOperation2(remainingTime) +//![1] + +//![2] +def executeOperationsForTime(ms): + timer = QElapsedTimer() + timer.start() + + while not timer.hasExpired(ms): + slowOperation1() +//![2] + +int restartExample() +{ +//![3] + timer = QElapsedTimer() + + count = 1 + timer.start() + + while True: + count *= 2 + slowOperation2(count) + if timer.restart() < 250: + break + + return count +//![3] +} + +int main(int argc, char **argv) +{ + QCoreApplication app(argc, argv); + + startExample(); + restartExample(); + executeSlowOperations(5); + executeOperationsForTime(5); +} diff --git a/doc/codesnippets/doc/src/snippets/qelapsedtimer/qelapsedtimer.pro b/doc/codesnippets/doc/src/snippets/qelapsedtimer/qelapsedtimer.pro new file mode 100644 index 0000000..b0a8f66 --- /dev/null +++ b/doc/codesnippets/doc/src/snippets/qelapsedtimer/qelapsedtimer.pro @@ -0,0 +1,2 @@ +SOURCES = main.cpp +QT -= gui diff --git a/doc/codesnippets/doc/src/snippets/qprocess-environment/main.cpp b/doc/codesnippets/doc/src/snippets/qprocess-environment/main.cpp index 696daeb..9168197 100644 --- a/doc/codesnippets/doc/src/snippets/qprocess-environment/main.cpp +++ b/doc/codesnippets/doc/src/snippets/qprocess-environment/main.cpp @@ -1,40 +1,39 @@ /**************************************************************************** ** -** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies). +** Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies). +** All rights reserved. ** Contact: Nokia Corporation (qt-info@nokia.com) ** ** This file is part of the documentation of the Qt Toolkit. ** -** $QT_BEGIN_LICENSE:LGPL$ -** Commercial Usage -** Licensees holding valid Qt Commercial licenses may use this file in -** accordance with the Qt Commercial License Agreement provided with the -** Software or, alternatively, in accordance with the terms contained in -** a written agreement between you and Nokia. +** $QT_BEGIN_LICENSE:BSD$ +** You may use this file under the terms of the BSD license as follows: ** -** GNU Lesser General Public License Usage -** Alternatively, this file may be used under the terms of the GNU Lesser -** General Public License version 2.1 as published by the Free Software -** Foundation and appearing in the file LICENSE.LGPL included in the -** packaging of this file. Please review the following information to -** ensure the GNU Lesser General Public License version 2.1 requirements -** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. +** "Redistribution and use in source and binary forms, with or without +** modification, are permitted provided that the following conditions are +** met: +** * Redistributions of source code must retain the above copyright +** notice, this list of conditions and the following disclaimer. +** * Redistributions in binary form must reproduce the above copyright +** notice, this list of conditions and the following disclaimer in +** the documentation and/or other materials provided with the +** distribution. +** * Neither the name of Nokia Corporation and its Subsidiary(-ies) nor +** the names of its contributors may be used to endorse or promote +** products derived from this software without specific prior written +** permission. ** -** In addition, as a special exception, Nokia gives you certain -** additional rights. These rights are described in the Nokia Qt LGPL -** Exception version 1.0, included in the file LGPL_EXCEPTION.txt in this -** package. -** -** GNU General Public License Usage -** Alternatively, this file may be used under the terms of the GNU -** General Public License version 3.0 as published by the Free Software -** Foundation and appearing in the file LICENSE.GPL included in the -** packaging of this file. Please review the following information to -** ensure the GNU General Public License version 3.0 requirements will be -** met: http://www.gnu.org/copyleft/gpl.html. -** -** If you are unsure which license is appropriate for your use, please -** contact the sales department at http://www.qtsoftware.com/contact. +** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE." ** $QT_END_LICENSE$ ** ****************************************************************************/ @@ -43,6 +42,7 @@ void startProcess() { + { //! [0] import re from PySide.QtCore import QProcess @@ -56,6 +56,18 @@ env = [regex.sub(r'PATH=\1;C:\\Bin', var) for var in env] process.setEnvironment(env) process.start("myapp") //! [0] + } + + { +//! [1] +process = QProcess() +env = QProcessEnvironment.systemEnvironment() +env.insert("TMPDIR", "C:\\MyApp\\temp") # Add an environment variable +env.insert("PATH", env.value("Path") + ";C:\\Bin") +process.setProcessEnvironment(env) +process.start("myapp") +//! [1] + } } int main(int argc, char *argv[]) diff --git a/doc/codesnippets/doc/src/snippets/qprocess/qprocess-simpleexecution.cpp b/doc/codesnippets/doc/src/snippets/qprocess/qprocess-simpleexecution.cpp index b17f9ef..779c909 100644 --- a/doc/codesnippets/doc/src/snippets/qprocess/qprocess-simpleexecution.cpp +++ b/doc/codesnippets/doc/src/snippets/qprocess/qprocess-simpleexecution.cpp @@ -56,7 +56,7 @@ int main(int argc, char *argv[]) program = "./../../../../examples/widgets/analogclock/analogclock"; //! [2] - arguments ["-style", "motif"] + arguments = ["-style", "motif"] myProcess = QProcess(parent) myProcess.start(program, arguments) From 079e105618e8d3bff8515b8c993a2c68d04a92db Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Thu, 2 Dec 2010 18:43:37 -0200 Subject: [PATCH 007/703] Remove unused ancient proxyslot.cpp file. --- libpyside/proxyslot.cpp | 76 ----------------------------------------- 1 file changed, 76 deletions(-) delete mode 100644 libpyside/proxyslot.cpp diff --git a/libpyside/proxyslot.cpp b/libpyside/proxyslot.cpp deleted file mode 100644 index e480f76..0000000 --- a/libpyside/proxyslot.cpp +++ /dev/null @@ -1,76 +0,0 @@ -/* -* This file is part of the PySide project. -* -* Copyright (C) 2009-2010 Nokia Corporation and/or its subsidiary(-ies). -* -* Contact: PySide team -* -* This library is free software; you can redistribute it and/or -* modify it under the terms of the GNU Lesser General Public -* License as published by the Free Software Foundation; either -* version 2.1 of the License, or (at your option) any later version. -* -* This library is distributed in the hope that it will be useful, -* but WITHOUT ANY WARRANTY; without even the implied warranty of -* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU -* Lesser General Public License for more details. -* -* You should have received a copy of the GNU Lesser General Public -* License along with this library; if not, write to the Free Software -* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA -*/ - -#include -#include -#include "proxyslot.h" -#include "abstractqobjectconnection.h" -#include "signalmanager.h" - -using namespace PySide; - -ProxySlot::ProxySlot(const QObject* signalSource) : m_metaObject(signalSource), m_signalSource(signalSource) -{ - m_nextSlotIndex = m_signalSource->metaObject()->methodCount()-1; -} - -bool ProxySlot::connect(AbstractQObjectConnection* connection) -{ - QObject* source = connection->source(); - attachAbstractConnection(connection); - int slotIndex = connection->slotIndex(); - int signalIndex = connection->signalIndex(); - - qDebug() << "conectando" << signalIndex << "em" << slotIndex; - if (signalIndex >= 0) { - return QMetaObject::connect(source, signalIndex, this, slotIndex, connection->type()); - } else { // dynamic signals! - // TODO: Register dynamic signal - } - return true; - -} - -void ProxySlot::attachAbstractConnection(AbstractQObjectConnection* connection) -{ - m_nextSlotIndex++; - m_connections[m_nextSlotIndex] = connection; - connection->setSlotIndex(m_nextSlotIndex); -} - -int ProxySlot::qt_metacall(QMetaObject::Call callType, int slotIndex, void** args) -{ - // 2 is the index of deleteLater slot - if (slotIndex == 2) { - deleteLater(); - SignalManager::instance().removeProxySlot(m_signalSource); - } - - if (m_connections.contains(slotIndex)) { -// thread_locker lock; - m_connections[slotIndex]->trigger(args); - return -1; - } - - return QObject::qt_metacall(callType, slotIndex, args); -} - From d36b2398b8d9ddd76c669f24106cbe02eada1b57 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Fri, 3 Dec 2010 15:55:41 -0200 Subject: [PATCH 008/703] PySidePropertyPrivate struct moved to the private header. --- libpyside/pysideproperty.cpp | 18 ------------------ libpyside/pysideproperty_p.h | 23 +++++++++++++++++++++++ 2 files changed, 23 insertions(+), 18 deletions(-) diff --git a/libpyside/pysideproperty.cpp b/libpyside/pysideproperty.cpp index 72b718c..dd5ca37 100644 --- a/libpyside/pysideproperty.cpp +++ b/libpyside/pysideproperty.cpp @@ -36,24 +36,6 @@ extern "C" { -struct PySidePropertyPrivate { - char* typeName; - PyObject* type; - PyObject* fget; - PyObject* fset; - PyObject* freset; - PyObject* fdel; - PyObject* notify; - char* notifySignature; - char* doc; - bool designable; - bool scriptable; - bool stored; - bool user; - bool constant; - bool final; -}; - static int qpropertyTpInit(PyObject*, PyObject*, PyObject*); static void qpropertyFree(void*); diff --git a/libpyside/pysideproperty_p.h b/libpyside/pysideproperty_p.h index 1ba9cb2..9c6893b 100644 --- a/libpyside/pysideproperty_p.h +++ b/libpyside/pysideproperty_p.h @@ -27,6 +27,29 @@ struct PySideProperty; +extern "C" +{ + +struct PySidePropertyPrivate { + char* typeName; + PyObject* type; + PyObject* fget; + PyObject* fset; + PyObject* freset; + PyObject* fdel; + PyObject* notify; + char* notifySignature; + char* doc; + bool designable; + bool scriptable; + bool stored; + bool user; + bool constant; + bool final; +}; + +} // extern "C" + namespace PySide { namespace Property { /** From a29f511f6ded054550feea317f089ac77b6b4994 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Fri, 3 Dec 2010 16:28:27 -0200 Subject: [PATCH 009/703] Moved pyside slot attr name do pysideslot_p.h. --- libpyside/dynamicqmetaobject.cpp | 1 + libpyside/dynamicqmetaobject_p.h | 1 - libpyside/pysideslot.cpp | 1 + libpyside/pysideslot_p.h | 1 + 4 files changed, 3 insertions(+), 1 deletion(-) diff --git a/libpyside/dynamicqmetaobject.cpp b/libpyside/dynamicqmetaobject.cpp index 0622bcb..3454932 100644 --- a/libpyside/dynamicqmetaobject.cpp +++ b/libpyside/dynamicqmetaobject.cpp @@ -26,6 +26,7 @@ #include "pysidesignal_p.h" #include "pysideproperty.h" #include "pysideproperty_p.h" +#include "pysideslot_p.h" #include #include diff --git a/libpyside/dynamicqmetaobject_p.h b/libpyside/dynamicqmetaobject_p.h index d31e908..c8c45a1 100644 --- a/libpyside/dynamicqmetaobject_p.h +++ b/libpyside/dynamicqmetaobject_p.h @@ -26,7 +26,6 @@ #include #include -#define PYSIDE_SLOT_LIST_ATTR "_slots" #define GLOBAL_RECEIVER_CLASS_NAME "__GlobalReceiver__" struct PySideProperty; diff --git a/libpyside/pysideslot.cpp b/libpyside/pysideslot.cpp index acd0bb9..7d22ca9 100644 --- a/libpyside/pysideslot.cpp +++ b/libpyside/pysideslot.cpp @@ -22,6 +22,7 @@ #include "dynamicqmetaobject_p.h" #include "pysidesignal_p.h" +#include "pysideslot_p.h" #include #include diff --git a/libpyside/pysideslot_p.h b/libpyside/pysideslot_p.h index b02c36a..1e863d2 100644 --- a/libpyside/pysideslot_p.h +++ b/libpyside/pysideslot_p.h @@ -23,6 +23,7 @@ #define PYSIDE_SLOT_P_H #include +#define PYSIDE_SLOT_LIST_ATTR "_slots" namespace PySide { namespace Slot { void init(PyObject* module); From 8fb60373627f5d9978df2b9f38d0180f5897477a Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Fri, 3 Dec 2010 17:04:37 -0200 Subject: [PATCH 010/703] Set the object meta object at the declaration time, not instanciation time. --- libpyside/dynamicqmetaobject.cpp | 58 -------------------- libpyside/dynamicqmetaobject.h | 5 +- libpyside/pyside.cpp | 91 ++++++++++++++++++++++++++++++++ libpyside/pyside.h | 4 ++ 4 files changed, 96 insertions(+), 62 deletions(-) diff --git a/libpyside/dynamicqmetaobject.cpp b/libpyside/dynamicqmetaobject.cpp index 3454932..1f6ff85 100644 --- a/libpyside/dynamicqmetaobject.cpp +++ b/libpyside/dynamicqmetaobject.cpp @@ -386,64 +386,6 @@ void DynamicQMetaObject::addProperty(const char* propertyName, PyObject* data) m_d->updateMetaObject(this); } - -DynamicQMetaObject* DynamicQMetaObject::createBasedOn(PyObject* pyObj, PyTypeObject* type, const QMetaObject* base) -{ - PyObject* key; - PyObject* value; - Py_ssize_t pos = 0; - - QString className(type->tp_name); - className = className.mid(className.lastIndexOf('.')+1); - DynamicQMetaObject *mo = new PySide::DynamicQMetaObject(className.toAscii(), base); - - QList properties; - - while (PyDict_Next(type->tp_dict, &pos, &key, &value)) { - - //Leave the properties to be register after signals because of notify object - if (value->ob_type == &PySidePropertyType) - properties.append(key); - - //Register signals - if (value->ob_type == &PySideSignalType) { - PyObject *attr = PyObject_GetAttr(pyObj, key); - PySideSignalInstance *data = reinterpret_cast(attr); - while(data) { - int index = base->indexOfSignal(data->d->signature); - if (index == -1) - mo->addSignal(data->d->signature); - data = reinterpret_cast(data->d->next); - } - } - - if (!PyFunction_Check(value)) - continue; - - //Register Slots - if (PyObject_HasAttrString(value, PYSIDE_SLOT_LIST_ATTR)) { - PyObject *signature_list = PyObject_GetAttrString(value, PYSIDE_SLOT_LIST_ATTR); - for(Py_ssize_t i = 0, i_max = PyList_Size(signature_list); i < i_max; i++) { - PyObject *signature = PyList_GET_ITEM(signature_list, i); - QString sig(PyString_AsString(signature)); - //slot the slot type and signature - QStringList slotInfo = sig.split(" ", QString::SkipEmptyParts); - int index = base->indexOfSlot(qPrintable(slotInfo[1])); - if (index == -1) - mo->addSlot(slotInfo[1].toAscii(), slotInfo[0].toAscii()); - } - } - } - - //Register properties - foreach(PyObject* key, properties) { - PyObject* value = PyDict_GetItem(type->tp_dict, key); - mo->addProperty(PyString_AsString(key), value); - } - - return mo; -} - void DynamicQMetaObject::removeSignal(uint index) { //Current Qt implementation does not support runtime remove signal diff --git a/libpyside/dynamicqmetaobject.h b/libpyside/dynamicqmetaobject.h index 8bd0282..7f64a6c 100644 --- a/libpyside/dynamicqmetaobject.h +++ b/libpyside/dynamicqmetaobject.h @@ -30,7 +30,7 @@ namespace PySide { -class PYSIDE_API DynamicQMetaObject : public QMetaObject +class DynamicQMetaObject : public QMetaObject { public: DynamicQMetaObject(const char* className, const QMetaObject* metaObject); @@ -44,9 +44,6 @@ public: void removeSlot(uint index); void removeProperty(uint index); - //Retrieve Python metadata to create QMetaObject (class name, signals, slot) - static DynamicQMetaObject* createBasedOn(PyObject* obj, PyTypeObject* type, const QMetaObject* base); - private: class DynamicQMetaObjectPrivate; DynamicQMetaObjectPrivate* m_d; diff --git a/libpyside/pyside.cpp b/libpyside/pyside.cpp index 81e5d65..79b4f4c 100644 --- a/libpyside/pyside.cpp +++ b/libpyside/pyside.cpp @@ -28,6 +28,7 @@ #include "pysidesignal_p.h" #include "pysideslot_p.h" #include "pysidemetafunction_p.h" +#include "dynamicqmetaobject.h" #include #include @@ -134,5 +135,95 @@ void destroyQCoreApplication() delete app; } +void initDynamicMetaObject(SbkObjectType* type, const QMetaObject* base) +{ + const char* typeName = type->super.ht_type.tp_name; + int len = strlen(typeName); + for (int i = len-1; i >= 0; --i) + if (typeName[i] == '.') + typeName += i + 1; + DynamicQMetaObject* mo = new PySide::DynamicQMetaObject(typeName, base); + Shiboken::ObjectType::setTypeUserData(type, mo, &Shiboken::callCppDestructor); +} + +void initQObjectSubType(SbkObjectType* type, PyObject* args, PyObject* kwds) +{ + PyTypeObject* qObjType = Shiboken::TypeResolver::get("QObject*")->pythonType(); + QByteArray className(PyString_AS_STRING(PyTuple_GET_ITEM(args, 0))); + + PyObject* bases = PyTuple_GET_ITEM(args, 1); + int numBases = PyTuple_GET_SIZE(args); + QMetaObject* baseMo = 0; + + for (int i = 0; i < numBases; ++i) { + PyTypeObject* base = reinterpret_cast(PyTuple_GET_ITEM(bases, i)); + if (PyType_IsSubtype(base, qObjType)) { + baseMo = reinterpret_cast(Shiboken::ObjectType::getTypeUserData(reinterpret_cast(base))); + // If it's a class like QObject, QWidget, etc, use the original QMetaObject instead of the dynamic one + // IMO this if is a bug, however it keeps the current behaviour. + if (!Shiboken::ObjectType::isUserType(base)) + baseMo = const_cast(baseMo->d.superdata); + break; + } + } + if (!baseMo) { + qWarning("Sub class of QObject not inheriting QObject!? Crash will happen when using %s.", className.constData()); + return; + } + + DynamicQMetaObject* mo = new PySide::DynamicQMetaObject(className.constData(), baseMo); + + Shiboken::ObjectType::setTypeUserData(type, mo, &Shiboken::callCppDestructor); + + PyObject* attrs = PyTuple_GET_ITEM(args, 2); + PyObject* key; + PyObject* value; + Py_ssize_t pos = 0; + + typedef std::pair PropPair; + QList properties; + + Shiboken::AutoDecRef slotAttrName(PyString_FromString(PYSIDE_SLOT_LIST_ATTR)); + + while (PyDict_Next(attrs, &pos, &key, &value)) { + if (value->ob_type == &PySidePropertyType) { + // Leave the properties to be register after signals because they may depend on notify signals + properties << PropPair(PyString_AS_STRING(key), value); + } else if (value->ob_type == &PySideSignalType) { // Register signals + PySideSignal* data = reinterpret_cast(value); + const char* signalName = PyString_AS_STRING(key); + data->signalName = strdup(signalName); + QByteArray sig; + sig.reserve(128); + for (int i = 0; i < data->signaturesSize; ++i) { + sig = signalName; + sig += '('; + if (data->signatures[i]) + sig += data->signatures[i]; + sig += ')'; + if (baseMo->indexOfSignal(sig) == -1) + mo->addSignal(sig); + } + } else if (PyFunction_Check(value)) { // Register slots + if (PyObject_HasAttr(value, slotAttrName)) { + PyObject* signatureList = PyObject_GetAttr(value, slotAttrName); + for(Py_ssize_t i = 0, i_max = PyList_Size(signatureList); i < i_max; ++i) { + PyObject* signature = PyList_GET_ITEM(signatureList, i); + QByteArray sig(PyString_AS_STRING(signature)); + //slot the slot type and signature + QList slotInfo = sig.split(' '); + int index = baseMo->indexOfSlot(slotInfo[1]); + if (index == -1) + mo->addSlot(slotInfo[1], slotInfo[0]); + } + } + } + } + + // Register properties + foreach (PropPair propPair, properties) + mo->addProperty(propPair.first, propPair.second); +} + } //namespace PySide diff --git a/libpyside/pyside.h b/libpyside/pyside.h index fe9ce3a..d84040d 100644 --- a/libpyside/pyside.h +++ b/libpyside/pyside.h @@ -29,6 +29,8 @@ #include #include +class SbkObjectType; + namespace PySide { @@ -75,6 +77,8 @@ template struct initQtMetaType { }; +PYSIDE_API void initDynamicMetaObject(SbkObjectType* type, const QMetaObject* base); +PYSIDE_API void initQObjectSubType(SbkObjectType* type, PyObject* args, PyObject* kwds); typedef void (*CleanupFunction)(void); From f02876e6c9acecdd1f202aeb5c2721fde581a0ac Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Wed, 1 Dec 2010 15:44:17 -0200 Subject: [PATCH 011/703] Initial implementation of qmlRegisterType. It's fully functional, but need some adjustaments in the build system that will be done in the next few days. Reviewer: Luciano Wolf Marcelo Lira --- PySide/QtDeclarative/CMakeLists.txt | 1 + .../QtDeclarative/pysideqmlregistertype.cpp | 143 ++++++++++++++++++ PySide/QtDeclarative/pysideqmlregistertype.h | 38 +++++ .../QtDeclarative/typesystem_declarative.xml | 41 +++++ 4 files changed, 223 insertions(+) create mode 100644 PySide/QtDeclarative/pysideqmlregistertype.cpp create mode 100644 PySide/QtDeclarative/pysideqmlregistertype.h diff --git a/PySide/QtDeclarative/CMakeLists.txt b/PySide/QtDeclarative/CMakeLists.txt index 1788adc..98673f7 100644 --- a/PySide/QtDeclarative/CMakeLists.txt +++ b/PySide/QtDeclarative/CMakeLists.txt @@ -1,6 +1,7 @@ project(QtDeclarative) set(QtDeclarative_SRC +${CMAKE_CURRENT_SOURCE_DIR}/pysideqmlregistertype.cpp ${CMAKE_CURRENT_BINARY_DIR}/PySide/QtDeclarative/qdeclarativecomponent_wrapper.cpp ${CMAKE_CURRENT_BINARY_DIR}/PySide/QtDeclarative/qdeclarativecontext_wrapper.cpp ${CMAKE_CURRENT_BINARY_DIR}/PySide/QtDeclarative/qdeclarativeengine_wrapper.cpp diff --git a/PySide/QtDeclarative/pysideqmlregistertype.cpp b/PySide/QtDeclarative/pysideqmlregistertype.cpp new file mode 100644 index 0000000..8980aa6 --- /dev/null +++ b/PySide/QtDeclarative/pysideqmlregistertype.cpp @@ -0,0 +1,143 @@ +/* + * This file is part of the Shiboken Python Bindings Generator project. + * + * Copyright (C) 2009-2010 Nokia Corporation and/or its subsidiary(-ies). + * + * Contact: PySide team + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + */ + +#include "pysideqmlregistertype.h" +#include +#include +#include +#include +#include +#include "qdeclarativeitem_wrapper.h" +#include + +#ifndef PYSIDE_MAX_QML_TYPES +// Maximum number of different types the user cna export to QML using qmlRegisterType. +#define PYSIDE_MAX_QML_TYPES 50 +#endif + +// All registered python types +static PyObject* pyTypes[PYSIDE_MAX_QML_TYPES]; +static void (*createFuncs[PYSIDE_MAX_QML_TYPES])(void*); + +/// QDeclarativeItem will create objects using placement new then this pointer is non-null. +void* PySide::nextQmlElementMemoryAddr = 0; +// Mutex used to avoid race condition on PySide::nextQmlElementMemoryAddr +static QMutex nextQmlElementMutex; + +template +struct ElementFactoryBase +{ + static void createInto(void* memory) + { + QMutexLocker locker(&nextQmlElementMutex); + PySide::nextQmlElementMemoryAddr = memory; + PyObject* obj = PyObject_CallObject(pyTypes[N], 0); + if (!obj || PyErr_Occurred()) + PyErr_Print(); + PySide::nextQmlElementMemoryAddr = 0; + } +}; + +template +struct ElementFactory : ElementFactoryBase +{ + static void init() + { + createFuncs[N] = &ElementFactoryBase::createInto; + ElementFactory::init(); + } +}; + +template<> +struct ElementFactory<0> : ElementFactoryBase<0> +{ + static void init() + { + createFuncs[0] = &ElementFactoryBase<0>::createInto; + } +}; + +void PySide::initQmlSupport() +{ + ElementFactory::init(); +} + +int PySide::qmlRegisterType(PyObject* pyObj, const char* uri, int versionMajor, int versionMinor, const char* qmlName) +{ + using namespace Shiboken; + + static PyTypeObject* declarativeItemType = TypeResolver::get("QDeclarativeItem*")->pythonType(); + assert(declarativeItemType); + static int nextType = 0; + + if (nextType >= PYSIDE_MAX_QML_TYPES) { + PyErr_Format(PyExc_TypeError, "QML doesn't really like language bindings, so you can only export %d types to QML.", PYSIDE_MAX_QML_TYPES); + return -1; + } + + if (pyObj->ob_type != &SbkObjectType_Type) { + PyErr_Format(PyExc_TypeError, "A shiboken-based python type expected, got %s.", pyObj->ob_type->tp_name); + return -1; + } + + if (!PySequence_Contains(((PyTypeObject*)pyObj)->tp_mro, (PyObject*)declarativeItemType)) { + PyErr_Format(PyExc_TypeError, "A type inherited from %s expected, got %s.", declarativeItemType->tp_name, ((PyTypeObject*)pyObj)->tp_name); + return -1; + } + + QMetaObject* metaObject = reinterpret_cast(ObjectType::getTypeUserData(reinterpret_cast(pyObj))); + if (!metaObject) { + PyErr_SetString(PyExc_TypeError, "FIXME: metaobject not initialized, this error msg should not exists at all!!"); + return -1; + } + + // All ready... now the ugly code begins... :-) + pyTypes[nextType] = pyObj; + + // Init proxy object static meta object + QDeclarativePrivate::RegisterType type; + type.version = 0; + type.typeId = qMetaTypeId(); + type.listId = qMetaTypeId >(); + type.objectSize = sizeof(QDeclarativeItemWrapper); + type.create = createFuncs[nextType]; + type.uri = uri; + type.versionMajor = versionMajor; + type.versionMinor = versionMinor; + type.elementName = qmlName; + type.metaObject = metaObject; + + type.attachedPropertiesFunction = QDeclarativePrivate::attachedPropertiesFunc(); + type.attachedPropertiesMetaObject = QDeclarativePrivate::attachedPropertiesMetaObject(); + + type.parserStatusCast = QDeclarativePrivate::StaticCastSelector::cast(); + type.valueSourceCast = QDeclarativePrivate::StaticCastSelector::cast(); + type.valueInterceptorCast = QDeclarativePrivate::StaticCastSelector::cast(); + + type.extensionObjectCreate = 0; + type.extensionMetaObject = 0; + type.customParser = 0; + + int qmlTypeId = QDeclarativePrivate::qmlregister(QDeclarativePrivate::TypeRegistration, &type); + ++nextType; + return qmlTypeId; +} diff --git a/PySide/QtDeclarative/pysideqmlregistertype.h b/PySide/QtDeclarative/pysideqmlregistertype.h new file mode 100644 index 0000000..3f83b29 --- /dev/null +++ b/PySide/QtDeclarative/pysideqmlregistertype.h @@ -0,0 +1,38 @@ +/* + * This file is part of the Shiboken Python Bindings Generator project. + * + * Copyright (C) 2009-2010 Nokia Corporation and/or its subsidiary(-ies). + * + * Contact: PySide team + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + */ + +#ifndef PYSIDEQMLREGISTERTYPE_H +#define PYSIDEQMLREGISTERTYPE_H + +#include + +namespace PySide +{ + +extern void* nextQmlElementMemoryAddr; + +void initQmlSupport(); +int qmlRegisterType(PyObject* pyObj, const char* uri, int versionMajor, int versionMinor, const char* qmlName); + +} + +#endif diff --git a/PySide/QtDeclarative/typesystem_declarative.xml b/PySide/QtDeclarative/typesystem_declarative.xml index 75c63e0..cc66602 100644 --- a/PySide/QtDeclarative/typesystem_declarative.xml +++ b/PySide/QtDeclarative/typesystem_declarative.xml @@ -23,14 +23,44 @@ + + + This function registers the Python type in the QML system with the name qmlName, in the library imported from uri having the version number composed from versionMajor and versionMinor. + Returns the QML type id. + + For example, this registers a Python class MySliderItem as a QML type named Slider for version 1.0 of a module called "com.mycompany.qmlcomponents": + + :: + + qmlRegisterType(MySliderItem, "com.mycompany.qmlcomponents", 1, 0, "Slider") + + Once this is registered, the type can be used in QML by importing the specified module name and version number: + + :: + + import com.mycompany.qmlcomponents 1.0 + + Slider { ... } + + Note that it's perfectly reasonable for a library to register types to older versions than the actual version of the library. Indeed, it is normal for the new library to allow QML written to previous versions to continue to work, even if more advanced versions of some of its types are available. + + + + %PYARG_0 = %CONVERTTOPYTHON[int](PySide::qmlRegisterType(%1, %2, %3, %4, %5)); + + + + + Shiboken::TypeResolver::createValueTypeResolver< QList<QObject*> >("QList<QObject*>"); + PySide::initQmlSupport(); @@ -60,7 +90,18 @@ + + + + + + if (PySide::nextQmlElementMemoryAddr) + %0 = new (PySide::nextQmlElementMemoryAddr) ::QDeclarativePrivate::QDeclarativeElement<%TYPE>(); + else + %0 = new %TYPE(%1); + + From 1c6fad98417ad5be5a4748ac865ed81f52b5d9c5 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Mon, 6 Dec 2010 11:42:36 -0200 Subject: [PATCH 012/703] Avoid removal of qmlregistertype.cpp by the build system. Reviewer: Marcelo Lira Luciano Wolf --- PySide/QtDeclarative/CMakeLists.txt | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/PySide/QtDeclarative/CMakeLists.txt b/PySide/QtDeclarative/CMakeLists.txt index 98673f7..0fc96d4 100644 --- a/PySide/QtDeclarative/CMakeLists.txt +++ b/PySide/QtDeclarative/CMakeLists.txt @@ -1,7 +1,6 @@ project(QtDeclarative) set(QtDeclarative_SRC -${CMAKE_CURRENT_SOURCE_DIR}/pysideqmlregistertype.cpp ${CMAKE_CURRENT_BINARY_DIR}/PySide/QtDeclarative/qdeclarativecomponent_wrapper.cpp ${CMAKE_CURRENT_BINARY_DIR}/PySide/QtDeclarative/qdeclarativecontext_wrapper.cpp ${CMAKE_CURRENT_BINARY_DIR}/PySide/QtDeclarative/qdeclarativeengine_wrapper.cpp @@ -50,12 +49,13 @@ set(QtDeclarative_libraries pyside ${QT_QTDECLARATIVE_LIBRARY}) set(QtDeclarative_deps QtGui QtNetwork) - +set(QtDeclarative_registerType "${CMAKE_CURRENT_SOURCE_DIR}/pysideqmlregistertype.cpp") create_pyside_module(QtDeclarative QtDeclarative_include_dirs QtDeclarative_libraries QtDeclarative_deps QtDeclarative_typesystem_path QtDeclarative_SRC - "") + "" + QtDeclarative_registerType) From edf5b58da83696ad908ac21b18bdd9a343d842ee Mon Sep 17 00:00:00 2001 From: Marcelo Lira Date: Fri, 3 Dec 2010 17:07:11 -0300 Subject: [PATCH 013/703] Added QRegExp.replace(QString, const char*) method. The only way to search and replace using QRegExp is using the QString::replace method. Since QString was removed, QRegExp now is useful only to search stuff, but not replace. For this purpose the QRegExp.replace method was added. The first argument is the string that will be operated over, the second argument contains the replacement, and the return value is a new modified Python string. Unit tests and documentation for QRegExp.replace were added as well. Reviewed by Hugo Parente Reviewed by Luciano Wolf --- PySide/QtCore/typesystem_core.xml | 35 +++++++++++++++++++++++++++++++ tests/QtCore/CMakeLists.txt | 1 + tests/QtCore/qregexp_test.py | 20 ++++++++++++++++++ 3 files changed, 56 insertions(+) create mode 100644 tests/QtCore/qregexp_test.py diff --git a/PySide/QtCore/typesystem_core.xml b/PySide/QtCore/typesystem_core.xml index 6da4f64..5ed694c 100644 --- a/PySide/QtCore/typesystem_core.xml +++ b/PySide/QtCore/typesystem_core.xml @@ -1390,6 +1390,41 @@ + + + + + + + + + Replaces every occurrence of the regular expression in *sourceString* with *after*. + Returns a new Python string with the modified contents. For example: + + :: + + s = "Banana" + re = QRegExp("a[mn]") + s = re.replace(s, "ox") + # s == "Boxoxa" + + + For regular expressions containing capturing parentheses, occurrences of \1, \2, ..., in *after* + are replaced with rx.cap(1), cap(2), ... + + :: + + t = "A <i>bon mot</i>." + re = QRegExp("<i>([^<]*)</i>") + t = re.replace(t, "\\emph{\\1}") + # t == "A \\emph{bon mot}." + + + + %1.replace(*%CPPSELF, %2); + %PYARG_0 = %CONVERTTOPYTHON[QString](%1); + + diff --git a/tests/QtCore/CMakeLists.txt b/tests/QtCore/CMakeLists.txt index b73a1ba..40b8386 100644 --- a/tests/QtCore/CMakeLists.txt +++ b/tests/QtCore/CMakeLists.txt @@ -49,6 +49,7 @@ PYSIDE_TEST(qobject_tr_as_instance_test.py) PYSIDE_TEST(qpoint_test.py) PYSIDE_TEST(qprocess_test.py) PYSIDE_TEST(qrect_test.py) +PYSIDE_TEST(qregexp_test.py) PYSIDE_TEST(qresource_test.py) PYSIDE_TEST(qsize_test.py) PYSIDE_TEST(qslot_object_test.py) diff --git a/tests/QtCore/qregexp_test.py b/tests/QtCore/qregexp_test.py new file mode 100644 index 0000000..5499185 --- /dev/null +++ b/tests/QtCore/qregexp_test.py @@ -0,0 +1,20 @@ +#!/usr/bin/python + +import unittest +from PySide.QtCore import QRegExp + +class QRegExpTest(unittest.TestCase): + + def testReplace1(self): + re = QRegExp('a[mn]') + string = re.replace('Banana', 'ox') + self.assertEqual(string, 'Boxoxa') + + def testReplace2(self): + re = QRegExp('([^<]*)') + string = re.replace('A bon mot.', '\\emph{\\1}') + self.assertEqual(string, 'A \\emph{bon mot}.') + +if __name__ == '__main__': + unittest.main() + From f5f2b23a70bb4dbd590cd24f28c0f5740e0f9ef6 Mon Sep 17 00:00:00 2001 From: Marcelo Lira Date: Mon, 6 Dec 2010 15:30:53 -0300 Subject: [PATCH 014/703] Fixes QImage constructor signature that used string buffer as image data source. The fixes uses the patch provided by Pieter Palmers on the bug #489 description[1]. A very simple test, to check the signature existence, was added. [1] http://bugs.openbossa.org/show_bug.cgi?id=489 Reviewed by Hugo Parente Reviewed by Luciano Wolf --- PySide/QtGui/typesystem_gui_common.xml | 30 ++++++++++++++++++++------ tests/QtGui/CMakeLists.txt | 1 + tests/QtGui/qimage_test.py | 20 +++++++++++++++++ 3 files changed, 45 insertions(+), 6 deletions(-) create mode 100644 tests/QtGui/qimage_test.py diff --git a/PySide/QtGui/typesystem_gui_common.xml b/PySide/QtGui/typesystem_gui_common.xml index cf4b674..485d542 100644 --- a/PySide/QtGui/typesystem_gui_common.xml +++ b/PySide/QtGui/typesystem_gui_common.xml @@ -665,11 +665,33 @@ - + + + + + + + + + + + + - + + + + + + + + + + @@ -678,10 +700,6 @@ - - - - diff --git a/tests/QtGui/CMakeLists.txt b/tests/QtGui/CMakeLists.txt index 2ad8269..49e9f5a 100644 --- a/tests/QtGui/CMakeLists.txt +++ b/tests/QtGui/CMakeLists.txt @@ -43,6 +43,7 @@ PYSIDE_TEST(qgraphicsitem_isblocked_test.py) PYSIDE_TEST(qgraphicsitem_test.py) PYSIDE_TEST(qgraphicsproxywidget_test.py) PYSIDE_TEST(qgraphicsscene_test.py) +PYSIDE_TEST(qimage_test.py) PYSIDE_TEST(qinputdialog_get_test.py) PYSIDE_TEST(qitemselection_test.py) PYSIDE_TEST(qlayout_ref_test.py) diff --git a/tests/QtGui/qimage_test.py b/tests/QtGui/qimage_test.py new file mode 100644 index 0000000..d8aa545 --- /dev/null +++ b/tests/QtGui/qimage_test.py @@ -0,0 +1,20 @@ + +'''Test cases for QImage''' + +import unittest + +from PySide.QtGui import QImage + +from helper import UsesQApplication + +class QImageTest(UsesQApplication): + '''Test case for calling setPixel with float as argument''' + + def testQImageStringBuffer(self): + '''Test if the QImage signatures receiving string buffers exist.''' + img0 = QImage('', 100, 100, QImage.Format_ARGB32) + img1 = QImage('', 100, 100, 0, QImage.Format_ARGB32) + +if __name__ == '__main__': + unittest.main() + From e76fffc6173a43189b6133873fcc8e310bf6aa48 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Wed, 8 Dec 2010 14:54:21 -0200 Subject: [PATCH 015/703] Fix copyright year. --- PySide/QtDeclarative/pysideqmlregistertype.cpp | 2 +- PySide/QtDeclarative/pysideqmlregistertype.h | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/PySide/QtDeclarative/pysideqmlregistertype.cpp b/PySide/QtDeclarative/pysideqmlregistertype.cpp index 8980aa6..e15379b 100644 --- a/PySide/QtDeclarative/pysideqmlregistertype.cpp +++ b/PySide/QtDeclarative/pysideqmlregistertype.cpp @@ -1,7 +1,7 @@ /* * This file is part of the Shiboken Python Bindings Generator project. * - * Copyright (C) 2009-2010 Nokia Corporation and/or its subsidiary(-ies). + * Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies). * * Contact: PySide team * diff --git a/PySide/QtDeclarative/pysideqmlregistertype.h b/PySide/QtDeclarative/pysideqmlregistertype.h index 3f83b29..11a5a9a 100644 --- a/PySide/QtDeclarative/pysideqmlregistertype.h +++ b/PySide/QtDeclarative/pysideqmlregistertype.h @@ -1,7 +1,7 @@ /* * This file is part of the Shiboken Python Bindings Generator project. * - * Copyright (C) 2009-2010 Nokia Corporation and/or its subsidiary(-ies). + * Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies). * * Contact: PySide team * From b4d1a3a4b616dffcd41247dc5584846372083db6 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Wed, 8 Dec 2010 15:06:52 -0200 Subject: [PATCH 016/703] Add support for extension into PySide properties. This is used by PySide implementation of QDeclarativeListProperty. --- libpyside/dynamicqmetaobject.cpp | 12 ++-- libpyside/pyside.cpp | 2 +- libpyside/pysideproperty.cpp | 105 +++++++++++++++++++++++++------ libpyside/pysideproperty.h | 10 +++ libpyside/pysideproperty_p.h | 4 ++ libpyside/signalmanager.cpp | 31 +-------- 6 files changed, 109 insertions(+), 55 deletions(-) diff --git a/libpyside/dynamicqmetaobject.cpp b/libpyside/dynamicqmetaobject.cpp index 1f6ff85..4c21a44 100644 --- a/libpyside/dynamicqmetaobject.cpp +++ b/libpyside/dynamicqmetaobject.cpp @@ -367,12 +367,14 @@ void DynamicQMetaObject::addProperty(const char* propertyName, PyObject* data) return; // retrieve notifyId - PySideProperty* property = reinterpret_cast(data); - const char* signalNotify = PySide::Property::getNotifyName(property); int notifyId = -1; - if (signalNotify) { - QByteArray signalSignature(signalNotify); - notifyId = m_d->m_signals.indexOf(signalNotify); + PySideProperty* property = reinterpret_cast(data); + if (property->d->notify) { + const char* signalNotify = PySide::Property::getNotifyName(property); + if (signalNotify) { + QByteArray signalSignature(signalNotify); + notifyId = m_d->m_signals.indexOf(signalNotify); + } } //search for a empty space diff --git a/libpyside/pyside.cpp b/libpyside/pyside.cpp index 79b4f4c..7442cfc 100644 --- a/libpyside/pyside.cpp +++ b/libpyside/pyside.cpp @@ -186,7 +186,7 @@ void initQObjectSubType(SbkObjectType* type, PyObject* args, PyObject* kwds) Shiboken::AutoDecRef slotAttrName(PyString_FromString(PYSIDE_SLOT_LIST_ATTR)); while (PyDict_Next(attrs, &pos, &key, &value)) { - if (value->ob_type == &PySidePropertyType) { + if (PyType_IsSubtype(value->ob_type, &PySidePropertyType)) { // Leave the properties to be register after signals because they may depend on notify signals properties << PropPair(PyString_AS_STRING(key), value); } else if (value->ob_type == &PySideSignalType) { // Register signals diff --git a/libpyside/pysideproperty.cpp b/libpyside/pysideproperty.cpp index dd5ca37..839e55f 100644 --- a/libpyside/pysideproperty.cpp +++ b/libpyside/pysideproperty.cpp @@ -36,6 +36,7 @@ extern "C" { +static PyObject* qpropertyTpNew(PyTypeObject* subtype, PyObject* args, PyObject* kwds); static int qpropertyTpInit(PyObject*, PyObject*, PyObject*); static void qpropertyFree(void*); @@ -78,7 +79,7 @@ PyTypeObject PySidePropertyType = { 0, /*tp_dictoffset */ qpropertyTpInit, /*tp_init */ 0, /*tp_alloc */ - PyType_GenericNew, /*tp_new */ + qpropertyTpNew, /*tp_new */ qpropertyFree, /*tp_free */ 0, /*tp_is_gc */ 0, /*tp_bases */ @@ -89,25 +90,70 @@ PyTypeObject PySidePropertyType = { 0, /*tp_del */ }; +static void qpropertyMetaCall(PySideProperty* pp, PyObject* self, QMetaObject::Call call, void** args) +{ + Shiboken::TypeResolver* typeResolver = Shiboken::TypeResolver::get(pp->d->typeName); + Q_ASSERT(typeResolver); + + switch(call) { + case QMetaObject::ReadProperty: + { + Shiboken::GilState gil; + PyObject* value = PySide::Property::getValue(pp, self); + if (value) { + typeResolver->toCpp(value, &args[0]); + Py_DECREF(value); + } else if (PyErr_Occurred()) { + PyErr_Print(); // Clear any errors but print them to stderr + } + break; + } + + case QMetaObject::WriteProperty: + { + Shiboken::GilState gil; + Shiboken::AutoDecRef value(typeResolver->toPython(args[0])); + PySide::Property::setValue(pp, self, value); + break; + } + + case QMetaObject::ResetProperty: + { + Shiboken::GilState gil; + PySide::Property::reset(pp, self); + break; + } + + case QMetaObject::QueryPropertyDesignable: + case QMetaObject::QueryPropertyScriptable: + case QMetaObject::QueryPropertyStored: + case QMetaObject::QueryPropertyEditable: + case QMetaObject::QueryPropertyUser: + // just to avoid gcc warnings + case QMetaObject::InvokeMetaMethod: + case QMetaObject::CreateInstance: + break; + } +} + +static PyObject* qpropertyTpNew(PyTypeObject* subtype, PyObject* args, PyObject* kwds) +{ + PySideProperty* me = reinterpret_cast(subtype->tp_alloc(subtype, 0)); + me->d = new PySidePropertyPrivate; + memset(me->d, 0, sizeof(PySidePropertyPrivate)); + PySidePropertyPrivate* pData = me->d; + pData->designable = true; + pData->scriptable = true; + pData->stored = true; + return (PyObject*) me; +} + int qpropertyTpInit(PyObject* self, PyObject* args, PyObject* kwds) { PyObject* type = 0; PySideProperty* data = reinterpret_cast(self); - PySidePropertyPrivate* pData = (PySidePropertyPrivate*) malloc(sizeof(PySidePropertyPrivate)); - data->d = pData; - pData->fset = 0; - pData->fget = 0; - pData->freset = 0; - pData->fdel = 0; - pData->final = 0; - pData->designable = true; - pData->scriptable = true; - pData->stored = true; - pData->typeName = 0; - pData->doc = 0; - pData->notify = 0; - pData->notifySignature = 0; - pData->constant = 0; + PySidePropertyPrivate* pData = data->d; + pData->metaCallHandler = &qpropertyMetaCall; static const char *kwlist[] = {"type", "fget", "fset", "freset", "fdel", "doc", "notify", "designable", "scriptable", "stored", "user", @@ -119,7 +165,6 @@ int qpropertyTpInit(PyObject* self, PyObject* args, PyObject* kwds) /*s*/ &(pData->doc), /*O*/ &(pData->notify), /*bbbbbb*/ &(pData->designable), &(pData->scriptable), &(pData->stored), &(pData->user), &(pData->constant), &(pData->final))) { - free(pData); return 0; } @@ -141,7 +186,7 @@ void qpropertyFree(void *self) free(data->d->typeName); free(data->d->doc); free(data->d->notifySignature); - free(data->d); + delete data->d; pySelf->ob_type->tp_base->tp_free(self); } @@ -163,7 +208,7 @@ void init(PyObject* module) bool isPropertyType(PyObject* pyObj) { if (pyObj) { - return pyObj->ob_type == &PySidePropertyType; + return PyType_IsSubtype(pyObj->ob_type, &PySidePropertyType); } return false; } @@ -231,7 +276,7 @@ PySideProperty* getObject(PyObject* source, PyObject* name) bool isReadable(const PySideProperty* self) { - return (self->d->fget != 0); + return true; } bool isWritable(const PySideProperty* self) @@ -285,5 +330,25 @@ const char* getNotifyName(PySideProperty* self) return self->d->notifySignature; } +void setMetaCallHandler(PySideProperty* self, MetaCallHandler handler) +{ + self->d->metaCallHandler = handler; +} + +void setTypeName(PySideProperty* self, const char* typeName) +{ + self->d->typeName = strdup(typeName); +} + +void setUserData(PySideProperty* self, void* data) +{ + self->d->userData = data; +} + +void* userData(PySideProperty* self) +{ + return self->d->userData; +} + } //namespace Property } //namespace PySide diff --git a/libpyside/pysideproperty.h b/libpyside/pysideproperty.h index f137e80..b5bad18 100644 --- a/libpyside/pysideproperty.h +++ b/libpyside/pysideproperty.h @@ -41,6 +41,9 @@ extern "C" namespace PySide { namespace Property { +typedef void (*MetaCallHandler)(PySideProperty*,PyObject*,QMetaObject::Call, void**); + + PYSIDE_API bool isPropertyType(PyObject* pyObj); /** @@ -82,6 +85,13 @@ PYSIDE_API const char* getNotifyName(PySideProperty* self); **/ PYSIDE_API PySideProperty* getObject(PyObject* source, PyObject* name); +PYSIDE_API void setMetaCallHandler(PySideProperty* self, MetaCallHandler handler); + +PYSIDE_API void setTypeName(PySideProperty* self, const char* typeName); + +PYSIDE_API void setUserData(PySideProperty* self, void* data); +PYSIDE_API void* userData(PySideProperty* self); + } //namespace Property } //namespace PySide diff --git a/libpyside/pysideproperty_p.h b/libpyside/pysideproperty_p.h index 9c6893b..7731f3e 100644 --- a/libpyside/pysideproperty_p.h +++ b/libpyside/pysideproperty_p.h @@ -24,6 +24,8 @@ #define PYSIDE_QPROPERTY_P_H #include +#include +#include "pysideproperty.h" struct PySideProperty; @@ -33,6 +35,7 @@ extern "C" struct PySidePropertyPrivate { char* typeName; PyObject* type; + PySide::Property::MetaCallHandler metaCallHandler; PyObject* fget; PyObject* fset; PyObject* freset; @@ -46,6 +49,7 @@ struct PySidePropertyPrivate { bool user; bool constant; bool final; + void* userData; }; } // extern "C" diff --git a/libpyside/signalmanager.cpp b/libpyside/signalmanager.cpp index 5ff62be..31621a7 100644 --- a/libpyside/signalmanager.cpp +++ b/libpyside/signalmanager.cpp @@ -248,7 +248,6 @@ int SignalManager::qt_metacall(QObject* object, QMetaObject::Call call, int id, PySideProperty* pp = 0; PyObject* pp_name = 0; QMetaProperty mp; - Shiboken::TypeResolver* typeResolver = 0; PyObject* pySelf = 0; if (call != QMetaObject::InvokeMetaMethod) { @@ -262,49 +261,23 @@ int SignalManager::qt_metacall(QObject* object, QMetaObject::Call call, int id, pp_name = PyString_FromString(mp.name()); pp = Property::getObject(pySelf, pp_name); if (!pp) { - qWarning("Invalid property."); + qWarning("Invalid property: %s.", mp.name()); Py_XDECREF(pp_name); return id - metaObject->methodCount(); } - typeResolver = Shiboken::TypeResolver::get(mp.typeName()); - Q_ASSERT(typeResolver); } switch(call) { #ifndef QT_NO_PROPERTIES case QMetaObject::ReadProperty: - { - Shiboken::GilState gil; - PyObject* value = Property::getValue(pp, pySelf); - if (value) { - typeResolver->toCpp(value, &args[0]); - Py_DECREF(value); - } else if (PyErr_Occurred()) { - PyErr_Print(); // Clear any errors but print them to stderr - } - break; - } - case QMetaObject::WriteProperty: - { - Shiboken::GilState gil; - Shiboken::AutoDecRef value(typeResolver->toPython(args[0])); - Property::setValue(pp, pySelf, value); - break; - } - case QMetaObject::ResetProperty: - { - Shiboken::GilState gil; - Property::reset(pp, pp_name); - break; - } - case QMetaObject::QueryPropertyDesignable: case QMetaObject::QueryPropertyScriptable: case QMetaObject::QueryPropertyStored: case QMetaObject::QueryPropertyEditable: case QMetaObject::QueryPropertyUser: + pp->d->metaCallHandler(pp, pySelf, call, args); break; #endif case QMetaObject::InvokeMetaMethod: From 621275639b45b36e64ad9a594be133fc9043c044 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Wed, 8 Dec 2010 15:15:29 -0200 Subject: [PATCH 017/703] Replace useless check by a assert. QMetaObject must already be ready at this point. --- PySide/QtDeclarative/pysideqmlregistertype.cpp | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/PySide/QtDeclarative/pysideqmlregistertype.cpp b/PySide/QtDeclarative/pysideqmlregistertype.cpp index e15379b..5a51706 100644 --- a/PySide/QtDeclarative/pysideqmlregistertype.cpp +++ b/PySide/QtDeclarative/pysideqmlregistertype.cpp @@ -105,10 +105,7 @@ int PySide::qmlRegisterType(PyObject* pyObj, const char* uri, int versionMajor, } QMetaObject* metaObject = reinterpret_cast(ObjectType::getTypeUserData(reinterpret_cast(pyObj))); - if (!metaObject) { - PyErr_SetString(PyExc_TypeError, "FIXME: metaobject not initialized, this error msg should not exists at all!!"); - return -1; - } + Q_ASSERT(metaObject); // All ready... now the ugly code begins... :-) pyTypes[nextType] = pyObj; From 8252145146de231387173d9b7beac284159f4b61 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Wed, 8 Dec 2010 16:35:45 -0200 Subject: [PATCH 018/703] Remove unused field "type" from PySideProperty private struct. --- libpyside/pysideproperty_p.h | 1 - 1 file changed, 1 deletion(-) diff --git a/libpyside/pysideproperty_p.h b/libpyside/pysideproperty_p.h index 7731f3e..5cef5da 100644 --- a/libpyside/pysideproperty_p.h +++ b/libpyside/pysideproperty_p.h @@ -34,7 +34,6 @@ extern "C" struct PySidePropertyPrivate { char* typeName; - PyObject* type; PySide::Property::MetaCallHandler metaCallHandler; PyObject* fget; PyObject* fset; From 3df02f96815b2183ff9b49db6e46db7700d5bc1e Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Wed, 8 Dec 2010 16:52:23 -0200 Subject: [PATCH 019/703] Add support for QML list properties. Reviewer: Marcelo Lira Luciano Wolf --- .../QtDeclarative/pysideqmlregistertype.cpp | 212 +++++++++++++++++- PySide/QtDeclarative/pysideqmlregistertype.h | 23 +- .../QtDeclarative/typesystem_declarative.xml | 4 +- 3 files changed, 228 insertions(+), 11 deletions(-) diff --git a/PySide/QtDeclarative/pysideqmlregistertype.cpp b/PySide/QtDeclarative/pysideqmlregistertype.cpp index 5a51706..362e56d 100644 --- a/PySide/QtDeclarative/pysideqmlregistertype.cpp +++ b/PySide/QtDeclarative/pysideqmlregistertype.cpp @@ -21,19 +21,32 @@ */ #include "pysideqmlregistertype.h" -#include +// Qt #include #include #include +// shiboken #include -#include "qdeclarativeitem_wrapper.h" #include +// pyside +#include +#include +#include + +// auto generated headers +#include "qdeclarativeitem_wrapper.h" +#include "pyside_qtcore_python.h" +#include "pyside_qtdeclarative_python.h" #ifndef PYSIDE_MAX_QML_TYPES // Maximum number of different types the user cna export to QML using qmlRegisterType. #define PYSIDE_MAX_QML_TYPES 50 #endif +// Forward declarations +static void propListMetaCall(PySideProperty* pp, PyObject* self, QMetaObject::Call call, void** args); + + // All registered python types static PyObject* pyTypes[PYSIDE_MAX_QML_TYPES]; static void (*createFuncs[PYSIDE_MAX_QML_TYPES])(void*); @@ -76,11 +89,6 @@ struct ElementFactory<0> : ElementFactoryBase<0> } }; -void PySide::initQmlSupport() -{ - ElementFactory::init(); -} - int PySide::qmlRegisterType(PyObject* pyObj, const char* uri, int versionMajor, int versionMinor, const char* qmlName) { using namespace Shiboken; @@ -138,3 +146,193 @@ int PySide::qmlRegisterType(PyObject* pyObj, const char* uri, int versionMajor, ++nextType; return qmlTypeId; } + +extern "C" +{ + +// This is the user data we store in the property. +struct DeclarativeListProperty +{ + PyTypeObject* type; + PyObject* append; + PyObject* at; + PyObject* clear; + PyObject* count; +}; + +static int propListTpInit(PyObject* self, PyObject* args, PyObject* kwds) +{ + static const char *kwlist[] = {"type", "append", "at", "clear", "count", 0}; + PySideProperty* pySelf = reinterpret_cast(self); + DeclarativeListProperty* data = new DeclarativeListProperty; + memset(data, 0, sizeof(DeclarativeListProperty)); + + if (!PyArg_ParseTupleAndKeywords(args, kwds, + "OO|OOO:QtDeclarative.ListProperty", (char**) kwlist, + &data->type, + &data->append, + &data->at, + &data->clear, + &data->count)) { + return 0; + } + PySide::Property::setMetaCallHandler(pySelf, &propListMetaCall); + PySide::Property::setTypeName(pySelf, "QDeclarativeListProperty"); + PySide::Property::setUserData(pySelf, data); + + return 1; +} + +void propListTpFree(void* self) +{ + PySideProperty* pySelf = reinterpret_cast(self); + delete reinterpret_cast(PySide::Property::userData(pySelf)); + // calls base type constructor + pySelf->ob_type->tp_base->tp_free(self); +} + +PyTypeObject PropertyListType = { + PyObject_HEAD_INIT(0) + 0, /*ob_size*/ + "ListProperty", /*tp_name*/ + sizeof(PySideProperty), /*tp_basicsize*/ + 0, /*tp_itemsize*/ + 0, /*tp_dealloc*/ + 0, /*tp_print*/ + 0, /*tp_getattr*/ + 0, /*tp_setattr*/ + 0, /*tp_compare*/ + 0, /*tp_repr*/ + 0, /*tp_as_number*/ + 0, /*tp_as_sequence*/ + 0, /*tp_as_mapping*/ + 0, /*tp_hash */ + 0, /*tp_call*/ + 0, /*tp_str*/ + 0, /*tp_getattro*/ + 0, /*tp_setattro*/ + 0, /*tp_as_buffer*/ + Py_TPFLAGS_DEFAULT, /*tp_flags*/ + 0, /*tp_doc */ + 0, /*tp_traverse */ + 0, /*tp_clear */ + 0, /*tp_richcompare */ + 0, /*tp_weaklistoffset */ + 0, /*tp_iter */ + 0, /*tp_iternext */ + 0, /*tp_methods */ + 0, /*tp_members */ + 0, /*tp_getset */ + &PySidePropertyType, /*tp_base */ + 0, /*tp_dict */ + 0, /*tp_descr_get */ + 0, /*tp_descr_set */ + 0, /*tp_dictoffset */ + propListTpInit, /*tp_init */ + 0, /*tp_alloc */ + 0, /*tp_new */ + propListTpFree, /*tp_free */ + 0, /*tp_is_gc */ + 0, /*tp_bases */ + 0, /*tp_mro */ + 0, /*tp_cache */ + 0, /*tp_subclasses */ + 0, /*tp_weaklist */ + 0, /*tp_del */ +}; + +} // extern "C" + +// Implementation of QDeclarativeListProperty::AppendFunction callback +void propListAppender(QDeclarativeListProperty* propList, QDeclarativeItem* item) +{ + Shiboken::AutoDecRef args(Shiboken::makeTuple(propList->object, item)); + + DeclarativeListProperty* data = reinterpret_cast(propList->data); + Shiboken::AutoDecRef retVal(PyObject_CallObject(data->append, args)); + + if (PyErr_Occurred()) + PyErr_Print(); +} + +// Implementation of QDeclarativeListProperty::CountFunction callback +int propListCount(QDeclarativeListProperty* propList) +{ + Shiboken::AutoDecRef args(Shiboken::makeTuple(propList->object)); + + DeclarativeListProperty* data = reinterpret_cast(propList->data); + Shiboken::AutoDecRef retVal(PyObject_CallObject(data->count, args)); + + // Check return type + if (PyErr_Occurred()) + PyErr_Print(); + else if (Shiboken::Converter::isConvertible(retVal)) + return Shiboken::Converter::toCpp(retVal); + + return 0; +} + +// Implementation of QDeclarativeListProperty::AtFunction callback +QDeclarativeItem* propListAt(QDeclarativeListProperty* propList, int index) +{ + Shiboken::AutoDecRef args(Shiboken::makeTuple(propList->object, index)); + + DeclarativeListProperty* data = reinterpret_cast(propList->data); + Shiboken::AutoDecRef retVal(PyObject_CallObject(data->at, args)); + + if (PyErr_Occurred()) + PyErr_Print(); + else if (PyType_IsSubtype(Py_TYPE(retVal), data->type)) + return Shiboken::Converter::toCpp(retVal); + + return 0; +} + +// Implementation of QDeclarativeListProperty::ClearFunction callback +void propListClear(QDeclarativeListProperty* propList) +{ + Shiboken::AutoDecRef args(Shiboken::makeTuple(propList->object)); + + DeclarativeListProperty* data = reinterpret_cast(propList->data); + Shiboken::AutoDecRef retVal(PyObject_CallObject(data->clear, args)); + + if (PyErr_Occurred()) + PyErr_Print(); +} + +// qt_metacall specialization for ListProperties +static void propListMetaCall(PySideProperty* pp, PyObject* self, QMetaObject::Call call, void** args) +{ + if (call != QMetaObject::ReadProperty) + return; + + DeclarativeListProperty* data = reinterpret_cast(PySide::Property::userData(pp)); + QDeclarativeListProperty declProp(Shiboken::Converter::toCpp(self), data, &propListAppender); + + if (data->count) + declProp.count = &propListCount; + if (data->at) + declProp.at = &propListAt; + if (data->clear) + declProp.clear = &propListClear; + + // Copy the data to the memory location requested by the meta call + void* v = args[0]; + *reinterpret_cast*>(v) = declProp; +} + + +void PySide::initQmlSupport(PyObject* module) +{ + ElementFactory::init(); + + // Export DeclarativeListProperty type + if (PyType_Ready(&PropertyListType) < 0) + return; + + Py_INCREF((PyObject*)&PropertyListType); + PyModule_AddObject(module, PropertyListType.tp_name, (PyObject*)&PropertyListType); + +} + + diff --git a/PySide/QtDeclarative/pysideqmlregistertype.h b/PySide/QtDeclarative/pysideqmlregistertype.h index 11a5a9a..aa25200 100644 --- a/PySide/QtDeclarative/pysideqmlregistertype.h +++ b/PySide/QtDeclarative/pysideqmlregistertype.h @@ -23,14 +23,33 @@ #ifndef PYSIDEQMLREGISTERTYPE_H #define PYSIDEQMLREGISTERTYPE_H -#include +#include + +struct SbkObjectType; namespace PySide { extern void* nextQmlElementMemoryAddr; -void initQmlSupport(); +/** + * Init the QML support doign things like registering QtDeclarative.ListProperty and create the necessary stuff for + * qmlRegisterType. + * + * \param module QtDeclarative python module + */ +void initQmlSupport(PyObject* module); + +/** + * PySide implementation of qmlRegisterType function. + * + * \param pyObj Python type to be registered. + * \param uri QML element uri. + * \param versionMajor QML component major version. + * \param versionMinor QML component minor version. + * \param qmlName QML element name + * \return the metatype id of the registered type. + */ int qmlRegisterType(PyObject* pyObj, const char* uri, int versionMajor, int versionMinor, const char* qmlName); } diff --git a/PySide/QtDeclarative/typesystem_declarative.xml b/PySide/QtDeclarative/typesystem_declarative.xml index cc66602..d1424ab 100644 --- a/PySide/QtDeclarative/typesystem_declarative.xml +++ b/PySide/QtDeclarative/typesystem_declarative.xml @@ -58,9 +58,9 @@ - + Shiboken::TypeResolver::createValueTypeResolver< QList<QObject*> >("QList<QObject*>"); - PySide::initQmlSupport(); + PySide::initQmlSupport(module); From a6955f9fed375c78d34de53ab00169257c61c114 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Thu, 9 Dec 2010 15:28:01 -0200 Subject: [PATCH 020/703] Changed file permissions to 0644. --- tests/QtDeclarative/bug_451.py | 0 tests/QtDeclarative/bug_456.py | 0 tests/QtDeclarative/connect_python_qml.py | 0 3 files changed, 0 insertions(+), 0 deletions(-) mode change 100755 => 100644 tests/QtDeclarative/bug_451.py mode change 100755 => 100644 tests/QtDeclarative/bug_456.py mode change 100755 => 100644 tests/QtDeclarative/connect_python_qml.py diff --git a/tests/QtDeclarative/bug_451.py b/tests/QtDeclarative/bug_451.py old mode 100755 new mode 100644 diff --git a/tests/QtDeclarative/bug_456.py b/tests/QtDeclarative/bug_456.py old mode 100755 new mode 100644 diff --git a/tests/QtDeclarative/connect_python_qml.py b/tests/QtDeclarative/connect_python_qml.py old mode 100755 new mode 100644 From 94d8426d1c47d6e761f07073b7e7c5960da9497e Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Thu, 9 Dec 2010 16:03:03 -0200 Subject: [PATCH 021/703] Add tests for qmlregisterType function and qml list properties. Reviewer: Marcelo Lira Luciano Wolf --- tests/QtDeclarative/CMakeLists.txt | 1 + tests/QtDeclarative/registertype.py | 92 ++++++++++++++++++++++++++++ tests/QtDeclarative/registertype.qml | 29 +++++++++ 3 files changed, 122 insertions(+) create mode 100644 tests/QtDeclarative/registertype.py create mode 100644 tests/QtDeclarative/registertype.qml diff --git a/tests/QtDeclarative/CMakeLists.txt b/tests/QtDeclarative/CMakeLists.txt index 5ceba42..5cd53e9 100644 --- a/tests/QtDeclarative/CMakeLists.txt +++ b/tests/QtDeclarative/CMakeLists.txt @@ -3,3 +3,4 @@ PYSIDE_TEST(bug_456.py) PYSIDE_TEST(qdeclarativenetwork_test.py) PYSIDE_TEST(qdeclarativeview_test.py) PYSIDE_TEST(connect_python_qml.py) +PYSIDE_TEST(registertype.py) diff --git a/tests/QtDeclarative/registertype.py b/tests/QtDeclarative/registertype.py new file mode 100644 index 0000000..434dac1 --- /dev/null +++ b/tests/QtDeclarative/registertype.py @@ -0,0 +1,92 @@ + +import sys +import unittest +import helper +from PySide.QtCore import * +from PySide.QtGui import * +from PySide.QtDeclarative import * + +class PieSlice (QDeclarativeItem): + + def __init__(self, parent = None): + QDeclarativeItem.__init__(self, parent) + # need to disable this flag to draw inside a QDeclarativeItem + self.setFlag(QGraphicsItem.ItemHasNoContents, False) + self._color = QColor() + self._fromAngle = 0 + self._angleSpan = 0 + + def getColor(self): + return self._color + + def setColor(self, value): + self._color = value + + def getFromAngle(self): + return self._angle + + def setFromAngle(self, value): + self._fromAngle = value + + def getAngleSpan(self): + return self._angleSpan + + def setAngleSpan(self, value): + self._angleSpan = value + + color = Property(QColor, getColor, setColor) + fromAngle = Property(int, getFromAngle, setFromAngle) + angleSpan = Property(int, getAngleSpan, setAngleSpan) + + def paint(self, painter, options, widget): + global paintCalled + pen = QPen(self._color, 2) + painter.setPen(pen); + painter.setRenderHints(QPainter.Antialiasing, True); + painter.drawPie(self.boundingRect(), self._fromAngle * 16, self._angleSpan * 16); + paintCalled = True + +class PieChart (QDeclarativeItem): + + def __init__(self, parent = None): + QDeclarativeItem.__init__(self, parent) + self._name = u'' + self._slices = [] + + def getName(self): + return self._name + + def setName(self, value): + self._name = value + + name = Property(unicode, getName, setName) + + def appendSlice(self, _slice): + global appendCalled + _slice.setParentItem(self) + self._slices.append(_slice) + appendCalled = True + + slices = ListProperty(PieSlice, append=appendSlice) + +appendCalled = False +paintCalled = False + +class TestQmlSupport(unittest.TestCase): + + def testIt(self): + app = QApplication([]) + + qmlRegisterType(PieChart, 'Charts', 1, 0, 'PieChart'); + qmlRegisterType(PieSlice, "Charts", 1, 0, "PieSlice"); + + view = QDeclarativeView() + view.setSource(QUrl.fromLocalFile(helper.adjust_filename('registertype.qml', __file__))) + view.show() + QTimer.singleShot(250, view.close) + app.exec_() + self.assertTrue(appendCalled) + self.assertTrue(paintCalled) + +if __name__ == '__main__': + unittest.main() diff --git a/tests/QtDeclarative/registertype.qml b/tests/QtDeclarative/registertype.qml new file mode 100644 index 0000000..fce15da --- /dev/null +++ b/tests/QtDeclarative/registertype.qml @@ -0,0 +1,29 @@ +import Charts 1.0 +import QtQuick 1.0 + +Item { + width: 300; height: 200 + + PieChart { + anchors.centerIn: parent + width: 100; height: 100 + + slices: [ + PieSlice { + anchors.fill: parent + color: "red" + fromAngle: 0; angleSpan: 110 + }, + PieSlice { + anchors.fill: parent + color: "black" + fromAngle: 110; angleSpan: 50 + }, + PieSlice { + anchors.fill: parent + color: "blue" + fromAngle: 160; angleSpan: 100 + } + ] + } +} From 02e4fa2b963b35d3a5cd737e3887938afb6da1e7 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Thu, 9 Dec 2010 16:13:39 -0200 Subject: [PATCH 022/703] Added unit test for bug#500 Reviewer: Lauro Mora Marcelo Lira --- tests/QtGui/CMakeLists.txt | 1 + tests/QtGui/bug_500.py | 15 +++++++++++++++ 2 files changed, 16 insertions(+) create mode 100644 tests/QtGui/bug_500.py diff --git a/tests/QtGui/CMakeLists.txt b/tests/QtGui/CMakeLists.txt index 49e9f5a..df81b3d 100644 --- a/tests/QtGui/CMakeLists.txt +++ b/tests/QtGui/CMakeLists.txt @@ -18,6 +18,7 @@ PYSIDE_TEST(bug_430.py) PYSIDE_TEST(bug_433.py) PYSIDE_TEST(bug_467.py) PYSIDE_TEST(bug_480.py) +PYSIDE_TEST(bug_500.py) PYSIDE_TEST(customproxywidget_test.py) PYSIDE_TEST(deepcopy_test.py) PYSIDE_TEST(float_to_int_implicit_conversion_test.py) diff --git a/tests/QtGui/bug_500.py b/tests/QtGui/bug_500.py new file mode 100644 index 0000000..8611495 --- /dev/null +++ b/tests/QtGui/bug_500.py @@ -0,0 +1,15 @@ +#!/usr/bin/python + +import unittest + +from PySide.QtCore import * +from PySide.QtGui import * +from helper import UsesQApplication + +class NeverDiesTest(UsesQApplication): + + def testIt(self): + QPrintDialog() + +if __name__ == "__main__": + unittest.main() From ee8d6262dcceb4d594a01623c947e9186e985221 Mon Sep 17 00:00:00 2001 From: Marcelo Lira Date: Mon, 13 Dec 2010 15:19:57 -0300 Subject: [PATCH 023/703] Fixed new style signal connection tests for the proper semantics. One example to clarify: for the "destroyed(QObject* = 0)" signal, "obj.destroyed.connect(...)" connects to "destroyed()", and "obj.destroyed[QObject].connect(...)" connects to "destroyed(QObject*)". Reviewed by Lauro Moura Reviewed by Luciano Wolf --- tests/QtGui/qdynamic_signal.py | 3 ++- tests/signals/signal_signature_test.py | 6 +++++- 2 files changed, 7 insertions(+), 2 deletions(-) diff --git a/tests/QtGui/qdynamic_signal.py b/tests/QtGui/qdynamic_signal.py index d44ee79..0eecb7d 100644 --- a/tests/QtGui/qdynamic_signal.py +++ b/tests/QtGui/qdynamic_signal.py @@ -1,6 +1,7 @@ import unittest +from PySide.QtCore import QObject from PySide.QtGui import QInputDialog from helper import UsesQApplication @@ -17,7 +18,7 @@ class DynamicSignalTest(UsesQApplication): self.assert_(len(lst)) obj = lst[0] self._called = False - obj.destroyed.connect(self.cb) + obj.destroyed[QObject].connect(self.cb) obj = None del dlg self.assert_(self._called) diff --git a/tests/signals/signal_signature_test.py b/tests/signals/signal_signature_test.py index 785ebb8..001f7d6 100644 --- a/tests/signals/signal_signature_test.py +++ b/tests/signals/signal_signature_test.py @@ -14,7 +14,7 @@ class Obj(QObject): def connectNotify(self, signal): self.signal = signal -def callback(): +def callback(arg=None): pass class TestConnectNotifyWithNewStyleSignals(UsesQCoreApplication): @@ -33,7 +33,11 @@ class TestConnectNotifyWithNewStyleSignals(UsesQCoreApplication): def testNewStyle(self): sender = Obj() + sender.destroyed.connect(callback) + self.assertEqual(sender.signal, SIGNAL('destroyed()')) + + sender.destroyed[QObject].connect(callback) self.assertEqual(sender.signal, SIGNAL('destroyed(QObject*)')) if __name__ == '__main__': From 86b7d6e25c2612313da8a9193c90cc60728d3264 Mon Sep 17 00:00:00 2001 From: Marcelo Lira Date: Mon, 13 Dec 2010 17:47:16 -0300 Subject: [PATCH 024/703] Added test for Python written models returning new objects without keeping reference to them. Reviewed by Lauro Moura eviewed by Luciano Wolf --- tests/pysidetest/CMakeLists.txt | 4 ++ tests/pysidetest/global.h | 1 + tests/pysidetest/modelview_test.py | 51 ++++++++++++++++++++++ tests/pysidetest/testview.cpp | 15 +++++++ tests/pysidetest/testview.h | 23 ++++++++++ tests/pysidetest/typesystem_pysidetest.xml | 7 +++ 6 files changed, 101 insertions(+) create mode 100644 tests/pysidetest/modelview_test.py create mode 100644 tests/pysidetest/testview.cpp create mode 100644 tests/pysidetest/testview.h diff --git a/tests/pysidetest/CMakeLists.txt b/tests/pysidetest/CMakeLists.txt index d983ef8..07b03d5 100644 --- a/tests/pysidetest/CMakeLists.txt +++ b/tests/pysidetest/CMakeLists.txt @@ -12,16 +12,19 @@ add_definitions(-DRXX_ALLOCATOR_INIT_0) set(pysidetest_SRC testobject.cpp +testview.cpp ) set(pysidetest_MOC_HEADERS testobject.h +testview.h ) qt4_wrap_cpp(pysidetest_MOC_SRC ${pysidetest_MOC_HEADERS}) set(testbinding_SRC ${CMAKE_CURRENT_BINARY_DIR}/testbinding/testobject_wrapper.cpp +${CMAKE_CURRENT_BINARY_DIR}/testbinding/testview_wrapper.cpp ${CMAKE_CURRENT_BINARY_DIR}/testbinding/testbinding_module_wrapper.cpp ) @@ -63,5 +66,6 @@ add_dependencies(testbinding pyside QtCore libpyside pysidetest) PYSIDE_TEST(homonymoussignalandmethod_test.py) +PYSIDE_TEST(modelview_test.py) PYSIDE_TEST(version_test.py) diff --git a/tests/pysidetest/global.h b/tests/pysidetest/global.h index 22d3375..e55a773 100644 --- a/tests/pysidetest/global.h +++ b/tests/pysidetest/global.h @@ -1,2 +1,3 @@ #include "pyside_global.h" #include "testobject.h" +#include "testview.h" diff --git a/tests/pysidetest/modelview_test.py b/tests/pysidetest/modelview_test.py new file mode 100644 index 0000000..ebab200 --- /dev/null +++ b/tests/pysidetest/modelview_test.py @@ -0,0 +1,51 @@ +#!/usr/bin/python + +import unittest +from testbinding import TestView +from PySide.QtCore import QAbstractListModel, QObject, QModelIndex + +'''Tests model/view relationship.''' + +object_name = 'test object' + +class MyObject(QObject): + pass + +class ListModelKeepsReference(QAbstractListModel): + def rowCount(self, parent=QModelIndex()): + return 1 + + def data(self, index, role): + self.obj = MyObject() + self.obj.setObjectName(object_name) + return self.obj + +class ListModelDoesntKeepsReference(QAbstractListModel): + def rowCount(self, parent=QModelIndex()): + return 1 + + def data(self, index, role): + obj = MyObject() + obj.setObjectName(object_name) + return obj + +class ModelViewTest(unittest.TestCase): + + def testListModelKeepsReference(self): + model = ListModelKeepsReference() + view = TestView(model) + obj = view.getData() + self.assertEqual(type(obj), MyObject) + self.assertEqual(obj.objectName(), object_name) + + def testListModelDoesntKeepsReference(self): + model = ListModelDoesntKeepsReference() + view = TestView(model) + obj = view.getData() + self.assertEqual(type(obj), MyObject) + self.assertEqual(obj.objectName(), object_name) + + +if __name__ == '__main__': + unittest.main() + diff --git a/tests/pysidetest/testview.cpp b/tests/pysidetest/testview.cpp new file mode 100644 index 0000000..c7e9c6d --- /dev/null +++ b/tests/pysidetest/testview.cpp @@ -0,0 +1,15 @@ +#include "testview.h" +#include +#include + +QObject* +TestView::getData() +{ + QModelIndex index; + QVariant data = m_model->data(index); + QObject* obj = 0; + if (data.canConvert()) + obj = data.value(); + return obj; +} + diff --git a/tests/pysidetest/testview.h b/tests/pysidetest/testview.h new file mode 100644 index 0000000..2ae4162 --- /dev/null +++ b/tests/pysidetest/testview.h @@ -0,0 +1,23 @@ +#ifndef TESTVIEW_H +#define TESTVIEW_H + +#include +#include +#ifdef pysidetest_EXPORTS +#define PYSIDE_EXPORTS 1 +#endif +#include "pysidemacros.h" + +class PYSIDE_API TestView : public QObject +{ + Q_OBJECT +public: + TestView(QAbstractListModel* model, QObject* parent = 0) : QObject(parent), m_model(model) {} + QAbstractListModel* model() { return m_model; } + QObject* getData(); +private: + QAbstractListModel* m_model; +}; + +#endif // TESTVIEW_H + diff --git a/tests/pysidetest/typesystem_pysidetest.xml b/tests/pysidetest/typesystem_pysidetest.xml index a966362..afa764c 100644 --- a/tests/pysidetest/typesystem_pysidetest.xml +++ b/tests/pysidetest/typesystem_pysidetest.xml @@ -2,5 +2,12 @@ + + + + + + + From bdaed6a95a3e4edb20d8e02d8b429be0f4d8da5e Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Tue, 14 Dec 2010 15:11:03 -0200 Subject: [PATCH 025/703] Fix bug#512 - "QGridLayout::getItemPosition() is not available" MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewer: Marcelo Lira Renato Araújo --- PySide/QtGui/typesystem_gui_common.xml | 24 +++++++++++++++++++++++- tests/QtGui/CMakeLists.txt | 1 + tests/QtGui/bug_512.py | 22 ++++++++++++++++++++++ 3 files changed, 46 insertions(+), 1 deletion(-) create mode 100644 tests/QtGui/bug_512.py diff --git a/PySide/QtGui/typesystem_gui_common.xml b/PySide/QtGui/typesystem_gui_common.xml index 485d542..cf8f273 100644 --- a/PySide/QtGui/typesystem_gui_common.xml +++ b/PySide/QtGui/typesystem_gui_common.xml @@ -2670,7 +2670,29 @@ addLayoutOwnership(%CPPSELF, %1); - + + + + + + + + + + + + + + + + + + + int a, b, c, d; + %CPPSELF.%FUNCTION_NAME(%1, &a, &b, &c, &d); + %PYARG_0 = Shiboken::makeTuple(a, b, c, d); + + diff --git a/tests/QtGui/CMakeLists.txt b/tests/QtGui/CMakeLists.txt index df81b3d..4bfb0d5 100644 --- a/tests/QtGui/CMakeLists.txt +++ b/tests/QtGui/CMakeLists.txt @@ -19,6 +19,7 @@ PYSIDE_TEST(bug_433.py) PYSIDE_TEST(bug_467.py) PYSIDE_TEST(bug_480.py) PYSIDE_TEST(bug_500.py) +PYSIDE_TEST(bug_512.py) PYSIDE_TEST(customproxywidget_test.py) PYSIDE_TEST(deepcopy_test.py) PYSIDE_TEST(float_to_int_implicit_conversion_test.py) diff --git a/tests/QtGui/bug_512.py b/tests/QtGui/bug_512.py new file mode 100644 index 0000000..386a7f9 --- /dev/null +++ b/tests/QtGui/bug_512.py @@ -0,0 +1,22 @@ +''' Test bug 512: http://bugs.openbossa.org/show_bug.cgi?id=512''' + +import unittest +from helper import UsesQApplication +from PySide.QtCore import * +from PySide.QtGui import * + +class BugTest(UsesQApplication): + def testCase(self): + w = QWidget(None) + lbl = QLabel("Hello", w); + g = QGridLayout() + g.addWidget(lbl, 0, 0) + w.setLayout(g) + w.show() + + t = g.getItemPosition(0) + self.assertEqual(type(t), tuple) + self.assertEqual(t, (0,0,1,1)) + +if __name__ == '__main__': + unittest.main() From 39d61bdc0565a5ce9ec301283a4485e43aaa1f62 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Tue, 14 Dec 2010 15:56:05 -0200 Subject: [PATCH 026/703] Fix bug#518 - "The file 'genindex.html' is not found (linked from contents.html)" Reviewer: Luciano Wolf Marcelo Lira --- doc/contents.rst | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/doc/contents.rst b/doc/contents.rst index 9ff4fb3..81b8fb6 100644 --- a/doc/contents.rst +++ b/doc/contents.rst @@ -6,10 +6,8 @@ PySide Documentation contents modules.rst -Indices and tables -================== +Module Index +============ -* :ref:`genindex` * :ref:`modindex` -* :ref:`search` From 8974ff4abd320ad6089919010c08b4461ff8c11e Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Tue, 14 Dec 2010 16:25:21 -0200 Subject: [PATCH 027/703] Fix bug#508 - "qmltopy1 crashes when setContextProperty is called twice without keeping a reference" MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewer: Renato Araújo Marcelo Lira --- PySide/QtDeclarative/typesystem_declarative.xml | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/PySide/QtDeclarative/typesystem_declarative.xml b/PySide/QtDeclarative/typesystem_declarative.xml index d1424ab..d4edee8 100644 --- a/PySide/QtDeclarative/typesystem_declarative.xml +++ b/PySide/QtDeclarative/typesystem_declarative.xml @@ -69,9 +69,11 @@ - - - + + QByteArray key("%FUNCTION_NAME_"); + key.append(%1.toLocal8Bit()); + Shiboken::Object::keepReference(reinterpret_cast<SbkObject*>(%PYSELF), key.constData(), %PYARG_2); + From 26d2bd6a7c50f93ef61845e2c9751205a6c2f912 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Tue, 14 Dec 2010 17:11:29 -0200 Subject: [PATCH 028/703] Fix bug#517 - "Documentation for QtDeclarative is not linked in contents.html, modules.html" MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewer: Renato Araújo Luciano Wolf --- doc/modules.rst | 1 + 1 file changed, 1 insertion(+) diff --git a/doc/modules.rst b/doc/modules.rst index 919aa3d..5a54d83 100644 --- a/doc/modules.rst +++ b/doc/modules.rst @@ -4,6 +4,7 @@ PySide modules .. toctree:: PySide/QtCore/index.rst + PySide/QtDeclarative/index.rst PySide/QtGui/index.rst PySide/QtHelp/index.rst PySide/QtMaemo5/index.rst From 0229e5413b18df40d76d152074e24a548fdbab69 Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Tue, 14 Dec 2010 17:43:01 -0300 Subject: [PATCH 029/703] Created unittest for bug #505. Reviewer: Luciano Wolf Marcelo Lira --- tests/QtCore/CMakeLists.txt | 1 + tests/QtCore/bug_505.py | 22 ++++++++++++++++++++++ 2 files changed, 23 insertions(+) create mode 100644 tests/QtCore/bug_505.py diff --git a/tests/QtCore/CMakeLists.txt b/tests/QtCore/CMakeLists.txt index 40b8386..b5bffe7 100644 --- a/tests/QtCore/CMakeLists.txt +++ b/tests/QtCore/CMakeLists.txt @@ -3,6 +3,7 @@ PYSIDE_TEST(bug_332.py) PYSIDE_TEST(bug_408.py) PYSIDE_TEST(bug_428.py) PYSIDE_TEST(bug_462.py) +PYSIDE_TEST(bug_505.py) PYSIDE_TEST(blocking_signals_test.py) PYSIDE_TEST(child_event_test.py) PYSIDE_TEST(deepcopy_test.py) diff --git a/tests/QtCore/bug_505.py b/tests/QtCore/bug_505.py new file mode 100644 index 0000000..5fbaa4f --- /dev/null +++ b/tests/QtCore/bug_505.py @@ -0,0 +1,22 @@ +import unittest + +from PySide.QtCore import QObject + +class MyBaseObject(QObject): + def __init__(self, parent=None): + QObject.__init__(self, parent) + self.setObjectName("PySide") + + def __del__(self): + if self.objectName() != "PySide": + raise NameError('Fail') + +class CheckForEventsTypes(unittest.TestCase): + def testDelObject(self): + p = MyBaseObject() + o = MyBaseObject(p) + del o + del p + +if __name__ == '__main__': + unittest.main() From 22b74854195c888b82b1f246d87e16ea18b2c978 Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Wed, 15 Dec 2010 17:52:29 -0300 Subject: [PATCH 030/703] Created function used in PyObject getAttro. Moved the code generated to a function in libpyside. Create unit test for bug #525. Reviewer: Hugo Parente Lima Marcelo Lira --- libpyside/pyside.cpp | 50 ++++++++++++++++++++++++++++++++++++++ libpyside/pyside.h | 9 +++++++ tests/QtGui/CMakeLists.txt | 1 + tests/QtGui/bug_525.py | 21 ++++++++++++++++ 4 files changed, 81 insertions(+) create mode 100644 tests/QtGui/bug_525.py diff --git a/libpyside/pyside.cpp b/libpyside/pyside.cpp index 7442cfc..da896ce 100644 --- a/libpyside/pyside.cpp +++ b/libpyside/pyside.cpp @@ -28,6 +28,7 @@ #include "pysidesignal_p.h" #include "pysideslot_p.h" #include "pysidemetafunction_p.h" +#include "pysidemetafunction.h" #include "dynamicqmetaobject.h" #include @@ -225,5 +226,54 @@ void initQObjectSubType(SbkObjectType* type, PyObject* args, PyObject* kwds) mo->addProperty(propPair.first, propPair.second); } +PyObject* getMetaDataFromQObject(QObject* cppSelf, PyObject* self, PyObject* name) +{ + PyObject* attr = PyObject_GenericGetAttr(self, name); + if (attr && Property::isPropertyType(attr)) { + PyObject *value = Property::getValue(reinterpret_cast(attr), self); + if (!value) + return 0; + Py_DECREF(attr); + Py_INCREF(value); + attr = value; + } + + //mutate native signals to signal instance type + if (attr && PyObject_TypeCheck(attr, &PySideSignalType)) { + PyObject* signal = reinterpret_cast(Signal::initialize(reinterpret_cast(attr), name, self)); + PyObject_SetAttr(self, name, reinterpret_cast(signal)); + return signal; + } + + //search on metaobject (avoid internal attributes started with '__') + if (!attr && !QString(PyString_AS_STRING(name)).startsWith("__")) { + const QMetaObject* metaObject = cppSelf->metaObject(); + QByteArray cname(PyString_AS_STRING(name)); + cname += '('; + //signal + QList signalList; + for(int i=0, i_max = metaObject->methodCount(); i < i_max; i++) { + QMetaMethod method = metaObject->method(i); + if (QString(method.signature()).startsWith(cname)) { + if (method.methodType() == QMetaMethod::Signal) { + signalList.append(method); + } else { + PySideMetaFunction* func = MetaFunction::newObject(cppSelf, i); + if (func) { + PyObject_SetAttr(self, name, (PyObject*)func); + return (PyObject*)func; + } + } + } + } + if (signalList.size() > 0) { + PyObject* pySignal = reinterpret_cast(Signal::newObjectFromMethod(self, signalList)); + PyObject_SetAttr(self, name, pySignal); + return pySignal; + } + } + return attr; +} + } //namespace PySide diff --git a/libpyside/pyside.h b/libpyside/pyside.h index d84040d..fae1b42 100644 --- a/libpyside/pyside.h +++ b/libpyside/pyside.h @@ -93,6 +93,15 @@ PYSIDE_API void runCleanupFunctions(); */ PYSIDE_API void destroyQCoreApplication(); +/** + * Check for properties and signals registered on MetaObject and return these + * \param cppSelf Is the QObject which contains the metaobject + * \param self Python object of cppSelf + * \param name Name of the argument which the function will try retrieve from MetaData + * \return The Python object which contains the Data obtained in metaObject or the Python attribute related with name + */ +PYSIDE_API PyObject* getMetaDataFromQObject(QObject* cppSelf, PyObject* self, PyObject* name); + } //namespace PySide diff --git a/tests/QtGui/CMakeLists.txt b/tests/QtGui/CMakeLists.txt index 4bfb0d5..7cde60f 100644 --- a/tests/QtGui/CMakeLists.txt +++ b/tests/QtGui/CMakeLists.txt @@ -20,6 +20,7 @@ PYSIDE_TEST(bug_467.py) PYSIDE_TEST(bug_480.py) PYSIDE_TEST(bug_500.py) PYSIDE_TEST(bug_512.py) +PYSIDE_TEST(bug_525.py) PYSIDE_TEST(customproxywidget_test.py) PYSIDE_TEST(deepcopy_test.py) PYSIDE_TEST(float_to_int_implicit_conversion_test.py) diff --git a/tests/QtGui/bug_525.py b/tests/QtGui/bug_525.py new file mode 100644 index 0000000..5e146eb --- /dev/null +++ b/tests/QtGui/bug_525.py @@ -0,0 +1,21 @@ +import unittest +from PySide.QtGui import QApplication +from PySide.QtGui import QMenu + +class M2(QMenu): + def __init__(self,parent=None): + super(M2,self).__init__(parent) + self.setTitle(self.tr("M2")) + +class TestMenuDerivedClass(unittest.TestCase): + def aboutToShowHandler(self): + pass + + def testConnectSignal(self): + app = QApplication([]) + m2 = M2() + # Test if the aboutToShow signal was translated to correct type + m2.aboutToShow.connect(self.aboutToShowHandler) + +if __name__ == '__main__': + unittest.main() From ce42ea6eebacdc4ae3cef913d03d06dd77bb1516 Mon Sep 17 00:00:00 2001 From: Marcelo Lira Date: Wed, 15 Dec 2010 19:11:40 -0300 Subject: [PATCH 031/703] Updated the PySide test related to Python model returning data to C++. --- tests/pysidetest/modelview_test.py | 33 +++++++++++++++++++++++------- tests/pysidetest/testview.cpp | 7 ++----- tests/pysidetest/testview.h | 2 +- 3 files changed, 29 insertions(+), 13 deletions(-) diff --git a/tests/pysidetest/modelview_test.py b/tests/pysidetest/modelview_test.py index ebab200..8629b61 100644 --- a/tests/pysidetest/modelview_test.py +++ b/tests/pysidetest/modelview_test.py @@ -12,12 +12,15 @@ class MyObject(QObject): pass class ListModelKeepsReference(QAbstractListModel): + def __init__(self, parent=None): + QAbstractListModel.__init__(self, parent) + self.obj = MyObject() + self.obj.setObjectName(object_name) + def rowCount(self, parent=QModelIndex()): return 1 def data(self, index, role): - self.obj = MyObject() - self.obj.setObjectName(object_name) return self.obj class ListModelDoesntKeepsReference(QAbstractListModel): @@ -29,8 +32,25 @@ class ListModelDoesntKeepsReference(QAbstractListModel): obj.setObjectName(object_name) return obj +class ListModelThatReturnsString(QAbstractListModel): + def rowCount(self, parent=QModelIndex()): + return 1 + + def data(self, index, role): + self.obj = 'string' + return self.obj + #return 'string' + + class ModelViewTest(unittest.TestCase): + def testListModelDoesntKeepsReference(self): + model = ListModelDoesntKeepsReference() + view = TestView(model) + obj = view.getData() + self.assertEqual(type(obj), QObject) + self.assertEqual(obj.objectName(), object_name) + def testListModelKeepsReference(self): model = ListModelKeepsReference() view = TestView(model) @@ -38,13 +58,12 @@ class ModelViewTest(unittest.TestCase): self.assertEqual(type(obj), MyObject) self.assertEqual(obj.objectName(), object_name) - def testListModelDoesntKeepsReference(self): - model = ListModelDoesntKeepsReference() + def testListModelThatReturnsString(self): + model = ListModelThatReturnsString() view = TestView(model) obj = view.getData() - self.assertEqual(type(obj), MyObject) - self.assertEqual(obj.objectName(), object_name) - + self.assertEqual(type(obj), unicode) + self.assertEqual(obj, 'string') if __name__ == '__main__': unittest.main() diff --git a/tests/pysidetest/testview.cpp b/tests/pysidetest/testview.cpp index c7e9c6d..22ef9dd 100644 --- a/tests/pysidetest/testview.cpp +++ b/tests/pysidetest/testview.cpp @@ -2,14 +2,11 @@ #include #include -QObject* +QVariant TestView::getData() { QModelIndex index; QVariant data = m_model->data(index); - QObject* obj = 0; - if (data.canConvert()) - obj = data.value(); - return obj; + return data; } diff --git a/tests/pysidetest/testview.h b/tests/pysidetest/testview.h index 2ae4162..1a65ea4 100644 --- a/tests/pysidetest/testview.h +++ b/tests/pysidetest/testview.h @@ -14,7 +14,7 @@ class PYSIDE_API TestView : public QObject public: TestView(QAbstractListModel* model, QObject* parent = 0) : QObject(parent), m_model(model) {} QAbstractListModel* model() { return m_model; } - QObject* getData(); + QVariant getData(); private: QAbstractListModel* m_model; }; From 42d887ff86c9eb56a721d7cb979c4242f4f4953e Mon Sep 17 00:00:00 2001 From: Marcelo Lira Date: Wed, 15 Dec 2010 19:12:24 -0300 Subject: [PATCH 032/703] Fixed ownership of the value returned by QAbstractItemModel::data(...). The value returned by Python to the virtual method QAbstractItemModel::data(...) called from C++ has its ownership transferred to C++. Reviewed by Lauro Moura Reviewed by Luciano Wolf --- PySide/QtCore/typesystem_core.xml | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/PySide/QtCore/typesystem_core.xml b/PySide/QtCore/typesystem_core.xml index 5ed694c..a30e50e 100644 --- a/PySide/QtCore/typesystem_core.xml +++ b/PySide/QtCore/typesystem_core.xml @@ -1116,6 +1116,11 @@ + + + + + From d4318366f11c910edc9d305d1c9db3924677bf4d Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Tue, 14 Dec 2010 18:23:33 -0200 Subject: [PATCH 033/703] Fix bug#491 - "pyside doesn't respect BUILD_TESTS" Reviewer: Lauro Moura Marcelo Lira --- CMakeLists.txt | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 5a6f6f5..db2bb3a 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -20,6 +20,7 @@ if(USE_XVFB) endif() endif() +option(BUILD_TESTS "Build tests." TRUE) option(ENABLE_VERSION_SUFFIX "Used to use current version in suffix to generated files. This is used to allow multiples versions installed simultaneous." FALSE) set(LIB_SUFFIX "" CACHE STRING "Define suffix of directory name (32/64)" ) set(LIB_INSTALL_DIR "${CMAKE_INSTALL_PREFIX}/lib${LIB_SUFFIX}" CACHE PATH "The subdirectory relative to the install prefix where libraries will be installed (default is /lib${LIB_SUFFIX})" FORCE) @@ -147,15 +148,16 @@ endif() set(GENERATOR_EXTRA_FLAGS --generatorSet=shiboken --enable-parent-ctor-heuristic --enable-pyside-extensions --enable-return-value-heuristic) -enable_testing() - add_subdirectory(libpyside) if(QT_QTUITOOLS_FOUND AND QT_QTDESIGNER_FOUND) add_subdirectory(plugins) endif() # project directories add_subdirectory(PySide) -add_subdirectory(tests) +if (BUILD_TESTS) + enable_testing() + add_subdirectory(tests) +endif () find_program(DOT_EXEC dot) if (QT_SRC_DIR AND DOT_EXEC) From 937b2cfc6d39b8fc915faec644b4c578ce3fadc5 Mon Sep 17 00:00:00 2001 From: Marcelo Lira Date: Fri, 17 Dec 2010 11:28:01 -0300 Subject: [PATCH 034/703] Updated model/view test to follow changes in Shiboken/9459b9da commit. Reviewed by Hugo Parente Reviewed by Lauro Moura --- tests/pysidetest/modelview_test.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/pysidetest/modelview_test.py b/tests/pysidetest/modelview_test.py index 8629b61..94cf3f0 100644 --- a/tests/pysidetest/modelview_test.py +++ b/tests/pysidetest/modelview_test.py @@ -48,7 +48,7 @@ class ModelViewTest(unittest.TestCase): model = ListModelDoesntKeepsReference() view = TestView(model) obj = view.getData() - self.assertEqual(type(obj), QObject) + self.assertEqual(type(obj), MyObject) self.assertEqual(obj.objectName(), object_name) def testListModelKeepsReference(self): From 7f42b68c29bc4e22add7d9bb1f7fbf98c99c88c0 Mon Sep 17 00:00:00 2001 From: Marcelo Lira Date: Fri, 17 Dec 2010 11:39:03 -0300 Subject: [PATCH 035/703] Fixed QML type registering test. Reviewed by Hugo Parente Reviewed by Lauro Moura --- tests/QtDeclarative/registertype.qml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/QtDeclarative/registertype.qml b/tests/QtDeclarative/registertype.qml index fce15da..7815623 100644 --- a/tests/QtDeclarative/registertype.qml +++ b/tests/QtDeclarative/registertype.qml @@ -1,5 +1,5 @@ +import Qt 4.7 import Charts 1.0 -import QtQuick 1.0 Item { width: 300; height: 200 From 803a2708402710b92cc5246931803c0c0144f01d Mon Sep 17 00:00:00 2001 From: Marcelo Lira Date: Fri, 17 Dec 2010 13:55:07 -0300 Subject: [PATCH 036/703] Added a call to QObject.metaObject() to check if a segfault is caused. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This completes the tests for bug #507[1]. Also removed an unnecessary commented line. [1] http://bugs.openbossa.org/show_bug.cgi?id=507 Reviewed by Hugo Parente Reviewed by Renato Araújo --- tests/pysidetest/modelview_test.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/pysidetest/modelview_test.py b/tests/pysidetest/modelview_test.py index 94cf3f0..0737456 100644 --- a/tests/pysidetest/modelview_test.py +++ b/tests/pysidetest/modelview_test.py @@ -39,7 +39,6 @@ class ListModelThatReturnsString(QAbstractListModel): def data(self, index, role): self.obj = 'string' return self.obj - #return 'string' class ModelViewTest(unittest.TestCase): @@ -50,6 +49,7 @@ class ModelViewTest(unittest.TestCase): obj = view.getData() self.assertEqual(type(obj), MyObject) self.assertEqual(obj.objectName(), object_name) + obj.metaObject() def testListModelKeepsReference(self): model = ListModelKeepsReference() From 58d43d6de9fe449e2abacfd6eb5fedca06ad7ec8 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Fri, 17 Dec 2010 14:41:57 -0200 Subject: [PATCH 037/703] Fix compilation under MS Windows. --- tests/pysidetest/CMakeLists.txt | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/tests/pysidetest/CMakeLists.txt b/tests/pysidetest/CMakeLists.txt index 07b03d5..0e5e9b8 100644 --- a/tests/pysidetest/CMakeLists.txt +++ b/tests/pysidetest/CMakeLists.txt @@ -32,8 +32,8 @@ set(GENERATOR_EXTRA_FLAGS --generatorSet=shiboken --enable-parent-ctor-heuristic add_custom_command(OUTPUT ${testbinding_SRC} COMMAND ${GENERATORRUNNER_BINARY} ${GENERATOR_EXTRA_FLAGS} ${CMAKE_CURRENT_SOURCE_DIR}/global.h - --include-paths=${CMAKE_CURRENT_SOURCE_DIR}:${QT_INCLUDE_DIR}:${QT_QTCORE_INCLUDE_DIR} - --typesystem-paths=${CMAKE_CURRENT_SOURCE_DIR}:${pyside_SOURCE_DIR}:${QtCore_SOURCE_DIR} + --include-paths=${CMAKE_CURRENT_SOURCE_DIR}${PATH_SEP}${QT_INCLUDE_DIR}${PATH_SEP}${QT_QTCORE_INCLUDE_DIR} + --typesystem-paths=${CMAKE_CURRENT_SOURCE_DIR}${PATH_SEP}${pyside_SOURCE_DIR}${PATH_SEP}${QtCore_SOURCE_DIR} --output-directory=${CMAKE_CURRENT_BINARY_DIR} ${CMAKE_CURRENT_SOURCE_DIR}/typesystem_pysidetest.xml WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR} From 5c7d93abed7ce374c32fbf73b5fe4ee3e00b972b Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Fri, 17 Dec 2010 15:30:18 -0200 Subject: [PATCH 038/703] Fix QML tests on Windows. --- tests/QtDeclarative/bug_451.py | 2 +- tests/QtDeclarative/bug_456.py | 2 +- tests/QtDeclarative/connect_python_qml.py | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/tests/QtDeclarative/bug_451.py b/tests/QtDeclarative/bug_451.py index 60e8dcc..c75eaa7 100644 --- a/tests/QtDeclarative/bug_451.py +++ b/tests/QtDeclarative/bug_451.py @@ -42,7 +42,7 @@ class TestBug(unittest.TestCase): obj = PythonObject() context = view.rootContext() context.setContextProperty("python", obj) - view.setSource(adjust_filename('bug_451.qml', __file__)) + view.setSource(QtCore.QUrl.fromLocalFile(adjust_filename('bug_451.qml', __file__))) root = view.rootObject() root.simpleFunction() self.assertEqual(obj.called, "simpleFunction") diff --git a/tests/QtDeclarative/bug_456.py b/tests/QtDeclarative/bug_456.py index 178ea7d..262b82e 100644 --- a/tests/QtDeclarative/bug_456.py +++ b/tests/QtDeclarative/bug_456.py @@ -29,7 +29,7 @@ class TestConnectionWithInvalidSignature(TimedQApplication): context = view.rootContext() context.setContextProperty("rotatevalue", rotatevalue) - view.setSource(adjust_filename('bug_456.qml', __file__)) + view.setSource(QtCore.QUrl.fromLocalFile(adjust_filename('bug_456.qml', __file__))) root = view.rootObject() button = root.findChild(QtCore.QObject, "buttonMouseArea") view.show() diff --git a/tests/QtDeclarative/connect_python_qml.py b/tests/QtDeclarative/connect_python_qml.py index bb50515..e8180f7 100644 --- a/tests/QtDeclarative/connect_python_qml.py +++ b/tests/QtDeclarative/connect_python_qml.py @@ -16,7 +16,7 @@ class TestConnectionWithInvalidSignature(TimedQApplication): self.buttonClicked = False self.buttonFailClicked = False view = QtDeclarative.QDeclarativeView() - view.setSource(QtCore.QUrl(adjust_filename('connect_python_qml.qml', __file__))) + view.setSource(QtCore.QUrl.fromLocalFile(adjust_filename('connect_python_qml.qml', __file__))) root = view.rootObject() button = root.findChild(QtCore.QObject, "buttonMouseArea") self.assertRaises(TypeError, QtCore.QObject.connect, [button,QtCore.SIGNAL('clicked()'), self.onButtonFailClicked]) From afd176ffaac193ab4b467efb4b7aa657909d92e6 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Fri, 17 Dec 2010 18:45:25 -0200 Subject: [PATCH 039/703] Use .pyd extension for pysidetest module on Windows. --- tests/pysidetest/CMakeLists.txt | 3 +++ 1 file changed, 3 insertions(+) diff --git a/tests/pysidetest/CMakeLists.txt b/tests/pysidetest/CMakeLists.txt index 0e5e9b8..7cf9e56 100644 --- a/tests/pysidetest/CMakeLists.txt +++ b/tests/pysidetest/CMakeLists.txt @@ -54,6 +54,9 @@ target_link_libraries(pysidetest ${QT_QTCORE_LIBRARY}) add_library(testbinding MODULE ${testbinding_SRC}) set_property(TARGET testbinding PROPERTY PREFIX "") +if(WIN32) + set_target_properties(testbinding PROPERTIES SUFFIX ".pyd") +endif() target_link_libraries(testbinding pysidetest pyside From 914398bbf3aad4b933b827b716c36377aa00f270 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Fri, 17 Dec 2010 18:58:26 -0200 Subject: [PATCH 040/703] Add GLuint as primitive type. If we don't do that any function with GLuint will be rejected by the generator on Windows. --- PySide/QtOpenGL/typesystem_opengl.xml | 1 + 1 file changed, 1 insertion(+) diff --git a/PySide/QtOpenGL/typesystem_opengl.xml b/PySide/QtOpenGL/typesystem_opengl.xml index f58d849..86a6d7b 100644 --- a/PySide/QtOpenGL/typesystem_opengl.xml +++ b/PySide/QtOpenGL/typesystem_opengl.xml @@ -20,6 +20,7 @@ --> + From 4204a86b97c3ea37f284fc5a922ea8aa696f3ddc Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Fri, 17 Dec 2010 19:01:37 -0200 Subject: [PATCH 041/703] Fix QtMultimedia test to not fail when no devices were found. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewer: Renato Araújo Marcelo Lira --- tests/QtMultimedia/audio_test.py | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/tests/QtMultimedia/audio_test.py b/tests/QtMultimedia/audio_test.py index 0d8813d..f3aa680 100644 --- a/tests/QtMultimedia/audio_test.py +++ b/tests/QtMultimedia/audio_test.py @@ -9,7 +9,11 @@ from PySide.QtMultimedia import * class testAudioDevices(unittest.TestCase): def testListDevices(self): - for devInfo in QAudioDeviceInfo.availableDevices(QAudio.AudioOutput): + devices = QAudioDeviceInfo.availableDevices(QAudio.AudioOutput) + if not len(devices): + return + + for devInfo in devices: if devInfo.deviceName() == 'null': continue fmt = QAudioFormat() From 50db2f3b2ea800fdc3e197705c210ab7afcfb0de Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Mon, 20 Dec 2010 11:18:42 -0200 Subject: [PATCH 042/703] Fix bug#558 - "print attribute of a QWebFrame cannot be accessed normally" --- PySide/QtGui/typesystem_gui_common.xml | 2 ++ PySide/QtWebKit/typesystem_webkit.xml | 1 + 2 files changed, 3 insertions(+) diff --git a/PySide/QtGui/typesystem_gui_common.xml b/PySide/QtGui/typesystem_gui_common.xml index cf8f273..c27c4a0 100644 --- a/PySide/QtGui/typesystem_gui_common.xml +++ b/PySide/QtGui/typesystem_gui_common.xml @@ -4909,11 +4909,13 @@ + + diff --git a/PySide/QtWebKit/typesystem_webkit.xml b/PySide/QtWebKit/typesystem_webkit.xml index da709a4..d6fc9a7 100644 --- a/PySide/QtWebKit/typesystem_webkit.xml +++ b/PySide/QtWebKit/typesystem_webkit.xml @@ -53,6 +53,7 @@ + From a9424b314ef086262ec1cc4b62a733d0dd86aaf8 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Mon, 20 Dec 2010 13:47:41 -0200 Subject: [PATCH 043/703] Fix bug#481 - "mimeData() missing from QListWidget, QTreeWidget, QTableWidget" MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewer: Renato Araújo Marcelo Lira --- PySide/QtGui/typesystem_gui_common.xml | 3 --- 1 file changed, 3 deletions(-) diff --git a/PySide/QtGui/typesystem_gui_common.xml b/PySide/QtGui/typesystem_gui_common.xml index c27c4a0..cc27c4b 100644 --- a/PySide/QtGui/typesystem_gui_common.xml +++ b/PySide/QtGui/typesystem_gui_common.xml @@ -3032,7 +3032,6 @@ - @@ -3265,7 +3264,6 @@ - @@ -4126,7 +4124,6 @@ - From db35d78b27389be9794b620c95cd290bf98a93dc Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Mon, 20 Dec 2010 15:06:33 -0200 Subject: [PATCH 044/703] Fix bug#544 - "QtCore.QRect missing binding for method getCoords" Reviewer: Marcelo Lira Lauro Moura --- PySide/QtCore/typesystem_core.xml | 88 +++++++++++++++++++++++++++++-- tests/QtCore/qrect_test.py | 12 ++++- 2 files changed, 95 insertions(+), 5 deletions(-) diff --git a/PySide/QtCore/typesystem_core.xml b/PySide/QtCore/typesystem_core.xml index a30e50e..507e55a 100644 --- a/PySide/QtCore/typesystem_core.xml +++ b/PySide/QtCore/typesystem_core.xml @@ -862,10 +862,48 @@ }; - + + + + + + + + + + + + + + + + + int a, b, c, d; + %CPPSELF.%FUNCTION_NAME(&a, &b, &c, &d); + %PYARG_0 = Shiboken::makeTuple(a, b, c, d); + - + + + + + + + + + + + + + + + + + int a, b, c, d; + %CPPSELF.%FUNCTION_NAME(&a, &b, &c, &d); + %PYARG_0 = Shiboken::makeTuple(a, b, c, d); + @@ -881,8 +919,50 @@ - - + + + + + + + + + + + + + + + + + + qreal a, b, c, d; + %CPPSELF.%FUNCTION_NAME(&a, &b, &c, &d); + %PYARG_0 = Shiboken::makeTuple(a, b, c, d); + + + + + + + + + + + + + + + + + + + + qreal a, b, c, d; + %CPPSELF.%FUNCTION_NAME(&a, &b, &c, &d); + %PYARG_0 = Shiboken::makeTuple(a, b, c, d); + + diff --git a/tests/QtCore/qrect_test.py b/tests/QtCore/qrect_test.py index 3c5f5be..a6d38d9 100644 --- a/tests/QtCore/qrect_test.py +++ b/tests/QtCore/qrect_test.py @@ -3,7 +3,7 @@ import unittest -from PySide.QtCore import QPoint, QRect +from PySide.QtCore import QPoint, QRect, QRectF class RectConstructor(unittest.TestCase): @@ -97,6 +97,16 @@ class RectOperator(unittest.TestCase): rect3 = rect1 | rect2 self.assertEqual(rect3, rect1) + def testGetCoordsAndRect(self): + rect1 = QRect(1, 2, 3, 4) + self.assertEqual(rect1.getRect(), (1, 2, 3, 4)) + self.assertEqual(rect1.getCoords(), (1, 2, 3, 5)) + + rect1 = QRectF(1, 2, 3, 4) + self.assertEqual(rect1.getRect(), (1, 2, 3, 4)) + self.assertEqual(rect1.getCoords(), (1, 2, 4, 6)) + + if __name__ == '__main__': unittest.main() From c350f418c7fc9650a89f5a9be29e7987927bdd9a Mon Sep 17 00:00:00 2001 From: Marcelo Lira Date: Mon, 20 Dec 2010 15:52:58 -0300 Subject: [PATCH 045/703] QObject.sender should not steal the returned object ownership to Python. --- PySide/QtCore/typesystem_core.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/PySide/QtCore/typesystem_core.xml b/PySide/QtCore/typesystem_core.xml index 507e55a..76bcaeb 100644 --- a/PySide/QtCore/typesystem_core.xml +++ b/PySide/QtCore/typesystem_core.xml @@ -1433,7 +1433,7 @@ - + From 05d011ccfa3ad442adb3639f9db87d49dd346299 Mon Sep 17 00:00:00 2001 From: Marcelo Lira Date: Mon, 20 Dec 2010 17:41:53 -0300 Subject: [PATCH 046/703] Fixed type system for TestView from pysidetest directory. --- tests/pysidetest/typesystem_pysidetest.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/pysidetest/typesystem_pysidetest.xml b/tests/pysidetest/typesystem_pysidetest.xml index afa764c..cf7774a 100644 --- a/tests/pysidetest/typesystem_pysidetest.xml +++ b/tests/pysidetest/typesystem_pysidetest.xml @@ -3,7 +3,7 @@ - + From 7771798cf27896c43054699c5f53468cd8bf14cf Mon Sep 17 00:00:00 2001 From: Marcelo Lira Date: Fri, 17 Dec 2010 19:37:35 -0300 Subject: [PATCH 047/703] Fixes bug #502. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The ownership of the editor returned by the Python override of QAbstractItemDelegate.createEditor(...) is now transferred to C++. A test was added to simulate the situation that triggers the bug, instead of relying on an example with a view, model and editable cells. See: http://bugs.openbossa.org/show_bug.cgi?id=502 Reviewed by Lauro Moura Reviewed by Renato Araújo --- PySide/QtGui/typesystem_gui_common.xml | 3 + tests/pysidetest/CMakeLists.txt | 9 ++- .../pysidetest/delegatecreateseditor_test.py | 55 +++++++++++++++++++ tests/pysidetest/testview.cpp | 20 +++++-- tests/pysidetest/testview.h | 10 +++- tests/pysidetest/typesystem_pysidetest.xml | 1 + 6 files changed, 91 insertions(+), 7 deletions(-) create mode 100644 tests/pysidetest/delegatecreateseditor_test.py diff --git a/PySide/QtGui/typesystem_gui_common.xml b/PySide/QtGui/typesystem_gui_common.xml index cc27c4b..940f730 100644 --- a/PySide/QtGui/typesystem_gui_common.xml +++ b/PySide/QtGui/typesystem_gui_common.xml @@ -3047,6 +3047,9 @@ + + + diff --git a/tests/pysidetest/CMakeLists.txt b/tests/pysidetest/CMakeLists.txt index 7cf9e56..4a4c27a 100644 --- a/tests/pysidetest/CMakeLists.txt +++ b/tests/pysidetest/CMakeLists.txt @@ -32,8 +32,8 @@ set(GENERATOR_EXTRA_FLAGS --generatorSet=shiboken --enable-parent-ctor-heuristic add_custom_command(OUTPUT ${testbinding_SRC} COMMAND ${GENERATORRUNNER_BINARY} ${GENERATOR_EXTRA_FLAGS} ${CMAKE_CURRENT_SOURCE_DIR}/global.h - --include-paths=${CMAKE_CURRENT_SOURCE_DIR}${PATH_SEP}${QT_INCLUDE_DIR}${PATH_SEP}${QT_QTCORE_INCLUDE_DIR} - --typesystem-paths=${CMAKE_CURRENT_SOURCE_DIR}${PATH_SEP}${pyside_SOURCE_DIR}${PATH_SEP}${QtCore_SOURCE_DIR} + --include-paths=${CMAKE_CURRENT_SOURCE_DIR}${PATH_SEP}${QT_INCLUDE_DIR}${PATH_SEP}${QT_QTCORE_INCLUDE_DIR}${PATH_SEP}${QT_QTGUI_INCLUDE_DIR} + --typesystem-paths=${CMAKE_CURRENT_SOURCE_DIR}${PATH_SEP}${pyside_SOURCE_DIR}${PATH_SEP}${QtCore_SOURCE_DIR}${PATH_SEP}${QtGui_SOURCE_DIR}${PATH_SEP}${QtGui_BINARY_DIR} --output-directory=${CMAKE_CURRENT_BINARY_DIR} ${CMAKE_CURRENT_SOURCE_DIR}/typesystem_pysidetest.xml WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR} @@ -44,8 +44,11 @@ include_directories(${CMAKE_CURRENT_SOURCE_DIR} ${CMAKE_CURRENT_BINARY_DIR} ${QT_INCLUDE_DIR} ${QT_QTCORE_INCLUDE_DIR} + ${QT_QTGUI_INCLUDE_DIR} ${SHIBOKEN_INCLUDE_DIR} + ${pyside_SOURCE_DIR} ${QtCore_BINARY_DIR}/PySide/QtCore + ${QtGui_BINARY_DIR}/PySide/QtGui ${libpyside_SOURCE_DIR} ${PYTHON_INCLUDE_PATH}) @@ -63,12 +66,14 @@ target_link_libraries(testbinding ${PYTHON_LIBRARIES} ${SHIBOKEN_LIBRARY} ${QT_QTCORE_LIBRARY} + ${QT_QTGUI_LIBRARY} ${SBK_PYTHON_LIBRARIES}) add_dependencies(testbinding pyside QtCore libpyside pysidetest) PYSIDE_TEST(homonymoussignalandmethod_test.py) +PYSIDE_TEST(delegatecreateseditor_test.py) PYSIDE_TEST(modelview_test.py) PYSIDE_TEST(version_test.py) diff --git a/tests/pysidetest/delegatecreateseditor_test.py b/tests/pysidetest/delegatecreateseditor_test.py new file mode 100644 index 0000000..0054e79 --- /dev/null +++ b/tests/pysidetest/delegatecreateseditor_test.py @@ -0,0 +1,55 @@ +#!/usr/bin/python + +import unittest +from helper import UsesQApplication + +from testbinding import TestView +from PySide.QtCore import Qt +from PySide.QtGui import QAbstractItemDelegate, QComboBox + +id_text = 'This is me' + +class DelegateDoesntKeepReferenceToEditor(QAbstractItemDelegate): + def createEditor(self, parent, option, index): + comboBox = QComboBox(parent) + comboBox.addItem(id_text) + return comboBox + + +class DelegateKeepsReferenceToEditor(QAbstractItemDelegate): + def __init__(self, parent=None): + QAbstractItemDelegate.__init__(self, parent) + self.comboBox = QComboBox() + self.comboBox.addItem(id_text) + + def createEditor(self, parent, option, index): + self.comboBox.setParent(parent) + return self.comboBox + + +class EditorCreatedByDelegateTest(UsesQApplication): + + def testDelegateDoesntKeepReferenceToEditor(self): + view = TestView(None) + delegate = DelegateDoesntKeepReferenceToEditor() + view.setItemDelegate(delegate) + editor = view.getEditorWidgetFromItemDelegate() + self.assertEqual(type(editor), QComboBox) + self.assertEqual(editor.count(), 1) + self.assertEqual(editor.itemData(0, Qt.DisplayRole), id_text) + editor.metaObject() + + def testDelegateKeepsReferenceToEditor(self): + view = TestView(None) + delegate = DelegateKeepsReferenceToEditor() + view.setItemDelegate(delegate) + editor = view.getEditorWidgetFromItemDelegate() + self.assertEqual(type(editor), QComboBox) + self.assertEqual(editor.count(), 1) + self.assertEqual(editor.itemData(0, Qt.DisplayRole), id_text) + editor.metaObject() + + +if __name__ == '__main__': + unittest.main() + diff --git a/tests/pysidetest/testview.cpp b/tests/pysidetest/testview.cpp index 22ef9dd..75620e0 100644 --- a/tests/pysidetest/testview.cpp +++ b/tests/pysidetest/testview.cpp @@ -1,12 +1,24 @@ #include "testview.h" -#include -#include + +#include +#include +#include QVariant TestView::getData() { QModelIndex index; - QVariant data = m_model->data(index); - return data; + return m_model->data(index); +} + +QWidget* +TestView::getEditorWidgetFromItemDelegate() const +{ + if (!m_delegate) + return 0; + + QModelIndex index; + QStyleOptionViewItem options; + return m_delegate->createEditor(0, options, index); } diff --git a/tests/pysidetest/testview.h b/tests/pysidetest/testview.h index 1a65ea4..76a6f00 100644 --- a/tests/pysidetest/testview.h +++ b/tests/pysidetest/testview.h @@ -2,12 +2,15 @@ #define TESTVIEW_H #include -#include #ifdef pysidetest_EXPORTS #define PYSIDE_EXPORTS 1 #endif #include "pysidemacros.h" +class QWidget; +class QAbstractListModel; +class QAbstractItemDelegate; + class PYSIDE_API TestView : public QObject { Q_OBJECT @@ -15,8 +18,13 @@ public: TestView(QAbstractListModel* model, QObject* parent = 0) : QObject(parent), m_model(model) {} QAbstractListModel* model() { return m_model; } QVariant getData(); + + void setItemDelegate(QAbstractItemDelegate* delegate) { m_delegate = delegate; } + QWidget* getEditorWidgetFromItemDelegate() const; + private: QAbstractListModel* m_model; + QAbstractItemDelegate* m_delegate; }; #endif // TESTVIEW_H diff --git a/tests/pysidetest/typesystem_pysidetest.xml b/tests/pysidetest/typesystem_pysidetest.xml index cf7774a..9cc4130 100644 --- a/tests/pysidetest/typesystem_pysidetest.xml +++ b/tests/pysidetest/typesystem_pysidetest.xml @@ -1,6 +1,7 @@ + From 3f0291dfe49cdf15325600aba362a0fc5662d19d Mon Sep 17 00:00:00 2001 From: Marcelo Lira Date: Tue, 21 Dec 2010 12:17:56 -0300 Subject: [PATCH 048/703] Fixed global functions from QT_TR_NOOP and QT_TRANSLATE_NOOP family. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit These function just return one of their arguments as result, and the buggy implementation was forgetting to increment the reference count for the returned object. A new unit test was added. Reviewed by Hugo Parente Reviewed by Renato Araújo --- PySide/QtCore/typesystem_core.xml | 30 ++++++++++++------- PySide/typesystem_templates.xml | 6 ++++ tests/QtCore/CMakeLists.txt | 1 + tests/QtCore/tr_noop_test.py | 48 +++++++++++++++++++++++++++++++ 4 files changed, 75 insertions(+), 10 deletions(-) create mode 100644 tests/QtCore/tr_noop_test.py diff --git a/PySide/QtCore/typesystem_core.xml b/PySide/QtCore/typesystem_core.xml index 76bcaeb..e416e57 100644 --- a/PySide/QtCore/typesystem_core.xml +++ b/PySide/QtCore/typesystem_core.xml @@ -2895,20 +2895,30 @@ - - (void)%1;%PYARG_0 = %PYARG_1; + + + + - - (void)%1;%PYARG_0 = %PYARG_1; + + + + - - (void)%1;(void)%2;%PYARG_0 = %PYARG_2; + + + + - - (void)%1;(void)%2;(void)%3;%PYARG_0 = %PYARG_2; + + + + - - (void)%1;%PYARG_0 = %PYARG_1; + + + + diff --git a/PySide/typesystem_templates.xml b/PySide/typesystem_templates.xml index 9d39bb4..4604fda 100644 --- a/PySide/typesystem_templates.xml +++ b/PySide/typesystem_templates.xml @@ -238,5 +238,11 @@ return %CONVERTTOPYTHON[%TRANSPOSED_TYPE](%CPPSELF.transposed()); + + + diff --git a/tests/QtCore/CMakeLists.txt b/tests/QtCore/CMakeLists.txt index b5bffe7..8ec3cdd 100644 --- a/tests/QtCore/CMakeLists.txt +++ b/tests/QtCore/CMakeLists.txt @@ -71,6 +71,7 @@ PYSIDE_TEST(setprop_on_ctor_test.py) PYSIDE_TEST(static_method_test.py) PYSIDE_TEST(static_protected_methods_test.py) PYSIDE_TEST(thread_signals_test.py) +PYSIDE_TEST(tr_noop_test.py) PYSIDE_TEST(translation_test.py) PYSIDE_TEST(unaryoperator_test.py) PYSIDE_TEST(unicode_test.py) diff --git a/tests/QtCore/tr_noop_test.py b/tests/QtCore/tr_noop_test.py new file mode 100644 index 0000000..92029e0 --- /dev/null +++ b/tests/QtCore/tr_noop_test.py @@ -0,0 +1,48 @@ +import unittest + +import sys +from PySide.QtCore import QT_TR_NOOP, QT_TR_NOOP_UTF8 +from PySide.QtCore import QT_TRANSLATE_NOOP, QT_TRANSLATE_NOOP3, QT_TRANSLATE_NOOP_UTF8 + +class QtTrNoopTest(unittest.TestCase): + + def setUp(self): + self.txt = 'Cthulhu fhtag!' + + def tearDown(self): + del self.txt + + def testQtTrNoop(self): + refcnt = sys.getrefcount(self.txt) + result = QT_TR_NOOP(self.txt) + self.assertEqual(result, self.txt) + self.assertEqual(sys.getrefcount(result), refcnt + 1) + + def testQtTrNoopUtf8(self): + refcnt = sys.getrefcount(self.txt) + result = QT_TR_NOOP_UTF8(self.txt) + self.assertEqual(result, self.txt) + self.assertEqual(sys.getrefcount(result), refcnt + 1) + + def testQtTranslateNoop(self): + refcnt = sys.getrefcount(self.txt) + result = QT_TRANSLATE_NOOP(None, self.txt) + self.assertEqual(result, self.txt) + self.assertEqual(sys.getrefcount(result), refcnt + 1) + + def testQtTranslateNoopUtf8(self): + refcnt = sys.getrefcount(self.txt) + result = QT_TRANSLATE_NOOP_UTF8(self.txt) + self.assertEqual(result, self.txt) + self.assertEqual(sys.getrefcount(result), refcnt + 1) + + def testQtTranslateNoop3(self): + refcnt = sys.getrefcount(self.txt) + result = QT_TRANSLATE_NOOP3(None, self.txt, None) + self.assertEqual(result, self.txt) + self.assertEqual(sys.getrefcount(result), refcnt + 1) + + +if __name__ == '__main__': + unittest.main() + From 3e66025bbb698ddd491d502bbb9f9483b17d82a0 Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Mon, 20 Dec 2010 17:49:54 -0300 Subject: [PATCH 049/703] Fixed indentation mistakes. Reviewer: Marcelo Lira Hugo Parente Lima --- cmake/Macros/PySideModules.cmake | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/cmake/Macros/PySideModules.cmake b/cmake/Macros/PySideModules.cmake index 639a0ab..060f4a6 100644 --- a/cmake/Macros/PySideModules.cmake +++ b/cmake/Macros/PySideModules.cmake @@ -77,7 +77,7 @@ macro(check_qt_class module class global_sources) file(WRITE ${SRC_FILE} "#include <${include_file}>\n" "#include \n" - "${NAMESPACE_USE}\n" + "${NAMESPACE_USE}\n" "int main() { typeid(${class}); }\n" ) try_compile(Q_WORKS ${CMAKE_BINARY_DIR} From 0d0cb0753edea1e209742c5777ca024b7a58b83a Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Mon, 20 Dec 2010 17:50:43 -0300 Subject: [PATCH 050/703] Added QSslCertificate to QtNetwork module. Reviewer: Marcelo Lira Hugo Parente Lima --- PySide/QtNetwork/CMakeLists.txt | 1 + PySide/QtNetwork/typesystem_network.xml | 2 +- 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/PySide/QtNetwork/CMakeLists.txt b/PySide/QtNetwork/CMakeLists.txt index 3afa0cf..0656c31 100644 --- a/PySide/QtNetwork/CMakeLists.txt +++ b/PySide/QtNetwork/CMakeLists.txt @@ -44,6 +44,7 @@ ${CMAKE_CURRENT_BINARY_DIR}/PySide/QtNetwork/qurlinfo_wrapper.cpp ${QtNetwork_47_SRC} ) +check_qt_class(QtNetwork QSslCertificate QtNetwork_SRC) check_qt_class(QtNetwork QSslCipher QtNetwork_SRC) check_qt_class(QtNetwork QSslConfiguration QtNetwork_SRC) check_qt_class(QtNetwork QSslError QtNetwork_SRC) diff --git a/PySide/QtNetwork/typesystem_network.xml b/PySide/QtNetwork/typesystem_network.xml index e608786..69d1787 100644 --- a/PySide/QtNetwork/typesystem_network.xml +++ b/PySide/QtNetwork/typesystem_network.xml @@ -33,8 +33,8 @@ - + From ed10989ff23d95d20f361944a6deffbeced63a0d Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Mon, 20 Dec 2010 18:55:02 -0300 Subject: [PATCH 051/703] Fixed QtUiTools plugin. Removed use of static QString to store the class name. Fix bug #533. Reviewer: Marcelo Lira Hugo Parente Lima --- plugins/customwidget.cpp | 7 ++----- plugins/customwidget.h | 2 +- 2 files changed, 3 insertions(+), 6 deletions(-) diff --git a/plugins/customwidget.cpp b/plugins/customwidget.cpp index 74b07dc..9a3e6f2 100644 --- a/plugins/customwidget.cpp +++ b/plugins/customwidget.cpp @@ -35,6 +35,7 @@ PyCustomWidget::PyCustomWidget(PyObject* objectType) : m_data(new PyCustomWidgetPrivate()) { m_data->pyObject = objectType; + m_name = QString(reinterpret_cast(objectType)->tp_name); } PyCustomWidget::~PyCustomWidget() @@ -73,11 +74,7 @@ QString PyCustomWidget::includeFile() const QString PyCustomWidget::name() const { - static QString objectName; - if (objectName.isEmpty()) { - objectName = QString(reinterpret_cast(m_data->pyObject)->tp_name); - } - return objectName; + return m_name; } QString PyCustomWidget::toolTip() const diff --git a/plugins/customwidget.h b/plugins/customwidget.h index e4eb76d..00393a1 100644 --- a/plugins/customwidget.h +++ b/plugins/customwidget.h @@ -52,7 +52,7 @@ public: private: QScopedPointer m_data; - + QString m_name; }; #endif From 45edcc54a6215e161cc0c176daf5e3b4dc3aeaff Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Tue, 21 Dec 2010 17:26:50 -0300 Subject: [PATCH 052/703] Used argument '-a' during the call of xvfb command. This argument allow the xvfb to find a free server number during the execution. --- CMakeLists.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index db2bb3a..5209bab 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -15,7 +15,7 @@ option(USE_XVFB "Uses xvfb-run with the unit tests to avoid QtGui tests popping if(USE_XVFB) find_program(XVFB_RUN NAMES xvfb-run) if (NOT ${XVFB_RUN} MATCHES "XVFB_RUN-NOTFOUND") - set(XVFB_EXEC ${XVFB_RUN}) + set(XVFB_EXEC ${XVFB_RUN} -a) message(STATUS "Using xvfb-run to perform QtGui tests.") endif() endif() From cebdd1f4dcb057436878b60295684c24cb09f1d9 Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Wed, 22 Dec 2010 10:17:21 -0300 Subject: [PATCH 053/703] Avoid QMatrix test while gcc is broken. --- tests/QtGui/deepcopy_test.py | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/tests/QtGui/deepcopy_test.py b/tests/QtGui/deepcopy_test.py index 2f8f7de..3e9f0f8 100644 --- a/tests/QtGui/deepcopy_test.py +++ b/tests/QtGui/deepcopy_test.py @@ -53,6 +53,10 @@ class QMatrixDeepCopy(DeepCopyHelper, unittest.TestCase): def setUp(self): self.original = QMatrix(1, 2, 3, 4, 5, 6) + +# Avoid these tests until get gcc fixed +# Related bug: http://gcc.gnu.org/bugzilla/show_bug.cgi?id=43247 +""" class QMatrix2x2DeepCopy(DeepCopyHelper, unittest.TestCase): def setUp(self): self.original = QMatrix2x2([1, 2, 3, 4]) @@ -88,6 +92,7 @@ class QMatrix4x3DeepCopy(DeepCopyHelper, unittest.TestCase): class QMatrix4x4DeepCopy(DeepCopyHelper, unittest.TestCase): def setUp(self): self.original = QMatrix4x4([1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16]) +""" if __name__ == '__main__': unittest.main() From d3b630e1682c89ee427964d81c32219c14863b1d Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Wed, 22 Dec 2010 10:25:32 -0300 Subject: [PATCH 054/703] Fix the QtMultimedia/audio_test.py to accept computers with only null device. --- tests/QtMultimedia/audio_test.py | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/tests/QtMultimedia/audio_test.py b/tests/QtMultimedia/audio_test.py index f3aa680..773524e 100644 --- a/tests/QtMultimedia/audio_test.py +++ b/tests/QtMultimedia/audio_test.py @@ -9,13 +9,19 @@ from PySide.QtMultimedia import * class testAudioDevices(unittest.TestCase): def testListDevices(self): + valid = False devices = QAudioDeviceInfo.availableDevices(QAudio.AudioOutput) if not len(devices): return + valid = True for devInfo in devices: if devInfo.deviceName() == 'null': - continue + # skip the test if the only device found is a invalid device + if len(devices) == 1: + return + else: + continue fmt = QAudioFormat() for codec in devInfo.supportedCodecs(): fmt.setCodec(codec) From 2734efb6b704c53bab64168be49ce06d6b5a03da Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Wed, 22 Dec 2010 16:14:47 -0300 Subject: [PATCH 055/703] Moved list_signal_test to pysidetest library. This isolate the test case, and avoid other problems with X during the buildbot compilation. Reviewer: Lauro Moura Hugo Parente Lima --- tests/pysidetest/CMakeLists.txt | 1 + tests/pysidetest/list_signal_test.py | 23 ++++++++++++++++++ tests/pysidetest/testobject.h | 3 +++ tests/signals/CMakeLists.txt | 1 - tests/signals/list_signal_test.py | 35 ---------------------------- 5 files changed, 27 insertions(+), 36 deletions(-) create mode 100644 tests/pysidetest/list_signal_test.py delete mode 100644 tests/signals/list_signal_test.py diff --git a/tests/pysidetest/CMakeLists.txt b/tests/pysidetest/CMakeLists.txt index 4a4c27a..b3215bc 100644 --- a/tests/pysidetest/CMakeLists.txt +++ b/tests/pysidetest/CMakeLists.txt @@ -76,4 +76,5 @@ PYSIDE_TEST(homonymoussignalandmethod_test.py) PYSIDE_TEST(delegatecreateseditor_test.py) PYSIDE_TEST(modelview_test.py) PYSIDE_TEST(version_test.py) +PYSIDE_TEST(list_signal_test.py) diff --git a/tests/pysidetest/list_signal_test.py b/tests/pysidetest/list_signal_test.py new file mode 100644 index 0000000..36d3c21 --- /dev/null +++ b/tests/pysidetest/list_signal_test.py @@ -0,0 +1,23 @@ +# -*- coding: utf-8 -*- + +import unittest +from testbinding import TestObject +from PySide.QtCore import QObject + +class ListConnectionTest(unittest.TestCase): + + def childrenChanged(self, children): + self._child = children[0] + + def testConnection(self): + o = TestObject(0) + c = QObject() + c.setObjectName("child") + self._child = None + o.childrenChanged.connect(self.childrenChanged) + o.addChild(c) + self.assertEquals(self._child.objectName(), "child") + +if __name__ == '__main__': + unittest.main() + diff --git a/tests/pysidetest/testobject.h b/tests/pysidetest/testobject.h index 9012359..d882870 100644 --- a/tests/pysidetest/testobject.h +++ b/tests/pysidetest/testobject.h @@ -14,6 +14,7 @@ public: TestObject(int idValue, QObject* parent = 0) : QObject(parent), m_idValue(idValue) {} int idValue() const { return m_idValue; } static int staticMethodDouble(int value) { return value * 2; } + void addChild(QObject* c) { m_children.append(c); emit childrenChanged(m_children); } void emitIdValueSignal(); void emitStaticMethodDoubleSignal(); @@ -22,9 +23,11 @@ signals: void idValue(int newValue); void justASignal(); void staticMethodDouble(); + void childrenChanged(const QList); private: int m_idValue; + QList m_children; }; #endif // TESTOBJECT_H diff --git a/tests/signals/CMakeLists.txt b/tests/signals/CMakeLists.txt index cad84f1..c9ef33e 100644 --- a/tests/signals/CMakeLists.txt +++ b/tests/signals/CMakeLists.txt @@ -6,7 +6,6 @@ PYSIDE_TEST(decorators_test.py) PYSIDE_TEST(invalid_callback_test.py) PYSIDE_TEST(lambda_gui_test.py) PYSIDE_TEST(lambda_test.py) -PYSIDE_TEST(list_signal_test.py) PYSIDE_TEST(leaking_signal_test.py) PYSIDE_TEST(multiple_connections_gui_test.py) PYSIDE_TEST(multiple_connections_test.py) diff --git a/tests/signals/list_signal_test.py b/tests/signals/list_signal_test.py deleted file mode 100644 index c65eb11..0000000 --- a/tests/signals/list_signal_test.py +++ /dev/null @@ -1,35 +0,0 @@ -# -*- coding: utf-8 -*- - -import unittest - -from PySide.QtCore import * -from PySide.QtGui import * - -class ListConnectionTest(unittest.TestCase): - - def modifyScene(self): - self.scene.addLine(0, 0, 10, 10) - - def sceneChanged(self, rects): - # Qt isn't so cute and sends this signal with empty lists and null rects sometimes. - if len(rects) > 0 and not rects[0].isNull(): - self.rects = rects - QApplication.quit() - - def testConnection(self): - app = QApplication([]) - - self.scene = QGraphicsScene() - QTimer.singleShot(0, self.modifyScene) - self.scene.changed.connect(self.sceneChanged) - - app.exec_() - self.assertEquals(len(self.rects), 1) - self.assertEquals(self.rects[0].x(), 0) - self.assertEquals(self.rects[0].y(), 0) - self.assertEquals(self.rects[0].width(), 10) - self.assertEquals(self.rects[0].height(), 10) - -if __name__ == '__main__': - unittest.main() - From af6514a1e81cadbad1ac754ea362ec24e107efb9 Mon Sep 17 00:00:00 2001 From: Lauro Neto Date: Wed, 22 Dec 2010 18:11:26 -0300 Subject: [PATCH 056/703] Fix testbinding dependency Reviewer: Marcelo Lira Reviewer: Renato Araujo --- tests/pysidetest/CMakeLists.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/pysidetest/CMakeLists.txt b/tests/pysidetest/CMakeLists.txt index b3215bc..83e9202 100644 --- a/tests/pysidetest/CMakeLists.txt +++ b/tests/pysidetest/CMakeLists.txt @@ -69,7 +69,7 @@ target_link_libraries(testbinding ${QT_QTGUI_LIBRARY} ${SBK_PYTHON_LIBRARIES}) -add_dependencies(testbinding pyside QtCore libpyside pysidetest) +add_dependencies(testbinding pyside QtCore QtGui libpyside pysidetest) PYSIDE_TEST(homonymoussignalandmethod_test.py) From 3468d8f78e1b0b54124adbe9d21d097c064bb85e Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Wed, 22 Dec 2010 19:12:42 -0300 Subject: [PATCH 057/703] Fixed variable scope. This keep the QByteArray live during the use of your content. Reviewer: Lauro Moura Hugo Parente Lima --- libpyside/pysidesignal.h | 1 + libpyside/signalmanager.cpp | 2 +- 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/libpyside/pysidesignal.h b/libpyside/pysidesignal.h index fb7c8f9..443572c 100644 --- a/libpyside/pysidesignal.h +++ b/libpyside/pysidesignal.h @@ -138,6 +138,7 @@ PYSIDE_API QString getCallbackSignature(const char* signal, QObject* receiver, P * @param signature The signal signature * @param isShortCircuit If this is a shortCircuit(python<->python) signal * @return Return true if this is a Qt Signal of false if not + * @todo replace return type to QList **/ QStringList getArgsFromSignature(const char* signature, bool* isShortCircuit = 0); diff --git a/libpyside/signalmanager.cpp b/libpyside/signalmanager.cpp index 31621a7..6cdc3e1 100644 --- a/libpyside/signalmanager.cpp +++ b/libpyside/signalmanager.cpp @@ -199,7 +199,7 @@ static bool emitNormalSignal(QObject* source, int signalIndex, const char* signa int i; for (i = 0; i < argsGiven; ++i) { - const char* typeName = argTypes[i].toAscii().constData(); + QByteArray typeName = argTypes[i].toAscii(); Shiboken::TypeResolver* typeResolver = Shiboken::TypeResolver::get(typeName); if (typeResolver) { int typeId = QMetaType::type(typeName); From 09840da111e373ebde987cc5f34b89aa49ae3a55 Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Thu, 23 Dec 2010 15:46:39 -0300 Subject: [PATCH 058/703] Used more common signature on function test to QList objects. Replaced "const QList" signature to "const QList&", more used on Qt code. --- tests/pysidetest/testobject.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/pysidetest/testobject.h b/tests/pysidetest/testobject.h index d882870..65506b9 100644 --- a/tests/pysidetest/testobject.h +++ b/tests/pysidetest/testobject.h @@ -23,7 +23,7 @@ signals: void idValue(int newValue); void justASignal(); void staticMethodDouble(); - void childrenChanged(const QList); + void childrenChanged(const QList&); private: int m_idValue; From 85715f3fc3de87bfa4ac07f4d76f1b69bb012109 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Thu, 23 Dec 2010 16:59:33 -0200 Subject: [PATCH 059/703] Fix bug#549 - "QGraphicsWidget::getContentsMargins() and QGraphicsWidget::getWindowFrameMargins() not available" MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewer: Renato Araújo Marcelo Lira --- PySide/QtGui/typesystem_gui_common.xml | 46 +++++++++++++++++++++++--- tests/QtGui/CMakeLists.txt | 1 + tests/QtGui/bug_549.py | 16 +++++++++ 3 files changed, 59 insertions(+), 4 deletions(-) create mode 100644 tests/QtGui/bug_549.py diff --git a/PySide/QtGui/typesystem_gui_common.xml b/PySide/QtGui/typesystem_gui_common.xml index 940f730..0994331 100644 --- a/PySide/QtGui/typesystem_gui_common.xml +++ b/PySide/QtGui/typesystem_gui_common.xml @@ -4834,10 +4834,48 @@ - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/tests/QtGui/CMakeLists.txt b/tests/QtGui/CMakeLists.txt index 7cde60f..fe62e8e 100644 --- a/tests/QtGui/CMakeLists.txt +++ b/tests/QtGui/CMakeLists.txt @@ -21,6 +21,7 @@ PYSIDE_TEST(bug_480.py) PYSIDE_TEST(bug_500.py) PYSIDE_TEST(bug_512.py) PYSIDE_TEST(bug_525.py) +PYSIDE_TEST(bug_549.py) PYSIDE_TEST(customproxywidget_test.py) PYSIDE_TEST(deepcopy_test.py) PYSIDE_TEST(float_to_int_implicit_conversion_test.py) diff --git a/tests/QtGui/bug_549.py b/tests/QtGui/bug_549.py new file mode 100644 index 0000000..6d07899 --- /dev/null +++ b/tests/QtGui/bug_549.py @@ -0,0 +1,16 @@ +import unittest + +from PySide.QtGui import * + +class TestBug549(unittest.TestCase): + def testBug(self): + app = QApplication([]) + w = QGraphicsWidget() + w.setContentsMargins(1, 2, 3, 4) + self.assertEquals(w.getContentsMargins(), (1, 2, 3, 4)) + w.setWindowFrameMargins(5, 6, 7, 8) + self.assertEquals(w.getWindowFrameMargins(), (5, 6, 7, 8)) + +if __name__ == '__main__': + unittest.main() + From 949f6b52558e150f8727c1496167d67c1c0799ef Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Mon, 27 Dec 2010 13:20:43 -0300 Subject: [PATCH 060/703] Removed some float comparisons from QColor test to avoid armel problems. Reviewed by Hugo Parente --- tests/QtGui/qcolor_test.py | 13 +------------ 1 file changed, 1 insertion(+), 12 deletions(-) diff --git a/tests/QtGui/qcolor_test.py b/tests/QtGui/qcolor_test.py index a636ad6..1a94728 100644 --- a/tests/QtGui/qcolor_test.py +++ b/tests/QtGui/qcolor_test.py @@ -2,7 +2,7 @@ import unittest import colorsys -from PySide.QtCore import Qt +from PySide.QtCore import Qt, qFuzzyCompare from PySide.QtGui import QColor @@ -14,12 +14,6 @@ class QColorGetTest(unittest.TestCase): def testGetRgb(self): self.assertEqual(self.color.getRgb(), (20, 40, 60, 80)) - def testGetRgbF(self): - self.assertEqual(self.color.getRgbF(), (20.0/255, 40.0/255, 60.0/255, 80.0/255)) - - def testGetHsl(self): - self.assertEqual(self.color.getHsl(), (210, 128, 40, self.color.alpha())) - def testGetHslF(self): hls = colorsys.rgb_to_hls(20.0/255, 40.0/255, 60.0/255) hsla = hls[0], hls[2], hls[1], self.color.alphaF() @@ -31,11 +25,6 @@ class QColorGetTest(unittest.TestCase): hsva = int(hsv[0]*360.0), int(hsv[1]*255), int(hsv[2]*256), self.color.alpha() self.assertEqual(self.color.getHsv(), hsva) - def testGetHsvF(self): - hsv = colorsys.rgb_to_hsv(20.0/255, 40.0/255, 60.0/255) - hsva = hsv[0], hsv[1], hsv[2], self.color.alphaF() - self.assertEqual(self.color.getHsvF(), hsva) - def testGetCmyk(self): # not supported by colorsys self.assertEqual(self.color.getCmyk(), (170, 85, 0, 195, 80)) From 97875193524f407ec4594969041d84f7aa8ec546 Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Mon, 27 Dec 2010 18:59:32 -0300 Subject: [PATCH 061/703] Fix QTreeWidget parent rules. QTreeWidget.clear() - remove all child ref from the current widget QTreeWidgetItem.parent() - use default policy for returned value Fix bug #547 Reviewer: Marcelo Lira Hugo Parente Lima --- PySide/QtGui/typesystem_gui_common.xml | 20 +++++++++++++ tests/QtGui/CMakeLists.txt | 1 + tests/QtGui/bug_547.py | 39 ++++++++++++++++++++++++++ 3 files changed, 60 insertions(+) create mode 100644 tests/QtGui/bug_547.py diff --git a/PySide/QtGui/typesystem_gui_common.xml b/PySide/QtGui/typesystem_gui_common.xml index 0994331..c2b6343 100644 --- a/PySide/QtGui/typesystem_gui_common.xml +++ b/PySide/QtGui/typesystem_gui_common.xml @@ -3030,6 +3030,18 @@ + + + QTreeWidgetItem *rootItem = %CPPSELF.invisibleRootItem(); + Shiboken::BindingManager &bm = Shiboken::BindingManager::instance(); + for (int i = 0; i < rootItem->childCount(); ++i) { + QTreeWidgetItem *item = rootItem->child(i); + SbkObject* wrapper = bm.retrieveWrapper(item); + if (wrapper) + Shiboken::Object::setParent(0, reinterpret_cast<PyObject*>(wrapper)); + } + + @@ -3228,6 +3240,14 @@ + + + + + + + + diff --git a/tests/QtGui/CMakeLists.txt b/tests/QtGui/CMakeLists.txt index fe62e8e..93b9c07 100644 --- a/tests/QtGui/CMakeLists.txt +++ b/tests/QtGui/CMakeLists.txt @@ -21,6 +21,7 @@ PYSIDE_TEST(bug_480.py) PYSIDE_TEST(bug_500.py) PYSIDE_TEST(bug_512.py) PYSIDE_TEST(bug_525.py) +PYSIDE_TEST(bug_547.py) PYSIDE_TEST(bug_549.py) PYSIDE_TEST(customproxywidget_test.py) PYSIDE_TEST(deepcopy_test.py) diff --git a/tests/QtGui/bug_547.py b/tests/QtGui/bug_547.py new file mode 100644 index 0000000..5636fb6 --- /dev/null +++ b/tests/QtGui/bug_547.py @@ -0,0 +1,39 @@ +""" Unittest for bug #547 """ +""" http://bugs.openbossa.org/show_bug.cgi?id=547 """ + +from PySide import QtGui +import sys +import unittest + +class MyMainWindow(unittest.TestCase): + def testClearFunction(self): + app = QtGui.QApplication(sys.argv) + self._tree = QtGui.QTreeWidget() + self._tree.setColumnCount(2) + self._i1 = None + self._i11 = None + + self._updateTree() + self.assertEqual(sys.getrefcount(self._i1), 3) + self.assertEqual(sys.getrefcount(self._i11), 3) + + self._i11.parent().setExpanded(True) + self._i11.setExpanded(True) + + self._updateTree() + self.assertEqual(sys.getrefcount(self._i1), 3) + self.assertEqual(sys.getrefcount(self._i11), 3) + + + def _updateTree(self): + self._tree.clear() + if self._i1 and self._i11: + self.assertEqual(sys.getrefcount(self._i1), 2) + self.assertEqual(sys.getrefcount(self._i11), 2) + + self._i1 = QtGui.QTreeWidgetItem(self._tree, ['1', ]) + self._i11 = QtGui.QTreeWidgetItem(self._i1, ['11', ]) + +if __name__ == '__main__': + unittest.main() + From 0029d0ef7e85cde40b945d6a55c321f459acda09 Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Tue, 28 Dec 2010 11:49:39 -0300 Subject: [PATCH 062/703] Test for QTDESIGNER before add QTUITOOLS. This test is necessary because the module QTUITOOLS uses some classes from QTDESIGNER. Reviewer: Marcelo Lira Bruno Araujo --- PySide/CMakeLists.txt | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/PySide/CMakeLists.txt b/PySide/CMakeLists.txt index 3b85e3d..35baf3c 100644 --- a/PySide/CMakeLists.txt +++ b/PySide/CMakeLists.txt @@ -23,7 +23,9 @@ HAS_QT_MODULE(QT_QTXML_FOUND QtXml) HAS_QT_MODULE(QT_QTTEST_FOUND QtTest) HAS_QT_MODULE(QT_QTOPENGL_FOUND QtOpenGL) HAS_QT_MODULE(QT_QTSQL_FOUND QtSql) -HAS_QT_MODULE(QT_QTUITOOLS_FOUND QtUiTools) +if(QT_QTDESIGNER_FOUND) + HAS_QT_MODULE(QT_QTUITOOLS_FOUND QtUiTools) +endif() HAS_QT_MODULE(QT_QTHELP_FOUND QtHelp) HAS_QT_MODULE(QT_QTXMLPATTERNS_FOUND QtXmlPatterns) HAS_QT_MODULE(QT_QTMAEMO5_FOUND QtMaemo5) From d96649862fff5ee8e22ac3f48c9a96fea04238bf Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Tue, 28 Dec 2010 14:09:16 -0300 Subject: [PATCH 063/703] Appended QtGui library dependency on pysidetest library. --- tests/pysidetest/CMakeLists.txt | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/tests/pysidetest/CMakeLists.txt b/tests/pysidetest/CMakeLists.txt index 83e9202..4b94a2a 100644 --- a/tests/pysidetest/CMakeLists.txt +++ b/tests/pysidetest/CMakeLists.txt @@ -53,12 +53,12 @@ include_directories(${CMAKE_CURRENT_SOURCE_DIR} ${PYTHON_INCLUDE_PATH}) add_library(pysidetest SHARED ${pysidetest_SRC} ${pysidetest_MOC_SRC}) -target_link_libraries(pysidetest ${QT_QTCORE_LIBRARY}) +target_link_libraries(pysidetest ${QT_QTCORE_LIBRARY} ${QT_QTGUI_LIBRARY}) add_library(testbinding MODULE ${testbinding_SRC}) set_property(TARGET testbinding PROPERTY PREFIX "") if(WIN32) - set_target_properties(testbinding PROPERTIES SUFFIX ".pyd") + set_target_properties(testbinding PROPERTIES SUFFIX ".pyd") endif() target_link_libraries(testbinding pysidetest From c406547057691d758de8324ffb6fabff93e7f1fa Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Tue, 28 Dec 2010 14:12:24 -0300 Subject: [PATCH 064/703] Appended ${QtGui_BINARY_DIR} on typesystem_path for QtMaemo5 module. --- PySide/QtMaemo5/CMakeLists.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/PySide/QtMaemo5/CMakeLists.txt b/PySide/QtMaemo5/CMakeLists.txt index fadf91d..30bf15c 100644 --- a/PySide/QtMaemo5/CMakeLists.txt +++ b/PySide/QtMaemo5/CMakeLists.txt @@ -11,7 +11,7 @@ ${CMAKE_CURRENT_BINARY_DIR}/${BINDING_NAME}/QtMaemo5/qmaemo5valuebutton_wrapper. ${CMAKE_CURRENT_BINARY_DIR}/${BINDING_NAME}/QtMaemo5/qtmaemo5_module_wrapper.cpp ) -set(QtMaemo5_typesystem_path "${QtCore_SOURCE_DIR}${PATH_SEP}${QtGui_SOURCE_DIR}${PATH_SEP}${QtMaemo5_SOURCE_DIR}") +set(QtMaemo5_typesystem_path "${QtCore_SOURCE_DIR}${PATH_SEP}${QtGui_SOURCE_DIR}${PATH_SEP}${QtMaemo5_SOURCE_DIR}${PATH_SEP}${QtGui_BINARY_DIR}") # QT_QTMAEMO5_* variables are not defined by CMake if(NOT QT_QTMAEMO5_INCLUDE_DIR) From 6849ba0864c245e15b5786d959b5afa730fb906b Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Tue, 28 Dec 2010 19:43:00 -0300 Subject: [PATCH 065/703] Fix test to avoid problems on slow computers. Reviewed by Hugo Parente --- tests/QtGui/virtual_protected_inheritance_test.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/QtGui/virtual_protected_inheritance_test.py b/tests/QtGui/virtual_protected_inheritance_test.py index 15de37d..be19952 100644 --- a/tests/QtGui/virtual_protected_inheritance_test.py +++ b/tests/QtGui/virtual_protected_inheritance_test.py @@ -57,7 +57,7 @@ class TimerEventTest(UsesQApplication): self.widget.killTimer(timer_id) - self.assertEqual(self.widget.runs, 5) + self.assert_(self.widget.runs >= self.widget.max_runs) if __name__ == '__main__': From 40f5c3ce0e88a54bf8b838b4951a23a3e147fd5a Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Tue, 28 Dec 2010 19:43:51 -0300 Subject: [PATCH 066/703] Fixed MetaObject creation based on typename. Reviewed by Hugo Parente --- libpyside/pyside.cpp | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/libpyside/pyside.cpp b/libpyside/pyside.cpp index da896ce..5cb107a 100644 --- a/libpyside/pyside.cpp +++ b/libpyside/pyside.cpp @@ -138,11 +138,7 @@ void destroyQCoreApplication() void initDynamicMetaObject(SbkObjectType* type, const QMetaObject* base) { - const char* typeName = type->super.ht_type.tp_name; - int len = strlen(typeName); - for (int i = len-1; i >= 0; --i) - if (typeName[i] == '.') - typeName += i + 1; + QByteArray typeName = QByteArray(type->super.ht_type.tp_name).split('.').last(); DynamicQMetaObject* mo = new PySide::DynamicQMetaObject(typeName, base); Shiboken::ObjectType::setTypeUserData(type, mo, &Shiboken::callCppDestructor); } From 6d18229268b42db54824cc277e339bac34ad3404 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Tue, 28 Dec 2010 12:21:50 -0200 Subject: [PATCH 067/703] Changes the arg name from p to parent to make parent heuristic work. --- PySide/QtDeclarative/typesystem_declarative.xml | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/PySide/QtDeclarative/typesystem_declarative.xml b/PySide/QtDeclarative/typesystem_declarative.xml index d4edee8..05d72e8 100644 --- a/PySide/QtDeclarative/typesystem_declarative.xml +++ b/PySide/QtDeclarative/typesystem_declarative.xml @@ -79,6 +79,11 @@ + + + + + From 92b893c53242a191b76291f8fb0ce68fd284c115 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Tue, 28 Dec 2010 14:50:46 -0200 Subject: [PATCH 068/703] Fix bug#563 - "Unhandled signal emitting with invalid signature (which leads to application crash)" --- libpyside/signalmanager.cpp | 2 +- tests/QtDeclarative/bug_456.py | 2 +- tests/QtDeclarative/bug_456.qml | 2 +- tests/QtDeclarative/connect_python_qml.py | 6 +++--- tests/QtDeclarative/connect_python_qml.qml | 20 ++++++++++---------- 5 files changed, 16 insertions(+), 16 deletions(-) diff --git a/libpyside/signalmanager.cpp b/libpyside/signalmanager.cpp index 6cdc3e1..75a0d19 100644 --- a/libpyside/signalmanager.cpp +++ b/libpyside/signalmanager.cpp @@ -188,7 +188,7 @@ static bool emitNormalSignal(QObject* source, int signalIndex, const char* signa Shiboken::AutoDecRef sequence(PySequence_Fast(args, 0)); int argsGiven = PySequence_Fast_GET_SIZE(sequence.object()); - if (argsGiven > argTypes.count()) { + if (argsGiven != argTypes.count()) { PyErr_Format(PyExc_TypeError, "%s only accepts %d arguments, %d given!", signal, argTypes.count(), argsGiven); return false; } diff --git a/tests/QtDeclarative/bug_456.py b/tests/QtDeclarative/bug_456.py index 262b82e..9ed70c8 100644 --- a/tests/QtDeclarative/bug_456.py +++ b/tests/QtDeclarative/bug_456.py @@ -33,7 +33,7 @@ class TestConnectionWithInvalidSignature(TimedQApplication): root = view.rootObject() button = root.findChild(QtCore.QObject, "buttonMouseArea") view.show() - button.clicked.emit() + button.entered.emit() self.assertEqual(rotatevalue.rotation, 100) if __name__ == '__main__': diff --git a/tests/QtDeclarative/bug_456.qml b/tests/QtDeclarative/bug_456.qml index e4596fd..e8b220e 100644 --- a/tests/QtDeclarative/bug_456.qml +++ b/tests/QtDeclarative/bug_456.qml @@ -56,7 +56,7 @@ Rectangle { id: buttonMouseArea objectName: "buttonMouseArea" anchors.fill: parent - onClicked: { + onEntered: { rotatevalue.rotation = rotatevalue.val() } } diff --git a/tests/QtDeclarative/connect_python_qml.py b/tests/QtDeclarative/connect_python_qml.py index e8180f7..669eec6 100644 --- a/tests/QtDeclarative/connect_python_qml.py +++ b/tests/QtDeclarative/connect_python_qml.py @@ -19,9 +19,9 @@ class TestConnectionWithInvalidSignature(TimedQApplication): view.setSource(QtCore.QUrl.fromLocalFile(adjust_filename('connect_python_qml.qml', __file__))) root = view.rootObject() button = root.findChild(QtCore.QObject, "buttonMouseArea") - self.assertRaises(TypeError, QtCore.QObject.connect, [button,QtCore.SIGNAL('clicked()'), self.onButtonFailClicked]) - button.clicked.connect(self.onButtonClicked) - button.clicked.emit() + self.assertRaises(TypeError, QtCore.QObject.connect, [button,QtCore.SIGNAL('entered()'), self.onButtonFailClicked]) + button.entered.connect(self.onButtonClicked) + button.entered.emit() view.show() self.app.exec_() self.assert_(self.buttonClicked) diff --git a/tests/QtDeclarative/connect_python_qml.qml b/tests/QtDeclarative/connect_python_qml.qml index dbf890f..df55e1b 100644 --- a/tests/QtDeclarative/connect_python_qml.qml +++ b/tests/QtDeclarative/connect_python_qml.qml @@ -6,15 +6,15 @@ Rectangle { color: "lightgray" Rectangle { - id: button - width: 150; height: 40 - color: "darkgray" - anchors.horizontalCenter: page.horizontalCenter - y: 150 - MouseArea { - id: buttonMouseArea - objectName: "buttonMouseArea" - anchors.fill: parent - } + id: button + width: 150; height: 40 + color: "darkgray" + anchors.horizontalCenter: page.horizontalCenter + y: 150 + MouseArea { + id: buttonMouseArea + objectName: "buttonMouseArea" + anchors.fill: parent + } } } From d8f3b9629a6b1f1ab91516fdc144eb4fd80e5128 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Tue, 28 Dec 2010 18:53:06 -0200 Subject: [PATCH 069/703] Fix bug#569 - "QTableWidgetItem is missing binding of __lt__ to operator<" MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewer: Renato Araújo Marcelo Lira --- PySide/QtGui/typesystem_gui_common.xml | 15 --------------- tests/QtGui/CMakeLists.txt | 1 + tests/QtGui/bug_569.py | 19 +++++++++++++++++++ 3 files changed, 20 insertions(+), 15 deletions(-) create mode 100644 tests/QtGui/bug_569.py diff --git a/PySide/QtGui/typesystem_gui_common.xml b/PySide/QtGui/typesystem_gui_common.xml index c2b6343..2998c59 100644 --- a/PySide/QtGui/typesystem_gui_common.xml +++ b/PySide/QtGui/typesystem_gui_common.xml @@ -3074,9 +3074,6 @@ - - - @@ -3085,8 +3082,6 @@ - - @@ -3110,9 +3105,6 @@ - - - @@ -3129,8 +3121,6 @@ - - @@ -3165,16 +3155,12 @@ - - - - @@ -3259,7 +3245,6 @@ - diff --git a/tests/QtGui/CMakeLists.txt b/tests/QtGui/CMakeLists.txt index 93b9c07..0cd9ac2 100644 --- a/tests/QtGui/CMakeLists.txt +++ b/tests/QtGui/CMakeLists.txt @@ -23,6 +23,7 @@ PYSIDE_TEST(bug_512.py) PYSIDE_TEST(bug_525.py) PYSIDE_TEST(bug_547.py) PYSIDE_TEST(bug_549.py) +PYSIDE_TEST(bug_569.py) PYSIDE_TEST(customproxywidget_test.py) PYSIDE_TEST(deepcopy_test.py) PYSIDE_TEST(float_to_int_implicit_conversion_test.py) diff --git a/tests/QtGui/bug_569.py b/tests/QtGui/bug_569.py new file mode 100644 index 0000000..00d92ed --- /dev/null +++ b/tests/QtGui/bug_569.py @@ -0,0 +1,19 @@ +from PySide.QtCore import * +from PySide.QtGui import * +import unittest + + +class TestBug569(unittest.TestCase): + + def testIt(self): + types = (QTableWidgetItem, QListWidgetItem, QTreeWidgetItem) + for t in types: + a = t() + a.__lt__ = lambda(other) : True + b = t() + b.__lt__ = lambda(other) : False + self.assertTrue(a < b) + self.assertFalse(b < a) + +if __name__ == '__main__': + unittest.main() From 1d05357e2657df96b16b5cb4f2e9cc2b6ca73d2b Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Wed, 29 Dec 2010 11:55:09 -0300 Subject: [PATCH 070/703] Changed api2 test to work on MacOS during a ssh session. --- tests/QtGui/api2_test.py | 15 +++++++-------- 1 file changed, 7 insertions(+), 8 deletions(-) diff --git a/tests/QtGui/api2_test.py b/tests/QtGui/api2_test.py index e458d8b..42edba0 100644 --- a/tests/QtGui/api2_test.py +++ b/tests/QtGui/api2_test.py @@ -2,6 +2,7 @@ import unittest +import sys from PySide.QtCore import QObject from PySide.QtGui import * @@ -38,23 +39,21 @@ class DoubleQObjectInheritanceTest(UsesQApplication): obj.setRange(1, 10) obj.setValue(0) - print "Value:", obj.value() + self.assertEqual(obj.value(), 1) class QClipboardTest(UsesQApplication): def testQClipboard(self): - clip = QClipboard() + #skip this test on MacOS because the clipboard is not available during the ssh session + #this cause problems in the buildbot + if sys.platform == 'darwin': + return + clip = QApplication.clipboard() clip.setText("Testing this thing!") text, subtype = clip.text("") self.assertEqual(subtype, "plain") self.assertEqual(text, "Testing this thing!") -#class QFileDialog(UsesQApplication): -# -# def testQFileDialog(self): -# string, filtr = QFileDialog.getOpenFileName() -# print string, filtr - if __name__ == '__main__': unittest.main() From ecb060f85c3de21b6f2e6ea94417685307252791 Mon Sep 17 00:00:00 2001 From: Lauro Neto Date: Tue, 28 Dec 2010 21:18:26 -0300 Subject: [PATCH 071/703] Improve QtScriptEngineDebugger test behavior The extra ContinueAction after evaluate() was crashing on MacOS X. Reviewer: Hugo Lima Reviewer: Renato Araujo --- tests/QtScriptTools/debugger_test.py | 25 ++++++++++++++----------- 1 file changed, 14 insertions(+), 11 deletions(-) diff --git a/tests/QtScriptTools/debugger_test.py b/tests/QtScriptTools/debugger_test.py index e525361..5634824 100644 --- a/tests/QtScriptTools/debugger_test.py +++ b/tests/QtScriptTools/debugger_test.py @@ -1,7 +1,7 @@ import unittest -from PySide.QtCore import SIGNAL +from PySide.QtCore import SIGNAL, QTimer from PySide.QtScript import QScriptEngine from PySide.QtScriptTools import QScriptEngineDebugger @@ -13,29 +13,32 @@ class DebuggerTest(UsesQApplication): UsesQApplication.setUp(self) self.engine = QScriptEngine() self.debugger = QScriptEngineDebugger() - self.has_suspended = False - self.has_resumed = False + self.has_suspended = 0 + self.has_resumed = 0 + self.count = 3 def suspended(self): - self.has_suspended = True - self.debugger.action(QScriptEngineDebugger.ContinueAction).trigger() + self.has_suspended += 1 + # Will emit evaluationResumed until there are more instructions to be run + QTimer.singleShot(100, self.debugger.action(QScriptEngineDebugger.StepIntoAction).trigger) def resumed(self): - self.has_resumed = True + # Will be called when debugger.state() change from Suspended to Running + # except for the first time. + self.has_resumed += 1 def testBasic(self): '''Interrupt and resume evaluation with QScriptEngineDebugger''' + self.debugger.attachTo(self.engine) self.debugger.setAutoShowStandardWindow(False) self.debugger.connect(SIGNAL('evaluationSuspended()'), self.suspended) self.debugger.connect(SIGNAL('evaluationResumed()'), self.resumed) self.debugger.action(QScriptEngineDebugger.InterruptAction).trigger() - self.engine.evaluate("3+4") - self.debugger.action(QScriptEngineDebugger.ContinueAction).trigger() - self.assert_(self.has_resumed) - self.assert_(self.has_suspended) - + self.engine.evaluate("3+4\n2+1\n5+1") + self.assertEqual(self.has_resumed, 2) + self.assertEqual(self.has_suspended, 3) if __name__ == '__main__': unittest.main() From 9b02c46c03a3e246146ccd5b63fda8cb0335aac7 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Wed, 29 Dec 2010 18:57:58 -0200 Subject: [PATCH 072/703] Fix bug#493 - "__eq__ and friends not implemented for QKeyEvent == QKeySequence" Reviewer: Marcelo Lira Lauro Moura --- PySide/QtGui/typesystem_gui_common.xml | 9 +++++++-- tests/QtGui/CMakeLists.txt | 1 + tests/QtGui/bug_493.py | 21 +++++++++++++++++++++ 3 files changed, 29 insertions(+), 2 deletions(-) create mode 100644 tests/QtGui/bug_493.py diff --git a/PySide/QtGui/typesystem_gui_common.xml b/PySide/QtGui/typesystem_gui_common.xml index 2998c59..be38ca9 100644 --- a/PySide/QtGui/typesystem_gui_common.xml +++ b/PySide/QtGui/typesystem_gui_common.xml @@ -128,7 +128,6 @@ - @@ -2427,7 +2426,13 @@ - + + + + %PYARG_0 = %CONVERTTOPYTHON[bool](!(&%CPPSELF == %1)); + + + diff --git a/tests/QtGui/CMakeLists.txt b/tests/QtGui/CMakeLists.txt index 0cd9ac2..65b10e8 100644 --- a/tests/QtGui/CMakeLists.txt +++ b/tests/QtGui/CMakeLists.txt @@ -18,6 +18,7 @@ PYSIDE_TEST(bug_430.py) PYSIDE_TEST(bug_433.py) PYSIDE_TEST(bug_467.py) PYSIDE_TEST(bug_480.py) +PYSIDE_TEST(bug_493.py) PYSIDE_TEST(bug_500.py) PYSIDE_TEST(bug_512.py) PYSIDE_TEST(bug_525.py) diff --git a/tests/QtGui/bug_493.py b/tests/QtGui/bug_493.py new file mode 100644 index 0000000..bf19fa7 --- /dev/null +++ b/tests/QtGui/bug_493.py @@ -0,0 +1,21 @@ +from PySide.QtCore import * +from PySide.QtGui import * +import unittest + + +class TestBug569(unittest.TestCase): + + def testIt(self): + # We need a qapp otherwise Qt will crash when trying to detect the + # current platform + app = QApplication([]) + ev1 = QKeyEvent(QEvent.KeyRelease, Qt.Key_Delete, Qt.NoModifier) + ev2 = QKeyEvent(QEvent.KeyRelease, Qt.Key_Copy, Qt.NoModifier) + ks = QKeySequence.Delete + self.assertEqual(ev1, ks) + self.assertEqual(ks, ev1) + self.assertNotEqual(ev2, ks) + self.assertNotEqual(ks, ev2) + +if __name__ == '__main__': + unittest.main() From 394cdb357d88e4c6968d3986ca7820756661fa35 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Thu, 30 Dec 2010 15:26:20 -0200 Subject: [PATCH 073/703] Fix bug 546 - "Python crash on exit" Reviewer: Marcelo Lira Lauro Moura --- PySide/QtGui/typesystem_gui_common.xml | 4 ++-- tests/QtGui/CMakeLists.txt | 1 + tests/QtGui/bug_546.py | 14 ++++++++++++++ 3 files changed, 17 insertions(+), 2 deletions(-) create mode 100644 tests/QtGui/bug_546.py diff --git a/PySide/QtGui/typesystem_gui_common.xml b/PySide/QtGui/typesystem_gui_common.xml index be38ca9..c7c8f17 100644 --- a/PySide/QtGui/typesystem_gui_common.xml +++ b/PySide/QtGui/typesystem_gui_common.xml @@ -3152,8 +3152,8 @@ - - + + diff --git a/tests/QtGui/CMakeLists.txt b/tests/QtGui/CMakeLists.txt index 65b10e8..4514731 100644 --- a/tests/QtGui/CMakeLists.txt +++ b/tests/QtGui/CMakeLists.txt @@ -22,6 +22,7 @@ PYSIDE_TEST(bug_493.py) PYSIDE_TEST(bug_500.py) PYSIDE_TEST(bug_512.py) PYSIDE_TEST(bug_525.py) +PYSIDE_TEST(bug_546.py) PYSIDE_TEST(bug_547.py) PYSIDE_TEST(bug_549.py) PYSIDE_TEST(bug_569.py) diff --git a/tests/QtGui/bug_546.py b/tests/QtGui/bug_546.py new file mode 100644 index 0000000..845b64e --- /dev/null +++ b/tests/QtGui/bug_546.py @@ -0,0 +1,14 @@ +import unittest +from PySide.QtGui import * + +class TestBug546(unittest.TestCase): + + """Test to check a crash at exit""" + def testIt(self): + app = QApplication([]) + textEdit = QPlainTextEdit() + completer = QCompleter(("foo", "bar"), textEdit) + completer.setWidget(textEdit) + +if __name__=='__main__': + unittest.main() From 9e6762eeb050496f74fdafa1325dd294bf564ce1 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Thu, 30 Dec 2010 16:36:23 -0200 Subject: [PATCH 074/703] Fix bug#514 - "Static method QByteArray.fromRawData is missing from QtCore" Reviewer: Marcelo Lira Lauro Moura --- PySide/QtCore/typesystem_core.xml | 10 +++++++++- tests/QtCore/qbytearray_test.py | 7 +++++++ 2 files changed, 16 insertions(+), 1 deletion(-) diff --git a/PySide/QtCore/typesystem_core.xml b/PySide/QtCore/typesystem_core.xml index e416e57..c785f79 100644 --- a/PySide/QtCore/typesystem_core.xml +++ b/PySide/QtCore/typesystem_core.xml @@ -1734,7 +1734,15 @@ - + + + + + + // %FUNCTION_NAME() - avoid generation of default function call + %PYARG_0 = %CONVERTTOPYTHON[QByteArray](QByteArray(%1)); + + diff --git a/tests/QtCore/qbytearray_test.py b/tests/QtCore/qbytearray_test.py index 2c0ee87..34dc42f 100644 --- a/tests/QtCore/qbytearray_test.py +++ b/tests/QtCore/qbytearray_test.py @@ -102,5 +102,12 @@ class QByteArrayOnQVariant(unittest.TestCase): a = QSettings().value("some_prop", QByteArray()) self.assertEqual(type(a), QByteArray) +class QByteArrayBug514(unittest.TestCase): + def testIt(self): + data = "foobar" + a = QByteArray.fromRawData(data) + self.assertEqual(type(a), QByteArray) + self.assertEqual(a.data(), data) + if __name__ == '__main__': unittest.main() From 814b80f42352199915a13a61280dfe62b8763670 Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Mon, 3 Jan 2011 10:01:04 -0300 Subject: [PATCH 075/703] Fixed test to work in all platform. --- tests/QtScriptTools/debugger_test.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/tests/QtScriptTools/debugger_test.py b/tests/QtScriptTools/debugger_test.py index 5634824..8805018 100644 --- a/tests/QtScriptTools/debugger_test.py +++ b/tests/QtScriptTools/debugger_test.py @@ -37,8 +37,8 @@ class DebuggerTest(UsesQApplication): self.debugger.action(QScriptEngineDebugger.InterruptAction).trigger() self.engine.evaluate("3+4\n2+1\n5+1") - self.assertEqual(self.has_resumed, 2) - self.assertEqual(self.has_suspended, 3) + self.assert_(self.has_resumed >= 1) + self.assert_(self.has_suspended >= 1) if __name__ == '__main__': unittest.main() From ba00068ce161bba9c62c0784876bcb38d252cd98 Mon Sep 17 00:00:00 2001 From: Lauro Neto Date: Mon, 3 Jan 2011 11:28:02 -0300 Subject: [PATCH 076/703] Avoid conflict in test case names Reviewer: Hugo Lima Reviewer: Marcelo Lira --- tests/QtCore/qdatastream_test.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/QtCore/qdatastream_test.py b/tests/QtCore/qdatastream_test.py index 1a75f79..7ccc12e 100644 --- a/tests/QtCore/qdatastream_test.py +++ b/tests/QtCore/qdatastream_test.py @@ -308,7 +308,7 @@ class QDataStreamShiftBitArray(unittest.TestCase): self._check_bitarray(data) -class QDataStreamShiftBitArray(unittest.TestCase): +class QDataStreamRawData(unittest.TestCase): def testRawData(self): data = QDataStream() self.assertEqual(data.readRawData(4), '\x00\x00\x00\x00') From 1af0e9f4fe50537d18c07cfa05578d3242ce21c9 Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Mon, 3 Jan 2011 13:43:29 -0300 Subject: [PATCH 077/703] Fixed QWidget.parent function. Create unit test for bug 576. Fixes bug #576. Reviewer: Marcelo Lira Lauro Moura --- PySide/QtGui/typesystem_gui_common.xml | 23 ++++++++++++++---- tests/QtGui/CMakeLists.txt | 1 + tests/QtGui/bug_576.py | 32 ++++++++++++++++++++++++++ 3 files changed, 51 insertions(+), 5 deletions(-) create mode 100644 tests/QtGui/bug_576.py diff --git a/PySide/QtGui/typesystem_gui_common.xml b/PySide/QtGui/typesystem_gui_common.xml index c7c8f17..8884c63 100644 --- a/PySide/QtGui/typesystem_gui_common.xml +++ b/PySide/QtGui/typesystem_gui_common.xml @@ -3287,6 +3287,24 @@ + + + + + + + + + + + + + + + + + + @@ -3413,11 +3431,6 @@ - - - - - diff --git a/tests/QtGui/CMakeLists.txt b/tests/QtGui/CMakeLists.txt index 4514731..8906a93 100644 --- a/tests/QtGui/CMakeLists.txt +++ b/tests/QtGui/CMakeLists.txt @@ -26,6 +26,7 @@ PYSIDE_TEST(bug_546.py) PYSIDE_TEST(bug_547.py) PYSIDE_TEST(bug_549.py) PYSIDE_TEST(bug_569.py) +PYSIDE_TEST(bug_576.py) PYSIDE_TEST(customproxywidget_test.py) PYSIDE_TEST(deepcopy_test.py) PYSIDE_TEST(float_to_int_implicit_conversion_test.py) diff --git a/tests/QtGui/bug_576.py b/tests/QtGui/bug_576.py new file mode 100644 index 0000000..b3c11a3 --- /dev/null +++ b/tests/QtGui/bug_576.py @@ -0,0 +1,32 @@ +""" Unittest for bug #576 """ +""" http://bugs.openbossa.org/show_bug.cgi?id=576 """ + +from PySide import QtGui, QtCore +import sys +import unittest + +class Bug576(unittest.TestCase): + def onButtonDestroyed(self, button): + self._destroyed = True + + def testWidgetParent(self): + self._destroyed = False + app = QtGui.QApplication(sys.argv) + w = QtGui.QWidget() + + b = QtGui.QPushButton("test") + b.destroyed[QtCore.QObject].connect(self.onButtonDestroyed) + self.assertEqual(sys.getrefcount(b), 2) + b.setParent(w) + self.assertEqual(sys.getrefcount(b), 3) + b.parent() + self.assertEqual(sys.getrefcount(b), 3) + b.setParent(None) + self.assertEqual(sys.getrefcount(b), 2) + del b + self.assert_(self._destroyed) + + +if __name__ == '__main__': + unittest.main() + From 1ed2877743ce786e1d71f804f1b4aa4f433aa4be Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Mon, 3 Jan 2011 14:24:19 -0200 Subject: [PATCH 078/703] Fix bug#577 - "Reference to QString in docs" --- .../snippets/code/src_gui_itemviews_qstandarditemmodel.cpp | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/doc/codesnippets/doc/src/snippets/code/src_gui_itemviews_qstandarditemmodel.cpp b/doc/codesnippets/doc/src/snippets/code/src_gui_itemviews_qstandarditemmodel.cpp index 8086919..b7f91e0 100644 --- a/doc/codesnippets/doc/src/snippets/code/src_gui_itemviews_qstandarditemmodel.cpp +++ b/doc/codesnippets/doc/src/snippets/code/src_gui_itemviews_qstandarditemmodel.cpp @@ -2,7 +2,7 @@ model = QStandardItemModel (4, 4) for row in range(4): for column in range(4): - item = QStandardItem(QString("row %0, column %1").arg(row).arg(column)) + item = QStandardItem("row %d, column %d" % (row, column)) model.setItem(row, column, item) //! [0] @@ -11,7 +11,7 @@ for row in range(4): model = QStandardItemModel() parentItem = model.invisibleRootItem() for i in range(4): - item = QStandardItem(QString("item %0").arg(i)) + item = QStandardItem("item %d" % i) parentItem.appendRow(item) parentItem = item //! [1] @@ -20,8 +20,7 @@ for i in range(4): //! [2] treeView = QTreeView(self) treeView.setModel(myStandardItemModel) -connect(treeView, SIGNAL('clicked(QModelIndex)') - this, SLOT('clicked(QModelIndex)')) +treeView.clicked[QModelIndex].connect(self.clicked) //! [2] From 7a3e7b6f86a514c661bf61c65d1098339e4ffba3 Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Mon, 3 Jan 2011 14:21:40 -0300 Subject: [PATCH 079/703] Fix QTreeWidgetItem.parent function. Create unit test for new use case. Fixes bug #547 Reviewer: Marcelo Lira Hugo Parente Lima --- PySide/QtGui/typesystem_gui_common.xml | 2 +- tests/QtGui/bug_547.py | 21 +++++++++++++++++++-- 2 files changed, 20 insertions(+), 3 deletions(-) diff --git a/PySide/QtGui/typesystem_gui_common.xml b/PySide/QtGui/typesystem_gui_common.xml index 8884c63..b6516ab 100644 --- a/PySide/QtGui/typesystem_gui_common.xml +++ b/PySide/QtGui/typesystem_gui_common.xml @@ -3231,7 +3231,7 @@ - + diff --git a/tests/QtGui/bug_547.py b/tests/QtGui/bug_547.py index 5636fb6..6b65254 100644 --- a/tests/QtGui/bug_547.py +++ b/tests/QtGui/bug_547.py @@ -6,8 +6,8 @@ import sys import unittest class MyMainWindow(unittest.TestCase): - def testClearFunction(self): - app = QtGui.QApplication(sys.argv) + app = QtGui.QApplication(sys.argv) + def testCase1(self): self._tree = QtGui.QTreeWidget() self._tree.setColumnCount(2) self._i1 = None @@ -24,6 +24,21 @@ class MyMainWindow(unittest.TestCase): self.assertEqual(sys.getrefcount(self._i1), 3) self.assertEqual(sys.getrefcount(self._i11), 3) + def testCase2(self): + self._tree = QtGui.QTreeWidget() + self._tree.setColumnCount(2) + self._i1 = None + self._i11 = None + + self._updateTree() + self.assertEqual(sys.getrefcount(self._i1), 3) + self.assertEqual(sys.getrefcount(self._i11), 3) + + self._i11.parent().setExpanded(True) + self._i11.setExpanded(True) + + self.assertEqual(sys.getrefcount(self._i1), 3) + self.assertEqual(sys.getrefcount(self._i11), 3) def _updateTree(self): self._tree.clear() @@ -32,7 +47,9 @@ class MyMainWindow(unittest.TestCase): self.assertEqual(sys.getrefcount(self._i11), 2) self._i1 = QtGui.QTreeWidgetItem(self._tree, ['1', ]) + self.assertEqual(sys.getrefcount(self._i1), 3) self._i11 = QtGui.QTreeWidgetItem(self._i1, ['11', ]) + self.assertEqual(sys.getrefcount(self._i11), 3) if __name__ == '__main__': unittest.main() From 1f1f82d5827c3ec77fcd4ee6b6ab47afa0473007 Mon Sep 17 00:00:00 2001 From: Marcelo Lira Date: Mon, 3 Jan 2011 16:38:30 -0300 Subject: [PATCH 080/703] Added test case for Bug #572. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Bug #572: Giving unicode value as 'body' argument to WebView's load method crashes python. Reviewed by Hugo Parente Reviewed by Renato Araújo --- tests/QtWebKit/webview_test.py | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/tests/QtWebKit/webview_test.py b/tests/QtWebKit/webview_test.py index a6a40fd..ab81a30 100644 --- a/tests/QtWebKit/webview_test.py +++ b/tests/QtWebKit/webview_test.py @@ -6,6 +6,7 @@ import sys from PySide.QtCore import QObject, SIGNAL, QUrl from PySide.QtWebKit import * +from PySide.QtNetwork import QNetworkRequest from helper import adjust_filename, TimedQApplication @@ -61,5 +62,8 @@ class TestLoadFinished(TimedQApplication): if ok: self.called = True + def testNamedArgumentTypeChecking(self): + self.assertRaises(TypeError, self.view.load, QNetworkRequest(), body=unicode('foo')) + if __name__ == '__main__': unittest.main() From cc7d8dd1386138a5e88afe64664f51c33aad2f56 Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Mon, 3 Jan 2011 19:54:40 -0300 Subject: [PATCH 081/703] Created support to function qAddPostRoutine. Created unit test for bug #515 Fixes bug #515 Reviewer: Marcelo Lira Lauro Moura --- PySide/QtCore/typesystem_core.xml | 31 +++++++++++++++++++++++++++++++ tests/QtCore/CMakeLists.txt | 1 + tests/QtCore/bug_515.py | 18 ++++++++++++++++++ 3 files changed, 50 insertions(+) create mode 100644 tests/QtCore/bug_515.py diff --git a/PySide/QtCore/typesystem_core.xml b/PySide/QtCore/typesystem_core.xml index c785f79..df04ca9 100644 --- a/PySide/QtCore/typesystem_core.xml +++ b/PySide/QtCore/typesystem_core.xml @@ -596,6 +596,37 @@ + + namespace PySide { + static QStack<PyObject*> globalPostRoutineFunctions; + void globalPostRoutineCallback() + { + foreach(PyObject* callback, globalPostRoutineFunctions) { + Shiboken::AutoDecRef result(PyObject_CallObject(callback, NULL)); + Py_DECREF(callback); + } + globalPostRoutineFunctions.clear(); + } + void addPostRoutine(PyObject* callback) + { + if (PyCallable_Check(callback)) { + globalPostRoutineFunctions << callback; + Py_INCREF(callback); + } else { + PyErr_SetString(PyExc_TypeError, "qAddPostRoutine: The argument must be a callable object."); + } + } + } // namespace + + + + PySide::addPostRoutine(%1); + + + + qAddPostRoutine(PySide::globalPostRoutineCallback); + + diff --git a/tests/QtCore/CMakeLists.txt b/tests/QtCore/CMakeLists.txt index 8ec3cdd..6851915 100644 --- a/tests/QtCore/CMakeLists.txt +++ b/tests/QtCore/CMakeLists.txt @@ -4,6 +4,7 @@ PYSIDE_TEST(bug_408.py) PYSIDE_TEST(bug_428.py) PYSIDE_TEST(bug_462.py) PYSIDE_TEST(bug_505.py) +PYSIDE_TEST(bug_515.py) PYSIDE_TEST(blocking_signals_test.py) PYSIDE_TEST(child_event_test.py) PYSIDE_TEST(deepcopy_test.py) diff --git a/tests/QtCore/bug_515.py b/tests/QtCore/bug_515.py new file mode 100644 index 0000000..c2bd9c7 --- /dev/null +++ b/tests/QtCore/bug_515.py @@ -0,0 +1,18 @@ +""" Unittest for bug #515 """ +""" http://bugs.openbossa.org/show_bug.cgi?id=515 """ + +from PySide import QtCore + +callCleanup = False +def _cleanup(): + global callCleanup + callCleanup = True + +def _checkCleanup(): + global callCleanup + assert(callCleanup) + +app = QtCore.QCoreApplication([]) +QtCore.qAddPostRoutine(_cleanup) +QtCore.qAddPostRoutine(_checkCleanup) +del app From 4351b2e5133e89c02ff26ecbf0f7df6e902efc64 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Tue, 4 Jan 2011 13:25:05 -0200 Subject: [PATCH 082/703] New format for __version_info__. The new format follow the same rules used by sys.version_info(). Reviewer: Marcelo Lira Lauro Moura --- CMakeLists.txt | 11 ++++++++++- PySide/__init__.py.in | 4 ++-- doc/conf.py.in | 2 +- libpyside/pyside.pc.in | 2 +- tests/QtCore/CMakeLists.txt | 1 + tests/QtCore/versioninfo_test.py | 20 ++++++++++++++++++++ 6 files changed, 35 insertions(+), 5 deletions(-) create mode 100644 tests/QtCore/versioninfo_test.py diff --git a/CMakeLists.txt b/CMakeLists.txt index 5209bab..33eda53 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -63,7 +63,16 @@ set(BINDING_NAME PySide) set(BINDING_API_MAJOR_VERSION "1") set(BINDING_API_MINOR_VERSION "0") set(BINDING_API_MICRO_VERSION "0") +set(BINDING_API_RELEASE_LEVEL "beta") # alpha, beta, candidate, or final +set(BINDING_API_SERIAL 3) # leave as 0 when release level is final set(BINDING_API_VERSION "${BINDING_API_MAJOR_VERSION}.${BINDING_API_MINOR_VERSION}.${BINDING_API_MICRO_VERSION}" CACHE STRING "PySide version" FORCE) +if (BINDING_API_RELEASE_LEVEL STREQUAL "final") + set(BINDING_API_VERSION_FULL "${BINDING_API_MAJOR_VERSION}.${BINDING_API_MINOR_VERSION}.${BINDING_API_MICRO_VERSION}" + CACHE STRING "PySide version [full]" FORCE) +else() + set(BINDING_API_VERSION_FULL "${BINDING_API_MAJOR_VERSION}.${BINDING_API_MINOR_VERSION}.${BINDING_API_MICRO_VERSION}~${BINDING_API_RELEASE_LEVEL}${BINDING_API_SERIAL}" + CACHE STRING "PySide version [full]" FORCE) +endif() set(PYSIDE_QT_VERSION "${QT_VERSION_MAJOR}.${QT_VERSION_MINOR}" CACHE STRING "Qt version used to compile PySide" FORCE) if(ENABLE_VERSION_SUFFIX) set(pyside_SUFFIX "-${BINDING_API_MAJOR_VERSION}.${BINDING_API_MINOR_VERSION}") @@ -123,7 +132,7 @@ add_custom_target(uninstall "${CMAKE_COMMAND}" -P "${CMAKE_CURRENT_BINARY_DIR}/cmake_uninstall.cmake") -set(ARCHIVE_NAME pyside-qt${QT_VERSION_MAJOR}.${QT_VERSION_MINOR}+${BINDING_API_VERSION}) +set(ARCHIVE_NAME pyside-qt${QT_VERSION_MAJOR}.${QT_VERSION_MINOR}+${BINDING_API_VERSION_FULL}) add_custom_target(dist COMMAND mkdir -p "${CMAKE_BINARY_DIR}/${ARCHIVE_NAME}" && git log > "${CMAKE_BINARY_DIR}/${ARCHIVE_NAME}/ChangeLog" && diff --git a/PySide/__init__.py.in b/PySide/__init__.py.in index f931fad..40731a8 100644 --- a/PySide/__init__.py.in +++ b/PySide/__init__.py.in @@ -1,5 +1,5 @@ __all__ = ['QtCore', 'QtGui', 'QtNetwork', 'QtOpenGL', 'QtSql', 'QtSvg', 'QtTest', 'QtWebKit', 'QtScript'] import private -__version__ = "@BINDING_API_VERSION@" -__version_info__ = (@BINDING_API_MAJOR_VERSION@, @BINDING_API_MINOR_VERSION@, @BINDING_API_MICRO_VERSION@) +__version__ = "@BINDING_API_VERSION_FULL@" +__version_info__ = (@BINDING_API_MAJOR_VERSION@, @BINDING_API_MINOR_VERSION@, @BINDING_API_MICRO_VERSION@, "@BINDING_API_RELEASE_LEVEL@", @BINDING_API_SERIAL@) diff --git a/doc/conf.py.in b/doc/conf.py.in index b9e7549..d2d7408 100644 --- a/doc/conf.py.in +++ b/doc/conf.py.in @@ -51,7 +51,7 @@ copyright = u'2009-2010, Nokia Corporation' # The short X.Y version. version = '@BINDING_API_VERSION@' # The full version, including alpha/beta/rc tags. -release = '@BINDING_API_VERSION@' +release = '@BINDING_API_VERSION_FULL@' # The language for content autogenerated by Sphinx. Refer to documentation # for a list of supported languages. diff --git a/libpyside/pyside.pc.in b/libpyside/pyside.pc.in index f7458a9..993e5a1 100644 --- a/libpyside/pyside.pc.in +++ b/libpyside/pyside.pc.in @@ -7,7 +7,7 @@ pythonpath=@SITE_PACKAGE@ Name: PySide@pyside_SUFFIX@ Description: Support library for Python bindings of Qt-based libraries. -Version: @BINDING_API_VERSION@ +Version: @BINDING_API_VERSION_FULL@ Libs: -L${libdir} -lpyside@pyside_SUFFIX@@LIBRARY_OUTPUT_SUFFIX@ Cflags: -I${includedir} Requires: shiboken diff --git a/tests/QtCore/CMakeLists.txt b/tests/QtCore/CMakeLists.txt index 6851915..7f8a773 100644 --- a/tests/QtCore/CMakeLists.txt +++ b/tests/QtCore/CMakeLists.txt @@ -76,6 +76,7 @@ PYSIDE_TEST(tr_noop_test.py) PYSIDE_TEST(translation_test.py) PYSIDE_TEST(unaryoperator_test.py) PYSIDE_TEST(unicode_test.py) +PYSIDE_TEST(versioninfo_test.py) if(X11) PYSIDE_TEST(qhandle_test.py) diff --git a/tests/QtCore/versioninfo_test.py b/tests/QtCore/versioninfo_test.py new file mode 100644 index 0000000..094d637 --- /dev/null +++ b/tests/QtCore/versioninfo_test.py @@ -0,0 +1,20 @@ +import unittest +import PySide + +class TestVersionInfo(unittest.TestCase): + def testIt(self): + + v = PySide.__version_info__ + self.assertEqual(type(v), tuple) + self.assertEqual(len(v), 5) + self.assertEqual(type(v[0]), int) + self.assertEqual(type(v[1]), int) + self.assertEqual(type(v[2]), int) + self.assertEqual(type(v[3]), str) + self.assertEqual(type(v[4]), int) + + self.assertEqual(type(PySide.__version__), str) + + +if __name__ == '__main__': + unittest.main() From f7fd9277f47359f8eb4490bcb8f5bdc84000035e Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Tue, 4 Jan 2011 18:32:24 -0300 Subject: [PATCH 083/703] Fixed function QDataStream.readRawData return value. The function readRawData now return None in case of error, otherwise a string with the read data. Reviewer: Marcelo Lira Hugo Parente Lima --- PySide/QtCore/typesystem_core.xml | 9 +++++++-- tests/QtCore/qdatastream_test.py | 8 ++++---- 2 files changed, 11 insertions(+), 6 deletions(-) diff --git a/PySide/QtCore/typesystem_core.xml b/PySide/QtCore/typesystem_core.xml index df04ca9..54513f9 100644 --- a/PySide/QtCore/typesystem_core.xml +++ b/PySide/QtCore/typesystem_core.xml @@ -2388,8 +2388,13 @@ QByteArray data; data.resize(%2); - %CPPSELF.%FUNCTION_NAME(data.data(), data.size()); - %PYARG_0 = PyString_FromStringAndSize(data.constData(), data.size()); + int result = %CPPSELF.%FUNCTION_NAME(data.data(), data.size()); + if (result == -1) { + Py_INCREF(Py_None); + %PYARG_0 = Py_None; + } else { + %PYARG_0 = PyString_FromStringAndSize(data.data(), result); + } diff --git a/tests/QtCore/qdatastream_test.py b/tests/QtCore/qdatastream_test.py index 7ccc12e..ad74457 100644 --- a/tests/QtCore/qdatastream_test.py +++ b/tests/QtCore/qdatastream_test.py @@ -311,15 +311,15 @@ class QDataStreamShiftBitArray(unittest.TestCase): class QDataStreamRawData(unittest.TestCase): def testRawData(self): data = QDataStream() - self.assertEqual(data.readRawData(4), '\x00\x00\x00\x00') + self.assertEqual(data.readRawData(4), None) ba = QByteArray() data = QDataStream(ba, QIODevice.WriteOnly) - data.writeRawData('ABC') - self.assertEqual(ba, 'ABC') + data.writeRawData('AB\x00C') + self.assertEqual(ba.data(), 'AB\x00C') data = QDataStream(ba) - self.assertEqual(data.readRawData(4), 'ABC\x00') + self.assertEqual(data.readRawData(4), 'AB\x00C') if __name__ == '__main__': unittest.main() From aa305dc5ae5f463c31938fb50cd92257b0fc7911 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Tue, 4 Jan 2011 18:46:40 -0200 Subject: [PATCH 084/703] Lock the gil on some hand written code to avoid crashes. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewer: Renato Araújo Marcelo Lira --- PySide/QtCore/typesystem_core.xml | 8 ++++---- PySide/QtDeclarative/pysideqmlregistertype.cpp | 6 ++++++ 2 files changed, 10 insertions(+), 4 deletions(-) diff --git a/PySide/QtCore/typesystem_core.xml b/PySide/QtCore/typesystem_core.xml index 54513f9..f41acd5 100644 --- a/PySide/QtCore/typesystem_core.xml +++ b/PySide/QtCore/typesystem_core.xml @@ -650,13 +650,13 @@ // Define a global variable to handle qInstallMsgHandler callback static PyObject* qtmsghandler = 0; - void - msghandlercallback(QtMsgType type, const char* msg) + static void msgHandlerCallback(QtMsgType type, const char* msg) { + Shiboken::GilState state; Shiboken::AutoDecRef arglist(Shiboken::makeTuple(type, msg)); Shiboken::AutoDecRef ret(PyObject_CallObject(qtmsghandler, arglist)); } - void QtCoreModuleExit() + static void QtCoreModuleExit() { PySide::SignalManager::instance().clear(); } @@ -673,7 +673,7 @@ %PYARG_0 = qtmsghandler ? qtmsghandler : Py_None; Py_INCREF(%PYARG_1); qtmsghandler = %PYARG_1; - qInstallMsgHandler(msghandlercallback); + qInstallMsgHandler(msgHandlerCallback); } if (%PYARG_0 == Py_None) diff --git a/PySide/QtDeclarative/pysideqmlregistertype.cpp b/PySide/QtDeclarative/pysideqmlregistertype.cpp index 362e56d..0b05758 100644 --- a/PySide/QtDeclarative/pysideqmlregistertype.cpp +++ b/PySide/QtDeclarative/pysideqmlregistertype.cpp @@ -27,6 +27,7 @@ #include // shiboken #include +#include #include // pyside #include @@ -63,6 +64,7 @@ struct ElementFactoryBase { QMutexLocker locker(&nextQmlElementMutex); PySide::nextQmlElementMemoryAddr = memory; + Shiboken::GilState state; PyObject* obj = PyObject_CallObject(pyTypes[N], 0); if (!obj || PyErr_Occurred()) PyErr_Print(); @@ -246,6 +248,7 @@ PyTypeObject PropertyListType = { // Implementation of QDeclarativeListProperty::AppendFunction callback void propListAppender(QDeclarativeListProperty* propList, QDeclarativeItem* item) { + Shiboken::GilState state; Shiboken::AutoDecRef args(Shiboken::makeTuple(propList->object, item)); DeclarativeListProperty* data = reinterpret_cast(propList->data); @@ -258,6 +261,7 @@ void propListAppender(QDeclarativeListProperty* propList, QDec // Implementation of QDeclarativeListProperty::CountFunction callback int propListCount(QDeclarativeListProperty* propList) { + Shiboken::GilState state; Shiboken::AutoDecRef args(Shiboken::makeTuple(propList->object)); DeclarativeListProperty* data = reinterpret_cast(propList->data); @@ -275,6 +279,7 @@ int propListCount(QDeclarativeListProperty* propList) // Implementation of QDeclarativeListProperty::AtFunction callback QDeclarativeItem* propListAt(QDeclarativeListProperty* propList, int index) { + Shiboken::GilState state; Shiboken::AutoDecRef args(Shiboken::makeTuple(propList->object, index)); DeclarativeListProperty* data = reinterpret_cast(propList->data); @@ -291,6 +296,7 @@ QDeclarativeItem* propListAt(QDeclarativeListProperty* propLis // Implementation of QDeclarativeListProperty::ClearFunction callback void propListClear(QDeclarativeListProperty* propList) { + Shiboken::GilState state; Shiboken::AutoDecRef args(Shiboken::makeTuple(propList->object)); DeclarativeListProperty* data = reinterpret_cast(propList->data); From bcb6a2eb75a85cba86c92ccb61ae6e34123758ee Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Wed, 5 Jan 2011 08:48:23 -0300 Subject: [PATCH 085/703] Fixed QWidget.setParent signature on typesystem. --- PySide/QtGui/typesystem_gui_common.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/PySide/QtGui/typesystem_gui_common.xml b/PySide/QtGui/typesystem_gui_common.xml index b6516ab..9c8b06b 100644 --- a/PySide/QtGui/typesystem_gui_common.xml +++ b/PySide/QtGui/typesystem_gui_common.xml @@ -3293,7 +3293,7 @@ - + From cfeea7ec045c1f9e7d4652ed2f672db2977de3a8 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Wed, 5 Jan 2011 14:10:38 -0200 Subject: [PATCH 086/703] Fix bug#557 - "Segmentation fault in QDeclarativeComponent.loadUrl()" MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The signature QDeclarativeComponent(QObject*) should not exist, it's not documented and just creates a useless QDeclarativeComponent when used, useless in the sense that it will segfault when used. Reviewer: Marcelo Lira Renato Araújo --- PySide/QtDeclarative/typesystem_declarative.xml | 1 + tests/QtDeclarative/CMakeLists.txt | 1 + tests/QtDeclarative/bug_557.py | 14 ++++++++++++++ 3 files changed, 16 insertions(+) create mode 100644 tests/QtDeclarative/bug_557.py diff --git a/PySide/QtDeclarative/typesystem_declarative.xml b/PySide/QtDeclarative/typesystem_declarative.xml index 05d72e8..5649bf2 100644 --- a/PySide/QtDeclarative/typesystem_declarative.xml +++ b/PySide/QtDeclarative/typesystem_declarative.xml @@ -66,6 +66,7 @@ + diff --git a/tests/QtDeclarative/CMakeLists.txt b/tests/QtDeclarative/CMakeLists.txt index 5cd53e9..84bc495 100644 --- a/tests/QtDeclarative/CMakeLists.txt +++ b/tests/QtDeclarative/CMakeLists.txt @@ -1,5 +1,6 @@ PYSIDE_TEST(bug_451.py) PYSIDE_TEST(bug_456.py) +PYSIDE_TEST(bug_557.py) PYSIDE_TEST(qdeclarativenetwork_test.py) PYSIDE_TEST(qdeclarativeview_test.py) PYSIDE_TEST(connect_python_qml.py) diff --git a/tests/QtDeclarative/bug_557.py b/tests/QtDeclarative/bug_557.py new file mode 100644 index 0000000..c78aaf1 --- /dev/null +++ b/tests/QtDeclarative/bug_557.py @@ -0,0 +1,14 @@ +from PySide.QtCore import * +from PySide.QtGui import * +from PySide.QtDeclarative import * + +import sys + +app = QApplication(sys.argv) + +engine = QDeclarativeEngine() +component = QDeclarativeComponent(engine) + +# This should segfault if the QDeclarativeComponent has not QDeclarativeEngine +component.loadUrl(QUrl.fromLocalFile('foo.qml')) + From e4eaf410aff780efc4e7f5bc693a7b031938d1c5 Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Wed, 5 Jan 2011 14:42:39 -0300 Subject: [PATCH 087/703] Fixed QtNetwork test to use '127.0.0.1' instead of 'localhost' This is necessary to make all test to be able run on any buildbot machine. Fix Http server shutdown sequence to avoid deadlocks. Fixes bug #587 Reviewer: Hugo Parente Lima Marcelo Lira --- tests/QtNetwork/accessManager_test.py | 12 +++++++++--- tests/QtNetwork/basic_auth_test.py | 19 +++++++++++-------- tests/QtNetwork/http_test.py | 12 +++++++++--- 3 files changed, 29 insertions(+), 14 deletions(-) diff --git a/tests/QtNetwork/accessManager_test.py b/tests/QtNetwork/accessManager_test.py index 172dab8..65a8480 100644 --- a/tests/QtNetwork/accessManager_test.py +++ b/tests/QtNetwork/accessManager_test.py @@ -19,20 +19,26 @@ class AccessManagerCase(UsesQCoreApplication): def tearDown(self): super(AccessManagerCase, self).tearDown() + if self.httpd: + self.httpd.shutdown() + self.httpd = None + + def goAway(self): self.httpd.shutdown() + self.app.quit() + self.httpd = None def slot_replyFinished(self, reply): self.assertEqual(type(reply), QNetworkReply) self.called = True - self.app.quit() + self.goAway() def testNetworkRequest(self): manager = QNetworkAccessManager() manager.finished.connect(self.slot_replyFinished) - manager.get(QNetworkRequest(QUrl("http://localhost:%s" % self.httpd.port()))) + manager.get(QNetworkRequest(QUrl("http://127.0.0.1:%s" % self.httpd.port()))) self.app.exec_() self.assert_(self.called) - self.httpd.shutdown() if __name__ == '__main__': unittest.main() diff --git a/tests/QtNetwork/basic_auth_test.py b/tests/QtNetwork/basic_auth_test.py index b095f09..bc41d65 100644 --- a/tests/QtNetwork/basic_auth_test.py +++ b/tests/QtNetwork/basic_auth_test.py @@ -15,19 +15,23 @@ class testAuthenticationSignal(UsesQCoreApplication): self._resultOk = False def tearDown(self): - self.httpd.shutdown() - del self.httpd + if self.httpd: + self.httpd.shutdown() + del self.httpd super(testAuthenticationSignal, self).tearDown() + def goAway(self): + self.httpd.shutdown() + self.app.quit() + self.httpd = None + def onAuthRequest(self, hostname, port, auth): self.assert_(isinstance(auth, QAuthenticator)) self._resultOk = True - self.app.quit() - + self.goAway() def testwaitSignal(self): - http = QHttp() - http.setHost("localhost", self.httpd.port()) + http = QHttp('127.0.0.1', self.httpd.port()) http.connect(SIGNAL("authenticationRequired(const QString&, quint16, QAuthenticator*)"), self.onAuthRequest) path = QUrl.toPercentEncoding("/index.html", "!$&'()*+,;=:@/") data = http.get(str(path)) @@ -35,8 +39,7 @@ class testAuthenticationSignal(UsesQCoreApplication): self.assert_(self._resultOk) def testwaitSignal2(self): - http = QHttp() - http.setHost("localhost", self.httpd.port()) + http = QHttp('127.0.0.1', self.httpd.port()) # Using new signal slot syntax causes a segfault http.authenticationRequired.connect(self.onAuthRequest) path = QUrl.toPercentEncoding("/index.html", "!$&'()*+,;=:@/") diff --git a/tests/QtNetwork/http_test.py b/tests/QtNetwork/http_test.py index ee6eeea..b6bfea5 100644 --- a/tests/QtNetwork/http_test.py +++ b/tests/QtNetwork/http_test.py @@ -16,18 +16,24 @@ class HttpSignalsCase(UsesQCoreApplication): super(HttpSignalsCase, self).setUp() self.httpd = TestServer() self.httpd.start() - self.http = QHttp('localhost' , self.httpd.port()) + self.http = QHttp("127.0.0.1" , self.httpd.port()) self.called = False def tearDown(self): - self.httpd.shutdown() + if self.httpd: + self.httpd.shutdown() + del self.httpd self.http = None self.httpd = None super(HttpSignalsCase, self).tearDown() + def goAway(self): + self.httpd.shutdown() + self.app.quit() + def callback(self, ident): self.called = True - self.app.quit() + self.goAway() def testDefaultArgs(self): #QHttp signal requestStarted signal From adb9268807aca51c9332e266d6649005c5e9577f Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Wed, 5 Jan 2011 19:11:53 -0200 Subject: [PATCH 088/703] Only try to play the ogg file if the system has the capability to do it. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This fix a failing test on macosx. Reviewer: Marcelo Lira Renato Araújo --- tests/phonon/basic_playing_test.py | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/tests/phonon/basic_playing_test.py b/tests/phonon/basic_playing_test.py index 45f6c12..4eb2ccd 100644 --- a/tests/phonon/basic_playing_test.py +++ b/tests/phonon/basic_playing_test.py @@ -38,9 +38,13 @@ class TestSimplePlaying(UsesQCoreApplication): del self.source def testFinishedSignal(self): - # Should pass if finished() is called - self.media.play() - self.app.exec_() + # Check for ogg support before playing it + if (phonon.Phonon.BackendCapabilities.isMimeTypeAvailable('audio/ogg')): + # Should pass if finished() is called + self.media.play() + self.app.exec_() + else: + print 'Ogg format not supported! Playback test skipped!' def testMediaSource(self): self.assertEqual(self.media.currentSource(), self.source) From 5985c015b2b7efe3dad01e37b869a765dd1b8588 Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Thu, 6 Jan 2011 13:32:55 -0300 Subject: [PATCH 089/703] Fixed QTreeWidgetItem.parent function policy. Fixes bug #585 Reviewer: Hugo Parente Lima Marcelo Lira --- PySide/QtGui/typesystem_gui_common.xml | 21 ++++++++++++++++++--- 1 file changed, 18 insertions(+), 3 deletions(-) diff --git a/PySide/QtGui/typesystem_gui_common.xml b/PySide/QtGui/typesystem_gui_common.xml index 9c8b06b..676829e 100644 --- a/PySide/QtGui/typesystem_gui_common.xml +++ b/PySide/QtGui/typesystem_gui_common.xml @@ -3232,13 +3232,28 @@ - - - + + // Only call the parent function if this return some value + // the parent can be the TreeWidget + if (%0) + Shiboken::Object::setParent(%PYARG_0, %PYSELF); + + + + + + + // Only call the parent function if this return some value + // the parent can be the TreeWidgetItem + if (%0) + Shiboken::Object::setParent(%PYARG_0, %PYSELF); + + + From b6343a7674347d1ddae27f61965eb83dd5b2223b Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Thu, 6 Jan 2011 13:32:35 -0300 Subject: [PATCH 090/703] Created unit test for bug #585. Reviewer: Hugo Parente Lima Marcelo Lira --- tests/QtGui/CMakeLists.txt | 1 + tests/QtGui/bug_585.py | 26 ++++++++++++++++++++++++++ 2 files changed, 27 insertions(+) create mode 100644 tests/QtGui/bug_585.py diff --git a/tests/QtGui/CMakeLists.txt b/tests/QtGui/CMakeLists.txt index 8906a93..6032808 100644 --- a/tests/QtGui/CMakeLists.txt +++ b/tests/QtGui/CMakeLists.txt @@ -27,6 +27,7 @@ PYSIDE_TEST(bug_547.py) PYSIDE_TEST(bug_549.py) PYSIDE_TEST(bug_569.py) PYSIDE_TEST(bug_576.py) +PYSIDE_TEST(bug_585.py) PYSIDE_TEST(customproxywidget_test.py) PYSIDE_TEST(deepcopy_test.py) PYSIDE_TEST(float_to_int_implicit_conversion_test.py) diff --git a/tests/QtGui/bug_585.py b/tests/QtGui/bug_585.py new file mode 100644 index 0000000..7c37150 --- /dev/null +++ b/tests/QtGui/bug_585.py @@ -0,0 +1,26 @@ +'''Test bug 585: http://bugs.openbossa.org/show_bug.cgi?id=585''' + +from PySide import QtCore ,QtGui +import sys +import unittest + + +class Bug585(unittest.TestCase): + def testCase(self): + app = QtGui.QApplication([]) + self._tree = QtGui.QTreeWidget() + self._tree.setColumnCount(2) + i1 = QtGui.QTreeWidgetItem(self._tree, ['1', ]) + i2 = QtGui.QTreeWidgetItem(self._tree, ['2', ]) + refCount = sys.getrefcount(i1) + + # this function return None + # because the topLevelItem does not has a parent item + # but still have a TreeWidget as a parent + self._tree.topLevelItem(0).parent() + + self.assertEqual(refCount, sys.getrefcount(i1)) + +if __name__ == '__main__': + unittest.main() + From 44b71a0ff22cf724b394003131b344ff013a0886 Mon Sep 17 00:00:00 2001 From: Marcelo Lira Date: Wed, 5 Jan 2011 18:54:02 -0300 Subject: [PATCH 091/703] Fixed PATH variable for tests on win32 platform. --- tests/CMakeLists.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/CMakeLists.txt b/tests/CMakeLists.txt index f4c73b4..f12e62c 100644 --- a/tests/CMakeLists.txt +++ b/tests/CMakeLists.txt @@ -7,7 +7,7 @@ else() if(WIN32) set(TEST_PYTHONPATH "${CMAKE_BINARY_DIR};${CMAKE_SOURCE_DIR}/tests/util;${testbinding_BINARY_DIR}") - set(TEST_LIBRARY_PATH "${libpyside_BINARY_DIR};${pysidetest_BINARY_DIR};$ENV{PATH}") + set(TEST_LIBRARY_PATH "${libpyside_BINARY_DIR};${pysidetest_BINARY_DIR};${SHIBOKEN_INCLUDE_DIR}/../../bin;$ENV{PATH}") set(LIBRARY_PATH_VAR "PATH") string(REPLACE "\\" "/" TEST_PYTHONPATH "${TEST_PYTHONPATH}") string(REPLACE "\\" "/" TEST_LIBRARY_PATH "${TEST_LIBRARY_PATH}") From 42e52dec9cd5db837a9fda2663b9c873dac1cd7b Mon Sep 17 00:00:00 2001 From: Marcelo Lira Date: Thu, 6 Jan 2011 16:23:16 -0300 Subject: [PATCH 092/703] Refactoring to Phonon basic playing test. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Also replaced the ogg audio tone file for a wav one. Reviewed by Hugo Parente Reviewed by Renato Araújo --- tests/phonon/basic_playing_test.py | 58 +++++++++++++---------------- tests/phonon/tone.ogg | Bin 4300 -> 0 bytes tests/phonon/tone.wav | Bin 0 -> 8942 bytes 3 files changed, 26 insertions(+), 32 deletions(-) delete mode 100644 tests/phonon/tone.ogg create mode 100644 tests/phonon/tone.wav diff --git a/tests/phonon/basic_playing_test.py b/tests/phonon/basic_playing_test.py index 4eb2ccd..49df7d5 100644 --- a/tests/phonon/basic_playing_test.py +++ b/tests/phonon/basic_playing_test.py @@ -1,34 +1,35 @@ import os import unittest - -from PySide import QtCore -from PySide import phonon - +from PySide.phonon import Phonon from helper import UsesQCoreApplication -# XXX Hack to get the correct filename -example_file = os.path.join(os.path.dirname(__file__),'tone.ogg') +sample_file = os.path.join(os.path.dirname(__file__), 'tone.wav') + +def checkBackendCapabilities(func): + def function(self, *args, **kw): + if Phonon.BackendCapabilities.isMimeTypeAvailable('audio/x-wav'): + func(self, *args, **kw) + else: + print 'Wav format not supported! Playback test skipped!' + return function + class TestSimplePlaying(UsesQCoreApplication): def setUp(self): super(TestSimplePlaying, self).setUp() self.app.setApplicationName('Dummy') - self.source = phonon.Phonon.MediaSource(example_file) - self.media = phonon.Phonon.MediaObject() + self.source = Phonon.MediaSource(sample_file) + self.media = Phonon.MediaObject() self.media.setCurrentSource(self.source) - QtCore.QObject.connect(self.media, - QtCore.SIGNAL('finished()'), - self.app, - QtCore.SLOT('quit()')) - + self.media.finished.connect(self.app.quit) self.called = False # prevent locking with: # request to play a stream, but no valid audio ... - self.output = phonon.Phonon.AudioOutput() - self.path = phonon.Phonon.createPath(self.media, self.output) + self.output = Phonon.AudioOutput() + self.path = Phonon.createPath(self.media, self.output) def tearDown(self): super(TestSimplePlaying, self).tearDown() @@ -37,14 +38,11 @@ class TestSimplePlaying(UsesQCoreApplication): del self.media del self.source + @checkBackendCapabilities def testFinishedSignal(self): - # Check for ogg support before playing it - if (phonon.Phonon.BackendCapabilities.isMimeTypeAvailable('audio/ogg')): - # Should pass if finished() is called - self.media.play() - self.app.exec_() - else: - print 'Ogg format not supported! Playback test skipped!' + # Should pass if finished() is called + self.media.play() + self.app.exec_() def testMediaSource(self): self.assertEqual(self.media.currentSource(), self.source) @@ -57,18 +55,14 @@ class TestSimplePlaying(UsesQCoreApplication): def state_cb(self, newState, OldState): self.called = True + @checkBackendCapabilities def testStateChanged(self): - # Check for ogg support before playing it - if (phonon.Phonon.BackendCapabilities.isMimeTypeAvailable('audio/ogg')): - QtCore.QObject.connect(self.media, - QtCore.SIGNAL('stateChanged(Phonon::State, Phonon::State)'), - self.state_cb) + self.media.stateChanged['Phonon::State', 'Phonon::State'].connect(self.state_cb) + self.media.play() + self.app.exec_() + self.assert_(self.called) - self.media.play() - self.app.exec_() - self.assert_(self.called) - else: - print 'Ogg format not supported! Playback test skipped!' if __name__ == '__main__': unittest.main() + diff --git a/tests/phonon/tone.ogg b/tests/phonon/tone.ogg deleted file mode 100644 index dc1a455d3bab7c403ce4e60717b157709d4cc479..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 4300 zcmai24Ny~8_P?nJ2_TISX{fRP7Y&7nuq6oAuw|AHspdgI9trYMYzah!@F59d*JFrp z@=z-&%3k*76or_mP^HMA zt+j6zkBmy9Av*BzV==ROu12st3NFQc|&S(rN`$Y%T0Dq00OaXY#(r|N{80>*{!U(77%8tjr6%;4Vibt!8R z#36h)x12>%owSl$!G`Xy9K{5;yG7ybcc%4-bI=4<78~?sXG2`*muEU^L+|?z&PBQe z49*j={Kcfq-VYqp-%`#9R$3l+44WMo>?P9CD~lOPr^Hv{T}=uQWj6~$YA_S+I?fXI zv!?nvmoD?-zx7Y>2)Vp1I#Dc=z@tjvTOwO3Q7x5}rZknOohwZ_SDtpYJpEC52D{>M z`?2)KBdXa<$7rZ^i=goi-oE+y_S=H?HJXZ^XHXX95{yy58L#gUcJ0sY&1oJ!aCSI< zYQTSLz}3bA7;>O?gIaTRUH{egr!>m`cMCr-;fKP(m*Yj8@giO{$s1SrJJ~!ufgq;g zq`z4ayh|B8u6zaBuHu~+wXv7Ji+%P<5U8*t6wc?Ei#Qj-8)U$OB4n>JY)L6v0#{HT z`Tggx4KH8__tgHzTs3`LU53pqY7onAqer>gH336q+ZUK_PWSMVz)g3z)xc_A__#{k z>@#9$YPLl%Z^r8m#1fx8X>L6^r&G=dU3Gf<=#YD}lgTg-b6zVgZWgZ$;LDlUIT@}c z!`hTN-SU|c7L2O2%|1gTV!OP@urTavnfX|73szKp+AJSoq{HZ6SuOv##GvMW3!iX^ zTgFwk<Z%k@Ln)UA3gN#J^W zMnO=qthxwCFI$pSG$|(WZpezK1NRMYcKxQyPqo>9auVFVp@J9Cr^KAXm|ci<{YT*ZmRCC ztX`?C^{r~msnQuo+VduRS4aP6`z3RBDR|HzbD|Zzr!wa}pA!YyG~h3KXty!!GB~t2 z`njhAfYA9m*BIM5l0XJ5k|B#^fJ7Yj`xyh&#bD7wFgW%ELS6`Mfgo#`)rz{vg0N&d zf0?(oP2kw}30u?6+~z7+x4F13!YAxpytFhIt_#(8%6~dw02K-f8KW7hdetvSX@Gb-HI( znP3ref}cy^u#Ak-ouM(TM4TZXV>#HU!78ykk6~XIZi(57E+z;7h?F31Z2V zhh$MKx$Y^F410?_M56D+5|3!f2FXIBNHUZ^8!WpfmVE9hSsa#K_k4SAqw2;sQ3||T zfvQ?+EPdUYpWgIXl!#>$wOz6_9FkBhNs!1=#FCT}S;`~HUTbL#P!mPhHb^AHl55}R zOBzdW6-(0h%C0?s(fV{gyoz`JLA^Hzb{d&W56Z#4R!9q9SV=)XFA#yD!49O!HAJ-a&m zz-7#Tb@ZUIxA*M8R}^*Bv}!3@9SwY|3!mybdwh?$&42J7~y} zyTVFj`kAp}CV3z06!RUq$~eNz(e5E~x!Nm!7ED|#oM>rqCl27+dD5v(zlV^wX|1HZ zzw3(hYpm0g$O+KSr{)?gS5j-%XEK9UI;j}-P44)g_W2eV9{-{U?A!urQD|DZj%;7oh+*- z2-Asra=N8~5>-}92=U>1A{KT<5dGz3Y98O(Lgt0Qu0T{hkr!Y|O^Y2;F;iV^yD|+W z$#YE>Q0}c~#}NHPp7H|z^7BNFiBfJbd#2Tb@NO}_&5*THM+lX+5tZbOFo&s_7WgqDrv*L+MQkLFOQs{} z-a|7295-79bZ@<9j9-8`Nsi-SMF7+twzPE=Rhend>rxnKCuFe&gLB8xOV2KwV|TJL znVa=&h>M<;3BF}3-6H+GGG`)uam^mW4=-mDLT^13)Xp5J=kn&X$sE{_{TzA2RqD#G zz>38|e(N={gpc7cc+{i2wKt^A-{uA5%ncxDUTd)g){RRbci}L34v3a_Ep@1Y3oT)2PPR5uHZX!5=GFa zeuV)v@=(Dv>sBg{2=W>;Az^eraf)x(cwJ2+UElhqLL6!es zMi`*ZTAu`8YYTfL-CmWy>TY|@%zIp@XQz!x zyLRBuyZBQ!GT}DD9&3UfJ8sfc;P*N;5T3RuLg4ESD8X@n4`j49l{l#+Nk4CWBXx9K zNhJb6wv)HsO6G!=P`ZBb3Z?35#BN+~O+6X_DM!Gov?ip21QzpEX%D}1o`n2lXZAn> zrOILJ@&J6uDyqzzj1HkiXV0myu9BX1Zn>;;?+ zj2d?+<+LE#KBsjD9k%jLOHzmg*H8o-RBa;$mvWblnQLE5)q()gHPk7*wvKsxeZ6~whZf+A&`p~9S)}Hz zt*orvU)wQuXAN&>mZtNQFC4sWWU8an?N=2C+t_v?cL-f?CsP-4N=;Wr<%px_A9-7N zJpaGF{^on7haTJyw21!giPX2Jdj5e>s_=Bh2fPPIUwgx);{WVx;hO&NmD%N`1>s-5 znR@r5x4-$OSd6gmIEh<^mY@6Cd*8&^rSaad+q@4`_I=%bWjL90@OB~Xrzig+++3N( z5O(!&;>H&b($MLYeMh>#7*1x}dEgRFJ?gO-gvg1WvVRTI&|@)8G@t5M`d(5y+F9u)FC-un5E=szP4n?C>m diff --git a/tests/phonon/tone.wav b/tests/phonon/tone.wav new file mode 100644 index 0000000000000000000000000000000000000000..2fa06a72a996900a3991c639a1120497a4d02f0f GIT binary patch literal 8942 zcmXY$Wl$Vjw1puAcX!v|8r-GjTkYjA=Fd;MO$ zI)A!PovN;`I%|J>t?ldTY6ez;Lvx_cc3piGxo9u@$?IsNxqfOQ?1haYG7}gVl`vm>~i0;*=N}Q zMeuysMEFxoDeeovbb<3?%EgI`$rrgUGF|uzl;NIYrotD(UI!2Rcl$i>9CTT*ud;%f z<{OM@O{}Ii7pOJHIEGRiFdwf*83?{#`p=ZjFhu*I+FuH8 zQXC@5yf*BOXFQMkckt_MOU2V4Mj!W+JExm5KZUCJN*xPYvT5m6$(9NHvCdIL)B&;% z>4>O8tohOK!;r`e!bnGCPTKRRz}SxoGAZmC_BoveaitYilJ%)AkGif5d>iYYG5D3R zp|+QIY<0GQ!R^dJ_6{||5^ z{2;s_uoF~)F`PD59G!sd42=mA^*8h3@ciJ?U|(%@-*n%=Q5&Zgq@XV~FZ_{Lfj#?- z-j(3bU|)m7c4s)hAASs807PZO`iWk$p4LDVYpD^dyQ3VMJE z;4KnJ)}YGJuSLtpX(WD0amxtG$t-}EnpWX{)-pLc#W58PwK`2d+ar5l4JS=b%%5K+{pS7ioZ*<|5_h|xgak|utpd~J z)2A5kS#a7dIQ`{b%Pjgxdybvpt`KgqrepC1Cd4zd{O_1Y; ztA&@P@0`DNuyNQBQXIXHxs7{^w*X!M*MJ2)3qBjmhS>~%j>rso8^{bdgze7E_?o++PQi7!H=N@_-7Nv%Trs^N&Kq&2TYql>Pmw~v_rhoIz8 z0bwR6QXVX4!JEphxYh4fOY zI%SKbNvZ=IL46Vf*_hHnZKJEjOvn96#HVUxn&r|9?aBq7b|&QA`7t1;2t1 z2krq)q9@jt$H;4CQu3jk)B^npD#yj(C%pa(X&-hn!3*2Q5KK@CqnK zG9YJAKF~U%ZpU6vXiC19{wTXK|5Ax_<<+{5CUl2ZpY({?)b)kBRh4b<4;SMb)(!3u zp%{q)xiytuO;BISeN|mJijqHEy+a_Vf?2O#03jtQh^yJFsVHX7S*z6qJ=f%KfYIK+{!! z+}O@C%+AWW+g%hU2+s^W4w*;XN5x>S;@a_D0GjZf5I`sZGVrFj%NTVO89@#435@nj z_J+IHI1SsDS_B$b>FsJ9E6>SBi~9;rb6scII=y{xxEo#&ifA3E+aZI5mAtktUU zFRsgbl=UiYF)1oOFGeY9pQ=G=A~k@z;4#q%>;?Ntb`)NkZB$20MLb(_bQ+k|pNA_p zu5hmf8&%r}dg_OoC;rS?tbE@(+Q*;vGn;b#5Ev2Tk(E$p)@aa$oliIaX%ppW?Do{_ zp|5hlU%^+xIKpkwGT1M;7`zAY0k{Z^;+JqAuwCfva4m#)h(O>ozaQRc_hBbKI|j=F zV@>@C&Ce?D<$@(7gi5%BSZ5jT|6$+GS;Z_EO(~4%^*!jAYWh%jqw;IXnS#RXvUI_e zx`d`!!{}|A3^kq{Nm_#V@e}kSS(4vV9B7EB?wFML{v<@&`7BgkchSf4w>1q7=4}(* z*@J20KW9&VId4Yqv7F$~ws1)BV?{qo(-hyF^U|3#v^B$9yF0A9IC}c}aQfd4dK9XM ze1f`%VZ<5WH}Qdh8!(M$!*^lzFgmCX1V`vb-~)Iz?6Zfa%N_gYR_><51||>-FDiIQ zaf;OP2D0y*d3q$do4No$60Ome`XE2+h_o~2r(3|GjQyObfDnv?iFZaDf0{ULP` zQphBD16o}miPTCCp$5*>lx)^+?& z^P%AxI@>XikMKLmbon&Z|Fm=r5=`bS=j`H~B|U6mGVtiY&X5>{2ud9@f>p!w0-u0X zsA47KKjOHtI_O!XW0+m=qQ8l+k=LZFt0UUR!FnRdzM<^&E`J7TLD%okZMG-d=uN0mdQ9i2U#=bUIc9FAQV>vp^ak3~=F-u!HF2 za0!G)$V`BvpSL%U`xB=`+wT?@#(8>M8r+c5+r^&4F76@QA+`7+sZ>3=6{Cz!{^MO~qR6jib`=>cd40^l~dNphy}{~rrU@x4h` z)8JX}^F)eA%6Dpv8*AI{_XH1Jn)o<3ylk*V+UGib$h^$yC=e;uATy!VrT$e{^ZX0* zOquG;dE$)UcB7C|*s-cWK?=rfNhTRx-hVb}JJHIc=cshW|dzB8R6&4+c3l~X0g z1!LK5kU}yOVq$lq;%UVcJu)ZB8~j6L17Cn>QVKbMilO&J$HX-!`lc#o!gK2iUzfeE zZmD-~-RT+}7#(At_5KyNA+-1J@hQ_)j$uA6(VNnr6+fRN=x`YQZI*4F=n(8$;W_9- z_vZ>$4I4+Ap$)P1xC49@pg@o&WB@~WI_?m2g!+tZ4^0cw^T+sDdbYa=JBV73n4%2} zv`5u?6>_8qBK&-@?7B=PN7lQe>k&)lGeTqB1IAsiS_JC{s)kDy3$t^+XH=zlB&x>Y zqnYT36bxCBNMbE~bCR|A|&hXC3FSuA5QWg1=u_dYV@BWBU z`trTZtYS76Vv-vkL)d6vOGp$`EY|EOsF=Jj!MIX z;Ar?~zyZKb$OjJagE)6A7A+8t4+{<6@i+I?^6GX~b+ohLG0!k!*R@u+Q#vQJBntBD zaaN!8IO*TJyve&7A4EQi#l^DnFXmDNgHwEF(Ca3wSjzt^a4C2 zP7;;DesG0!iQ-KA5TzNblkg_lB;6+aQ@(zQNTo$xRMYtmroR1Q!70xL`YQAGUw_sZ zaI8JthC=^HWXsj7WN2Q|-!pczMA{iR7rP&M&-*`3TY3C z4BYn_q*@DBA`iN2Ag^rG< zYjt*&sFI5O3)#5ztYqH=|JanM%d~$ftmJh_=i5Xs@C*2a)JA?yrO+i~Hse&1a#O!# zHs;zFah40$AQ~oHKX>07d_0~uyYb6&vv5!QgnU+z^Co|zD3gq|lDPVe&I_XjGf5i; z$23=FFCpJ9fBj(luwO_!v@*63*Ncw?R)Ky10G{A&a9=V1qQsFdp-Mq?crz^4L)+!1 z{Y@)f(;@>-ZCy2O1s17#;mf@2>|f5DJIdODub(VdPA87W_YZa&v^4+xRux~mUGO<4 zBBLwjrx_0Cj9_SKqD{(@>6+aSE>&^BlQ);%z)6C`OM9w=5>wT$RjSM+w7CP>LNF!J}A6V!)vn`J~GX>O0~zkba<@8D&QtT z{-H9+r>NH$Ron%emFAfRT56yUu{?bV} zm#6q$8ZFAlpT*&DcJLV3W8F;ubz|0j+;#9;_s>?B2Cf>`a@V5%+~myORL>-Zc%PUF zdK*=i(oI@}NEiSng9uUt`Is_EQ;%+o?M~22nM$9{HY?~aDXE;SGi&ba_}2G!gfi8+ zAhq^zd*+W1V+E@s&tsu7i8;Atm1fPy`bWkNmY#OP&R^V{yi@&51Mh~oBf7$u&}rCH z+z$RR5D#F0VtfkD2#Y`~guf2^5^Ng)`qI4o-KretZJNz*ouAc}*DzI9mfaQ05P)$l zGDnam6wuSSQb>b!G|Y(~9p_yr>;(#I(!zvJHz&I?lgY`L*SBP=Bhy z62rA6;3|GY_Kos&4MV-E^WqjpwtP;}Zfjn%zHb7?g4@C_hSSiuv5UA3JPGIn(gA5e z1>Xeusrm45#Iq2az)Yy?ee2HbY+`rLa@aUfpQ>4^k}CI9!c1t0`!4GV!-qd|+ZC(V z7R;t(Ms)hH9i2^=>)b2RB`x{avu~%DCgT#Yv6WE~5DR6v z>Q$kDGlrVFD?8?BquHKf=dj4vjGPlCsoVbkc z6sJVxIPd6r+5kn1ybN-IKZtLLbHq5XhZIT)pv6apLw;&3IV!yJ}@ zA{o%q*bba5z(#mOh$X-YRH$YhVfipk;o=CPko17xzO!C0-9{WYZA#32&!_4Rs1GXT z%G?m+6Nu+jW==ghx1YP|zWjT(dOUitxO<}&*T7x#yG*|5W3GQDDzzo?Ra|tm6n&p! zNFD-biGD;q;!UD7s6$F3zo6F9FUR2GYm@G!-On1#yIG8`cvHLC7}<{P#SFikY?@bH z1%LDZ0U3l@LGEKgv_zy_xk@&qbYYXbmXUT3oVh$gU~u?;pi8I`vK_UDX~pRP`h*t3 zAHq+90znE$#SLKSC{`p-Xjvc+oEKK8zqIH!c1~P?Vd@BF6Cf zK>T;?iu*kC1d#IpF(E+_HCOUK-&J5eu?55aY!8$dBFF%ZI4N4_us9#V8ycb6G;CFGh*Rz^32{a&TrK^(U36g@sxjd$9wT$+MP1}gIvx{X@)R7;3 zjUCd>`E`#fKbFkq|DAm^JuTTK!7TP=lnKq5QV9`cg7}azMKjZ5DSq zaT#LBcFvu`^JNy*|J9#uE$E^R#EtdNNdJ1Yv9^mno@5H(sNs_l#Yn$ae0vV3!)^4` ztkgQ!f#BNZx#CmkuNLeWc8o-!{jtBHo3#nR2wsF4fEO5qYVUb;Cz2;@HRz6iyw7t_ z5!WyWjJ3R3njxc((m8p>eW@IgP`)Mh2TX@YFL%W^Dwgiec#Js@T<9uov93R@Ixe*@ zY|BZ_=t&7m)QP(oeL~x%z{rB6^I!w9oG1oPf$U@&^wEgv47 z6kE8sI{4e=Pd$S*Yc{u-5J7@2m!}e|iPQgW>}iRyvv6*3=Ybvh(E=wz+7JP#e=u&i zG<*tRLAXZHBzys$;e~P57&g=m#DfsEz$bqHcpJHsohodJ7M8{_dZQZi$}O^=#LWbI zxsWW=r-Xyet+y*i^T!htLmNGc?cW;pYK1Edis^ZNS%GPJNvQZ+F@y93YA+ceVZchL zVwDnoKz~vp`9Fvub}>5f5lNzH0$F}}OGVY?V>PCY&21lho(z#DI_8vD-fo@lKR(@O zzQ#2upe=q?_Ow68D67c&My$jPZZ8wyRe! zEvQa$kFfRGbdZ}2>o_XKOCs{6vPIHEl27CJVtk@FX$q7C(pzwV_=%WE)B`0*H_0kg zdwO*=DQ+MUlj@oIESIIIr);WPuc5g0Zg<$=&GD$&&0qeT^?SA_6=#h&`r(CIu~n=M+1t4n*;)+5O$yh$BR8iy+js; zz6d&jEBUN>JakF7PqGR%9WzkSwo}tlV3Nug_T!yl!=G6>yuQP{9={kqZ8oakAJ&=K zZ2t316X6{!rIc>DvtW+Ev8)}14?7wGo+=X^-H@;M>wWQb}zmhk$tIiikj#6p=pS@*<%*`jZ`yHF8WuCd7@sh#DZq~M24Kg)Muc@}K@W)+a&amoO|<@jG2HU5ouBiZy8%oY-VrDi%8vYwYQTKQ z?cYSn4tYVbuXQ#DHdj--lkGfybn4CA%Kz3oqH z=8Jn%qa(w8+?^MiPwHAKCrWe+`m)Q@nNofvyo()-dPVzA;Udp~N?~Vu#tq%fURXbH&~=UU%=UTczZ%36R*RH|x~y#60zMNEB?uCdfgXGel$@MJ6Om(~ zB|%R9_k2P;mt9O8Os&tDy)&HF<~+xyI3pD!;=(t@euZiO=wFD1HA|0Y0>}IZ9(J|1 zgw%^v%a?^0?&P#*Fs43F#KeKnd`gS@mh4Ts3$lYJL?oz8f|2JagEWKa#n?Yka-x>u zloMMJP-<88_~&%89C{`RXNNl_vk6 zoa_vXOt~(^ub$nG__M)qfpvh}ROppNkz9vLp5}dh29p5GOLo@IjqdEQeZS9veIca? zN7OZpF77-2H6TxLBk&L|0|@*oRtz&1?gFLOM*(m@e{Xj8n@*o?uUQBfKh(?9s8o)V zy(%s$n9F6wQhVxgFtBxdMRtB^qJ3zpN2L8#qk1hj#6n7*e-5=-nO-T<$WhRLziemXYBFP@rY0j1Ut@;HkZ%TH?%jmvFWJyAnN6KiueD~V8Y z^6iw9n|2R%eq(pXQpp6=AJP1+G9i~CffZul`N}E*u~2ur zWA(2Et0~11jXq3ALldUXrV?IKnvcvzrza=F61-xQqAt?@p>RSz#0LCL6a*u||47~B z57cWT}Qv)>2wvxLa4n7}GpWXZAx>>rX0wpILoLBhEMR%kH zl-Sg}b#55-nVncKJG^sU^xW~u@aGGb3Tr@$qE9gIaVhvKKo#U~jesCLH#7|iM6DrY zL-zyk!((BOJvdxo_Fh)PrX+*kT4HJ<3fqze!U*0Iwl`;Fq2vU%e!N&Woiv)&Ki+B6 z((^N}DzB8eFfr$SMr#Tp(KYT1q!1fw5;QMN1ARa*umU1T0~trf(d(oCiHnDnKAmxx zgD(^-FKh|!(i_ki^O$+FG`?=Pn|-9f^qGB+*F)r;RJuZz+H-AvL%QjtRlof= zmqQOlh#{AQ-i7)ii%?YX=H&c>71nYo@Clq4T-6H`l%ffVwI zM1|(iTSOCZ4%{W(pm@?=MXARsBs@q~Ojpdlmd{!;Q*pK~sA;V|xi=D;sCUoHtls=R Ga_~P Date: Thu, 6 Jan 2011 18:45:44 -0300 Subject: [PATCH 093/703] Fixes connecting signal to decorated slot. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Decorated methods on classes derived from QObject are not called when connected to Qt signals because they get a name different from the decorated method. To solve this decorated methods are registered as global slots. An unit test was added. Reviewed by Hugo Parente Reviewed by Renato Araújo --- PySide/QtCore/glue/qobject_connect.cpp | 13 ++++++++- tests/pysidetest/CMakeLists.txt | 5 ++-- tests/pysidetest/decoratedslot_test.py | 39 ++++++++++++++++++++++++++ 3 files changed, 54 insertions(+), 3 deletions(-) create mode 100644 tests/pysidetest/decoratedslot_test.py diff --git a/PySide/QtCore/glue/qobject_connect.cpp b/PySide/QtCore/glue/qobject_connect.cpp index 91c830a..f6b0dce 100644 --- a/PySide/QtCore/glue/qobject_connect.cpp +++ b/PySide/QtCore/glue/qobject_connect.cpp @@ -1,9 +1,20 @@ +static bool isDecorator(PyObject* method, PyObject* self) +{ + Shiboken::AutoDecRef methodName(PyObject_GetAttrString(method, "__name__")); + if (!PyObject_HasAttr(self, methodName)) + return true; + Shiboken::AutoDecRef otherMethod(PyObject_GetAttr(self, methodName)); + return otherMethod.object() != method; +} + static bool getReceiver(PyObject* callback, QObject** receiver, PyObject** self) { + bool forceGlobalReceiver = false; if (PyMethod_Check(callback)) { *self = PyMethod_GET_SELF(callback); if (Shiboken::Converter::checkType(*self)) *receiver = Shiboken::Converter::toCpp(*self); + forceGlobalReceiver = isDecorator(callback, *self); } else if (PyCFunction_Check(callback)) { *self = PyCFunction_GET_SELF(callback); if (*self && Shiboken::Converter::checkType(*self)) @@ -14,7 +25,7 @@ static bool getReceiver(PyObject* callback, QObject** receiver, PyObject** self) *self = 0; } - bool usingGlobalReceiver = !*receiver; + bool usingGlobalReceiver = !*receiver || forceGlobalReceiver; if (usingGlobalReceiver) { PySide::SignalManager& signalManager = PySide::SignalManager::instance(); *receiver = signalManager.globalReceiver(); diff --git a/tests/pysidetest/CMakeLists.txt b/tests/pysidetest/CMakeLists.txt index 4b94a2a..61ee424 100644 --- a/tests/pysidetest/CMakeLists.txt +++ b/tests/pysidetest/CMakeLists.txt @@ -72,9 +72,10 @@ target_link_libraries(testbinding add_dependencies(testbinding pyside QtCore QtGui libpyside pysidetest) -PYSIDE_TEST(homonymoussignalandmethod_test.py) +PYSIDE_TEST(decoratedslot_test.py) PYSIDE_TEST(delegatecreateseditor_test.py) +PYSIDE_TEST(homonymoussignalandmethod_test.py) +PYSIDE_TEST(list_signal_test.py) PYSIDE_TEST(modelview_test.py) PYSIDE_TEST(version_test.py) -PYSIDE_TEST(list_signal_test.py) diff --git a/tests/pysidetest/decoratedslot_test.py b/tests/pysidetest/decoratedslot_test.py new file mode 100644 index 0000000..63a5be7 --- /dev/null +++ b/tests/pysidetest/decoratedslot_test.py @@ -0,0 +1,39 @@ +#!/usr/bin/python + +import unittest +from PySide.QtCore import QObject +from testbinding import TestObject + +class Receiver(QObject): + def __init__(self): + QObject.__init__(self) + self.called = False + + def ReceiverDecorator(func): + def decoratedFunction(self, *args, **kw): + func(self, *args, **kw) + return decoratedFunction + + # This method with the same name of the internal decorated function + # is here to test the binding capabilities. + def decoratedFunction(self): + pass + + @ReceiverDecorator + def slot(self): + self.called = True + + +class DecoratedSlotTest(unittest.TestCase): + + def testCallingOfDecoratedSlot(self): + obj = TestObject(0) + receiver = Receiver() + obj.staticMethodDouble.connect(receiver.slot) + obj.emitStaticMethodDoubleSignal() + self.assert_(receiver.called) + + +if __name__ == '__main__': + unittest.main() + From 36b7f922b2de2bffc80b60e9a8e1536083c2cad6 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Thu, 6 Jan 2011 19:30:03 -0200 Subject: [PATCH 094/703] Fix bug#560 - "Lack of QtCore.Signal documentation" MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewer: Renato Araújo Marcelo Lira --- doc/CMakeLists.txt | 1 + doc/conf.py.in | 4 +- doc/extras/PySide.QtCore.Signal.rst | 144 ++++++++++++++++++++++++++++ doc/extras/PySide.QtCore.Slot.rst | 95 ++++++++++++++++++ 4 files changed, 242 insertions(+), 2 deletions(-) create mode 100644 doc/extras/PySide.QtCore.Signal.rst create mode 100644 doc/extras/PySide.QtCore.Slot.rst diff --git a/doc/CMakeLists.txt b/doc/CMakeLists.txt index 7f72f41..c460543 100644 --- a/doc/CMakeLists.txt +++ b/doc/CMakeLists.txt @@ -28,6 +28,7 @@ add_custom_target("docrsts" --documentation-data-dir=${DOC_DATA_DIR} --output-directory=${CMAKE_CURRENT_BINARY_DIR}/rst --documentation-code-snippets-dir=${CMAKE_CURRENT_SOURCE_DIR}/codesnippets + --documentation-extra-sections-dir=${CMAKE_CURRENT_SOURCE_DIR}/extras ${CMAKE_CURRENT_BINARY_DIR}/typesystem_doc.xml WORKING_DIRECTORY ${${module}_SOURCE_DIR} COMMENT "Running generator to generate documentation..." diff --git a/doc/conf.py.in b/doc/conf.py.in index d2d7408..b984126 100644 --- a/doc/conf.py.in +++ b/doc/conf.py.in @@ -42,7 +42,7 @@ master_doc = 'contents' # General information about the project. project = u'PySide' -copyright = u'2009-2010, Nokia Corporation' +copyright = u'2009-2011, Nokia Corporation' # The version info for the project you're documenting, acts as replacement for # |version| and |release|, also used in various other places throughout the @@ -68,7 +68,7 @@ release = '@BINDING_API_VERSION_FULL@' # List of directories, relative to source directory, that shouldn't be searched # for source files. -exclude_trees = ['_build'] +exclude_trees = ['_build', 'extras'] # The reST default role (used for this markup: `text`) to use for all documents. #default_role = None diff --git a/doc/extras/PySide.QtCore.Signal.rst b/doc/extras/PySide.QtCore.Signal.rst new file mode 100644 index 0000000..441473e --- /dev/null +++ b/doc/extras/PySide.QtCore.Signal.rst @@ -0,0 +1,144 @@ +.. module:: PySide.QtCore +.. _Signal: + +Signal +****** + +Synopsis +-------- + +Functions +^^^^^^^^^ + ++---------------------------------------------------------------------------------------------+ +|def :meth:`connect` (receiver) | ++---------------------------------------------------------------------------------------------+ +|def :meth:`disconnect` (receiver) | ++---------------------------------------------------------------------------------------------+ +|def :meth:`emit` (\*args) | ++---------------------------------------------------------------------------------------------+ + +Detailed Description +-------------------- + + The :class:`~.Signal` class provides a way to declare and connect Qt signals in a pythonic way. + + PySide adopt PyQt's new signal and slot syntax as-is. The PySide implementation is functionally compatible with the PyQt 4.5 one, with the exceptions listed bellow. + + .. note:: Parts of the documentation bellow are from the `PyQt4 documentation `_ public available on the internet Copyright (c) 2010 Riverbank Computing Limited just modified to fit the PySide implementation. + + +Defining New Signals with QtCore.Signal() +----------------------------------------- + + PySide automatically defines signals for all Qt's built-in signals. New signals can be defined as class attributes using the QtCore.Signal() factory. + + QtCore.Signal() takes a number of type arguments that corresponds to the signature of the signal. Each type may be a Python type object or a string that is the name of a C++ type. Alternatively each argument could be a sequence of type arguments. In this case each sequence defines the signature of a different signal overload. The first overload will be the default. + + QtCore.Signal() takes an optional name keyword argument that is the name of the signal. If it is omitted then the name of the class attribute is used. + + The following example shows the definition of a number of new signals: + + :: + + from PySide import QtCore + + class Foo(QtCore.QObject): + + # This defines a signal called 'closed' that takes no arguments. + closed = QtCore.Signal() + + # This defines a signal called 'rangeChanged' that takes two + # integer arguments. + range_changed = QtCore.Signal(int, int, name='rangeChanged') + + # This defines a signal called 'valueChanged' that has two overloads, + # one that takes an integer argument and one that takes a QString + # argument. + valueChanged = QtCore.Signal((int, ), (unicode, )) + + # The following will create exactly the same overloaded signal as + # above and demonstrates the use of C++ type names instead of Python + # type objects, and lists instead of tuples. + valueChanged = QtCore.pyqtSignal(['int'], ['unicode']) + + New signals should only be defined in sub-classes of QObject. + + New signals defined in this way will be automatically added to the class's QMetaObject. This means that they will appear in Qt Designer and can be introspected using the QMetaObject API. + +Connecting, Disconnecting and Emitting Signals +---------------------------------------------- + + Signals are connected and disconnected to slots using the :meth:`Signal.connect` and :meth:`Signal.disconnect` methods of a bound signal and emitted using the :meth:`Signal.emit` method. + + The following code demonstrates the definition, connection and emit of a signal without arguments: + + :: + + from PySide import QtCore + + class Foo(QtCore.QObject): + # Define a new signal called 'trigger' that has no arguments. + trigger = QtCore.pyqtSignal() + + def connect_and_emit_trigger(self): + # Connect the trigger signal to a slot. + self.trigger.connect(self.handle_trigger) + + # Emit the signal. + self.trigger.emit() + + def handle_trigger(self): + # Show that the slot has been called. + print "trigger signal received" + + The following code demonstrates the connection of overloaded signals: + + :: + + from PySide import QtGui + + class Bar(QtGui.QComboBox): + + def connect_activated(self): + # The PyQt documentation will define what the default overload is. + # In this case it is the overload with the single integer argument. + self.activated.connect(self.handle_int) + + # For non-default overloads we have to specify which we want to + # connect. In this case the one with the single string argument. + # (Note that we could also explicitly specify the default if we + # wanted to.) + self.activated[str].connect(self.handle_string) + + def handle_int(self, index): + print "activated signal passed integer", index + + def handle_string(self, text): + print "activated signal passed string", text + +Connecting Signals Using Keyword Arguments +------------------------------------------ + + It is also possible to connect signals by passing a slot as a keyword argument corresponding to the name of the signal when creating an object. For example the following three fragments are equivalent: + + :: + + act = QtGui.QAction("Action", self) + act.triggered.connect(self.on_triggered) + + act = QtGui.QAction("Action", self, triggered=self.on_triggered) + + +.. method:: Signal.connect(receiver[, type=Qt.AutoConnection]) + + Create a connection between this signal and a `receiver`, the `receiver` can be a Python callable, a :class:`Slot` or a :class:`Signal`. + +.. method:: Signal.disconnect(receiver) + + Disconnect this signal from a `receiver`, the `receiver` can be a Python callable, a :class:`Slot` or a :class:`Signal`. + +.. method:: Signal.emit(*args) + + `args` is the optional sequence of arguments to pass to any connected slots. + diff --git a/doc/extras/PySide.QtCore.Slot.rst b/doc/extras/PySide.QtCore.Slot.rst new file mode 100644 index 0000000..27791d0 --- /dev/null +++ b/doc/extras/PySide.QtCore.Slot.rst @@ -0,0 +1,95 @@ +.. module:: PySide.QtCore +.. _Slot: + +Slot +**** + +Detailed Description +-------------------- + + PySide adopt PyQt's new signal and slot syntax as-is. The PySide implementation is functionally compatible with the PyQt 4.5 one, with the exceptions listed bellow. + + .. note:: Parts of the documentation bellow are from the `PyQt4 documentation `_ public available on the internet Copyright (c) 2010 Riverbank Computing Limited just modified to fit the PySide implementation. + + Although PySide allows any Python callable to be used as a slot when connecting signals, it is sometimes necessary to explicitly mark a Python method as being a Qt slot and to provide a C++ signature for it. PySide provides the QtCore.Slot() function decorator to do this. + + All of the non-keyword arguments to the decorator are interpreted as the types of the corresponding C++ arguments. A type is either a Python type object or a string that specifies a C++ type. The decorator also takes two optional keywords arguments: name and result. name is the name of the slot that will be seen by C++. If ommitted the name of the Python method being decorated will be used. result is the type of the result and may also be a Python type object or a string that specifies a C++ type. + + For example: + + :: + + @QtCore.Slot() + def foo(self): + """ C++: void foo() """ + + @QtCore.Slot(int, unicode) + def foo(self, arg1, arg2): + """ C++: void foo(int, QString) """ + + @QtCore.Slot(int, name='bar') + def foo(self, arg1): + """ C++: void bar(int) """ + + @QtCore.Slot(int, result=int) + def foo(self, arg1): + """ C++: int foo(int) """ + + @QtCore.Slot(int, QtGui.QWidget) + def foo(self, arg1): + """ C++: int foo(int, QWidget*) """ + + It is also possible to chain the decorators in order to define a Python method several times with different signatures. + + For example: + + :: + + @QtCore.Slot(int) + @QtCore.Slot('QString') + def valueChanged(self, value): + """ Two slots will be defined in the QMetaObject. """ + +Connecting Slots By Name +------------------------ + + PySide supports the QtCore.QMetaObject.connectSlotsByName() function that is most commonly used by pyside-uic generated Python code to automatically connect signals to slots that conform to a simple naming convention besides the QtCore.Slot decoration. + + For example the :class:`PySide.QtGui.QSpinBox` class has the following signals: + + :: + + void valueChanged(int i); + void valueChanged(const QString& text); + + For example, if you were interested in the integer variant of the signal then your slot definition would look like the following: + + :: + + @QtCore.Slot(int) + def on_spinbox_valueChanged(self, i): + # i will be an integer. + pass + + If you wanted to handle both variants of the signal, but with different Python methods, then your slot definitions might look like the following: + + :: + + @QtCore.Slot(int, name='on_spinbox_valueChanged') + def spinbox_int_value(self, i): + # i will be an integer. + pass + + @QtCore.Slot(unicode, name='on_spinbox_valueChanged') + def spinbox_qstring_value(self, s): + # s will be a Python unicode object. + pass + + The following shows an example using a button when you are not interested in the optional argument: + + :: + + @QtCore.Slot() + def on_button_clicked(self): + pass + From 4c79d1e8cd54b3bf7dc0d2ea3d5f5b000a862fc7 Mon Sep 17 00:00:00 2001 From: Marcelo Lira Date: Thu, 6 Jan 2011 20:56:14 -0300 Subject: [PATCH 095/703] Fixes the fix in the commit a1cf8f03. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Reviewed by Hugo Parente Reviewed by Renato Araújo --- PySide/QtCore/glue/qobject_connect.cpp | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/PySide/QtCore/glue/qobject_connect.cpp b/PySide/QtCore/glue/qobject_connect.cpp index f6b0dce..91a272c 100644 --- a/PySide/QtCore/glue/qobject_connect.cpp +++ b/PySide/QtCore/glue/qobject_connect.cpp @@ -4,7 +4,8 @@ static bool isDecorator(PyObject* method, PyObject* self) if (!PyObject_HasAttr(self, methodName)) return true; Shiboken::AutoDecRef otherMethod(PyObject_GetAttr(self, methodName)); - return otherMethod.object() != method; + return reinterpret_cast(otherMethod.object())->im_func != \ + reinterpret_cast(method)->im_func; } static bool getReceiver(PyObject* callback, QObject** receiver, PyObject** self) From f4f48519ec2dade5a016b87bc089e90a0caf71a4 Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Fri, 7 Jan 2011 18:58:15 -0300 Subject: [PATCH 096/703] Fix Qvariant to Cpp conversion. Fixes bug #589 Reviewer: Hugo Parente Lima Marcelo Lira --- PySide/QtCore/qvariant_conversions.h | 2 ++ 1 file changed, 2 insertions(+) diff --git a/PySide/QtCore/qvariant_conversions.h b/PySide/QtCore/qvariant_conversions.h index 0b89534..283cf4f 100644 --- a/PySide/QtCore/qvariant_conversions.h +++ b/PySide/QtCore/qvariant_conversions.h @@ -19,6 +19,8 @@ struct Converter if (PyObject_TypeCheck(type, &SbkObjectType_Type)) { SbkObjectType* sbkType = reinterpret_cast(type); const char* typeName = Shiboken::ObjectType::getOriginalName(sbkType); + if (!typeName) + return 0; bool valueType = '*' != typeName[qstrlen(typeName) - 1]; // Do not convert user type of value From 1caaffba59c8a6897d58e7682842f4b4a86405f2 Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Fri, 7 Jan 2011 18:58:40 -0300 Subject: [PATCH 097/703] Created unit test for bug 589. Reviewer: Hugo Parente Lima Marcelo Lira --- tests/QtGui/CMakeLists.txt | 1 + tests/QtGui/bug_589.py | 19 +++++++++++++++++++ 2 files changed, 20 insertions(+) create mode 100644 tests/QtGui/bug_589.py diff --git a/tests/QtGui/CMakeLists.txt b/tests/QtGui/CMakeLists.txt index 6032808..e8d4804 100644 --- a/tests/QtGui/CMakeLists.txt +++ b/tests/QtGui/CMakeLists.txt @@ -28,6 +28,7 @@ PYSIDE_TEST(bug_549.py) PYSIDE_TEST(bug_569.py) PYSIDE_TEST(bug_576.py) PYSIDE_TEST(bug_585.py) +PYSIDE_TEST(bug_589.py) PYSIDE_TEST(customproxywidget_test.py) PYSIDE_TEST(deepcopy_test.py) PYSIDE_TEST(float_to_int_implicit_conversion_test.py) diff --git a/tests/QtGui/bug_589.py b/tests/QtGui/bug_589.py new file mode 100644 index 0000000..0c7cdec --- /dev/null +++ b/tests/QtGui/bug_589.py @@ -0,0 +1,19 @@ +# trimmed down diagramscene.py to demonstrate crash in sizeHint() + +import sys +from PySide import QtCore, QtGui +import unittest + +class CustomWidget(QtGui.QGraphicsProxyWidget): + def itemChange(self, eventType, value): + QtGui.QGraphicsProxyWidget.itemChange(self, eventType, value) + +class Bug589(unittest.TestCase): + def testCase(self): + widget = QtGui.QGraphicsProxyWidget() + custom = CustomWidget() + custom.setParentItem(widget) + +if __name__ == "__main__": + app = QtGui.QApplication(sys.argv) + unittest.main() From 64a35df0c16663bea2693701f576005e2f8ebb4c Mon Sep 17 00:00:00 2001 From: Marcelo Lira Date: Mon, 10 Jan 2011 15:26:54 -0300 Subject: [PATCH 098/703] Added condition for a phonon test that fails on Win32 with Qt 4.7.1. This is due to a bug on Phonon::createPath that happens with the specific combination of Win32 platform and Qt 4.7.1. The bug is reported as fixed for Qt 4.7.2, but it wasn't released yet. For more details on the bug: http://bugreports.qt.nokia.com/browse/QTBUG-13062 Reviewed by Hugo Parente Reviewed by Lauro Moura --- tests/phonon/CMakeLists.txt | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/tests/phonon/CMakeLists.txt b/tests/phonon/CMakeLists.txt index c2b939e..ee94c0b 100644 --- a/tests/phonon/CMakeLists.txt +++ b/tests/phonon/CMakeLists.txt @@ -1,3 +1,7 @@ -PYSIDE_TEST(basic_playing_test.py) +if (NOT WIN32 OR NOT ${QTVERSION} VERSION_EQUAL 4.7.1) + # Any usage of Phonon::createPath will fail on Win32 and Qt 4.7.1. + # Check: http://bugreports.qt.nokia.com/browse/QTBUG-13062 + PYSIDE_TEST(basic_playing_test.py) +endif() PYSIDE_TEST(bug_328.py) PYSIDE_TEST(capabilities_test.py) From 99cbdef40cda9379651951d0f187fbba6e829ae1 Mon Sep 17 00:00:00 2001 From: Marcelo Lira Date: Tue, 11 Jan 2011 18:53:06 -0300 Subject: [PATCH 099/703] Added test for QPainter.setPen() method. MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Calls it with enum, to call the setPen(Qt.PenStyle) signature, and with an integer, to call the setPen(QColor) signature (QColor is implicitly built from an unsigned int in C++). For more details see Bug #511: http://bugs.openbossa.org/show_bug.cgi?id=511 Reviewed by Luciano Wolf Reviewed by Renato Araújo --- tests/QtGui/qpen_test.py | 30 +++++++++++++++++++++++++++--- 1 file changed, 27 insertions(+), 3 deletions(-) diff --git a/tests/QtGui/qpen_test.py b/tests/QtGui/qpen_test.py index f9e9b18..b1e0b7a 100644 --- a/tests/QtGui/qpen_test.py +++ b/tests/QtGui/qpen_test.py @@ -1,10 +1,25 @@ import unittest +from helper import UsesQApplication -from PySide.QtCore import Qt -from PySide.QtGui import QPen +from PySide.QtCore import Qt, QTimer +from PySide.QtGui import QPen, QPainter, QWidget -class QPenTest(unittest.TestCase): +class Painting(QWidget): + def __init__(self): + QWidget.__init__(self) + self.penFromEnum = None + self.penFromInteger = None + + def paintEvent(self, event): + painter = QPainter(self) + painter.setPen(Qt.NoPen) + self.penFromEnum = painter.pen() + painter.setPen(int(Qt.NoPen)) + self.penFromInteger = painter.pen() + + +class QPenTest(UsesQApplication): def testCtorWithCreatedEnums(self): '''A simple case of QPen creation using created enums.''' @@ -14,6 +29,15 @@ class QPenTest(unittest.TestCase): join = Qt.PenJoinStyle(0) pen = QPen(Qt.blue, width, style, cap, join) + def testSetPenWithPenStyleEnum(self): + '''Calls QPainter.setPen with both enum and integer. Bug #511.''' + w = Painting() + w.show() + QTimer.singleShot(1000, self.app.quit) + self.app.exec_() + self.assertEqual(w.penFromEnum.style(), Qt.NoPen) + self.assertEqual(w.penFromInteger.style(), Qt.SolidLine) + if __name__ == '__main__': unittest.main() From 7e667036d58a0549dd08a152149e1ba1f410bfb7 Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Tue, 11 Jan 2011 17:58:52 -0300 Subject: [PATCH 100/703] Use python base name as library prefix. Use the same CMAKE_BUILD_TYPE as shiboken if none was specified. Append SHIBOKEN_PYTHON_BASENAME in the library suffix. Fix bug #509. Reviewer: Marcelo Lira Lauro Moura --- CMakeLists.txt | 2 +- libpyside/CMakeLists.txt | 5 ++++- libpyside/PySideConfig-spec.cmake.in | 9 +++++++++ libpyside/PySideConfig.cmake.in | 14 +++++--------- 4 files changed, 19 insertions(+), 11 deletions(-) create mode 100644 libpyside/PySideConfig-spec.cmake.in diff --git a/CMakeLists.txt b/CMakeLists.txt index 33eda53..856ed6a 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -56,7 +56,7 @@ else() endif() if(NOT CMAKE_BUILD_TYPE) - set(CMAKE_BUILD_TYPE Release) + set(CMAKE_BUILD_TYPE ${SHIBOKEN_BUILD_TYPE}) endif() set(BINDING_NAME PySide) diff --git a/libpyside/CMakeLists.txt b/libpyside/CMakeLists.txt index 04bf0a7..6450045 100644 --- a/libpyside/CMakeLists.txt +++ b/libpyside/CMakeLists.txt @@ -24,7 +24,7 @@ target_link_libraries(pyside set_target_properties(pyside PROPERTIES VERSION ${BINDING_API_VERSION} SOVERSION "${BINDING_API_MAJOR_VERSION}.${BINDING_API_MINOR_VERSION}" - OUTPUT_NAME "pyside${pyside_SUFFIX}" + OUTPUT_NAME "pyside${pyside_SUFFIX}-${SHIBOKEN_PYTHON_BASENAME}" DEFINE_SYMBOL PYSIDE_EXPORTS) # @@ -54,6 +54,7 @@ configure_file("${CMAKE_CURRENT_SOURCE_DIR}/pyside.pc.in" "${CMAKE_CURRENT_BINARY_DIR}/pyside${pyside_SUFFIX}.pc" @ONLY) # create cmake-config files configure_file("${CMAKE_CURRENT_SOURCE_DIR}/PySideConfig.cmake.in" "${CMAKE_CURRENT_BINARY_DIR}/PySideConfig.cmake" @ONLY) +configure_file("${CMAKE_CURRENT_SOURCE_DIR}/PySideConfig-spec.cmake.in" "${CMAKE_CURRENT_BINARY_DIR}/PySideConfig-${SHIBOKEN_PYTHON_BASENAME}.cmake" @ONLY) configure_file("${CMAKE_CURRENT_SOURCE_DIR}/PySideConfigVersion.cmake.in" "${CMAKE_CURRENT_BINARY_DIR}/PySideConfigVersion.cmake" @ONLY) install(FILES ${libpyside_HEADERS} @@ -65,5 +66,7 @@ install(TARGETS pyside EXPORT pyside install(FILES "${CMAKE_CURRENT_BINARY_DIR}/pyside${pyside_SUFFIX}.pc" DESTINATION "${LIB_INSTALL_DIR}/pkgconfig") install(FILES "${CMAKE_CURRENT_BINARY_DIR}/PySideConfig.cmake" DESTINATION "${LIB_INSTALL_DIR}/cmake/PySide-${BINDING_API_VERSION}") +install(FILES "${CMAKE_CURRENT_BINARY_DIR}/PySideConfig-${SHIBOKEN_PYTHON_BASENAME}.cmake" + DESTINATION "${LIB_INSTALL_DIR}/cmake/PySide-${BINDING_API_VERSION}") install(FILES "${CMAKE_CURRENT_BINARY_DIR}/PySideConfigVersion.cmake" DESTINATION "${LIB_INSTALL_DIR}/cmake/PySide-${BINDING_API_VERSION}") diff --git a/libpyside/PySideConfig-spec.cmake.in b/libpyside/PySideConfig-spec.cmake.in new file mode 100644 index 0000000..b5b73dc --- /dev/null +++ b/libpyside/PySideConfig-spec.cmake.in @@ -0,0 +1,9 @@ +# PYSIDE_INCLUDE_DIR - Directories to include to use PySide +# PYSIDE_LIBRARY - Files to link against to use PySide +# PYSIDE_PYTHONPATH - Path to where the PySide Python module files could be found +# PYSIDE_TYPESYSTEMS - Type system files that should be used by other bindings extending PySide + +SET(PYSIDE_INCLUDE_DIR "@CMAKE_INSTALL_PREFIX@/include/PySide@pyside_SUFFIX@") +SET(PYSIDE_LIBRARY "@LIB_INSTALL_DIR@/@CMAKE_SHARED_LIBRARY_PREFIX@pyside@pyside_SUFFIX@@LIBRARY_OUTPUT_SUFFIX@@CMAKE_SHARED_LIBRARY_SUFFIX@") +SET(PYSIDE_PYTHONPATH "@SITE_PACKAGE@") +SET(PYSIDE_TYPESYSTEMS "@CMAKE_INSTALL_PREFIX@/share/PySide@pyside_SUFFFIX@/typesystems") diff --git a/libpyside/PySideConfig.cmake.in b/libpyside/PySideConfig.cmake.in index b5b73dc..28203da 100644 --- a/libpyside/PySideConfig.cmake.in +++ b/libpyside/PySideConfig.cmake.in @@ -1,9 +1,5 @@ -# PYSIDE_INCLUDE_DIR - Directories to include to use PySide -# PYSIDE_LIBRARY - Files to link against to use PySide -# PYSIDE_PYTHONPATH - Path to where the PySide Python module files could be found -# PYSIDE_TYPESYSTEMS - Type system files that should be used by other bindings extending PySide - -SET(PYSIDE_INCLUDE_DIR "@CMAKE_INSTALL_PREFIX@/include/PySide@pyside_SUFFIX@") -SET(PYSIDE_LIBRARY "@LIB_INSTALL_DIR@/@CMAKE_SHARED_LIBRARY_PREFIX@pyside@pyside_SUFFIX@@LIBRARY_OUTPUT_SUFFIX@@CMAKE_SHARED_LIBRARY_SUFFIX@") -SET(PYSIDE_PYTHONPATH "@SITE_PACKAGE@") -SET(PYSIDE_TYPESYSTEMS "@CMAKE_INSTALL_PREFIX@/share/PySide@pyside_SUFFFIX@/typesystems") +if (NOT PYTHON_BASENAME) + message(STATUS "Using default python: @PYTHON_BASENAME@") + SET(PYTHON_BASENAME @PYTHON_BASENAME@) +endif() +include(@LIB_INSTALL_DIR@/cmake/PySide-@pyside_VERSION@/PySideConfig-${PYTHON_BASENAME}.cmake) From 3ac4080bfe3052b8ee805a0a983a68cf142241b2 Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Wed, 12 Jan 2011 19:26:27 -0300 Subject: [PATCH 101/703] Create a new parent test. Check if the parent does not increase the reference if you set the parent twice. --- tests/QtCore/qobject_parent_test.py | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/tests/QtCore/qobject_parent_test.py b/tests/QtCore/qobject_parent_test.py index eb8cae2..df81216 100644 --- a/tests/QtCore/qobject_parent_test.py +++ b/tests/QtCore/qobject_parent_test.py @@ -25,6 +25,13 @@ class ParentRefCountCase(unittest.TestCase): self.child.setParent(self.parent) self.assertEqual(getrefcount(self.child), 3) + def testSetParentTwice(self): + self.assertEqual(getrefcount(self.child), 2) + self.child.setParent(self.parent) + self.assertEqual(getrefcount(self.child), 3) + self.child.setParent(self.parent) + self.assertEqual(getrefcount(self.child), 3) + def testConstructor(self): #QObject(QObject) refcount changes child = QObject(self.parent) From f98566eebd41613236ad88b7aba676d4b081bb12 Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Thu, 13 Jan 2011 10:29:49 -0300 Subject: [PATCH 102/703] Fixed path to include file used on cmake files. Reviewer: Bruno Araujo --- libpyside/PySideConfig.cmake.in | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/libpyside/PySideConfig.cmake.in b/libpyside/PySideConfig.cmake.in index 28203da..f25487c 100644 --- a/libpyside/PySideConfig.cmake.in +++ b/libpyside/PySideConfig.cmake.in @@ -2,4 +2,4 @@ if (NOT PYTHON_BASENAME) message(STATUS "Using default python: @PYTHON_BASENAME@") SET(PYTHON_BASENAME @PYTHON_BASENAME@) endif() -include(@LIB_INSTALL_DIR@/cmake/PySide-@pyside_VERSION@/PySideConfig-${PYTHON_BASENAME}.cmake) +include(@LIB_INSTALL_DIR@/cmake/PySide-@BINDING_API_VERSION@/PySideConfig-${PYTHON_BASENAME}.cmake) From 67f0db5a2b6ad96d41bda2b96112bba3cba55862 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Mon, 10 Jan 2011 17:52:37 -0200 Subject: [PATCH 103/703] Add polymorphic-id-expression to QGraphicsObject and QDeclarativeItem. --- PySide/QtDeclarative/typesystem_declarative.xml | 2 +- PySide/QtGui/typesystem_gui_common.xml | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/PySide/QtDeclarative/typesystem_declarative.xml b/PySide/QtDeclarative/typesystem_declarative.xml index 5649bf2..e754006 100644 --- a/PySide/QtDeclarative/typesystem_declarative.xml +++ b/PySide/QtDeclarative/typesystem_declarative.xml @@ -97,7 +97,7 @@ - + diff --git a/PySide/QtGui/typesystem_gui_common.xml b/PySide/QtGui/typesystem_gui_common.xml index 676829e..1d1ea01 100644 --- a/PySide/QtGui/typesystem_gui_common.xml +++ b/PySide/QtGui/typesystem_gui_common.xml @@ -5584,7 +5584,7 @@ --> - + From a24e8ed2811a9d4f116d3c2e05721a4e47b7a09f Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Tue, 11 Jan 2011 15:17:56 -0200 Subject: [PATCH 104/703] Don't crash when a unknown type is given as a meta call argument. --- libpyside/signalmanager.cpp | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/libpyside/signalmanager.cpp b/libpyside/signalmanager.cpp index 75a0d19..2581d71 100644 --- a/libpyside/signalmanager.cpp +++ b/libpyside/signalmanager.cpp @@ -324,8 +324,14 @@ static int PySide::callMethod(QObject* object, int id, void** args) void* data = args[i+1]; const char* dataType = paramTypes[i].constData(); - PyObject* arg = Shiboken::TypeResolver::get(dataType)->toPython(data); - PyTuple_SET_ITEM(preparedArgs, i, arg); + Shiboken::TypeResolver* tr = Shiboken::TypeResolver::get(dataType); + if (tr) { + PyObject* arg = tr->toPython(data); + PyTuple_SET_ITEM(preparedArgs, i, arg); + } else { + PyErr_Format(PyExc_TypeError, "Can't call meta function because I have no idea how to handle %s", dataType); + return -1; + } } QString methodName = method.signature(); From bcad6d0392ace27a9a4acb0097f2e170cb5f6e21 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Wed, 12 Jan 2011 12:31:59 -0200 Subject: [PATCH 105/703] Fix documentation for QWidget.winId() --- PySide/QtGui/typesystem_gui_common.xml | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/PySide/QtGui/typesystem_gui_common.xml b/PySide/QtGui/typesystem_gui_common.xml index 1d1ea01..37ffb89 100644 --- a/PySide/QtGui/typesystem_gui_common.xml +++ b/PySide/QtGui/typesystem_gui_common.xml @@ -3475,6 +3475,19 @@ + + + Returns the window system identifier of the widget. + + Portable in principle, but if you use it you are probably about to do something non-portable. Be careful. + + If a widget is non-native (alien) and winId() is invoked on it, that widget will be provided a native handle. + + On X11 the type returned is long, on other platforms it's a PyCObject. + + This value may change at run-time. An event with type PySide.QtCore.QEvent.WinIdChange will be sent to the widget following a change in window system identifier. + + From 4587eec6cb142f4fd3d6f302b4ee840c3cc77886 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Wed, 12 Jan 2011 14:56:56 -0200 Subject: [PATCH 106/703] Remove protected fields of event classes. Event classes have a lot of non-documented protected fields, those fields are removed from PySide because they are Qt implementation details, besides the fact they are accessible by ordinary event methods. --- PySide/QtGui/typesystem_gui_common.xml | 78 +++++++++++++++++++++++++- 1 file changed, 76 insertions(+), 2 deletions(-) diff --git a/PySide/QtGui/typesystem_gui_common.xml b/PySide/QtGui/typesystem_gui_common.xml index 37ffb89..61bf68d 100644 --- a/PySide/QtGui/typesystem_gui_common.xml +++ b/PySide/QtGui/typesystem_gui_common.xml @@ -71,11 +71,86 @@ - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + @@ -144,7 +219,6 @@ - From 776b41613d765bbeae21ff8626ebbccfbd1e35d3 Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Wed, 12 Jan 2011 15:45:35 -0200 Subject: [PATCH 107/703] Removed useless rejections Reviewer: Marcelo Lira Lauro Moura --- PySide/QtCore/typesystem_core.xml | 287 +------------------------ PySide/QtGui/typesystem_gui_common.xml | 66 +----- 2 files changed, 11 insertions(+), 342 deletions(-) diff --git a/PySide/QtCore/typesystem_core.xml b/PySide/QtCore/typesystem_core.xml index f41acd5..031244b 100644 --- a/PySide/QtCore/typesystem_core.xml +++ b/PySide/QtCore/typesystem_core.xml @@ -56,17 +56,6 @@ - - - - - - - - - - - @@ -88,9 +77,11 @@ + + @@ -182,26 +173,6 @@ - - - - - - - - - - - - - - - - - - - - @@ -256,239 +227,6 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - @@ -506,7 +244,6 @@ - @@ -1369,12 +1106,6 @@ %PYARG_0 = %CONVERTTOPYTHON[bool](retval); - - - - @@ -2297,6 +2028,7 @@ + @@ -2608,6 +2340,7 @@ + @@ -2651,6 +2384,7 @@ + @@ -2759,8 +2493,6 @@ - - @@ -2801,8 +2533,6 @@ - - @@ -2997,10 +2727,6 @@ - - - - @@ -3016,8 +2742,6 @@ - - @@ -3025,6 +2749,7 @@ + diff --git a/PySide/QtGui/typesystem_gui_common.xml b/PySide/QtGui/typesystem_gui_common.xml index 61bf68d..e6dabc4 100644 --- a/PySide/QtGui/typesystem_gui_common.xml +++ b/PySide/QtGui/typesystem_gui_common.xml @@ -151,53 +151,6 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - @@ -561,7 +514,7 @@ - + @@ -570,7 +523,7 @@ - + @@ -2136,8 +2089,6 @@ - - @@ -3159,8 +3110,6 @@ - - @@ -3198,8 +3147,6 @@ - - @@ -3336,9 +3283,6 @@ - - - @@ -5760,11 +5704,11 @@ - - - + + + From d9940e55a41b83d30ce41e8002f614bfe16d54bf Mon Sep 17 00:00:00 2001 From: Renato Araujo Oliveira Filho Date: Thu, 13 Jan 2011 13:51:51 -0300 Subject: [PATCH 108/703] Fix typo on Cmake files. Reviewer: Bruno Araujo --- libpyside/PySideConfig-spec.cmake.in | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/libpyside/PySideConfig-spec.cmake.in b/libpyside/PySideConfig-spec.cmake.in index b5b73dc..b017b9e 100644 --- a/libpyside/PySideConfig-spec.cmake.in +++ b/libpyside/PySideConfig-spec.cmake.in @@ -4,6 +4,6 @@ # PYSIDE_TYPESYSTEMS - Type system files that should be used by other bindings extending PySide SET(PYSIDE_INCLUDE_DIR "@CMAKE_INSTALL_PREFIX@/include/PySide@pyside_SUFFIX@") -SET(PYSIDE_LIBRARY "@LIB_INSTALL_DIR@/@CMAKE_SHARED_LIBRARY_PREFIX@pyside@pyside_SUFFIX@@LIBRARY_OUTPUT_SUFFIX@@CMAKE_SHARED_LIBRARY_SUFFIX@") +SET(PYSIDE_LIBRARY "@LIB_INSTALL_DIR@/@CMAKE_SHARED_LIBRARY_PREFIX@pyside@pyside_SUFFIX@@LIBRARY_OUTPUT_SUFFIX@-@SHIBOKEN_PYTHON_BASENAME@@CMAKE_SHARED_LIBRARY_SUFFIX@") SET(PYSIDE_PYTHONPATH "@SITE_PACKAGE@") -SET(PYSIDE_TYPESYSTEMS "@CMAKE_INSTALL_PREFIX@/share/PySide@pyside_SUFFFIX@/typesystems") +SET(PYSIDE_TYPESYSTEMS "@CMAKE_INSTALL_PREFIX@/share/PySide@pyside_SUFFIX@/typesystems") From b57192c596230ef8fb6a9cb1fe51d3a72e719e4f Mon Sep 17 00:00:00 2001 From: Hugo Parente Lima Date: Thu, 13 Jan 2011 17:51:14 -0200 Subject: [PATCH 109/703] Fix bug#584 - "python pickle module can't treat QByteArray object of PySide" Reviewer: Luciano Wolf Lauro Moura --- PySide/QtCore/typesystem_core.xml | 36 +++++++++++++------------- PySide/QtGui/typesystem_gui_common.xml | 6 ++--- PySide/typesystem_templates.xml | 5 +--- tests/QtCore/qbytearray_test.py | 11 ++++++++ 4 files changed, 33 insertions(+), 25 deletions(-) diff --git a/PySide/QtCore/typesystem_core.xml b/PySide/QtCore/typesystem_core.xml index 031244b..24ce91f 100644 --- a/PySide/QtCore/typesystem_core.xml +++ b/PySide/QtCore/typesystem_core.xml @@ -433,7 +433,7 @@ - + @@ -451,7 +451,7 @@ - + @@ -504,7 +504,7 @@ - + @@ -562,7 +562,7 @@ - + @@ -574,7 +574,7 @@ - + @@ -586,7 +586,7 @@ - + @@ -605,7 +605,7 @@ - + @@ -617,7 +617,7 @@ - + @@ -682,7 +682,7 @@ - + @@ -736,7 +736,7 @@ - + @@ -755,7 +755,7 @@ - + @@ -768,7 +768,7 @@ - + @@ -788,7 +788,7 @@ - + @@ -1217,7 +1217,7 @@ - + @@ -1232,7 +1232,7 @@ - + @@ -1281,7 +1281,7 @@ - + @@ -1294,8 +1294,8 @@ - - + + diff --git a/PySide/QtGui/typesystem_gui_common.xml b/PySide/QtGui/typesystem_gui_common.xml index e6dabc4..50247c3 100644 --- a/PySide/QtGui/typesystem_gui_common.xml +++ b/PySide/QtGui/typesystem_gui_common.xml @@ -499,14 +499,14 @@ - PyObject *points = PyList_New(%CPPSELF.count()); - for (int i = 0; i < %CPPSELF.count(); ++i){ + PyObject* points = PyList_New(%CPPSELF.count()); + for (int i = 0, max = %CPPSELF.count(); i < max; ++i){ int x, y; %CPPSELF.point(i, &x, &y); PyList_SET_ITEM(points, i, %CONVERTTOPYTHON[QPoint](QPoint(x, y))); } - + diff --git a/PySide/typesystem_templates.xml b/PySide/typesystem_templates.xml index 4604fda..dd07459 100644 --- a/PySide/typesystem_templates.xml +++ b/PySide/typesystem_templates.xml @@ -188,10 +188,7 @@ +