changeset 253:073b9153ed8a

Rev. 264 done right. Problems: - classwizard segfaults on exit due to a bug in signals/slots or runtime. - hellogl doesn't compile with dmd2 due to a bug in the compiler backend
author maxter
date Sun, 30 Aug 2009 09:59:12 +0000
parents 37eed70de029
children 34a37904ff77
files cpp/qt_qtd/qtd_core.cpp examples/dialogs/classwizard/classwizard_d1.d generator/cppimplgenerator.cpp generator/cppimplgenerator.h generator/dgenerator.cpp generator/dgenerator.h generator/generator.cpp generator/generator.h generator/typesystem_core-java.java generator/typesystem_core.xml qt/core/QMetaObject.d qt/d1/qt/QtDObject.d qt/d1/qt/QtdObject.d qt/d1/qt/Signal.d qt/d2/qt/QtDObject.d qt/d2/qt/QtdObject.d qt/d2/qt/Signal.d
diffstat 17 files changed, 865 insertions(+), 678 deletions(-) [+]
line wrap: on
line diff
--- a/cpp/qt_qtd/qtd_core.cpp	Sat Aug 22 12:50:58 2009 +0000
+++ b/cpp/qt_qtd/qtd_core.cpp	Sun Aug 30 09:59:12 2009 +0000
@@ -12,6 +12,12 @@
 #include "qtd_core.h"
 #include <iostream>
 
+
+extern "C" DLL_PUBLIC void* qtd_qobject(void* parent)
+{
+    return new QObject((QObject*)parent);
+}
+
 extern "C" DLL_PUBLIC QModelIndex qtd_to_QModelIndex(QModelIndexAccessor mia)
 {
     return * (QModelIndex *) (&mia) ;
@@ -40,13 +46,13 @@
 }
 
 #ifdef CPP_SHARED
-QTD_EXPORT_VAR(_d_toUtf8)
-QTD_EXPORT_VAR(__qtd_dummy)
+QTD_EXPORT_VAR(qtd_toUtf8);
+QTD_EXPORT_VAR(qtd_dummy);
 
-extern "C" DLL_PUBLIC void __qtd_qtd_core_initCallBacks(pfunc_abstr d_func, pfunc_abstr dummy) {
-    QTD_EXPORT_VAR_SET(_d_toUtf8, d_func);
-    QTD_EXPORT_VAR_SET(__qtd_dummy, dummy);
-//    std::cout << _d_toUtf8 << "\n";
+extern "C" DLL_PUBLIC void qtd_core_initCallBacks(pfunc_abstr d_func, pfunc_abstr dummy) {
+    QTD_EXPORT_VAR_SET(qtd_toUtf8, d_func);
+    QTD_EXPORT_VAR_SET(qtd_dummy, dummy);
+    //std::cout << "qtd_core initialized" << std::endl;
 }
 #endif
 
--- a/examples/dialogs/classwizard/classwizard_d1.d	Sat Aug 22 12:50:58 2009 +0000
+++ b/examples/dialogs/classwizard/classwizard_d1.d	Sun Aug 30 09:59:12 2009 +0000
@@ -139,7 +139,7 @@
 			block ~= "#endif\n";
 		}
 
-		auto headerFile = new QFile(outputDir ~ "/" ~ header);
+        scope headerFile = new QFile(outputDir ~ "/" ~ header);
 		if (!headerFile.open(QFile.WriteOnly | QFile.Text)) {
 			QMessageBox.warning(null, tr("Simple Wizard"),
 					Format(tr("Cannot write file {}:\n{}"),
@@ -193,7 +193,7 @@
 			}
 		}
 
-		auto implementationFile = new QFile(outputDir ~ "/" ~ implementation);
+        scope implementationFile = new QFile(outputDir ~ "/" ~ implementation);
 		if (!implementationFile.open(QFile.WriteOnly | QFile.Text)) {
 			QMessageBox.warning(null, tr("Simple Wizard"),
 					Format(tr("Cannot write file {}:\n{}"),
--- a/generator/cppimplgenerator.cpp	Sat Aug 22 12:50:58 2009 +0000
+++ b/generator/cppimplgenerator.cpp	Sun Aug 30 09:59:12 2009 +0000
@@ -465,26 +465,6 @@
     return !java_class->isQObject() && !java_class->typeEntry()->isValue();
 }
 
-void writeQtdEntityFunction(QTextStream &s, const AbstractMetaClass *java_class)
-{
-//    if (!(java_class->typeEntry()->isObject() || java_class->typeEntry()->isQObject()))
-//        return;
-    if (!java_class->hasVirtualFunctions())
-        return;
-
-    s << "extern \"C\" DLL_PUBLIC void *__" << java_class->name() << "_entity(void *q_ptr)" << endl;
-    s << "{" << endl;
-    {
-        Indentation indent(INDENT);
-            s << INDENT << "Qtd_QObjectEntity* a = dynamic_cast<Qtd_QObjectEntity*>((" << java_class->qualifiedCppName() << "*)q_ptr);" << endl
-              << INDENT << "if (a != NULL)" << endl
-              << INDENT << "    return a->d_entity();" << endl
-              << INDENT << "else" << endl
-              << INDENT << "    return NULL;" << endl;
-    }
-    s << "}" << endl << endl;
-}
-
 void CppImplGenerator::writeInterfaceCasts(QTextStream &s, const AbstractMetaClass *java_class)
 {
         // pointers to native interface objects for classes that implement interfaces
@@ -532,11 +512,6 @@
         s << "    emit_callbacks_" << java_class->name() << "[" << i << "] = (EmitCallback)"
              "sigs[" << i << "];" << endl;
 
-    if (java_class->isQObject())
-        s << "    qtd_D_" << java_class->name() << "_delete = "
-             "(qtd_pf_D_" << java_class->name() << "_delete)qobj_del;" << endl;
-
-
     s << "}" << endl;
 }
 
@@ -571,7 +546,13 @@
     if (java_class->isQObject())
         s << "#include <qtdynamicmetaobject.h>" << endl;
 */
+    if (java_class->isQObject())
+        s << "#include <QObjectEntity.h>" << endl;
+
     s << "#include <iostream>" << endl;
+
+
+
     Include inc = java_class->typeEntry()->include();
     if (!inc.name.isEmpty()) {
         s << "#include ";
@@ -608,7 +589,8 @@
     writeDefaultConstructedValues(s, java_class);
 
     if (hasCustomDestructor(java_class)) */
-    writeFinalDestructor(s, java_class);
+    if (!java_class->isQObject())
+        writeFinalDestructor(s, java_class);
 
     if (java_class->isQObject())
         writeSignalsHandling(s, java_class);
@@ -620,7 +602,8 @@
         }
         writeShellDestructor(s, java_class);
 
-        writeQtdEntityFunction(s, java_class);
+        if (!java_class->isQObject() && java_class->hasVirtualFunctions())
+            writeQtdEntityFunction(s, java_class);
 
         if (java_class->isQObject())
             writeQObjectFunctions(s, java_class);
@@ -723,6 +706,14 @@
 */
 // qtd    writeJavaLangObjectOverrideFunctions(s, java_class);
 
+    if (java_class->isQObject())
+    {
+        s << endl << endl
+          << "extern \"C\" DLL_PUBLIC void* qtd_" << java_class->name() << "_staticMetaObject() {" << endl
+          << "    return (void*)&" << java_class->name() << "::staticMetaObject;" << endl
+          << "}" << endl;
+    }
+
     s << endl << endl;
 
     priGenerator->addSource(java_class->package(), fileNameForClass(java_class));
@@ -838,7 +829,7 @@
                 }
 
                 s << function->marshalledName() << "_dispatch("
-                  << "this->d_entity()";
+                  << "this->dId";
 
                 if (f_type) {
                     if (f_type->isTargetLangString())
@@ -861,7 +852,7 @@
                     if (f_type->name() == "QModelIndex") {
                         s << INDENT << "QModelIndex __qt_return_value = qtd_to_QModelIndex( __d_return_value );" << endl;
 #ifdef Q_OS_WIN32
-s << "__qtd_dummy();" << endl; // hack!!!
+s << "qtd_dummy();" << endl; // hack!!!
 #endif
                         s << INDENT << "return __qt_return_value;" << endl;
                     } else if (f_type->typeEntry()->isStructInD())
@@ -1214,6 +1205,37 @@
     }
 }
 
+void CppImplGenerator::writeQObjectEntity(QTextStream &s, const AbstractMetaClass *java_class)
+{
+    QString entityName = java_class->name() + "Entity";
+    QString className = java_class->name();
+
+    s << "class " << entityName << " : public QObject, public QtD_QObjectEntity" << endl
+      << "{" << endl
+      << "public:" << endl
+      << "    Q_OBJECT_CHECK" << endl
+      << "    virtual int qt_metacall(QMetaObject::Call, int, void **);" << endl << endl
+
+      << "    " << entityName << "(QObject *qObject, void *dId) : QObject(), QtD_QObjectEntity(qObject, dId) {}" << endl
+      << "};" << endl << endl;
+
+    // QObject_Link::qt_metacall()
+    s << "int " << entityName << "::qt_metacall(QMetaObject::Call _c, int _id, void **_a)" << endl
+      << "{" << endl      
+      << "    _id = QObject::qt_metacall(_c, _id, _a);" << endl
+      << "    if (_id < 0 || _c != QMetaObject::InvokeMetaMethod)" << endl
+      << "        return _id;" << endl
+//      << "    Q_ASSERT(_id < 2);" << endl      
+      << "    emit_callbacks_" << java_class->name() << "[_id](dId, _a);" << endl      
+      << "    return -1;" << endl
+      << "}" << endl << endl;
+
+    s << "extern \"C\" DLL_PUBLIC void qtd_" << className << "_createEntity(void *nativeId, void* dId)" << endl
+      << "{" << endl
+      << "    new " << entityName << "((QObject*)nativeId, dId);" << endl
+      << "}" << endl << endl;
+}
+
 void CppImplGenerator::writeQObjectFunctions(QTextStream &s, const AbstractMetaClass *java_class)
 {
     // QObject::metaObject()
@@ -1257,21 +1279,16 @@
       << "  return " << java_class->qualifiedCppName() << "::qt_metacast(_clname);" << endl
       << "}" << endl << endl;
 */
-
-//    writeSignalsHandling(s, java_class);
-/*
-    // QObject_Link::qt_metacall()
+    
     s << "int " << shellClassName(java_class) << "::qt_metacall(QMetaObject::Call _c, int _id, void **_a)" << endl
       << "{" << endl;
 
-    s << "    _id = " << java_class->qualifiedCppName() << "::qt_metacall(_c, _id, _a);" << endl
+    s << "    _id = " << java_class->qualifiedCppName() << "::qt_metacall(_c, _id, _a);" << endl    
       << "    if (_id < 0 || _c != QMetaObject::InvokeMetaMethod)" << endl
-      << "        return _id;" << endl
-//      << "    Q_ASSERT(_id < 2);" << endl
-      << "    emit_callbacks_" << java_class->name() << "[_id](this->d_entity(), _a);" << endl
+      << "        return _id;" << endl      
+      << "    emit_callbacks_" << java_class->name() << "[_id](this->dId, _a);" << endl      
       << "    return -1;" << endl
       << "}" << endl << endl;
-*/
 }
 
 void CppImplGenerator::writeSignalHandler(QTextStream &s, const AbstractMetaClass *d_class, AbstractMetaFunction *function)
@@ -1316,65 +1333,6 @@
 
 }
 
