Trolltech Home | Qt-interest Home | Recent Threads | All Threads | Author | Date
All threads index page 5

Qt-interest Archive, April 2007
Error in function call QObject::property(name) (Qt4.3.0beta)


Message 1 in thread

Hi,

I created an QAxObject base on IDispatch *
Then, I made a function call:
QString html = iObject.generateDocumentation();
where the html was generated correctly.

 From the html I found a property: "int myInt", which was originated 
from an QAxBindable class:
Q_PROPERTY( int myInt READ myInt WRITE setMyInt )

Clicking on the property I got help:
“Read this property's value using QObject::property:
int val =object->property("myInt").toInt();
“

I did it like:
int val = iObject.property("myInt").toInt();
// int val = iObject.myInt(); // same above
but I got error:
ASERT "id < 0" in file .\qaxbase.cpp, line 3642

I got stuck in how to retrieve an OLE object.
Is this a bug in QObject or a bug in the QAxObject base on 
IDispatch(machine generated by dumpcpp tool)?

Thanks,
Lingfa

--
 [ signature omitted ] 

Message 2 in thread

"Lingfa Yang" <lingfa@xxxxxxx> wrote in message 
news:4624F3FA.9060800@xxxxxxxxxx
> Hi,
>
> I created an QAxObject base on IDispatch *
> Then, I made a function call:
> QString html = iObject.generateDocumentation();
> where the html was generated correctly.
>
> From the html I found a property: "int myInt", which was originated from 
> an QAxBindable class:
> Q_PROPERTY( int myInt READ myInt WRITE setMyInt )


What does the QAxBindable class do here? QAxBindable is usually used in 
QAxServer, whereas QAxObject is used in QAxContainer.


> Clicking on the property I got help:
> ?Read this property's value using QObject::property:
> int val =object->property("myInt").toInt();
> ?
>
> I did it like:
> int val = iObject.property("myInt").toInt();
> // int val = iObject.myInt(); // same above
> but I got error:
> ASERT "id < 0" in file .\qaxbase.cpp, line 3642
>
> I got stuck in how to retrieve an OLE object.
> Is this a bug in QObject or a bug in the QAxObject base on 
> IDispatch(machine generated by dumpcpp tool)?


Did this work with 4.2.x?

Does the object the IDispatch*  you get back refers to have a property 
"myInt" (according to the type library)?


Volker


--
 [ signature omitted ] 

Message 3 in thread

Volker Hilsheimer wrote:

>"Lingfa Yang" <lingfa@xxxxxxx> wrote in message 
>news:4624F3FA.9060800@xxxxxxxxxx
>  
>
>>Hi,
>>
>>I created an QAxObject base on IDispatch *
>>Then, I made a function call:
>>QString html = iObject.generateDocumentation();
>>where the html was generated correctly.
>>
>>From the html I found a property: "int myInt", which was originated from 
>>an QAxBindable class:
>>Q_PROPERTY( int myInt READ myInt WRITE setMyInt )
>>    
>>
>
>
>What does the QAxBindable class do here? QAxBindable is usually used in 
>QAxServer, whereas QAxObject is used in QAxContainer.
>  
>
You're right. Here, in container, nothing to do with QAxBindable class.
What I just mentioned, or made sure, there were a property NAME "myInt", 
a READ function "myInt" , and a WRITE func "setMyInt" when I generated 
the ActiveQt control.

>>Clicking on the property I got help:
>>“Read this property's value using QObject::property:
>>int val =object->property("myInt").toInt();
>>“
>>
>>I did it like:
>>int val = iObject.property("myInt").toInt();
>>// int val = iObject.myInt(); // same above
>>but I got error:
>>ASERT "id < 0" in file .\qaxbase.cpp, line 3642
>>
>>I got stuck in how to retrieve an OLE object.
>>Is this a bug in QObject or a bug in the QAxObject base on 
>>IDispatch(machine generated by dumpcpp tool)?
>>    
>>
>
>
>Did this work with 4.2.x?
>  
>
Not 4.2.x, but I did test in 4.1.1, which failed either --- that's why I 
downloaded the newest version of Qt.

>Does the object the IDispatch*  you get back refers to have a property 
>"myInt" (according to the type library)?
>
>  
>
Yes, it is in the type library.
Thanks,

>Volker
>  
>


--
 [ signature omitted ] 

Message 4 in thread

