@@ -344,6 +344,13 PyObject* PythonQtPrivate::wrapQObject(QObject* obj) | |||||
344 | return Py_None; |
|
344 | return Py_None; | |
345 | } |
|
345 | } | |
346 | PythonQtInstanceWrapper* wrap = findWrapperAndRemoveUnused(obj); |
|
346 | PythonQtInstanceWrapper* wrap = findWrapperAndRemoveUnused(obj); | |
|
347 | if (wrap && wrap->_wrappedPtr) { | |||
|
348 | // uh oh, we want to wrap a QObject, but have a C++ wrapper at that | |||
|
349 | // address, so probably that C++ wrapper has been deleted earlier and | |||
|
350 | // now we see a QObject with the same address. | |||
|
351 | // Do not use the old wrapper anymore. | |||
|
352 | wrap = NULL; | |||
|
353 | } | |||
347 | if (!wrap) { |
|
354 | if (!wrap) { | |
348 | // smuggling it in... |
|
355 | // smuggling it in... | |
349 | PythonQtClassInfo* classInfo = _knownClassInfos.value(obj->metaObject()->className()); |
|
356 | PythonQtClassInfo* classInfo = _knownClassInfos.value(obj->metaObject()->className()); | |
@@ -368,6 +375,16 PyObject* PythonQtPrivate::wrapPtr(void* ptr, const QByteArray& name) | |||||
368 | } |
|
375 | } | |
369 |
|
376 | |||
370 | PythonQtInstanceWrapper* wrap = findWrapperAndRemoveUnused(ptr); |
|
377 | PythonQtInstanceWrapper* wrap = findWrapperAndRemoveUnused(ptr); | |
|
378 | PythonQtInstanceWrapper* possibleStillAliveWrapper = NULL; | |||
|
379 | if (wrap && wrap->_wrappedPtr) { | |||
|
380 | // we have a previous C++ wrapper... if the wrapper is for a C++ object, | |||
|
381 | // we are not sure if it may have been deleted earlier and we just see the same C++ | |||
|
382 | // pointer once again. To make sure that we do not reuse a wrapper of the wrong type, | |||
|
383 | // we compare the classInfo() pointer and only reuse the wrapper if it has the same | |||
|
384 | // info. This is only needed for non-QObjects, since we know it when a QObject gets deleted. | |||
|
385 | possibleStillAliveWrapper = wrap; | |||
|
386 | wrap = NULL; | |||
|
387 | } | |||
371 | if (!wrap) { |
|
388 | if (!wrap) { | |
372 | PythonQtClassInfo* info = _knownClassInfos.value(name); |
|
389 | PythonQtClassInfo* info = _knownClassInfos.value(name); | |
373 | if (!info) { |
|
390 | if (!info) { | |
@@ -378,7 +395,7 PyObject* PythonQtPrivate::wrapPtr(void* ptr, const QByteArray& name) | |||||
378 | return p; |
|
395 | return p; | |
379 | } |
|
396 | } | |
380 |
|
397 | |||
381 |
// we do not know the metaobject yet, but we might know it by it |
|
398 | // we do not know the metaobject yet, but we might know it by its name: | |
382 | if (_knownQObjectClassNames.find(name)!=_knownQObjectClassNames.end()) { |
|
399 | if (_knownQObjectClassNames.find(name)!=_knownQObjectClassNames.end()) { | |
383 | // yes, we know it, so we can convert to QObject |
|
400 | // yes, we know it, so we can convert to QObject | |
384 | QObject* qptr = (QObject*)ptr; |
|
401 | QObject* qptr = (QObject*)ptr; | |
@@ -445,7 +462,12 PyObject* PythonQtPrivate::wrapPtr(void* ptr, const QByteArray& name) | |||||
445 | info->setMetaObject(wrapper->metaObject()); |
|
462 | info->setMetaObject(wrapper->metaObject()); | |
446 | } |
|
463 | } | |
447 |
|
464 | |||
|
465 | if (possibleStillAliveWrapper && possibleStillAliveWrapper->classInfo() == info) { | |||
|
466 | wrap = possibleStillAliveWrapper; | |||
|
467 | Py_INCREF(wrap); | |||
|
468 | } else { | |||
448 | wrap = createNewPythonQtInstanceWrapper(wrapper, info, ptr); |
|
469 | wrap = createNewPythonQtInstanceWrapper(wrapper, info, ptr); | |
|
470 | } | |||
449 | // mlabDebugConst("MLABPython","new c++ wrapper added " << wrap->_wrappedPtr << " " << wrap->_obj->className() << " " << wrap->classInfo()->wrappedClassName().latin1()); |
|
471 | // mlabDebugConst("MLABPython","new c++ wrapper added " << wrap->_wrappedPtr << " " << wrap->_obj->className() << " " << wrap->classInfo()->wrappedClassName().latin1()); | |
450 | } else { |
|
472 | } else { | |
451 | Py_INCREF(wrap); |
|
473 | Py_INCREF(wrap); |
@@ -56,16 +56,32 static PyObject *PythonQtStdOutRedirect_write(PyObject *self, PyObject *args) | |||||
56 | { |
|
56 | { | |
57 | PythonQtStdOutRedirect* s = (PythonQtStdOutRedirect*)self; |
|
57 | PythonQtStdOutRedirect* s = (PythonQtStdOutRedirect*)self; | |
58 | if (s->_cb) { |
|
58 | if (s->_cb) { | |
|
59 | QString output; | |||
|
60 | if (PyTuple_GET_SIZE(args)>=1) { | |||
|
61 | PyObject* obj = PyTuple_GET_ITEM(args,0); | |||
|
62 | if (PyUnicode_Check(obj)) { | |||
|
63 | PyObject *tmp = PyUnicode_AsUTF8String(obj); | |||
|
64 | if(tmp) { | |||
|
65 | output = QString::fromUtf8(PyString_AS_STRING(tmp)); | |||
|
66 | Py_DECREF(tmp); | |||
|
67 | } else { | |||
|
68 | return NULL; | |||
|
69 | } | |||
|
70 | } else { | |||
59 | char *string; |
|
71 | char *string; | |
60 | if (!PyArg_ParseTuple(args, "s", &string)) |
|
72 | if (!PyArg_ParseTuple(args, "s", &string)) { | |
61 | return NULL; |
|
73 | return NULL; | |
|
74 | } | |||
|
75 | output = QString::fromLatin1(string); | |||
|
76 | } | |||
|
77 | } | |||
62 |
|
78 | |||
63 | if (s->softspace > 0) { |
|
79 | if (s->softspace > 0) { | |
64 | (*s->_cb)(QString("")); |
|
80 | (*s->_cb)(QString("")); | |
65 | s->softspace = 0; |
|
81 | s->softspace = 0; | |
66 | } |
|
82 | } | |
67 |
|
83 | |||
68 |
(*s->_cb)( |
|
84 | (*s->_cb)(output); | |
69 | } |
|
85 | } | |
70 | return Py_BuildValue(""); |
|
86 | return Py_BuildValue(""); | |
71 | } |
|
87 | } |
General Comments 0
You need to be logged in to leave comments.
Login now