-void CppImplGenerator::writeQObjectLink(QTextStream &s, const AbstractMetaClass *java_class)
-{
-    QString linkName = java_class->name() + "_Link";
-    QString className = java_class->name();
-
-    if (cpp_shared)
-        s << "extern \"C\" typedef void (*qtd_pf_D_" << java_class->name() << "_delete)(void *d_ptr);" << endl
-          << "qtd_pf_D_" << java_class->name() << "_delete qtd_D_" << java_class->name() << "_delete;" << endl << endl;
-    else
-        s << "extern \"C\" void qtd_D_" << java_class->name() << "_delete(void *d_ptr);" << endl << endl;
-
-    s << "class " << linkName << " : public QObject, public QObjectUserData" << endl
-      << "{" << endl
-      << "public:" << endl
-      << "    Q_OBJECT_CHECK" << endl
-      << "    virtual int qt_metacall(QMetaObject::Call, int, void **);" << endl << endl
-
-      << "    " << linkName << "(QObject *parent, void *d_ptr) : QObject() { _d_ptr = d_ptr; }" << endl
-      << "    ~" << linkName << "() { qtd_D_" << className << "_delete(_d_ptr); }" << endl
-      << "    void *d_entity() const { return _d_ptr; }" << endl << endl
-
-      << "private:" << endl
-      << "    void *_d_ptr;" << endl
-      << "};" << endl << endl;
-
-    // QObject_Link::qt_metacall()
-    s << "int " << linkName << "::qt_metacall(QMetaObject::Call _c, int _id, void **_a)" << endl
-      << "{" << endl
-      << "    _id = QObject::qt_metacall(_c, _id, _a);" << endl
-      << "    if (_id < 0 || _c != QMetaObject::InvokeMetaMethod)" << endl
-      << "        return _id;" << endl
-//      << "    Q_ASSERT(_id < 2);" << endl
-      << "    emit_callbacks_" << java_class->name() << "[_id](this->d_entity(), _a);" << endl
-      << "    return -1;" << endl
-      << "}" << endl << endl;
-
-    s << QString("inline %1_Link *get_%1_link(%1 *obj)").arg(className) << endl
-      << "{" << endl
-      << "    return static_cast<" << linkName << "*>(obj->userData(USER_DATA_ID));" << endl
-      << "}" << endl << endl;
-
-    s << QString("extern \"C\" DLL_PUBLIC void* qtd_%1_d_pointer(%1 *obj)").arg(className) << endl
-      << "{" << endl
-      << "    if (obj->userData(USER_DATA_ID)) {" << endl
-      << "        " << QString("%1_Link *qobj_helper = get_%1_link(obj);").arg(className) << endl
-      << "        return qobj_helper->d_entity();" << endl
-      << "    } else" << endl
-      << "        return NULL;" << endl
-      << "}" << endl << endl;
-
-    s << QString("extern \"C\" DLL_PUBLIC void qtd_%1_create_link(%1 *obj, void* d_obj)").arg(className) << endl
-      << "{" << endl
-      << "    if(obj->userData(USER_DATA_ID))" << endl
-      << "        return;" << endl
-      << "    " << QString("%1 *qobj_link = new %1(obj, d_obj);").arg(linkName) << endl
-      << "    obj->setUserData(USER_DATA_ID, qobj_link);" << endl
-      << "}" << endl << endl;
-}
-
 void CppImplGenerator::writeSignalsHandling(QTextStream &s, const AbstractMetaClass *java_class)
 {
     s << "extern \"C\" typedef void (*EmitCallback)(void*, void**);" << endl;
@@ -1406,31 +1364,7 @@
         s << endl << "};" << endl << endl;
     }
 
-    writeQObjectLink(s, java_class);
-
-    // Functions connecting/disconnecting shell's slots
-    for(int i = 0; i < signal_funcs.size(); i++) {
-        AbstractMetaFunction *signal = signal_funcs.at(i);
-        QString sigExternName = signalExternName(java_class, signal);
-
-        s << "extern \"C\" DLL_PUBLIC void " << sigExternName << "_connect"
-          << "(void* native_id)" << endl << "{" << endl
-          << "    " << shellClassName(java_class) << " *qobj = (" << shellClassName(java_class) << "*) native_id;" << endl
-          << "    const QMetaObject &mo = " << java_class->name() << "::staticMetaObject;" << endl
-          << "    const QMetaObject &mo2 = " << java_class->name() << "_Link::staticMetaObject;" << endl
-          << "    int signalId = mo.indexOfSignal(\"" << signal->minimalSignature() << "\");" << endl
-          << "    mo.connect(qobj, signalId, get_" << java_class->name() << "_link(qobj), mo2.methodCount() + " << i << ");" << endl
-          << "}" << endl;
-
-        s << "extern \"C\" DLL_PUBLIC void " << sigExternName << "_disconnect"
-          << "(void* native_id)" << endl << "{" << endl
-          << "    " << shellClassName(java_class) << " *qobj = (" << shellClassName(java_class) << "*) native_id;" << endl
-          << "    const QMetaObject &mo = " << shellClassName(java_class) << "::staticMetaObject;" << endl
-          << "    const QMetaObject &mo2 = " << java_class->name() << "_Link::staticMetaObject;" << endl
-          << "    int signalId = mo.indexOfSignal(\"" << signal->minimalSignature() << "\");" << endl
-          << "    mo.disconnect(qobj, signalId, get_" << java_class->name() << "_link(qobj), mo2.methodCount() + " << i << ");" << endl
-          << "}" << endl << endl;
-    }
+    writeQObjectEntity(s, java_class);
 }
 
 
@@ -1452,8 +1386,10 @@
             s << ", ";
     }
     s << ")";
-    if (cls->hasVirtualFunctions())
-        s << "," << endl << "      Qtd_QObjectEntity(d_ptr)";
+    if (cls->isQObject())
+        s << "," << endl << "      QtD_QObjectEntity(this, d_ptr)";
+    else if (cls->hasVirtualFunctions())
+        s << "," << endl << "      QtD_Entity(d_ptr)";
 /* qtd        s << "    m_meta_object(0)," << endl;
     s << "      m_vtable(0)," << endl
       << "      m_link(0)" << endl;
@@ -1462,6 +1398,7 @@
     s << "{" << endl;
     {
         Indentation indent(INDENT);
+
         writeCodeInjections(s, java_function, cls, CodeSnip::Beginning, TypeSystem::ShellCode);
         writeCodeInjections(s, java_function, cls, CodeSnip::End, TypeSystem::ShellCode);
     }
@@ -1474,35 +1411,9 @@
       << shellClassName(java_class) << "()" << endl
       << "{" << endl;
     {
-/* qtd
-        Indentation indent(INDENT);
-
-        s << "#ifdef QT_DEBUG" << endl
-          << INDENT << "if (m_vtable)" << endl
-          << INDENT << "    m_vtable->deref();" << endl
-          << "#endif" << endl
-          << INDENT << "if (m_link) {" << endl;
-
-        AbstractMetaClassList interfaces = java_class->interfaces();
-        if (interfaces.size() + (java_class->baseClass() != 0 ? 1 : 0) > 1) {
-            if (java_class->baseClass() != 0)
-                interfaces += java_class->baseClass();
-            foreach (AbstractMetaClass *iface, interfaces) {
-                AbstractMetaClass *impl = iface->isInterface() ? iface->primaryInterfaceImplementor() : iface;
-                s << INDENT << "    m_link->unregisterSubObject((" << impl->qualifiedCppName() << " *) this);" << endl;
-            }
-        }
-
-        if (!java_class->isQObject()) {
-            s << INDENT << "    JNIEnv *__jni_env = qtjambi_current_environment();" << endl
-              << INDENT << "    if (__jni_env != 0) m_link->nativeShellObjectDestroyed(__jni_env);" << endl;
-        }
-
-#if defined(QTJAMBI_DEBUG_TOOLS)
-        s << INDENT << "    qtjambi_increase_shellDestructorCalledCount(QString::fromLatin1(\"" << java_class->name() << "\"));" << endl;
-#endif
-
-         s << INDENT << "}" << endl; */
+        //s << "    std::cout << \"In shell destructor of " << java_class->name() << ", nativeId: \" << this << std::endl;";  
+        if (java_class->isQObject())
+            s << "    destroyEntity(this);";
     }
     s << "}" << endl << endl;
 }
@@ -1818,6 +1729,20 @@
     s << "}" << endl << endl;
 }
 
+void CppImplGenerator::writeQtdEntityFunction(QTextStream &s, const AbstractMetaClass *java_class)
+{
+    s << "extern \"C\" DLL_PUBLIC void *__" << java_class->name() << "_entity(void *q_ptr)" << endl;
+    s << "{" << endl;
+    {
+        Indentation indent(INDENT);
+            s << INDENT << "QtD_Entity* a = dynamic_cast<QtD_Entity*>((" << java_class->qualifiedCppName() << "*)q_ptr);" << endl
+              << INDENT << "if (a != NULL)" << endl
+              << INDENT << "    return a->dId;" << endl
+              << INDENT << "else" << endl
+              << INDENT << "    return NULL;" << endl;
+    }
+    s << "}" << endl << endl;
+}
 
 void CppImplGenerator::writeVirtualFunctionOverride(QTextStream &s,
                                                     const AbstractMetaFunction *java_function,
@@ -2156,8 +2081,11 @@
                 function_prefix = "__override_";
                 extra_param.append("__do_static_call");
                 s << INDENT
-                  << "bool __do_static_call = __this_nativeId ? "
-                  << "__" << java_class->name() << "_entity(__this_nativeId) : false;" << endl;
+                  << "bool __do_static_call = __this_nativeId ? ";
+                if (java_class->isQObject())
+                    s << "QtD_QObjectEntity::getQObjectEntity((QObject*)__this_nativeId) : false;" << endl;
+                else
+                    s << "__" << java_class->name() << "_entity(__this_nativeId) : false;" << endl;
             } else {
                 option = OriginalName;
             }
@@ -2214,7 +2142,7 @@
         AbstractMetaType *d_type = argument->type();
         const TypeEntry *te = d_type->typeEntry();
         if ((te && d_type->isNativePointer() && te->name() == "QString"))
-            s << QString("    _d_toUtf8(__qt_%1.utf16(), __qt_%1.size(), &%1);").arg(argument->indexedName()) << endl;
+            s << QString("    qtd_toUtf8(__qt_%1.utf16(), __qt_%1.size(), &%1);").arg(argument->indexedName()) << endl;
     }
 }
 
@@ -2366,25 +2294,7 @@
         s << INDENT << "extern \"C\" DLL_PUBLIC void qtd_" << cls->name() << "_destructor(void *ptr)" << endl
           << INDENT << "{" << endl;
         {
-            Indentation indent(INDENT);
-/* qtd
-            if (!cls->isQObject() && !cls->generateShellClass()) {
-                s << INDENT << "QtJambiLink *link = QtJambiLink::findLinkForUserObject(ptr);" << endl
-                  << INDENT << "if (link) link->resetObject(qtjambi_current_environment());" << endl;
-            }
-
-            // Code injectsions...
-            foreach (const CodeSnip &snip, cls->typeEntry()->codeSnips()) {
-                if (snip.language == TypeSystem::DestructorFunction) {
-                    s << snip.code();
-                }
-            }
-*/
             s << INDENT << "delete (" << shellClassName(cls) << " *)ptr;" << endl;
-
-#if defined(QTJAMBI_DEBUG_TOOLS)
-            s << INDENT << "qtjambi_increase_destructorFunctionCalledCount(QString::fromLatin1(\"" << cls->name() << "\"));" << endl;
-#endif
         }
 
         s << INDENT << "}" << endl << endl;
@@ -3080,13 +2990,13 @@
         if(java_type->typeEntry()->qualifiedCppName() == "QStringRef") {
             s << INDENT << "const QString *str_ref = " << qt_name << ".string();" << endl
               << INDENT << "if(str_ref)" << endl
-              << INDENT << "    _d_toUtf8(str_ref->utf16(), str_ref->size(), " << java_name << ");" << endl
+              << INDENT << "    qtd_toUtf8(str_ref->utf16(), str_ref->size(), " << java_name << ");" << endl
               << INDENT << "else {" << endl
               << INDENT << "    QString empty_str;" << endl
-              << INDENT << "    _d_toUtf8(empty_str.utf16(), empty_str.size(), " << java_name << ");" << endl
+              << INDENT << "    qtd_toUtf8(empty_str.utf16(), empty_str.size(), " << java_name << ");" << endl
               << INDENT << "}" << endl;
         } else {
-            s << INDENT << QString("_d_toUtf8(%1.utf16(), %1.size(), %2);").arg(qt_name, java_name) << endl;
+            s << INDENT << QString("qtd_toUtf8(%1.utf16(), %1.size(), %2);").arg(qt_name, java_name) << endl;
         }
     } else if (java_type->isTargetLangChar()) {
         s << INDENT << "jchar " << java_name << " = " << qt_name << ".unicode();" << endl;
--- a/generator/cppimplgenerator.h	Sat Aug 22 12:50:58 2009 +0000
+++ b/generator/cppimplgenerator.h	Sun Aug 30 09:59:12 2009 +0000
@@ -196,6 +196,7 @@
                                 int argument_index);
 
     void writeDefaultConstructedValues(QTextStream &s, const AbstractMetaClass *java_class);
+    void writeQObjectEntity(QTextStream &s, const AbstractMetaClass *java_class);
 
     bool hasCustomDestructor(const AbstractMetaClass *java_class) const;
 
@@ -212,6 +213,7 @@
     void writeQObjectLink(QTextStream &s, const AbstractMetaClass *java_class);
     void writeSignalHandler(QTextStream &s, const AbstractMetaClass *java_class, AbstractMetaFunction *signal);
     static void writeInitCallbacks(QTextStream &s, const AbstractMetaClass *java_class);
+    static void writeQtdEntityFunction(QTextStream &s, const AbstractMetaClass *java_class);
     void writeRefArguments(QTextStream &s, const AbstractMetaFunction *java_function);
 
 private:
--- a/generator/dgenerator.cpp	Sat Aug 22 12:50:58 2009 +0000
+++ b/generator/dgenerator.cpp	Sun Aug 30 09:59:12 2009 +0000
@@ -317,7 +317,7 @@
     }
 */
     // Generates Java 1.5 type enums
