ActiveX Wrapper for Managed

R

RDI

I have been devloping a wrapper for an activex control. I succeeded to
do it using ATL.

Once I moved to MFC, the wrapper failed to be called from a managed
application. It throws an exception, and by calling GetLastError and
FormatMessage; I get always one of the two messages "This function is
only valid in win32 mode" or "Invalid pointer". However, it's working
good using an evc++ 4.0 test application.

My MFC wrapper uses; CWnd, CWnd::CreateControl and InvokeHelper.
Actually, the exception happend when I try to call CWnd::CreateControl.

Any IDEAS!!!!!!!!
 
R

RDI

Thank you Chris Tacke, but I didn't call the methods of the activex
class directly using P/Invoke, what I have said that I have developed a
WCE DLL to wrapp the activex then I call its exported methods by
P/Invoke.

Thank you Sergey. As I mentioned before I've already done what you have
asked. The problem now that when I call the DLL to create the control,
it failed causing the exception I mentioned before.

here is the code of the DLL function:
///////////////////////////////////////////////////////////////////////////////////////////////////////////////
MyActiveX m_Obiect;
extern "C" __declspec(dllexport) BOOL Initialize(HINSTANCE hInstance,
HWND hWnd, HWND *hWndCtrl, RECT* rectIn, BOOL bVisible)
{
RECT rect = { 0, 254, 240, 268 };
CWnd *wndParent = CWnd::FromHandle(hWnd);
try
{
hInstance = AfxGetInstanceHandle();
m_Obiect.Create(L"", WS_CHILD,rect, wndParent, IDC_PLAYER);
hWndCtrl = &m_Obiect.m_hWnd;

}
catch(...)
{
LPVOID lpMsgBuf;
DWORD err;
err = GetLastError();
FormatMessage(
FORMAT_MESSAGE_ALLOCATE_BUFFER |
FORMAT_MESSAGE_FROM_SYSTEM |
FORMAT_MESSAGE_IGNORE_INSERTS,
NULL,
err,
0, // Default language
(LPTSTR) &lpMsgBuf,
0,
NULL
);
MessageBox( NULL, (LPCTSTR)lpMsgBuf, L"Error", MB_OK |
MB_ICONINFORMATION );
MessageBox( NULL, str, L"Error", MB_OK | MB_ICONINFORMATION );
// Free the buffer.
LocalFree( lpMsgBuf );
return 0;
}
///////////////////////////////////////////////////////////////////////////////////////////////////////////////
The ActiveX(MyActiveX) Create function :
///////////////////////////////////////////////////////////////////////////////////////////////////////////////
class MyActiveX:CWnd
{
CLSID const& GetClsid()
{
static CLSID const clsid
= { 0x56d6f312, 0xb0f6, 0x11d0, { 0x94, 0xab, 0x0, 0x80, 0xc7, 0x4c,
0x7e, 0x95 } };
return clsid;
}

BOOL Create(LPCTSTR lpszWindowName, DWORD dwStyle,
const RECT& rect, CWnd* pParentWnd, UINT nID,
CFile* pPersist = NULL, BOOL bStorage = FALSE,
BSTR bstrLicKey = NULL)
{ return CreateControl(GetClsid(), lpszWindowName, dwStyle, rect,
pParentWnd, nID,
pPersist, bStorage, bstrLicKey);
}
};
///////////////////////////////////////////////////////////////////////////////////////////////////////////////
Mangaed Code
///////////////////////////////////////////////////////////////////////////////////////////////////////////////
[DllImport("MyWrapper.dll")]
private static extern int Initialize(IntPtr hInstance, IntPtr hWnd,
ref IntPtr hWndCtrl, IntPtr rect,
bool bVisible);
 
S

Sergey Bogdanov

I'm not sure if it's the problem but I suppose the line:

hWndCtrl = &m_Obiect.m_hWnd;

should be rewritten as:

*hWndCtrl = m_Obiect.m_hWnd;

Also can you send us how you invoke Initialize function?


Best regards,
Sergey Bogdanov
http://www.sergeybogdanov.com

Thank you Chris Tacke, but I didn't call the methods of the activex
class directly using P/Invoke, what I have said that I have developed a
WCE DLL to wrapp the activex then I call its exported methods by
P/Invoke.

Thank you Sergey. As I mentioned before I've already done what you have
asked. The problem now that when I call the DLL to create the control,
it failed causing the exception I mentioned before.

here is the code of the DLL function:
///////////////////////////////////////////////////////////////////////////////////////////////////////////////
MyActiveX m_Obiect;
extern "C" __declspec(dllexport) BOOL Initialize(HINSTANCE hInstance,
HWND hWnd, HWND *hWndCtrl, RECT* rectIn, BOOL bVisible)
{
RECT rect = { 0, 254, 240, 268 };
CWnd *wndParent = CWnd::FromHandle(hWnd);
try
{
hInstance = AfxGetInstanceHandle();
m_Obiect.Create(L"", WS_CHILD,rect, wndParent, IDC_PLAYER);
hWndCtrl = &m_Obiect.m_hWnd;

}
catch(...)
{
LPVOID lpMsgBuf;
DWORD err;
err = GetLastError();
FormatMessage(
FORMAT_MESSAGE_ALLOCATE_BUFFER |
FORMAT_MESSAGE_FROM_SYSTEM |
FORMAT_MESSAGE_IGNORE_INSERTS,
NULL,
err,
0, // Default language
(LPTSTR) &lpMsgBuf,
0,
NULL
);
MessageBox( NULL, (LPCTSTR)lpMsgBuf, L"Error", MB_OK |
MB_ICONINFORMATION );
MessageBox( NULL, str, L"Error", MB_OK | MB_ICONINFORMATION );
// Free the buffer.
LocalFree( lpMsgBuf );
return 0;
}
///////////////////////////////////////////////////////////////////////////////////////////////////////////////
The ActiveX(MyActiveX) Create function :
///////////////////////////////////////////////////////////////////////////////////////////////////////////////
class MyActiveX:CWnd
{
CLSID const& GetClsid()
{
static CLSID const clsid
= { 0x56d6f312, 0xb0f6, 0x11d0, { 0x94, 0xab, 0x0, 0x80, 0xc7, 0x4c,
0x7e, 0x95 } };
return clsid;
}

BOOL Create(LPCTSTR lpszWindowName, DWORD dwStyle,
const RECT& rect, CWnd* pParentWnd, UINT nID,
CFile* pPersist = NULL, BOOL bStorage = FALSE,
BSTR bstrLicKey = NULL)
{ return CreateControl(GetClsid(), lpszWindowName, dwStyle, rect,
pParentWnd, nID,
pPersist, bStorage, bstrLicKey);
}
};
///////////////////////////////////////////////////////////////////////////////////////////////////////////////
Mangaed Code
///////////////////////////////////////////////////////////////////////////////////////////////////////////////
[DllImport("MyWrapper.dll")]
private static extern int Initialize(IntPtr hInstance, IntPtr hWnd,
ref IntPtr hWndCtrl, IntPtr rect,
bool bVisible);
 
R

RDI

Well, I'm not sure about your supposition, since the same code is
working fine when I call it from MFC application
Anyway, the following is the invoke code....
//////////////////////////////////////////////////////////////////////////////////////////////////////
[DllImport("MyWrapper.dll")]
private static extern int Initialize(IntPtr hInstance, IntPtr
hWnd,
ref IntPtr hWndCtrl, IntPtr rect,
bool bVisible);
..
..
..
// Initialize the Object
//parent's handle
IntPtr hWnd = OpenNETCF.Win32.Win32Window.FindWindow(null, this.Text);

//the handle to be created
IntPtr nHWmp = IntPtr.Zero;
IntPtr rect;
rect = IntPtr.Zero; // don't worry, I handle it in the DLL
Init(IntPtr.Zero, hWnd, ref nHWmp, rect, false);
..
..
..
//////////////////////////////////////////////////////////////////////////////////////////////////////
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top