views:

252

answers:

2

Hi,

I'm trying to combine some existing Qt code written in C++ with some code written in Java using Qt Jambi, but I'm not quite sure how to do it. I'm basically trying to acieve two things:

  1. Pass a QObject from C++ to Java using JNI
  2. Pass a Qt Jambi QObject from Java to C++

It looks like I can pass the pointer directly and then wrap it in QNativePointer on the Java side, but I can't figure out how to turn a QNativePointer back into the original object, wrapped by Qt Jambi.

Eg: I can pass a QWidget* as a long to Java and then create a QNativePointer in Java, but how can I then construct a QWidget out of this? QJambiObject and QObject dont seem to have a "setNativePointer" method and I'm not sure how to convert it.

In C++:

QWidget* widget = ...
jclass cls = env->FindClass("Test");
jmethodID mid = env->GetStaticMethodID(cls, "test", "(I)V");
env->CallStaticVoidMethod(cls, mid, int(widget));

In Java:

public class Test {
    public static void test (int ptr) {
        QNativePointer pointer = new QNativePointer(QNativePointer.Type.Int);
        pointer.setIntValue(ptr);

        QWidget widget = ...

Thanks!

+1  A: 

I wouldn't expect that this is possible in the way, you are trying to achieve this. If I understand your approach correctly, you are somehow trying to cast the in-memory representation of a C++ QWidget object to a Java QWidget object. This could only work if the in-memory representation of Java and C++ objects would be the same, which I doubt seriously.

Even if that would be the case, it wouldn't probably work either, because I am pretty sure, that the QtJambi version of the QWidget class isn't a one to one clone of the C++ QWidget class.

For this to work, you would have to somehow read the values of the C++ QWidget, create a QtJambi QWidget object and then set these values to the new QtJambi widget. I am not aware of a conversion method, that would do this job, nor am I sure if that is possible at all.

Customizer
Actually, in an older version of Qt Jambi (I don't remember which offhand), theres a fromNativePointer() or something similar in QJambiObject which "seems" like what I want. In the newest versions, it seems to be undocumented though. Been busy with other things and haven't had a chance to test it yet though...
Dan
From what I can tell, the Jambi widget wraps a native widget, proxying the method calls to the native widget through the internal pointer. In Jambi all QObjects derive from QJambiObject which also contain a QNAtivePointer. I may be wrong, but it looks like its the case. The Jambi Generator wraps the widgets almost (there are some things that need to be done manually) completely automatically.
Dan
Ah, I forgot the point, that every QtJambi object actually has to have a link to a corresponding C++ Qt object. So actually the methods you mentioned could work. But it's questionable that these methods get documented, if they are undocumented now, in the near future, facing the fact, that Trolltech abandoned the QtJambi project and is currently trying to transform it to a community based project.
Customizer
+1  A: 

For other people looking at this, check this out: http://labs.trolltech.com/blogs/2007/08/24/extremely-interesting-jambi-trick-x-instantiating-java-widgets-from-c/

Especially this part:

The qtjambi_from_QWidget() call will either create a new Java widget if the parent widget was created in C++, or it will return the existing Java object if the parent was created in Java. If it has to create a new java object, the type of this will be the closest Java supertype known to Qt Jambi. If you have mapped your own C++ widgets and want to use them correctly in calls such as these, you have to make sure the initialization code of your generated library is called prior to the conversion takes place. Also note that in qtjambi_core.h you will find several other convenient conversion functions that can be used to convert back and forth between C++ and JNI, as well as other convenient, JNI-based code.

Erik De Rijcke