-    s << "    public enum " << d_enum->enclosingClass()->name() << "_" << d_enum->name() << " {" << endl;
+    s << "public enum " << d_enum->enclosingClass()->name() << "_" << d_enum->name() << " {" << endl;
     const AbstractMetaEnumValueList &values = d_enum->values();
     EnumTypeEntry *entry = d_enum->typeEntry();
 
@@ -477,11 +477,11 @@
 }
 
 static QString function_call_for_ownership(TypeSystem::Ownership owner)
-{
+{  
     if (owner == TypeSystem::CppOwnership) {
-        return "__set_native_ownership(true)";
+        return "__setFlags(QtdObjectFlags.nativeOwnership, true)";
     } else /* qtd 2 if (owner == TypeSystem::TargetLangOwnership) */ {
-        return "__set_native_ownership(false)";
+        return "__setFlags(QtdObjectFlags.nativeOwnership, false)";
     }/* else if (owner == TypeSystem::DefaultOwnership) {
         return "__no_real_delete = false";
 
@@ -696,21 +696,21 @@
     s << INDENT;
     if ( (has_return_type && d_function->argumentReplaced(0).isEmpty() ) || d_function->isConstructor()) { //qtd
         if(d_function->type() && d_function->type()->isQObject()) { // qtd
-            s << "void *__qt_return_value = ";
+            s << "void *ret = ";
         } else if(return_in_arg) // qtd
             ;
         else if (d_function->isConstructor()) { // qtd
-            s << "void* __qt_return_value = ";
+            s << "void* ret = ";
         } else if (return_type && return_type->isValue() && !return_type->typeEntry()->isStructInD()) {
-            s << "void* __qt_return_value = ";
+            s << "void* ret = ";
         } else if (return_type && return_type->isVariant()) {
-            s << "void* __qt_return_value = ";
+            s << "void* ret = ";
         } else if (return_type && ( return_type->isObject() ||
                   (return_type->isNativePointer() && return_type->typeEntry()->isValue()) ||
                    return_type->typeEntry()->isInterface()) ) {
-            s << "void* __qt_return_value = ";
+            s << "void* ret = ";
         } else if (return_type && return_type->isArray()) {
-            s << return_type->arrayElementType()->name() + "* __qt_return_value = ";
+            s << return_type->arrayElementType()->name() + "* ret = ";
         } else {
             returnImmediately = true;
             s << "return ";
@@ -765,9 +765,9 @@
 
     if (!d_function->isConstructor() && !d_function->isStatic()) {
         if(dVersion == 2 && d_function->isConstant())
-            s << "(cast(" << d_function->ownerClass()->name() << ")this).nativeId";
+            s << "(cast(" << d_function->ownerClass()->name() << ")this).__nativeId";
         else
-            s << "nativeId";
+            s << "__nativeId";
     }
 
     if (d_function->isConstructor() &&
@@ -801,7 +801,7 @@
             QString arg_name = arg->argumentName();
 
             if (type->isVariant())
-                s << arg_name << " is null ? null : " << arg_name << ".nativeId";
+                s << arg_name << " is null ? null : " << arg_name << ".__nativeId";
             else if (te->designatedInterface())
                 s << arg_name << " is null ? null : " << arg_name << ".__ptr_" << te->designatedInterface()->name();
             else if (modified_type == "string" /* && type->fullName() == "char" */) {
@@ -831,9 +831,9 @@
                 } // else if (value type is abstract) then we will get a null pointer exception, which is all right
 
                 if(dVersion == 2 && type->isConstant())
-                    s << "(cast(" << type->name() << ")" << arg_name << ").nativeId";
+                    s << "(cast(" << type->name() << ")" << arg_name << ").__nativeId";
                 else
-                    s << arg_name << ".nativeId";
+                    s << arg_name << ".__nativeId";
             }
         }
     }
@@ -864,14 +864,14 @@
 /* qtd2
     if (needs_return_variable) {
         if (owner != TypeSystem::InvalidOwnership) {
-            s << INDENT << "if (__qt_return_value != null) {" << endl;
+            s << INDENT << "if (ret != null) {" << endl;
             if (return_type->isContainer())
-                writeOwnershipForContainer(s, owner, return_type, "__qt_return_value");
+                writeOwnershipForContainer(s, owner, return_type, "ret");
             else
-                s << INDENT << "    __qt_return_value." << function_call_for_ownership(owner) << ";" << endl;
+                s << INDENT << "    ret." << function_call_for_ownership(owner) << ";" << endl;
             s << INDENT << "}" << endl;
         }
-        s << INDENT << "return __qt_return_value;" << endl;
+        s << INDENT << "return ret;" << endl;
     }
 */
     if (d_function->isConstructor()) {
@@ -893,29 +893,31 @@
         }
 
         if ( ( has_return_type && d_function->argumentReplaced(0).isEmpty() )) // qtd
+        {
             if(return_type->isQObject())
-                s << "qtd_" << return_type->name() << "_from_ptr(__qt_return_value);" << endl;
+                s << return_type->name() << ".__getObject(ret);" << endl;
+        }
 
         if (return_type->isValue() && !return_type->typeEntry()->isStructInD())
-            s << "new " << return_type->name() << "(__qt_return_value, false);" << endl;
+            s << "new " << return_type->name() << "(ret);" << endl;
 
         if (return_type->isVariant())
-            s << "new QVariant(__qt_return_value, false);" << endl;
+            s << "new QVariant(ret);" << endl;
 
         if (return_type->isNativePointer() && return_type->typeEntry()->isValue())
-            s << "new " << return_type->name() << "(__qt_return_value, true);" << endl;
+            s << "new " << return_type->name() << "(ret, QtdObjectFlags.nativeOwnership);" << endl;
 
         if (return_type->isObject()) {
             if(d_function->storeResult())
-                s << INDENT << QString("__m_%1.nativeId = __qt_return_value;").arg(d_function->name()) << endl
+                s << INDENT << QString("__m_%1.__nativeId = ret;").arg(d_function->name()) << endl
                   << INDENT << QString("return __m_%1;").arg(d_function->name()) << endl;
             else
-                s << "qtd_" << return_type->name() << "_from_ptr(__qt_return_value);" << endl;
+                s << "qtd_" << return_type->name() << "_from_ptr(ret);" << endl;
             s << endl;
         }
 
         if (return_type->isArray()) {
-            s << "__qt_return_value[0 .. " << return_type->arrayElementCount() << "];" << endl;
+            s << "ret[0 .. " << return_type->arrayElementCount() << "];" << endl;
         }
 
         foreach (ReferenceCount referenceCount, referenceCounts) {
@@ -1680,60 +1682,32 @@
     if (!d_class->hasConstructors())
         return;
 
-    s << endl;
-    if (d_class->baseClassName().isEmpty()) {
-        s << INDENT << "~this() { " << endl;
+    bool isTheQObject = d_class->name() == "QObject";
+    if (isTheQObject || !d_class->isQObject())
+    {
+        s << INDENT << "protected override void __deleteNative() {" << endl;
         {
-            Indentation indent(INDENT);
-
-/*
-            if(d_class->name() == "QObject")
-                s << INDENT << "if(!__gc_managed)" << endl
-                        << INDENT << "    remove(__gc_ref_list, this);" << endl
-                        << INDENT << "if(!__no_real_delete && __gc_managed) {" << endl
-                        << INDENT << "    __qobject_is_deleting = true;" << endl
-                        << INDENT << "    scope(exit) __qobject_is_deleting = false;" << endl
-                        << INDENT << "    __free_native_resources();" << endl
-                        << INDENT << "}" << endl;
-*/
-            if(d_class->name() == "QObject")
-                s << INDENT << "if(!__no_real_delete) {" << endl
-                  << INDENT << "    __qobject_is_deleting = true;" << endl
-                  << INDENT << "    scope(exit) __qobject_is_deleting = false;" << endl
-                  << INDENT << "    __free_native_resources();" << endl
-                  << INDENT << "}" << endl;
-            else
-                s << INDENT << "if(!__no_real_delete)" << endl
-                  << INDENT << "    __free_native_resources();" << endl;
+            if (isTheQObject)
+                s << INDENT << "qtd_delete_qobject(__nativeId);" << endl;
+            else if (!d_class->isQObject())
+                s << INDENT << "qtd_" << d_class->name() << "_destructor(__nativeId);" << endl;
         }
         s << INDENT << "}" << endl << endl;
     }
-
-    s << INDENT << "protected void __free_native_resources() {" << endl;
-    {
-        Indentation indent(INDENT);
-        s << INDENT << "qtd_" << d_class->name() << "_destructor(nativeId());" << endl;
-    }
-    s << INDENT << "}" << endl << endl;
 }
 
-void DGenerator::writeOwnershipMethods(QTextStream &s, const AbstractMetaClass *d_class)
+void DGenerator::writeFlagsSetter(QTextStream &s, const AbstractMetaClass *d_class)
 {
-    s << INDENT << "void __set_native_ownership(bool ownership_)";
     if (d_class->isInterface() || d_class->isNamespace())
-        s << ";";
-    else {
-        s << " {" << endl
-          << INDENT << "    __no_real_delete = ownership_;" << endl
-          << INDENT << "}" << endl << endl;
-    }
+        s << INDENT << "void __setFlags(QtdObjectFlags flags, bool val);";
+    else // COMPILER BUG:
+        s << INDENT << "void __setFlags(QtdObjectFlags flags, bool val) { super.__setFlags(flags, val); }";
 }
 
 void DGenerator::writeSignalHandlers(QTextStream &s, const AbstractMetaClass *d_class)
 {
     AbstractMetaFunctionList signal_funcs = signalFunctions(d_class);
 
-    //TODO: linkage trivia should be abstracted away
     QString attr;
 
     s << "// signal handlers" << endl;
@@ -1789,8 +1763,7 @@
                     if(ctype->isAbstract())
                         type_name = type_name + "_ConcreteWrapper";
                     s << INDENT << "scope " << arg_name << " = new " << type_name
-                                << "(cast(void*)(" << arg_ptr << "), true);" << endl
-                                << INDENT << arg_name << ".__no_real_delete = true;";
+                                << "(cast(void*)(" << arg_ptr << "), QtdObjectFlags.nativeOwnership);" << endl;
                 }
                 s << endl;
             }
@@ -1816,6 +1789,20 @@
 
     bool fakeClass = d_class->attributes() & AbstractMetaAttributes::Fake;
 
+
+    QString auxModName = d_class->package() + "." + d_class->name() + "_aux";
+    FileOut auxFile(outputDirectory() + "/" + subDirectoryForClass(d_class) + "/" + d_class->name() + "_aux.d");
+    auxFile.isDone = true;
+    auxFile.stream << "module " << auxModName << ";" << endl << endl;
+
+    bool staticInit = d_class->isQObject() || (cpp_shared && d_class->generateShellClass() && !d_class->isInterface());
+    if (staticInit)
+    {
+        auxFile.isDone = false;
+        auxFile.stream << "extern(C) void static_init_" << d_class->name() << "();" << endl;
+        auxFile.stream << "static this() { static_init_" << d_class->name() << "; }" << endl << endl;
+    }
+
     if (m_docs_enabled) {
         m_doc_parser = new DocParser(m_doc_directory + "/" + d_class->name().toLower() + ".jdoc");
     }
@@ -1897,14 +1884,31 @@
         }
     }
 
+    // Enums aliases outside of the class - hack
+    if (!d_class->enums().isEmpty()) {
+        auxFile.isDone = false;
+        foreach (AbstractMetaEnum *d_enum, d_class->enums())
+            writeEnum(auxFile.stream, d_enum);
+    }
+
+    // Auxiliary file contents should have been written at this point
+    if (!auxFile.isDone)
+    {
+        s << "public import " << auxModName << ";" << endl;
+        auxFile.done();
+    }
+
     if (!m_isRecursive) {
         s << "public import qt.QGlobal;" << endl
           << "public import qt.core.Qt;" << endl
-          << "private import qt.QtDObject;" << endl
+          << "private import qt.QtdObject;" << endl
           << "private import qt.core.QString;" << endl
           << "private import qt.qtd.Array;" << endl;
         if (d_class->isQObject()) {
-            s << "public import qt.Signal;" << endl;
+            s << "public import qt.Signal;" << endl
+              << "public import qt.core.QMetaObject;" << endl
+              << "public import qt.qtd.Traits;" << endl;
+
             if (d_class->name() != "QObject")
                 s << "public import qt.core.QObject;" << endl;
         }
@@ -1924,9 +1928,6 @@
         if(d_class->isQObject())
             s << "private import " << d_class->package() << ".ArrayOps2;" << endl;
 
-        if (!d_class->enums().isEmpty())
-            s << "public import " << d_class->package() << "." << d_class->name() << "_enum;" << endl << endl;
-
         s << "// automatic imports-------------" << endl;
         writeRequiredImports(s, d_class);
         s << endl;
@@ -1935,35 +1936,23 @@
             s << "import std.stdio;" << endl
               << "import std.string;" << endl
               << "import std.utf;" << endl
-              << "import core.memory;";
+              << "import core.memory;" << endl;
         }
         else
         {
             s << "import tango.io.Stdout;" << endl
               << "import tango.stdc.stringz;" << endl
               << "import tango.text.convert.Utf;" << endl
-              << "import tango.core.Memory;";
+              << "import tango.core.Memory;" << endl;
         }