>>>Hi,
>>>
>>>I created an QAxObject base on IDispatch *
>>>Then, I made a function call:
>>>QString html = iObject.generateDocumentation();
>>>where the html was generated correctly.
>>>
>>>From the html I found a property: "int myInt", which was originated 
>>>from an QAxBindable class:
>>>Q_PROPERTY( int myInt READ myInt WRITE setMyInt )
>>>
>>
>>
>>What does the QAxBindable class do here? QAxBindable is usually used in 
>>QAxServer, whereas QAxObject is used in QAxContainer.
>>
> You're right. Here, in container, nothing to do with QAxBindable class.
> What I just mentioned, or made sure, there were a property NAME "myInt", 
> a READ function "myInt" , and a WRITE func "setMyInt" when I generated 
> the ActiveQt control.


So, you have an ActiveQt based control (i.e. a QWidget that you have 
exposed as an ActiveX control), and you use that ActiveX control in your 
Qt application via QAxObject/QAxWidget?

Why? Just use the QWidget directly.


Volker


--
 [ signature omitted ] 

Message 5 in thread

>So, you have an ActiveQt based control (i.e. a QWidget that you have 
>exposed as an ActiveX control), and you use that ActiveX control in your 
>Qt application via QAxObject/QAxWidget?
>
>Why? Just use the QWidget directly.
>
>
>Volker
>  
>
Very good question!
That is the need from automating PowerPoint.
We need to insert these controls to PowerPoint and pass to our clients 
for better presentation.
For example, a plotter holds xy-data. We insert the plotter control and 
persistent data to PowerPoint, so that customer can zoom in/out/shift 
during the slider show, which is much better than just insert several 
frames of STATIC plot images.

What we are doing is after adding the control:
    shape = shapes->AddOLEObject(100, 100, 512, 320, className, false);
how to handle(initialize/customize) the object.
I can get IDispatch, and make a handler.
    IDispatch *idispatch = shape->OLEFormat->Object();
    qwtwrapperaxLib::IQwtSimplePlotAx iObject(idispatch);
but this iObject somehow does not works well.

Any further suggestions are appreciated.

Lingfa




--
 [ signature omitted ] 

Message 6 in thread

"Lingfa Yang" <lingfa@xxxxxxx> wrote in message 
news:46250286.9060107@xxxxxxxxxx
>
>>So, you have an ActiveQt based control (i.e. a QWidget that you have 
>>exposed as an ActiveX control), and you use that ActiveX control in your 
>>Qt application via QAxObject/QAxWidget?
>>
>>Why? Just use the QWidget directly.
>>
>>
>>Volker
>>
> Very good question!
> That is the need from automating PowerPoint.
> We need to insert these controls to PowerPoint and pass to our clients 
> for better presentation.

Ok, that explains why you make your QWidget into an ActiveX. But why do 
you use that widget not directly in your Qt code? Anyway...

> For example, a plotter holds xy-data. We insert the plotter control and 
> persistent data to PowerPoint, so that customer can zoom in/out/shift 
> during the slider show, which is much better than just insert several 
> frames of STATIC plot images.
>
> What we are doing is after adding the control:
>    shape = shapes->AddOLEObject(100, 100, 512, 320, className, false);
> how to handle(initialize/customize) the object.
> I can get IDispatch, and make a handler.
>    IDispatch *idispatch = shape->OLEFormat->Object();
>    qwtwrapperaxLib::IQwtSimplePlotAx iObject(idispatch);
> but this iObject somehow does not works well.
>
> Any further suggestions are appreciated.

Are you sure that the IDispatch returned references a 
qwtwrapperaxLib::IQwtSimplePlotAx?


Volker


--
 [ signature omitted ] 

Message 7 in thread

>Ok, that explains why you make your QWidget into an ActiveX. But why do 
>you use that widget not directly in your Qt code? Anyway...
>
>  
>
If the ActiveX does not take user’s date, adding the control to ppt is 
enough, then, the user can load the data during the slide-show --- but 
this is not good. The good approach is save both the data and the 
control to ppt, so that the user needn’t loading.

>
>Are you sure that the IDispatch returned references a 
>qwtwrapperaxLib::IQwtSimplePlotAx?
>  
>

It does not return the reference to IQwtSimplePlotAx, instead, the class 
takes IDispatch in its constructor to create a handler.

dumpcpp generates two classes, one with “I”, the other without.
class QWTWRAPPERAXLIB_EXPORT IQwtSimplePlotAx : public QAxObject
class QWTWRAPPERAXLIB_EXPORT QwtSimplePlotAx : public QAxWidget
The first one takes IDispatch in its contructor:
IQwtSimplePlotAx(IDispatch *subobject = 0, QAxObject *parent = 0)
: QAxObject((IUnknown*)subobject, parent)
{
internalRelease();
}
The second one takes iface;
QwtSimplePlotAx(IQwtSimplePlotAx *iface)
: QAxWidget()
{
initializeFrom(iface);
delete iface;
}
or default constuctor:
QwtSimplePlotAx(QWidget *parent = 0, Qt::WindowFlags f = 0)
: QAxWidget(parent, f)
{
setControl("{52ac57f1-f548-4012-aaa3-5d589a02c8f3}");
}
The default one, itself, works well. (I am 100% sure about its property 
calls or direct function calls.)

