aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--PySide/QtCore/glue/qcoreapplication_init.cpp11
-rw-r--r--PySide/QtCore/typesystem_core.xml11
-rw-r--r--PySide/QtGui/glue/qapplication_init.cpp20
-rw-r--r--libpyside/pyside.cpp21
-rw-r--r--libpyside/pyside.h9
-rw-r--r--libpyside/signalmanager.cpp7
6 files changed, 59 insertions, 20 deletions
diff --git a/PySide/QtCore/glue/qcoreapplication_init.cpp b/PySide/QtCore/glue/qcoreapplication_init.cpp
index 7601dbd1d..14ccbb8f9 100644
--- a/PySide/QtCore/glue/qcoreapplication_init.cpp
+++ b/PySide/QtCore/glue/qcoreapplication_init.cpp
@@ -1,21 +1,20 @@
// Global variables used to store argc and argv values
static int QCoreApplicationArgCount;
static char** QCoreApplicationArgValues;
-static bool leavingPython = false;
/**
* Called at QtCore module exit
*/
void DeleteQCoreApplicationAtExit()
{
- leavingPython = true;
QCoreApplication *cpp = QCoreApplication::instance();
if (cpp) {
Shiboken::BindingManager &bmngr = Shiboken::BindingManager::instance();
PyObject* pySelf = bmngr.retrieveWrapper(cpp);
- if (pySelf)
- bmngr.invalidateWrapper(pySelf);
- cpp->deleteLater();
+ cpp->flush();
+ QCoreApplication::processEvents();
+ bmngr.invalidateWrapper(pySelf);
+ delete cpp;
}
}
@@ -54,7 +53,7 @@ int SbkQCoreApplication_Init(PyObject* self, PyObject* args, PyObject*)
PySide::signalUpdateSource(self);
cptr->metaObject();
- Py_AtExit(DeleteQCoreApplicationAtExit);
+ PySide::registerCleanupFunction(DeleteQCoreApplicationAtExit);
Py_INCREF(self);
return 1;
}
diff --git a/PySide/QtCore/typesystem_core.xml b/PySide/QtCore/typesystem_core.xml
index d7c5891a7..f10ed0709 100644
--- a/PySide/QtCore/typesystem_core.xml
+++ b/PySide/QtCore/typesystem_core.xml
@@ -552,8 +552,8 @@
</inject-code>
<add-function signature="__moduleShutdown()">
- <inject-code class="target" position="beginning">
- PySide::SignalManager::instance().clear();
+ <inject-code class="target" position="beginning">
+ PySide::runCleanupFunctions();
</inject-code>
</add-function>
@@ -1875,12 +1875,7 @@
<!-- Obsolete -->
<modify-function signature="argc()" remove="all"/>
<!-- Obsolete -->
- <modify-function signature="notify(QObject*,QEvent*)">
- <inject-code class="shell" position="beginning">
- Shiboken::ThreadStateSaver threadStateSaver;
- if (!leavingPython)
- threadStateSaver.save();
- </inject-code>
+ <modify-function signature="notify(QObject*,QEvent*)" allow-thread="yes">
<modify-argument index="2" invalidate-after-use="yes"/>
</modify-function>
<modify-function signature="QCoreApplication(int &amp;, char **)" access="private"/>
diff --git a/PySide/QtGui/glue/qapplication_init.cpp b/PySide/QtGui/glue/qapplication_init.cpp
index 699633a1d..208d59a52 100644
--- a/PySide/QtGui/glue/qapplication_init.cpp
+++ b/PySide/QtGui/glue/qapplication_init.cpp
@@ -4,19 +4,29 @@ extern PyObject* moduleQtGui;
static int QApplicationArgCount;
static char** QApplicationArgValues;
static const char QAPP_MACRO[] = "qApp";
-static bool leavingPython = false;
void DeleteQApplicationAtExit()
{
- leavingPython = true;
PySide::SignalManager::instance().clear();
QCoreApplication* cpp = QApplication::instance();
if (cpp) {
Shiboken::BindingManager &bmngr = Shiboken::BindingManager::instance();
- PyObject* pySelf = bmngr.retrieveWrapper(cpp);
- if (pySelf)
+ cpp->flush();
+
+ // Delete all widgets, this is slow but is necessary to avoid problems with python object
+ foreach(QWidget* w, QApplication::allWidgets()) {
+ PyObject* pySelf = bmngr.retrieveWrapper(w);
+
+ w->deleteLater();
+ //Make sure all events will send before invalidated the python object
+ QApplication::processEvents();
bmngr.invalidateWrapper(pySelf);
+ }
+
+ PyObject* pySelf = bmngr.retrieveWrapper(cpp);
cpp->deleteLater();
+ QApplication::processEvents();
+ bmngr.invalidateWrapper(pySelf);
}
}
@@ -62,7 +72,7 @@ int SbkQApplication_Init(PyObject* self, PyObject* args, PyObject*)
}
PyObject_SetAttrString(moduleQtGui, QAPP_MACRO, self);
- Py_AtExit(DeleteQApplicationAtExit);
+ PySide::registerCleanupFunction(DeleteQApplicationAtExit);
Py_INCREF(self);
return 1;
}
diff --git a/libpyside/pyside.cpp b/libpyside/pyside.cpp
index ddec19803..bd4ab7c64 100644
--- a/libpyside/pyside.cpp
+++ b/libpyside/pyside.cpp
@@ -24,18 +24,22 @@
#include "pyside.h"
#include "signalmanager.h"
#include "qproperty.h"
+#include "qsignal.h"
#include <basewrapper.h>
#include <conversions.h>
#include <algorithm>
-#include "qsignal.h"
+#include <QStack>
extern "C" void init_signal(PyObject* module);
extern "C" void init_slot(PyObject* module);
extern "C" void init_qproperty(PyObject* module);
+static QStack<PySide::CleanupFunction> cleanupFunctionList;
+
namespace PySide
{
+
void init(PyObject *module)
{
init_signal(module);
@@ -82,5 +86,20 @@ bool fillQtProperties(PyObject* qObj, const QMetaObject* metaObj, PyObject* kwds
return true;
}
+void registerCleanupFunction(CleanupFunction func)
+{
+ cleanupFunctionList.push(func);
+}
+
+void runCleanupFunctions()
+{
+ while (!cleanupFunctionList.isEmpty()) {
+ CleanupFunction f = cleanupFunctionList.pop();
+ f();
+ }
+}
+
+
+
} //namespace PySide
diff --git a/libpyside/pyside.h b/libpyside/pyside.h
index cae050b5d..2c5afb536 100644
--- a/libpyside/pyside.h
+++ b/libpyside/pyside.h
@@ -75,6 +75,15 @@ template<typename T>
struct initQtMetaType<T, false> {
};
+
+typedef void (*CleanupFunction)(void);
+
+/**
+ * Register a function to be called before python die
+ */
+PYSIDE_API void registerCleanupFunction(CleanupFunction func);
+PYSIDE_API void runCleanupFunctions();
+
} //namespace PySide
diff --git a/libpyside/signalmanager.cpp b/libpyside/signalmanager.cpp
index 8208796b2..3724500d5 100644
--- a/libpyside/signalmanager.cpp
+++ b/libpyside/signalmanager.cpp
@@ -22,6 +22,7 @@
#include "signalmanager.h"
#include "qproperty.h"
+#include "pyside.h"
#include <QHash>
#include <QStringList>
@@ -223,6 +224,11 @@ struct SignalManager::SignalManagerPrivate
GlobalReceiver m_globalReceiver;
};
+static void clearSignalManager()
+{
+ PySide::SignalManager::instance().clear();
+}
+
SignalManager::SignalManager() : m_d(new SignalManagerPrivate)
{
// Register Qt primitive typedefs used on signals.
@@ -234,6 +240,7 @@ SignalManager::SignalManager() : m_d(new SignalManagerPrivate)
TypeResolver::createValueTypeResolver<PyObjectWrapper>(PYTHON_TYPE);
TypeResolver::createValueTypeResolver<PyObjectWrapper>("object");
TypeResolver::createValueTypeResolver<PyObjectWrapper>("PySide::PyObjectWrapper");
+ PySide::registerCleanupFunction(clearSignalManager);
}
void SignalManager::clear()