-        s << endl << endl << endl;
+
+        s << endl << endl;
     }
 
     if (m_doc_parser) {
         s << m_doc_parser->documentation(d_class) << endl << endl;
     }
 
-    // Enums aliases outside of the class - hack
-    if (!d_class->enums().isEmpty()) {
-        QString fileName = QString("%1_enum.d").arg(d_class->name());
-        FileOut fileOut(outputDirectory() + "/" + subDirectoryForClass(d_class) + "/" + fileName);
-
-        fileOut.stream << "module " << d_class->package() << "." << d_class->name() << "_enum;" << endl << endl;
-        foreach (AbstractMetaEnum *d_enum, d_class->enums())
-            writeEnum(fileOut.stream, d_enum);
-    }
-
-
-    s << endl;
-
 /* qtd    s << "@QtJambiGeneratedClass" << endl;
 
     if ((d_class->typeEntry()->typeFlags() & ComplexTypeEntry::Deprecated) != 0) {
@@ -2156,21 +2145,14 @@
     foreach (AbstractMetaEnum *d_enum, d_class->enums())
         writeEnumAlias(s, d_enum);
 
-    if (!d_class->enums().isEmpty() && !d_class->functions().isEmpty())
-        s << endl;
-
-    // Signals
-    AbstractMetaFunctionList signal_funcs;
-
-    signal_funcs = signalFunctions(d_class);
-    if (signal_funcs.size())
+    // Signals    
+    if (d_class->isQObject())
     {
-        writeSignalConnectors(s, d_class, signal_funcs);
+        AbstractMetaFunctionList signal_funcs = signalFunctions(d_class, false);
+        writeSignalSignatures(s, d_class, signal_funcs);
+   
         foreach (AbstractMetaFunction *signal, signal_funcs)
-        {
-            if (d_class == signal->implementingClass())
-                writeSignal(s, signal);
-        }
+            writeSignal(s, signal);
     }
 
     // Class has subclasses but also only private constructors
@@ -2251,37 +2233,39 @@
           << INDENT << "private native boolean __qt_signalInitialization(long ptr, String name);" << endl;
     }
 */
+    if (d_class->isQObject())
+        writeQObjectFunctions(s, d_class);
+
     // Add dummy constructor for use when constructing subclasses
     if (!d_class->isNamespace() && !d_class->isInterface() && !fakeClass) {
         s << endl
           << INDENT << "public "
           << "this";
 
-        if(d_class->name() == "QObject")
+
+        Indentation indent(INDENT);
+
+        s << "(void* native_id, QtdObjectFlags flags = QtdObjectFlags.none) {" << endl
+          << INDENT << "super(native_id, flags);" << endl;
+
+        if (d_class->name() == "QObject")
         {
-            {
-                Indentation indent(INDENT);
-                s << "(void* native_id, bool gc_managed) {" << endl
-/*                  << INDENT << "if(!gc_managed)" << endl
-                  << INDENT << "    __gc_ref_list ~= this;" << endl
-                  << INDENT << "__gc_managed = gc_managed;" << endl */
-                  << INDENT << "super(native_id);" << endl;
-            }
+            // To prevent GC from collecting the object, add it to the statically rooted linked list
+            s << INDENT << "    __next = __root;" << endl
+            << INDENT << "    __root = this;" << endl
+            << INDENT << "    if (__next) {" << endl
+            << INDENT << "        __next.__prev = this;" << endl
+            << INDENT << "    }" << endl << endl;
         }
-        else {
-            Indentation indent(INDENT);
-            if(d_class->isQObject())
-                s << "(void* native_id, bool gc_managed) {" << endl
-                  << INDENT << "super(native_id, gc_managed);" << endl;
-            else
-                s << "(void* native_id, bool no_real_delete = false) {" << endl
-                  << INDENT << "super(native_id, no_real_delete);" << endl;
-        }
+
+        /*
         if (cpp_shared) {
             if (d_class->generateShellClass() && !d_class->isInterface())
-                s << INDENT << "if (!init_flag_" << d_class->name() << ")" << endl
+                s << INDENT << "if (!static_inited)" << endl
                   << INDENT << "    static_init_" << d_class->name() << "();" << endl << endl;
         }
+        */
+
         // customized store-result instances
         d_funcs = d_class->functionsInTargetLang();
         for (int i=0; i<d_funcs.size(); ++i) {
@@ -2304,7 +2288,7 @@
                 s << INDENT << "    __m_" << d_function->name() << " = new "
                         << type_name << "(cast(void*)null);" << endl;
                 if (d_function->type()->isQObject())
-                    s << INDENT << "    __m_" << d_function->name() << ".__no_real_delete = true;" << endl;
+                    s << INDENT << "    __m_" << d_function->name() << ".__setFlags(QtdObjectFlags.nativeOwnership, true);" << endl;
             }
         }
 
@@ -2316,14 +2300,14 @@
                 AbstractMetaClass *iface = interfaces.at(i);
 
                 s << INDENT << "    __m_ptr_" << iface->name() << " = qtd_" << d_class->name() << "_cast_to_" << iface->qualifiedCppName()
-                  << "(nativeId);" << endl;
+                  << "(__nativeId);" << endl;
             }
         }
 
 
         s << INDENT << "}" << endl << endl;
 
-/******************!!!DUBLICATE OF ABOVE!!!*********************/
+/******************!!!DUPLICATE OF ABOVE!!!*********************/
         for (int i=0; i<d_funcs.size(); ++i) {
             AbstractMetaFunction *d_function = d_funcs.at(i);
             uint included_attributes = 0;
@@ -2387,7 +2371,7 @@
 
 /* qtd    writeJavaLangObjectOverrideFunctions(s, d_class);
 */
-    writeOwnershipMethods(s, d_class);
+    writeFlagsSetter(s, d_class);
     s << "// Injected code in class" << endl;
     writeExtraFunctions(s, d_class);
 // qtd2    writeToStringFunction(s, d_class);
@@ -2428,13 +2412,11 @@
 
         {
             Indentation indent(INDENT);
-            s << INDENT << "public this(void* native_id, bool no_real_delete = true) {" << endl
-              << INDENT << "    super(native_id, no_real_delete);" << endl;
-
-
-
-
-            /******************!!!DUBLICATE!!!*********************/
+            QString hasShellFlag = d_class->generateShellClass() ? " | QtdObjectFlags.hasShell" : "";
+            s << INDENT << "public this(void* native_id, QtdObjectFlags flags = QtdObjectFlags.nativeOwnership) {" << endl
+              << INDENT << "    super(native_id, flags);" << endl << endl;
+            
+            /******************!!!DUPLICATE!!!*********************/
             d_funcs = d_class->functionsInTargetLang();
             for (int i=0; i<d_funcs.size(); ++i) {
                 AbstractMetaFunction *d_function = d_funcs.at(i);
@@ -2452,7 +2434,7 @@
                     s << INDENT << "    __m_" << d_function->name() << " = new "
                             << type_name << "(cast(void*)null);" << endl;
                     if (d_function->type()->isQObject())
-                        s << INDENT << "    __m_" << d_function->name() << ".__no_real_delete = true;" << endl;
+                        s << INDENT << "    __m_" << d_function->name() << ".__setFlags(QtdObjectFlags.nativeOwnership, true);" << endl;
                 }
             }
 
@@ -2509,18 +2491,15 @@
 
     if (d_class->generateShellClass()) { // qtd2
         if (d_class->hasVirtualFunctions()
-            && (d_class->typeEntry()->isObject() || d_class->typeEntry()->isQObject()) )
+            && (d_class->typeEntry()->isObject() && !d_class->typeEntry()->isQObject()) )
         s << endl << "extern (C) void *__" << d_class->name() << "_entity(void *q_ptr);" << endl << endl;
     }
 
-    if (d_class->isQObject())
-        writeQObjectFunctions(s, d_class);
-
 
 //    if (d_class->needsConversionFunc)
         writeConversionFunction(s, d_class);
 
-    if (d_class->hasConstructors())
+    if (d_class->hasConstructors() && !d_class->isQObject())
         s << "extern (C) void qtd_" << d_class->name() << "_destructor(void *ptr);" << endl << endl;
 
     // qtd
@@ -2564,22 +2543,29 @@
             writeShellVirtualFunction(s, function, d_class, pos);
     }
 
