2

This my IDL file. IFrame is a dual interface and inherits both IDispatch and IUnknown.

[
    object,
    uuid(C5AD0517-37FC-479C-9C7A-A063B17E4A2E),
    dual,
    nonextensible,
    pointer_default(unique)
]
    interface IFrame : IDispatch{
};
[
    uuid(F7D50952-4AF1-491B-B0AA-35083AEFA998),
    version(1.0),
]
library bdsCOMLib
{
    importlib("stdole2.tlb");
    [
        uuid(9C2E7E2D-A39C-4FE7-BEEB-3BF65F9D4C05)      
    ]
    coclass Frame
    {
        [default] interface IFrame;
    };
};

And this is the CFrame class declaration which is suppose to implement IFrame:

class ATL_NO_VTABLE CFrame :
public CComObjectRootEx<CComSingleThreadModel>,
public CComCoClass<CFrame, &CLSID_Frame>,
public IDispatchImpl<IFrame, &IID_IFrame, &LIBID_bdsCOMLib, /*wMajor =*/ 1, /*wMinor =*/ 0>
{
    public:
        CFrame()
        {
        }

    DECLARE_REGISTRY_RESOURCEID(IDR_FRAME)


    BEGIN_COM_MAP(CFrame)
        COM_INTERFACE_ENTRY(IFrame)
        COM_INTERFACE_ENTRY(IDispatch)
    END_COM_MAP()



    DECLARE_PROTECT_FINAL_CONSTRUCT()

    HRESULT FinalConstruct()
    {
        return S_OK;
    }

    void FinalRelease()
    {
    }
};
OBJECT_ENTRY_AUTO(__uuidof(Frame), CFrame)

The COM server gets registered and it works fine when I use the Frame object in VBA but by early binding. I want to use this object with VBScript, so I do need late binding.

But late binding cannot be done. I read up on the situation and it seems that the ATL (and IDispatchImp class) do all the implementation needed for IDispatch which gives me the ability to use the object with automation tools (e.g. VBScript).

However, in practice the script gives "Active X control cannot be created" error. It's the same in VBA when I try early binding.

What am I doing wrong? I am using Visual Studio 2012 on Windows 7 64-bit but my COM server is 32-bit (and it is registered with the system).

user3707763
  • 121
  • 1
  • 8
  • Basically this is good for VBScript as well. Your scripting host however should be of matching bitness. If you are using `cscript`, then make sure you start 32-bit version `C:\Windows\SYSWOW64\cscript.exe` for your 32-bit COM server. – Roman R. Jul 08 '14 at 13:50
  • @RomanR. I think that's a non issue here. VBA uses 32-bit host and still late binding does not work. The fault is with the COM server I guess not the client. – user3707763 Jul 08 '14 at 13:58
  • The code is incomplete and the fragment you posted hardly has anything wrong in it (provided that the server has correct registration, including type library). Some hosts might expect that you implement certain additional interfaces though, e.g. `IProvideoClassIInfo`. Your immediate debugging strategy is to put a break point in constructor to see if your class is even instantiated. Then if yes, you see what interfaces are queried before the failure takes place. If your constructor is not reached, then you have a registration issue. – Roman R. Jul 08 '14 at 14:09
  • What's the typelib version declared in the .idl? – sharptooth Jul 08 '14 at 14:22
  • @sharptooth isn't it version(1.0)? – user3707763 Jul 08 '14 at 14:23
  • @user3707763: It should be, but who knows what your .idl says. – sharptooth Jul 08 '14 at 14:37
  • @sharptooth: this part is quoted above, it's 1.0 – Roman R. Jul 08 '14 at 14:47
  • @RomanR.: Indeed, I didn't notice it. The next thing that looks strange is that the interface definition is outside the library definition. – sharptooth Jul 08 '14 at 14:50
  • @sharptooth because they have different uuids. – user3707763 Jul 08 '14 at 14:56
  • @user3707763: Sure they have different uuids but in all the projects I've seen the interfaces were declared inside the library definition. – sharptooth Jul 08 '14 at 15:00
  • @sharptooth: No, it's okay and it's default behavior. IDL compiler would include into TLB all such interfaces referenced by stuff inside library block. The rest would compile well, be available to C++ code, but will be not included to TLB. – Roman R. Jul 08 '14 at 15:01
  • If everything else fails you can put breakpoints into `IDispatchImpl` methods and check how they behave. You'll likely need a `Sleep()` in the constructor so that you have time to attach to the right process. – sharptooth Jul 08 '14 at 15:15
  • Use SysInternals' Process Monitor to diagnose registry problems. Forgetting to register the ProgId in your .rgs script would be a common oversight. – Hans Passant Jul 08 '14 at 16:11
  • @HansPassant the ProgID is registered in the system – user3707763 Jul 08 '14 at 17:45
  • You need to define the IFrame Interface inside the Typelibrary too! I can not see the IFrame interface and I can not see the implementation of it. – xMRi Aug 07 '14 at 06:03

0 Answers0