Our company has Qt license support, so should I dig that path, or stay 
with this board?

Thanks,
Lingfa

--
 [ signature omitted ] 

Message 8 in thread

"Lingfa Yang" <lingfa@xxxxxxx> wrote in message 
news:462633C7.1020605@xxxxxxxxxx
>
>>Ok, that explains why you make your QWidget into an ActiveX. But why do 
>>you use that widget not directly in your Qt code? Anyway...
>>
>>
> If the ActiveX does not take user?s date, adding the control to ppt is 
> enough, then, the user can load the data during the slide-show --- but 
> this is not good. The good approach is save both the data and the 
> control to ppt, so that the user needn?t loading.
>
>>
>>Are you sure that the IDispatch returned references a 
>>qwtwrapperaxLib::IQwtSimplePlotAx?
>>
>
> It does not return the reference to IQwtSimplePlotAx, instead, the class 
> takes IDispatch in its constructor to create a handler.

Exactly. If the IDispatch* returned is not implemented by a 
QwtSimplePlotAx object, then everything will go wrong. You must be sure 
that the IDispatch* returned is the one implemented by an object of the 
type that you want to create.

It's like connecting to a slot in an object that doesn't have such a slot. 
You can still do it, but it won't work.


> dumpcpp generates two classes, one with ?I?, the other without.
> class QWTWRAPPERAXLIB_EXPORT IQwtSimplePlotAx : public QAxObject
> class QWTWRAPPERAXLIB_EXPORT QwtSimplePlotAx : public QAxWidget
> The first one takes IDispatch in its contructor:
> IQwtSimplePlotAx(IDispatch *subobject = 0, QAxObject *parent = 0)
> : QAxObject((IUnknown*)subobject, parent)
> {
> internalRelease();
> }
> The second one takes iface;
> QwtSimplePlotAx(IQwtSimplePlotAx *iface)
> : QAxWidget()
> {
> initializeFrom(iface);
> delete iface;
> }
> or default constuctor:
> QwtSimplePlotAx(QWidget *parent = 0, Qt::WindowFlags f = 0)
> : QAxWidget(parent, f)
> {
> setControl("{52ac57f1-f548-4012-aaa3-5d589a02c8f3}");
> }
> The default one, itself, works well. (I am 100% sure about its property 
> calls or direct function calls.)
>
> Our company has Qt license support, so should I dig that path, or stay 
> with this board?


You can go through support, but guess who will answer your ActiveQt 
question :)


Volker


--
 [ signature omitted ] 

Message 9 in thread

>Exactly. If the IDispatch* returned is not implemented by a 
>QwtSimplePlotAx object, then everything will go wrong. 
>  
>
Thank you so much.

This is a key point --- very close to problem solved I guess.

First, I do not explicitly implement any return which brings IDispatch*. 
My augment is that IDispatch is obtained from 
PowerPoint::OLEFormat::Object(), which is machine-generated code.
inline IDispatch* OLEFormat::Object() const
{
    QVariant qax_result = property("Object");
    if (!qax_result.constData()) return 0;
    Q_ASSERT(qax_result.isValid());
    return *(IDispatch**)qax_result.constData();
}
 From above, why I have to implement an IDispatch* return in my coding?

Second, I tried to find a how-to-do Qt example about the IDispatch* 
return. Not found in examples\ActiveQt!
Would you please tell me how to implement?

I appreciate your crucial help.
Lingfa


--
 [ signature omitted ] 

Message 10 in thread

Lingfa Yang wrote:

>
>> Exactly. If the IDispatch* returned is not implemented by a 
>> QwtSimplePlotAx object, then everything will go wrong.  
>>
> My augment is that IDispatch is obtained from 
> PowerPoint::OLEFormat::Object(), which is machine-generated code.
>
One more progress is I took the same control and inserted to ppt by MFC:

    OLEFormat oOLEFmt = oShape.GetOLEFormat();
    IQwtSimplePlotAx oSimplePlot = oOLEFmt.GetObject();
     // manapulate the interface object
    long myInt = oSimplePlot.GetMyInt(); // right
   oSimplePlot.SetMyInt(myInt+10);  // right
    long newValue = oSimplePlot.GetMyInt(); // excellent

Everything works well --- I mean by MFC the same (IDispatch *) was 
returned, and an interface object was obtained in the same manner, and 
one can feel free to manapulate programmatically. --- which means there 
is nothing wrong about  my ActiveX control. So what's wrong with my Qt 
automating ppt?
Thanks,
Lingfa


--
 [ signature omitted ]