-    //init callbacks from dll to D side
-    if (cpp_shared) {
-        bool shellClass = d_class->generateShellClass();
-        if (shellClass && !d_class->isInterface()) {
-            QString initArgs = "void* virtuals";
+    // write static constructor
+    if (staticInit) {
+        QString initArgs;
+        if (cpp_shared)
+        {
+            initArgs = "void* virtuals";
             if (d_class->isQObject())
-                initArgs += ", void* signals, void* qobj_del";
+                initArgs += ", void* signals";
 
             s << "private extern (C) void qtd_" << d_class->name()
-              << QString("_initCallBacks(%1);").arg(initArgs) << endl << endl
-              << "private bool init_flag_" << d_class->name() << " = false;" << endl
-              << "void static_init_" << d_class->name() << "() {" << endl
-              << INDENT << "init_flag_" << d_class->name() << " = true;" << endl << endl
-
-              // virtual functions
-              << INDENT << "void*[" << virtualFunctions.size() << "] virt_arr;" << endl;
+            << QString("_initCallBacks(%1);").arg(initArgs) << endl << endl;
+        }
+
+        s << "extern(C) void static_init_" << d_class->name() << "() {" << endl;
+
+        if (d_class->isQObject()) {
+            s << INDENT << "if (!" << d_class->name() << "._staticMetaObject) " << endl
+            << INDENT << "    " << d_class->name() << ".createStaticMetaObject;" << endl << endl;
+        }
+
+        if (cpp_shared) {
+             // virtual functions
+            s << INDENT << "void*[" << virtualFunctions.size() << "] virt_arr;" << endl;
             for (int pos = 0; pos<virtualFunctions.size(); ++pos) {
                 const AbstractMetaFunction *function = virtualFunctions.at(pos);
                 if (!notWrappedYet(function)) // qtd2
@@ -2590,8 +2576,9 @@
             else
                 initArgs = "virt_arr.ptr";
 
-            // signals
             if (d_class->isQObject()) {
+
+                // signals
                 AbstractMetaFunctionList signal_funcs = signalFunctions(d_class);
                 s << endl << INDENT << "void*[" << signal_funcs.size() << "] sign_arr;" << endl;
                 for(int i = 0; i < signal_funcs.size(); i++) {
@@ -2602,16 +2589,12 @@
                     initArgs += ", null";
                 else
                     initArgs += ", sign_arr.ptr";
-
-                // QObject_delete
-                s << endl << INDENT << "void *qobj_del;" << endl
-                  << INDENT << "qobj_del = &qtd_D_" << d_class->name() << "_delete;" << endl;
-                initArgs += ", qobj_del";
             }
 
-            s << INDENT << "qtd_" << d_class->name() << QString("_initCallBacks(%1);").arg(initArgs) << endl
-              << "}" << endl << endl;
+            s << INDENT << "qtd_" << d_class->name() << QString("_initCallBacks(%1);").arg(initArgs) << endl;
         }
+
+        s << "}" << endl << endl;
     }
 
     writeSignalHandlers(s, d_class);
@@ -2628,71 +2611,88 @@
         write(s, cls);
         m_isRecursive = false;
     }
+
+
+    if (d_class->isQObject())
+    {
+      s << "private extern(C) void* qtd_" << d_class->name() << "_staticMetaObject();" << endl << endl
+        << "private extern(C) void qtd_" << d_class->name() << "_createEntity(void* nativeId, void* dId);" <<  endl << endl;
+    }
 }
 
 void DGenerator::writeConversionFunction(QTextStream &s, const AbstractMetaClass *d_class)
 {
     const ComplexTypeEntry *ctype = d_class->typeEntry();
-    if(!ctype->isQObject() && !ctype->isObject())
+    if(ctype->isQObject() || !ctype->isObject())
         return;
     QString class_name = ctype->name();
     QString return_type_name = class_name;
     if(ctype->designatedInterface())
         return_type_name = ctype->designatedInterface()->name();
-    s << return_type_name << " qtd_" << class_name << "_from_ptr(void* __qt_return_value) {" << endl;
-
-    if(ctype->isQObject()) {
-        QString type_name = class_name;
-        if(ctype->isAbstract())
-            type_name = type_name + "_ConcreteWrapper";
-
-        s << INDENT << "if (__qt_return_value is null)" << endl
-          << INDENT << "    return null;" << endl
-          << INDENT << "void* d_obj = qtd_" << class_name << "_d_pointer(__qt_return_value);" << endl
-          << INDENT << "if (d_obj is null) {" << endl
-          << INDENT << "    auto new_obj = new " << type_name << "(__qt_return_value, false);" << endl
-          << INDENT << "    qtd_" << class_name << "_create_link(new_obj.nativeId, cast(void*) new_obj);" << endl
-          << INDENT << "    new_obj.__no_real_delete = true;" << endl
-          << INDENT << "    return new_obj;" << endl
-          << INDENT << "} else" << endl
-          << INDENT << "    return cast(" << class_name << ") d_obj;" << endl;
-    } else if (ctype->isObject()) {
-        QString type_name = class_name;
-        if(ctype->isAbstract())
-            type_name = ctype->targetLangName() + "_ConcreteWrapper";
-
-        // if class has virtual functions then it has classname_entity function so
-        // we can look for D Object pointer. otherwise create new wrapper
-        if (d_class->hasVirtualFunctions()) {
-            s << INDENT << "void* d_obj = __" << ctype->targetLangName() << "_entity(__qt_return_value);" << endl
-              << INDENT << "if (d_obj !is null) {" << endl
-              << INDENT << "    auto d_obj_ref = cast (Object) d_obj;" << endl
-              << INDENT << "    return cast(" << return_type_name << ") d_obj_ref;" << endl
-              << INDENT << "} else {" << endl
-              << INDENT << "    auto return_value = new " << type_name << "(__qt_return_value, true);" << endl
-              << INDENT << "    return_value.__no_real_delete = true;" << endl
-              << INDENT << "    return return_value;" << endl
-              << INDENT << "}" << endl;
-        } else {
-            s << INDENT << "auto return_value = new " << type_name << "(__qt_return_value, true);" << endl
-              << INDENT << "return_value.__no_real_delete = true;" << endl
-              << INDENT << "return return_value;" << endl;
-        }
+
+    s << return_type_name << " qtd_" << class_name << "_from_ptr(void* ret) {" << endl;
+
+
+    QString type_name = class_name;
+    if(ctype->isAbstract())
+        type_name = ctype->targetLangName() + "_ConcreteWrapper";
+
+    // if class has virtual functions then it has classname_entity function so
+    // we can look for D Object pointer. otherwise create new wrapper
+    if (d_class->hasVirtualFunctions()) {
+        s << INDENT << "void* d_obj = __" << ctype->targetLangName() << "_entity(ret);" << endl
+          << INDENT << "if (d_obj !is null) {" << endl
+          << INDENT << "    auto d_obj_ref = cast (Object) d_obj;" << endl
+          << INDENT << "    return cast(" << return_type_name << ") d_obj_ref;" << endl
+          << INDENT << "} else {" << endl
+          << INDENT << "    auto return_value = new " << type_name << "(ret, QtdObjectFlags.nativeOwnership);" << endl
+          << INDENT << "    return return_value;" << endl
+          << INDENT << "}" << endl;
+    } else {
+        s << INDENT << "auto return_value = new " << type_name << "(ret, QtdObjectFlags.nativeOwnership);" << endl
+          << INDENT << "return return_value;" << endl;
     }
     s << "}" << endl << endl;
 }
 
-
 void DGenerator::writeQObjectFunctions(QTextStream &s, const AbstractMetaClass *d_class)
 {
-    s << "extern(C) void* qtd_" << d_class->name() << "_d_pointer(void *obj);" << endl
-      << "extern(C) void qtd_" << d_class->name() << "_create_link(void *obj, void* d_obj);" << endl << endl;
-    s << "private extern (C) void qtd_D_" << d_class->name() << "_delete(void *d_ptr) {" << endl
-      << "    auto d_ref = cast(QObject) d_ptr;" << endl
-      << "    d_ref.__no_real_delete = true;" << endl
-      << "    if(!d_ref.__qobject_is_deleting)"
-      << "        delete d_ref;" << endl
-      << "}" << endl << endl;
+    QString concreteArg;
+    if (d_class->isAbstract())
+        concreteArg += ", " + d_class->name() + "_ConcreteWrapper";
+
+  s << "    private static QMetaObject _staticMetaObject;" << endl
+    << "    protected static void createStaticMetaObject() {" << endl
+    << "        assert(!_staticMetaObject);" << endl
+    << "        QMetaObject base;" << endl;
+
+    if (d_class->name() != "QObject")
+    {
+        QString baseName = d_class->baseClassName();
+      s << "        if (!" << baseName << "._staticMetaObject)" << endl
+        << "            " << baseName << ".createStaticMetaObject;" << endl
+        << "        base = " << baseName << "._staticMetaObject;" << endl;
+    }
+
+  s << "        _staticMetaObject = new QMetaObject(qtd_" << d_class->name() << "_staticMetaObject, base);"   << endl
+    << "        _staticMetaObject.construct!(" << d_class->name() << concreteArg << ");" << endl
+    << "    }" << endl << endl
+
+    << "    QMetaObject metaObject() {" << endl
+    << "        return _staticMetaObject;" << endl
+    << "    }" << endl << endl
+
+    << "    static QMetaObject staticMetaObject() {" << endl
+    << "        return _staticMetaObject;" << endl
+    << "    }" << endl << endl
+
+    << "    static " << d_class->name() << " __getObject(void* nativeId) {" << endl
+    << "        return static_cast!(" << d_class->name() << ")(_staticMetaObject.getObject(nativeId));" << endl
+    << "    }" << endl << endl
+
+    << "    static void __createEntity(void* nativeId, void* dId) {" << endl
+    << "        return qtd_" << d_class->name() << "_createEntity(nativeId, dId);" << endl
+    << "    }" << endl << endl;
 }
 
 /*
@@ -2705,16 +2705,18 @@
 {
     if(ctype->isQObject()) {
         QString type_name = ctype->name();
-        s << "return qtd_" << type_name << "_from_ptr(__qt_return_value);" << endl;
+        if (ctype->isAbstract())
+            type_name += "_ConcreteWrapper";
+        s << "return " << type_name << ".__getObject(ret);" << endl;
     } else if (ctype->isValue() && !ctype->isStructInD()) {
-        s << INDENT << "return new " << ctype->name() << "(__qt_return_value, false);" << endl;
+        s << INDENT << "return new " << ctype->name() << "(ret);" << endl;
     } else if (ctype->isVariant()) {
-        s << INDENT << "return new QVariant(__qt_return_value, false);" << endl;
+        s << INDENT << "return new QVariant(ret);" << endl;
     } else if (ctype->name() == "QModelIndex" || ctype->isStructInD()) {
-        s << INDENT << "return __qt_return_value;" << endl;
+        s << INDENT << "return ret;" << endl;
     } else if (ctype->isObject()) {
         QString type_name = ctype->name();
-        s << "return qtd_" << type_name << "_from_ptr(__qt_return_value);" << endl;
+        s << "return qtd_" << type_name << "_from_ptr(ret);" << endl;
     }
 }
 
@@ -2755,41 +2757,36 @@
     }
 }
 
-void DGenerator::writeSignalConnectors(QTextStream &s, const AbstractMetaClass *d_class, AbstractMetaFunctionList signal_funcs)
+void DGenerator::writeSignalSignatures(QTextStream &s, const AbstractMetaClass *d_class, AbstractMetaFunctionList signal_funcs)
 {
-    s << INDENT << "private static SlotConnector[" << signal_funcs.size() << "] __slotConnectors;" << endl;
-    s << INDENT << "private static SlotConnector[" << signal_funcs.size() << "] __slotDisconnectors;" << endl << endl;
-
-    s << INDENT << "protected void onSignalHandlerCreated(ref SignalHandler sh) {" << endl;
+    s << INDENT << "private const string[" << signal_funcs.size() << "] __signalSignatures = [";
     {
         Indentation indent(INDENT);
-        s << INDENT << "sh.firstSlotConnected = &onFirstSlot;" << endl;
-        s << INDENT << "sh.lastSlotDisconnected = &onLastSlot;" << endl << endl;
-
-        for(int i = 0; i < signal_funcs.size(); i++) {
-            AbstractMetaFunction *signal = signal_funcs.at(i);
-            QString sigExternName = signalExternName(d_class, signal);
-            s << INDENT << "__slotConnectors[" << i << "] = &" << sigExternName << "_connect;" << endl;
-            s << INDENT << "__slotDisconnectors[" << i << "] = &" << sigExternName << "_disconnect;" << endl;
+        for (int i = 0; i < signal_funcs.size(); ++i)
+        {            
+            if (i)
+                s << ", ";                
+            s << endl << INDENT << "    \"" << signal_funcs.at(i)->minimalSignature() << "\"";
         }
     }
-    s << INDENT << "}" << endl << endl;
-
-    s << INDENT << "private final void onFirstSlot(int signalId) {" << endl;
+    s << INDENT << "];" << endl << endl;
+
+    s << INDENT << "int signalSignature(int signalId, ref stringz signature) {" << endl;
     {
         Indentation indent(INDENT);
-        s << INDENT << "if (signalId < __slotConnectors.length) {" << endl;
-        s << INDENT << "    __slotConnectors[signalId](nativeId);" << endl;
-        s << INDENT << "}" << endl;
-    }
-    s << INDENT << "}" << endl;
-
-    s << INDENT << "private final void onLastSlot(int signalId) {" << endl;
-    {
-        Indentation indent(INDENT);
-        s << INDENT << "if (signalId < __slotDisconnectors.length) {" << endl;
-        s << INDENT << "    __slotDisconnectors[signalId](nativeId);" << endl;
-        s << INDENT << "}" << endl;
+        
+        if (d_class->name() != "QObject")
+        {
+            s << INDENT << "signalId = super.signalSignature(signalId, signature);" << endl
+              << INDENT << "if (signature)" << endl
+              << INDENT << "    return signalId;" << endl;            
+        }
+        
+        s << INDENT << "if (signalId < __signalSignatures.length)" << endl
+          << INDENT << "    signature = __signalSignatures[signalId].ptr;" << endl
+          << INDENT << "else" << endl
+          << INDENT << "    signalId -= __signalSignatures.length;" << endl
+          << INDENT << "return signalId;" << endl;
     }
     s << INDENT << "}" << endl;
 }
@@ -2854,7 +2851,7 @@
                     s << INDENT << "auto " << arg_name << "_d_qstr = QString(" << arg_name << ", true);" << endl
                       << INDENT << "string " << arg_name << "_d_ref = " << arg_name << "_d_qstr.toNativeString();";
                 } else if(type->isVariant())
-                    s << INDENT << "scope " << arg_name << "_d_ref = new QVariant(" << arg_name << ", true);";
+                    s << INDENT << "scope " << arg_name << "_d_ref = new QVariant(" << arg_name << ", QtdObjectFlags.nativeOwnership);";
                 else if (type->typeEntry()->isStructInD())
                     continue;
                 else if (!type->hasNativeId() && !(type->typeEntry()->isValue() && type->isNativePointer()))
@@ -2866,7 +2863,7 @@
                     const ComplexTypeEntry *ctype = static_cast<const ComplexTypeEntry *>(type->typeEntry());
                     if(ctype->isAbstract())
                         type_name = type_name + "_ConcreteWrapper";
-                    s << INDENT << "scope " << arg_name << "_d_ref = new " << type_name << "(" << arg_name << ", true);";
+                    s << INDENT << "scope " << arg_name << "_d_ref = new " << type_name << "(" << arg_name << ", QtdObjectFlags.nativeOwnership);";
                 }
                 else if (type->isQObject()) {
                     QString type_name = type->name();
@@ -2874,13 +2871,7 @@
                     if(ctype->isAbstract())
                         type_name = type_name + "_ConcreteWrapper";
 
-                    s << INDENT << "scope " << arg_name << "_so = new StackObject!(" << type_name << ");" << endl
-                      << INDENT << "auto " << arg_name << "_d_ref = " << arg_name << "_so(" << arg_name <<", true);" << endl
-                      << INDENT << arg_name << "_d_ref.__no_real_delete = true;";
-/*
-                    s << INDENT << "scope " << arg_name << "_d_ref = new " << type_name << "(" << arg_name <<", true);" << endl
-                      << INDENT << arg_name << "_d_ref.__no_real_delete = true;";
-*/
+                    s << INDENT << "scope " << arg_name << "_d_ref = new " << type_name << "(" << arg_name << ", QtdObjectFlags.nativeOwnership);" << endl;
                 }
                 s << endl;
             }
@@ -2959,7 +2950,7 @@
         if(f_type) {
             if(f_type->isObject() || f_type->isQObject() || f_type->isVariant() ||
                (f_type->isValue() && !f_type->typeEntry()->isStructInD())) {
-                QString native_id = "nativeId";
+                QString native_id = "__nativeId";
                 if (f_type->typeEntry()->designatedInterface())
                     native_id =  "__ptr_" + f_type->typeEntry()->designatedInterface()->name();
                 s << INDENT << "return ret_value is null? null : ret_value." << native_id << ";" << endl;
@@ -3255,34 +3246,7 @@
             }
         }
 
-        if(d_function->implementingClass()->isQObject())
-        {
-            bool hasParentArg = false;
-            AbstractMetaArgumentList arguments = d_function->arguments();
-            int arg_index = 0;
-            for (int i=0; i<arguments.count(); ++i) {
-                const AbstractMetaArgument *arg = arguments.at(i);
-                if (arg->argumentName().contains("parent", Qt::CaseInsensitive)) {
-                    arg_index = i;
-                    hasParentArg = true;
-                }
-            }
-
-            const AbstractMetaArgument *arg = arguments.at(arg_index);
-//            QString ctor_call = d_function->implementingClass()->name() == "QObject"? "this" : "super";
-            QString ctor_call = "this";
-            if (hasParentArg) {
-                s << INDENT << "bool gc_managed = " << arg->argumentName() << " is null ? true : false;" << endl
-                  << INDENT << ctor_call << "(__qt_return_value, gc_managed);" << endl;
-            } else {
-                s << INDENT << ctor_call << "(__qt_return_value, true);" << endl;
-            }
-
-            // creating a link object associated with the current QObject for signal handling and metadata
-            s << INDENT << "qtd_" << d_function->ownerClass()->name() << "_create_link(this.nativeId, cast(void*) this);" << endl;
-        }
-        else
-            s << INDENT << "this(__qt_return_value);" << endl;
+        s << INDENT << "this(ret);" << endl;
     }
     s << INDENT << "}" << endl << endl;
 
