Problem casting an interface from a COM object
Posted on 2003-11-26
I have the weirdest problem when instantiating a COM object...
I have a program installed, lets call it X. X provides a COM interface and a TLB file which I can import into Delphi.
I am writing another program, lets call it Y and want to use the COM interface in X.
I import the TLB file and create ActiveX components from it and use these from within my program. Everything works!
I later decide to construct the interface dynamically, rather than when the form is created and switch to creating the ActiveX components on the fly. Everything works!
I then install my program (Y), along with program X onto another computer, that does not have Delphi. I get an interface not supported exception. I install the two programs on a third computer that does have delphi with the same result. The program works on my machine (regardless of whether the Delphi IDE is running) but not on the other two :-(
After much tinkering I decide to try importing the TLB file onto the other machine that has Delphi installed. Once I did that my program (Y) runs happily getting the interface from program X. Note I did not recompile my program after installing the ActiveX components on that machine.
Now it gets stranger. Thinking that the issue was the ActiveX classes were not registered when the components were not a part of the form I explicitly registered them in my code (program Y), then uninstalled the package containing the activeX components then ran the modified program on both computers with Delphi installed - it worked! I happily installed the two programs again on the computer without Delph installed and got the interface not supported exception again!!!
Now, after some more tinkering I have this snippet of code, that works correctly and with no interface not supported exception:
(* works! *) FREQUESTOBJECT := ItRequestDispatchObject(CreateOLEObject('ProgramX.REQUESTOBJECT'));
(* works! *) FSTATUSOBJECT := ItStatusDispatchObject(CreateOLEObject(''ProgramX.STATUSOBJECT'));
This working snippet is derived from this non working snippet:
FREQUESTOBJECT := CreateOLEObject('ProgramX.REQUESTOBJECT') as ItRequestDispatchObject;
FSTATUSOBJECT := CreateOLEObject('ProgramX.STATUSOBJECT') as ItStatusDispatchObject;
I can't figure out why the hard cast works, and the soft cast does not. I would have thought that the soft cast version throwing an exception would have meant the interfaces were toast and would not work at all, but this isn't the case!!!
If anyone could throw some light on this I would like to hear it!