@@ -3353,7 +3317,7 @@
             s << endl
               << "    @Override" << endl
               << "    public String toString() {" << endl
-              << "        if (nativeId() == 0)" << endl
+              << "        if (__nativeId == 0)" << endl
               << "            throw new QNoNativeResourcesException(\"Function call on incomplete object of type: \" +getClass().getName());" << endl
               << "        return __qt_toString(nativeId());" << endl
               << "    }" << endl
--- a/generator/dgenerator.h	Sat Aug 22 12:50:58 2009 +0000
+++ b/generator/dgenerator.h	Sun Aug 30 09:59:12 2009 +0000
@@ -151,10 +151,10 @@
     const TypeEntry* fixedTypeEntry(const TypeEntry *type);
 
     void writeDestructor(QTextStream &s, const AbstractMetaClass *d_class);
-    void writeOwnershipMethods(QTextStream &s, const AbstractMetaClass *d_class);
+    void writeFlagsSetter(QTextStream &s, const AbstractMetaClass *d_class);
     void writeSignalHandlers(QTextStream &s, const AbstractMetaClass *d_class);
     void writeEnumAlias(QTextStream &s, const AbstractMetaEnum *d_enum);
-    void writeSignalConnectors(QTextStream &s, const AbstractMetaClass *d_class, AbstractMetaFunctionList signal_funcs);
+    void writeSignalSignatures(QTextStream &s, const AbstractMetaClass *d_class, AbstractMetaFunctionList signal_funcs);
     void writeQObjectFunctions(QTextStream &s, const AbstractMetaClass *d_class);
     void writeConversionFunction(QTextStream &s, const AbstractMetaClass *d_class);
 
--- a/generator/generator.cpp	Sat Aug 22 12:50:58 2009 +0000
+++ b/generator/generator.cpp	Sun Aug 30 09:59:12 2009 +0000
@@ -193,21 +193,23 @@
     return false;
 }
 
-AbstractMetaFunctionList signalFunctions(const AbstractMetaClass *cls)
+AbstractMetaFunctionList signalFunctions(const AbstractMetaClass *cls, bool includeBase)
 {
     AbstractMetaFunctionList r;
     if (cls->generateShellClass())
     {
-        AbstractMetaClass *base = cls->baseClass();
-        if (base)
-            r += signalFunctions(base);
+        if (includeBase)
+        {
+            AbstractMetaClass *base = cls->baseClass();
+            if (base)
+                r += signalFunctions(base);
+        }
 
         foreach (AbstractMetaFunction *f, cls->functions())
         {
             if (!f->isSignal()
                 || cls != f->implementingClass()
                 || notWrappedYet(f)
-// qtd2                || f->isPrivate() // we want private signals to be accessible as well
                 || f->isModifiedRemoved(TypeSystem::TargetLangCode))
                 continue;
 
--- a/generator/generator.h	Sat Aug 22 12:50:58 2009 +0000
+++ b/generator/generator.h	Sun Aug 30 09:59:12 2009 +0000
@@ -170,6 +170,6 @@
 
 bool notWrappedYet(const AbstractMetaFunction *java_function);
 bool isLinearContainer(const ContainerTypeEntry *type);
-AbstractMetaFunctionList signalFunctions(const AbstractMetaClass *cls);
+AbstractMetaFunctionList signalFunctions(const AbstractMetaClass *cls, bool includeBase = true);
 
 #endif // GENERATOR_H
--- a/generator/typesystem_core-java.java	Sat Aug 22 12:50:58 2009 +0000
+++ b/generator/typesystem_core-java.java	Sun Aug 30 09:59:12 2009 +0000
@@ -22,7 +22,7 @@
 * exception, Nokia gives you certain additional rights. These rights
 * are described in the Nokia Qt GPL Exception version 1.2, included in
 * the file GPL_EXCEPTION.txt in this package.
-* 
+*
 * Qt for Windows(R) Licensees
 * As a special exception, Nokia, as the sole copyright holder for Qt
 * Designer, grants users of the Qt/Eclipse Integration plug-in the
@@ -46,10 +46,9 @@
 
 class QObject___ extends QObject {
     
+    /* TODO: test whether the linked list is really a better solution
     public bool __stackAllocated = false;
     
-    public bool __qobject_is_deleting = false;
-    
     new(size_t size, void* p = null)
     {
         if (!p)
@@ -72,12 +71,89 @@
             }
         }
     }
+    */
     
-    // list of QObjects references to prevent them from garbage collecting if they are managed by Qt
-    private static QObject[] __gc_ref_list;
+    private
+    {
+        static QObject __root;
+        QObject __next;
+        QObject __prev;
+    }
+    
+    override void onSignalHandlerCreated(ref SignalHandler sh)
+    {
+        sh.signalEvent = &onSignalEvent;
+    }
+    
+    private void onSignalEvent(int signalId, SignalEventId event)
+    {
+        stringz signature;
+        signalSignature(signalId, signature);        
+        if (signature)
+        {
+            switch (event)
+            {
+                case SignalEventId.firstSlotConnected:
+                    qtd_connect(__nativeId, signature, signalId, cast(bool)(__flags_ & QtdObjectFlags.dynamicEntity));
+                    break;
+                case SignalEventId.lastSlotDisconnected:
+                    qtd_disconnect(__nativeId, signature, signalId, cast(bool)(__flags_ & QtdObjectFlags.dynamicEntity));
+                    break;
+                default:
+                    assert (false);
+            }
+        }
+    }
     
-    // this flag needs to be set false when QObject is deleted from inside Qt so when deleting it from D it won't delete C++ object
-    public bool __no_real_delete = false;
+    ~this()
+    {
+        if (__prev)
+            __prev.__next = __next;
+        else
+            __root = __next;
+        
+        if (__next)      
+            __next.__prev = __prev;        
+    }
+    
+    /**
+    */
+    T findChild(T : QObject = QObject)(string name = null)
+    {
+        foreach (obj; children)
+        {
+            auto tmp = cast(T)obj;
+            if (tmp && (!name.length || tmp.objectName == name))
+                return tmp;
+            
+            tmp = obj.findChild!(T)(name);
+            if (tmp)
+                return tmp;
+        }
+        
+        return null;
+    }
+    
+    /**
+    */
+    T[] findChildren(T : QObject = QObject)(string name = null)
+    {
+        T[] result;
+        
+        void find(QObject[] objects)
+        {        
+            foreach (obj; objects)
+            {
+                auto tmp = cast(T)obj;
+                if (tmp && (!name.length || tmp.objectName == name))
+                    result ~= tmp;
+                find(obj.children);
+            }
+        }
+        
+        find(children);
+        return result;
+    }
 }// class
 
 abstract class QAbstractItemModel___ extends QAbstractItemModel {
@@ -141,14 +217,14 @@
 	{
 //        if (m_instance != null)
 //            throw new RuntimeException("QCoreApplication can only be initialized once");
-            
+
 		argc = args.length;
 		argv = toStringzArray(args);
 		this(&argc, argv);
 
 //        m_instance.aboutToQuit.connect(m_instance, "disposeOfMyself()");
 	}
-	
+
 	private int argc;
 	private char **argv;
 /*
@@ -489,7 +565,7 @@
 
     public final long write(string str) {
 	return write(str.ptr, str.length);
-    } 
+    }
 }// class
 
 class QCryptographicHash___ extends QCryptographicHash {
--- a/generator/typesystem_core.xml	Sat Aug 22 12:50:58 2009 +0000
+++ b/generator/typesystem_core.xml	Sun Aug 30 09:59:12 2009 +0000
@@ -1,5 +1,5 @@
 <?xml version="1.0" encoding="UTF-8"?>
-<typesystem package="qt.core" default-superclass="QtDObject">
+<typesystem package="qt.core" default-superclass="QtdObject">
 <inject-code>
     qt.Utilities.loadQtLibrary("QtCore");
     </inject-code>
@@ -787,7 +787,7 @@
     </modify-function>
 
     <modify-function signature="setYMD(int, int, int)" remove="all"/> <!--### Obsolete in 4.3-->
-  
+
         <inject-code>
             <import-file name="typesystem_core-java.java" quote-after-line="class QDate___" quote-before-line="}// class"/>
         </inject-code>
@@ -814,7 +814,7 @@
     <modify-function signature="operator=(QDir)" remove="all"/>
     <modify-function signature="operator=(QString)" remove="all"/>
     <modify-function signature="addResourceSearchPath(QString)" remove="all"/> <!--### Obsolete in 4.3-->
-  
+
         <inject-code>
             <import-file name="typesystem_core-java.java" quote-after-line="class QDir___" quote-before-line="}// class"/>
         </inject-code>
@@ -882,7 +882,7 @@
     <modify-function signature="operator-=(QSize)"> <access modifier="private"/> </modify-function>
     <modify-function signature="rheight()"> <remove/> </modify-function>
     <modify-function signature="rwidth()"> <remove/> </modify-function>
-  
+
         <inject-code>
             <insert-template name="core.multiply-devide-add-subtract">
                 <replace from="%TYPE" to="QSize"/>
@@ -897,7 +897,7 @@
     <modify-function signature="operator-=(QSizeF)"> <access modifier="private"/> </modify-function>
     <modify-function signature="rheight()"> <remove/> </modify-function>
     <modify-function signature="rwidth()"> <remove/> </modify-function>
-  
+
         <inject-code>
             <insert-template name="core.multiply-devide-add-subtract">
                 <replace from="%TYPE" to="QSizeF"/>
@@ -1067,7 +1067,7 @@
     <modify-function signature="operator^=(QBitArray)" access="private"/>
     <modify-function signature="operator|=(QBitArray)" access="private"/>
     <modify-function signature="operator~()const" access="private"/>
-  
+
       <inject-code>
           <import-file name="typesystem_core-java.java" quote-after-line="class QBitArray___" quote-before-line="}// class"/>
       </inject-code>
@@ -1091,7 +1091,7 @@
 
     <modify-function signature="modelAboutToBeReset()" private-signal="yes"/>
     <modify-function signature="modelReset()" private-signal="yes"/>
-    
+
         <modify-function signature="parent()const" remove="java"/>
         <extra-includes>
             <include file-name="QStringList" location="global"/>
@@ -1194,13 +1194,13 @@
   <interface-type name="QFactoryInterface" java-name="QAbstractFactory"/>
 
   <value-type name="QByteArray">
-    
+
     <modify-function signature="at(int)const">
         <modify-argument index="return">
             <replace-type modified-type="ubyte"/>
         </modify-argument>
     </modify-function>
-    
+
     <extra-includes>
         <include file-name="QNoImplicitBoolCast" location="global"/>
     </extra-includes>
@@ -1738,7 +1738,7 @@
     <modify-function signature="readLink(QString)" remove="all"/> <!--### Obsolete in 4.3-->
     <modify-function signature="map(long long,long long,QFile::MemoryMapFlags)" remove="all"/> <!-- Can't provide same API and performance -->
     <modify-function signature="unmap(unsigned char*)" remove="all"/> <!-- Can't provide same API and performance -->
-  
+
         <inject-code>
             <import-file name="typesystem_core-java.java" quote-after-line="class QFile___" quote-before-line="}// class"/>
         </inject-code>
@@ -1759,11 +1759,11 @@
             <access modifier="private"/>
             <rename to="getByte"/>
         </modify-function>
-	
+
 	<modify-function signature="write(const char*)">
             <access modifier="private"/>
         </modify-function>
-	
+
 	<modify-function signature="write(const char*,long long)">
             <access modifier="private"/>
         </modify-function>
@@ -2025,7 +2025,7 @@
     <modify-function signature="toUnicode(const char*)const">
         <remove/>
     </modify-function>
-  
+
         <inject-code>
             <import-file name="typesystem_core-java.java" quote-after-line="class QTextCodec___" quote-before-line="}// class"/>
         </inject-code>
@@ -2116,7 +2116,7 @@
     <modify-function signature="translate(const char*,const char*,const char*,int)const">
         <remove/>
     </modify-function>
-  
+
         <extra-includes>
             <include file-name="QTextCodec" location="global"/>
          </extra-includes>
@@ -2200,7 +2200,7 @@
     <modify-function signature="buffer()const">
         <remove/>
     </modify-function>
-  
+
 
         <inject-code>
             <import-file name="typesystem_core-java.java" quote-after-line="class QBuffer___" quote-before-line="}// class"/>
@@ -2269,7 +2269,7 @@
     </extra-includes>
     <modify-function signature="map(long long,long long,QFile::MemoryMapFlags)" remove="all"/>
     <modify-function signature="unmap(unsigned char*)" remove="all"/>
-  
+
     <inject-code>
         <import-file name="typesystem_core-java.java" quote-after-line="class QAbstractFileEngine___" quote-before-line="}// class"/>
     </inject-code>
@@ -2316,7 +2316,7 @@
     <modify-function signature="mapping(QWidget*)const" remove="all"/>
 
     <modify-function signature="setMapping(QObject*,QWidget*)" remove="all"/>
-  
+
         <inject-code>
             <import-file name="typesystem_core-java.java" quote-after-line="class QSignalMapper___" quote-before-line="}// class"/>
         </inject-code>
@@ -2361,6 +2361,80 @@
   </object-type>
 
   <object-type name="QObject">
+	<inject-code class="native">
+
+#ifdef CPP_SHARED
+QTD_EXPORT_VAR(qtd_delete_d_qobject);
+
+extern "C" DLL_PUBLIC void qtd_QObjectEntity_initCallBacks(pfunc_abstr del_d_qobj)
+{
+	QTD_EXPORT_VAR_SET(qtd_delete_d_qobject, del_d_qobj);
+}
+#endif
+
+
+extern "C" DLL_PUBLIC void* qtd_get_d_qobject(void *nativeId)
+{
+    QtD_QObjectEntity *entity = QtD_QObjectEntity::getQObjectEntity((QObject*)nativeId);
+    return entity ? entity-&gt;dId : NULL;
+}
+
+extern "C" DLL_PUBLIC void qtd_delete_qobject(void *nativeId)
+{    
+    delete (QObject*)nativeId;    
+}
+
+extern "C" DLL_PUBLIC void qtd_create_qobject_entity(void* nativeId, void *dId)
+{
+	new QtD_QObjectEntity((QObject*)nativeId, dId);
+}
+
+extern "C" DLL_PUBLIC void* qtd_QObject_metaObject(void* nativeId)
+{
+    return (void*)((QObject*)nativeId)->metaObject();
+}
+
+extern "C" DLL_PUBLIC void qtd_connect(void* nativeId, char* signal, int id, bool dynamicEntity)
+{   
+    QObject *sender = (QObject*)nativeId;
+    QObject *receiver = dynamicEntity ? dynamic_cast&lt;QObject*&gt;(QtD_QObjectEntity::getQObjectEntity(sender)) : sender;
+    const QMetaObject *mo = sender->metaObject();
+    int nativeSigId = mo-&gt;indexOfSignal(signal);
+    QMetaObject::connect(sender, nativeSigId, receiver, receiver-&gt;metaObject()-&gt;methodCount() + id);
+}
+
+extern "C" DLL_PUBLIC void qtd_disconnect(void* nativeId, char* signal, int id, bool dynamicEntity)
+{
+    QObject *sender = (QObject*)nativeId;
+    QObject *receiver = dynamicEntity ? dynamic_cast&lt;QObject*&gt;(QtD_QObjectEntity::getQObjectEntity(sender)) : sender;
+    const QMetaObject *mo = sender->metaObject();    
+    int nativeSigId = mo-&gt;indexOfSignal(signal);
+    QMetaObject::disconnect(sender, nativeSigId, receiver, receiver-&gt;metaObject()-&gt;methodCount() + id);
+}
+
+ 	</inject-code>
+
+	<inject-code class="java-free">
+extern(C) void* qtd_get_d_qobject(void* nativeId);
+extern(C) void qtd_delete_qobject(void* nativeId);
+extern(C) void* qtd_create_qobject_entity(void* nativeId, void* dId);
+extern(C) void* qtd_QObject_metaObject(void* nativeId);
+extern(C) void qtd_connect(void *nativeId, cstringz signal, int id, bool dynamicEntity);
+extern(C) void qtd_disconnect(void *nativeId, cstringz signal, int id, bool dynamicEntity);
+
+extern(C) void qtd_delete_d_qobject(void* dId)
+{
+    auto obj = cast(QObject)dId;
+	
+	if (!(obj.__flags &amp; QtdObjectFlags.dOwnership))
+	{
+		// Avoid deleting native object twice
+		obj.__setFlags(QtdObjectFlags.nativeOwnership, true);
+		delete obj;
+	}
+}
+	</inject-code>
+
     <modify-function signature="childEvent(QChildEvent*)">
         <modify-argument index="1" invalidate-after-use="yes"/>
     </modify-function>
@@ -2401,6 +2475,7 @@
                 __gc_managed = false;
             }
         </inject-code> -->
+
     </modify-function>
 
     <modify-function signature="deleteLater()">
@@ -2424,11 +2499,9 @@
         <include file-name="QVarLengthArray" location="global"/>
     </extra-includes>
 
-
-
-      <inject-code class="java">
-          <import-file name="typesystem_core-java.java" quote-after-line="class QObject___" quote-before-line="}// class"/>
-      </inject-code>
+	<inject-code class="java">
+	  <import-file name="typesystem_core-java.java" quote-after-line="class QObject___" quote-before-line="}// class"/>
+	</inject-code>
   </object-type>
 
   <object-type name="QCoreApplication">
@@ -2480,7 +2553,7 @@
             <define-ownership class="java" owner="c++"/>
         </modify-argument>
     </modify-function>
-  
+
       <modify-function signature="QCoreApplication(int &amp;, char  **)">
           <inject-code class="shell">
               // qtjambi_register_variant_handler();
@@ -2527,7 +2600,7 @@
   <object-type name="QDataStream">
   <!-- qtd2 -->
   <modify-function signature="device() const" remove="all"/>
-  
+
     <modify-function signature="setDevice(QIODevice*)">
         <modify-argument index="1">
             <reference-count action="set" variable-name="__rcDevice"/>
@@ -2557,7 +2630,7 @@
     <modify-function signature="readBytes(char&amp;*,uint&amp;)"> <remove/> </modify-function>
     <modify-function signature="writeRawData(const char*,int)"> <remove/> </modify-function>
     <modify-function signature="writeBytes(const char*,uint)"> <remove/> </modify-function>
-  
+
       <template name="core.datastream_operator_shift_right">
           <insert-template name="core.stream_operator_shift_right">
               <replace from="%STREAM_TYPE" to="QDataStream"/>
@@ -2742,10 +2815,10 @@
   </object-type>
 
   <object-type name="QTextStream">
-  
+
       <modify-function signature="setCodec(QTextCodec *)" remove="all"/>
       <modify-function signature="codec() const" remove="all"/>
-  
+
     <modify-function signature="QTextStream(QByteArray *, QFlags&lt;QIODevice::OpenModeFlag&gt;)"> <remove/> </modify-function>
     <modify-function signature="QTextStream(QString*,QFlags&lt;QIODevice::OpenModeFlag&gt;)"> <remove/> </modify-function>
     <modify-function signature="operator&gt;&gt;(QChar&amp;)"> <remove/> </modify-function>
@@ -2832,7 +2905,7 @@
           <rename to="writeString"/>
           <modify-argument index="0" replace-value="this"/>
       </modify-function>
-      
+
       <modify-function signature="operator&gt;&gt;(char&amp;)">
           <access modifier="private"/>
           <modify-argument index="0" replace-value="this"/>
@@ -2907,7 +2980,7 @@
   <value-type name="QFuture" generate="no">
     <modify-function signature="operator T() const" remove="all"/>
     <modify-function signature="operator=(const QFuture &amp;)" remove="all"/>
-  
+
     <modify-function signature="operator==(const QFuture &amp;)const">
         <modify-argument index="1">
             <replace-type modified-type="qt.core.QFuture"/>
@@ -2920,7 +2993,7 @@
   <value-type name="QtJambiVoidFuture" java-name="QFutureVoid">
     <modify-function signature="resultCount()const" remove="all"/>
     <modify-function signature="isResultReadyAt(int)const" remove="all"/>
-  
+
     <modify-function signature="QFuture(const QFuture &amp;)">
         <modify-argument index="1">
             <replace-type modified-type="qt.core.QFutureVoid"/>
@@ -2944,7 +3017,7 @@
   <object-type name="QFutureWatcherBase">
     <modify-function signature="connectNotify(const char *)" remove="all"/>
     <modify-function signature="disconnectNotify(const char *)" remove="all"/>
-  
+
     <inject-code class="shell-declaration">
 
         // private, pure virtual and considered internal
@@ -2977,7 +3050,7 @@
 
   <object-type name="QFutureWatcher" generate="no">
     <modify-function signature="future()const" remove="all"/>
-  
+
     <modify-function signature="setFuture(const QFuture &amp;)">
         <modify-argument index="1">
             <replace-type modified-type="qt.core.QFuture&lt;T&gt;"/>
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/qt/core/QMetaObject.d	Sun Aug 30 09:59:12 2009 +0000
@@ -0,0 +1,134 @@
+module qt.core.QMetaObject;
+
+import qt.QGlobal;
+import qt.core.QObject;
+import qt.QtdObject;
+
+final class QMetaObject
+{
+    private
+    {
+        void* _nativeId;
+        QMetaObject _base; // super class
+        QMetaObject _firstDerived; // head of the linked list of derived classes
+        QMetaObject _next; // next sibling on this derivation level
+        ClassInfo _classInfo;
+
+        QObject function(void* nativeId) _createWrapper;
+    }
+    
+    private void addDerived(QMetaObject mo)
+    {
+        mo._next = _firstDerived;
+        _firstDerived = mo;
+    }
+    
+    // NOTE: construction is split between this non-templated constructor and 'construct' function below.
+    this(void* nativeId, QMetaObject base)
+    {
+        _nativeId = nativeId;
+        if (base)
+        {
+            base.addDerived(this);
+            _base = base;
+        }
+    }
+    
+    // TODO: remove when D acquires templated constructors       
+    void construct(T : QObject, Concrete = T)()
+    {
+        _classInfo = T.classinfo;        
+
+        _createWrapper = function QObject(void* nativeId) {
+                // COMPILER BUG: cast is should not be needed
+                auto obj = new Concrete(nativeId, cast(QtdObjectFlags)(QtdObjectFlags.nativeOwnership | QtdObjectFlags.dynamicEntity));
+                // TODO: Probably this should be a virtual call from T's constructor
+                T.__createEntity(nativeId, cast(void*)obj);
+                return obj;
+            };
+    }
+    
+    /++
+    +/
+    QMetaObject base()
+    {
+        return _base;
+    }
+    
+    /++
+    +/
+    void* nativeId()
+    {
+        return _nativeId;
+    }
+
+    /++
+    +/
+    ClassInfo classInfo()
+    {
+        return _classInfo;
+    }
+    
+    private QMetaObject lookupDerived(void*[] moIds)
+    {
+        assert (moIds.length >= 1);
+                
+        for (auto mo = _firstDerived; mo !is null; mo = mo._next)
+        {
+            if (mo._nativeId == moIds[0])
+            {
+                if (moIds.length == 1) // exact match found
+                    return mo;
+                else // look deeper
+                    return mo.lookupDerived(moIds[1..$]);
+            }
+        }
+        
+        // no initialized wrapper that matches the native object.
+        // use the base class wrapper
+        return this;
+    }
+    
+    QObject getObject(void* nativeObjId)
+    {
+        QObject result;
+        
+        if (nativeObjId)
+        {
+            result = cast(QObject)qtd_get_d_qobject(nativeObjId);            
+            if (!result)
+            {
+                auto moId = qtd_QObject_metaObject(nativeObjId);
+                if (_nativeId == moId)
+                     result = _createWrapper(nativeObjId);
+                else
+                {
+                    // get native metaobjects for the entire derivation lattice
+                    // up to, but not including, the current metaobject.
+                    size_t moCount = 1;
+                    
+                    for (void* tmp = moId;;)
+                    {
+                        tmp = qtd_QMetaObject_superClass(tmp);                        
+                        assert(tmp);
+                        if (tmp == _nativeId)                        
+                            break;
+                        moCount++;
+                    }
+                   
+                    void*[] moIds = (cast(void**)alloca(moCount * (void*).sizeof))[0..moCount];
+
+                    moIds[--moCount] = moId;
+                    while (moCount > 0)
+                        moIds[--moCount] = moId = qtd_QMetaObject_superClass(moId);
+                                    
+                    result = lookupDerived(moIds)._createWrapper(nativeObjId);
+                }                
+            }
+        }
+
+        return result;
+    }
+}
+
+extern(C) void* qtd_QMetaObject_superClass(void* nativeId);
\ No newline at end of file
--- a/qt/d1/qt/QtDObject.d	Sat Aug 22 12:50:58 2009 +0000
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,70 +0,0 @@
-/**
-*
-*  Copyright: Copyright QtD Team, 2008-2009
-*  License: <a href="http://www.boost.org/LICENSE_1_0.txt>Boost License 1.0</a>
-*
-*  Copyright QtD Team, 2008-2009
-*  Distributed under the Boost Software License, Version 1.0.
-*  (See accompanying file boost-license-1.0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
-*
-*/
-
-module qt.QtDObject;
-
-//import tango.util.container.HashMap;
-import qt.Signal;
-
-package class QtDObject
-{
-    public final void* nativeId() { return native__id; }
-
-	public final void nativeId(void *native_id) { native__id = native_id; }
-
-	private void* native__id = null;
-
-    mixin SignalHandlerOps;
-
-    public this()
-    {
-        /* intentionally empty */
-    }
-
-    package this(void* native_id, bool no_real_delete = false)
-    {
-        native__id = native_id;
-/*		auto qObj = cast(QObject) this;
-		if (qObj is null)
-		    register(native__id);*/
-        __no_real_delete = no_real_delete;
-    }
-/*
-	~this() {
-	    unregister(native__id);
-	}
-*/
-    // this flag controls if D object when destroying should or shouldn't delete real C++ object
-	public bool __no_real_delete = false;
-
-    package void __free_native_resources();
-
-
-	/*          hash table of Object instances            */
-/*    private static HashMap!(void*, Object) _map;
-
-	static this() {
-        _map = new HashMap!(void*, Object);
-	}
-
-	package static void register(void* qt_object, Object d_object) {
-	    _map.add(qt_object, d_object);
-	}
-
-	package static void unregister(void* qt_object) {
-	    _map.removeKey(qt_object);
-	}
-
-	package static Object lookup(void* qt_object) {
-	    return _map[qt_object];
-	}
-	*/
-}
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/qt/d1/qt/QtdObject.d	Sun Aug 30 09:59:12 2009 +0000
@@ -0,0 +1,91 @@
+/**
+*
+*  Copyright: Copyright QtD Team, 2008-2009
+*  License: <a href="http://www.boost.org/LICENSE_1_0.txt>Boost License 1.0</a>
+*
+*  Copyright QtD Team, 2008-2009
+*  Distributed under the Boost Software License, Version 1.0.
+*  (See accompanying file boost-license-1.0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
+*
+*/
+
+module qt.QtdObject;
+
+import qt.Signal;
+//import tango.io.Stdout;
+
+enum QtdObjectFlags : ubyte
+{
+    none,
+    nativeOwnership           = 0x1,
+    dOwnership                = 0x2,
+    dynamicEntity             = 0x4
+    //gcManaged               = 0x4
+}
+
+package abstract class QtdObject
+{
+    protected QtdObjectFlags __flags_;
+    void* __nativeId;
+    
+    mixin SignalHandlerOps;
+    
+    this(void* nativeId, QtdObjectFlags flags = QtdObjectFlags.none)
+    {
+        //Stdout.formatln("Created D object {} {:x}", nativeId, flags).newline;
+        __nativeId = nativeId;
+        __flags_ = flags;
+    }
+
+    final QtdObjectFlags __flags()
+    {
+        return __flags_;
+    }
+
+    /+ final +/ void __setFlags(QtdObjectFlags flags, bool value)
+    {
+        if (value)
+            __flags_ |= flags;
+        else
+            __flags_ &= ~flags;
+    }
+
+    // COMPILER BUG: 3206
+    protected void __deleteNative()
+    {
+        assert(false);
+    }
+
+    ~this()
+    {
+        //Stdout.formatln("Deleting D object {}", __nativeId);
+        if (!(__flags_ & QtdObjectFlags.nativeOwnership))
+        {
+            // avoid deleting D object twice.
+            //Stdout.formatln("About to delete native object {}", __nativeId);
+            __flags_ |= QtdObjectFlags.dOwnership;
+            __deleteNative;
+        }
+        //Stdout.formatln("Deleted native D object {}", __nativeId);
+    }    
+}
+
+class QtdMetaObject
+{
+    private
+    {
+        void* _typeId;
+        QtdMetaObject _base;
+    }
+    
+    QtdMetaObject base()
+    {
+        return _base;
+    }
+    
+    this(void* typeId, QtdMetaObject base)
+    {
+        _typeId = typeId;
+        _base = base;
+    }
+}
\ No newline at end of file
--- a/qt/d1/qt/Signal.d	Sat Aug 22 12:50:58 2009 +0000
+++ b/qt/d1/qt/Signal.d	Sun Aug 30 09:59:12 2009 +0000
@@ -100,6 +100,11 @@
         memmove(a.ptr + dest, a.ptr + src, length * T.sizeof);
 }
 
+enum SignalEventId
+{
+    firstSlotConnected,
+    lastSlotDisconnected
+}
 
 public class SignalException : Exception
 {
@@ -368,7 +373,7 @@
     }
 }
 
-public alias void delegate(int signalId) SignalEvent;
+public alias void delegate(int signalId, SignalEventId event) SignalEvent;
 
 struct SignalConnections
 {
@@ -481,12 +486,9 @@
     SignalConnections[] connections;
     Object owner;
     int blocked;
-
-    // Called after a slot has been connected to an empty signal
-    SignalEvent firstSlotConnected;
-    // Called after the last slot has been disconnected from a signal
-    SignalEvent lastSlotDisconnected;
-
+    
+    SignalEvent signalEvent;
+   
     alias SignalConnections.SlotType SlotType;
     alias SignalConnections.ReceiverType ReceiverType;
 
@@ -508,8 +510,8 @@
             connections.length = signalId + 1;
         auto slot = connections[signalId].addSlot!(slotListId)(SlotType!(slotListId)(receiver, invoker));
 
-        if (firstSlotConnected && connections[signalId].slotCount == 1)
-            firstSlotConnected(signalId);
+        if (signalEvent && connections[signalId].slotCount == 1)
+            signalEvent(signalId, SignalEventId.firstSlotConnected);
 
         return slot;
     }
@@ -518,8 +520,8 @@
     {
         connections[signalId].removeSlot!(slotListId)(slotId);
 
-        if (lastSlotDisconnected && !connections[signalId].slotCount)
-            lastSlotDisconnected(signalId);
+        if (signalEvent && !connections[signalId].slotCount)
+            signalEvent(signalId, SignalEventId.lastSlotDisconnected);
     }
 
     private SlotType!(slotListId)* addObjectSlot(int slotListId)(size_t signalId, Object obj, Dg receiver,
--- a/qt/d2/qt/QtDObject.d	Sat Aug 22 12:50:58 2009 +0000
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,71 +0,0 @@
-/**
-*
-*  Copyright: Copyright QtD Team, 2008-2009
-*  License: <a href="http://www.boost.org/LICENSE_1_0.txt>Boost License 1.0</a>
-*
-*  Copyright QtD Team, 2008-2009
-*  Distributed under the Boost Software License, Version 1.0.
-*  (See accompanying file boost-license-1.0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
-*
-*/
-
-module qt.QtDObject;
-
-//import tango.util.container.HashMap;
-import qt.Signal;
-
-package class QtDObject
-{
-//    public final const(void*) nativeId() const { return native__id; }
-    public final void* nativeId() { return native__id; }
-
-    public final void nativeId(void *native_id) { native__id = native_id; }
-
-    private void* native__id = null;
-
-    mixin SignalHandlerOps;
-
-    public this()
-    {
-        /* intentionally empty */
-    }
-
-    package this(void* native_id, bool no_real_delete = false)
-    {
-        native__id = native_id;
-/*		auto qObj = cast(QObject) this;
-		if (qObj is null)
-		    register(native__id);*/
-        __no_real_delete = no_real_delete;
-    }
-/*
-	~this() {
-	    unregister(native__id);
-	}
-*/
-    // this flag controls if D object when destroying should or shouldn't delete real C++ object
-	public bool __no_real_delete = false;
-
-    package void __free_native_resources();
-
-
-	/*          hash table of Object instances            */
-/*    private static HashMap!(void*, Object) _map;
-
-	static this() {
-        _map = new HashMap!(void*, Object);
-	}
-
-	package static void register(void* qt_object, Object d_object) {
-	    _map.add(qt_object, d_object);
-	}
-
-	package static void unregister(void* qt_object) {
-	    _map.removeKey(qt_object);
-	}
-
-	package static Object lookup(void* qt_object) {
-	    return _map[qt_object];
-	}
-	*/
-}
\ No newline at end of file
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/qt/d2/qt/QtdObject.d	Sun Aug 30 09:59:12 2009 +0000
@@ -0,0 +1,66 @@
+/**
+*
+*  Copyright: Copyright QtD Team, 2008-2009
+*  License: <a href="http://www.boost.org/LICENSE_1_0.txt>Boost License 1.0</a>
+*
+*  Copyright QtD Team, 2008-2009
+*  Distributed under the Boost Software License, Version 1.0.
+*  (See accompanying file boost-license-1.0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
+*
+*/
+
+module qt.QtdObject;
+
+import qt.Signal;
+
+enum QtdObjectFlags : ubyte
+{
+    none,
+    nativeOwnership           = 0x1,
+    dOwnership                = 0x2,
+    dynamicEntity             = 0x4
+    //gcManaged               = 0x4
+}
+
+package abstract class QtdObject
+{
+    protected QtdObjectFlags __flags_;
+    void* __nativeId;
+
+    mixin SignalHandlerOps;
+        
+    this(void* nativeId, QtdObjectFlags flags = QtdObjectFlags.none)
+    {
+        __nativeId = nativeId;
+        __flags_ = flags;
+    }
+
+    final QtdObjectFlags __flags()
+    {
+        return __flags_;
+    }
+
+    /+ final +/ void __setFlags(QtdObjectFlags flags, bool value)
+    {
+        if (value)
+            __flags_ |= flags;
+        else
+            __flags_ &= ~flags;
+    }
+
+    // COMPILER BUG: 3206
+    protected void __deleteNative()
+    {
+        assert(false);
+    }
+
+    ~this()
+    {
+        if (!(__flags_ & QtdObjectFlags.nativeOwnership))
+        {
+            // avoid deleting D object twice.
+            __flags_ |= QtdObjectFlags.dOwnership;
+            __deleteNative;
+        }
+    }
+}
--- a/qt/d2/qt/Signal.d	Sat Aug 22 12:50:58 2009 +0000
+++ b/qt/d2/qt/Signal.d	Sun Aug 30 09:59:12 2009 +0000
@@ -71,6 +71,11 @@
         memmove(a.ptr + dest, a.ptr + src, length * T.sizeof);
 }
 
+enum SignalEventId
+{
+    firstSlotConnected,
+    lastSlotDisconnected
+}
 
 public class SignalException : Exception
 {
@@ -331,7 +336,7 @@
     }
 }
 
-public alias void delegate(int signalId) SignalEvent;
+public alias void delegate(int signalId, SignalEventId event) SignalEvent;
 
 struct SignalConnections
 {
@@ -444,12 +449,9 @@
     SignalConnections[] connections;
     Object owner;
     int blocked;
-
-    // Called after a slot has been connected to an empty signal
-    SignalEvent firstSlotConnected;
-    // Called after the last slot has been disconnected from a signal
-    SignalEvent lastSlotDisconnected;
-
+    
+    SignalEvent signalEvent;
+       
     alias SignalConnections.SlotType SlotType;
     alias SignalConnections.ReceiverType ReceiverType;
 
@@ -471,8 +473,8 @@
             connections.length = signalId + 1;
         auto slot = connections[signalId].addSlot!(slotListId)(SlotType!(slotListId)(receiver, invoker));
 
-        if (firstSlotConnected && connections[signalId].slotCount == 1)
-            firstSlotConnected(signalId);
+       if (signalEvent && connections[signalId].slotCount == 1)
+            signalEvent(signalId, SignalEventId.firstSlotConnected);
 
         return slot;
     }
@@ -481,8 +483,8 @@
     {
         connections[signalId].removeSlot!(slotListId)(slotId);
 
-        if (lastSlotDisconnected && !connections[signalId].slotCount)
-            lastSlotDisconnected(signalId);
+        if (signalEvent && !connections[signalId].slotCount)
+            signalEvent(signalId, SignalEventId.lastSlotDisconnected);
     }
 
     private SlotType!(slotListId)* addObjectSlot(int slotListId)(size_t signalId, Object obj, Dg receiver,