windowless ActiveX control with a dll as a container

Is it possible to add and instantiate an activeX control into a dll.  I found that when I try to instantiate the activeX control, it requires a CWnd by using the Create function.  I am using the ActiveX control like this:
-I create it using the ActiveX wizard in a separate project.  
-Then I use the 'Add to Project' menu in VC++ 5.0 and choose 'registered activeX controls.
-This puts a new object into my dll project, but it derives it from CWnd, which seems strange to me.

The ActiveX object is called CAmstelLight.

CAmstelLight m_pAmstel ;

BOOL bSuccess = m_pAmstel->Create((LPCTSTR)"AmstelLight Control",WS_BORDER,rectControl1,(CWnd*)m_p????,1000);


So when I try to call create on the new Activex control in the dll project of mine, I have no CWnd to pass to it, because dll is windowless!!

What is going on?
Thanks
georitaAsked:
Who is Participating?
I wear a lot of hats...

"The solutions and answers provided on Experts Exchange have been extremely helpful to me over the last few years. I wear a lot of hats - Developer, Database Administrator, Help Desk, etc., so I know a lot of things but not a lot about one thing. Experts Exchange gives me answers from people who do know a lot about one thing, in a easy to use platform." -Todd S.

NorbertCommented:
The functions you see probably looks like one of the two below
      virtual BOOL Create(LPCTSTR lpszClassName,
            LPCTSTR lpszWindowName, DWORD dwStyle,
            const RECT& rect,
            CWnd* pParentWnd, UINT nID,
            CCreateContext* pContext = NULL)
      { return CreateControl(GetClsid(), lpszWindowName, dwStyle, rect, pParentWnd, nID); }

    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); }

Dit you try to pass NULL as Parent?
0
georitaAuthor Commented:
Yes I tried sending in NULL and it didn't work.
0
NorbertCommented:
>>>Yes I tried sending in NULL and it didn't work
which error occures ?

What about creating a invisible window inside your dll and passing down the pointer to that window?
0
Cloud Class® Course: Microsoft Office 2010

This course will introduce you to the interfaces and features of Microsoft Office 2010 Word, Excel, PowerPoint, Outlook, and Access. You will learn about the features that are shared between all products in the Office suite, as well as the new features that are product specific.

georitaAuthor Commented:
Invisible window?  Like a 'fake' Cwnd object?  If it is the latter, I have trie d to fool it, but it didn't work either......
0
NorbertCommented:
please tell what happens
0
georitaAuthor Commented:
const RECT rectControl1 = {0,0,12,12};
const RECT rectControl2 = {0,0,5,5};

CWnd* pMainWnd = AfxGetMainWnd();

CWinLessX* pWinless;

 BOOL bSuccess = pWinless->Create((LPCTSTR)"AmstelLight  Control",WS_BORDER,rectControl1,
 (CWnd*)pMainWnd,1000);
if(!bSuccess )
  AfxMessageBox("No luck!!") ;


This code was put into a dll's InitInstance() .  CWinLessX is an ActiveX control that I inserted into the dll project.  The Cwnd object is a bogus one.
What happens?  It aborts when the call to create is made.
0
NorbertCommented:
if the code above is snipped from the real program without changings it can't work

CWinLessX* pWinless; //Pointer to the ActiveX but it points to nothing meanigfull until it is assigned

//because pWinless points to not to a CWinLessX Object the create call *MUST* fail
 pWinless->Create
 BOOL bSuccess = pWinless->Create((LPCTSTR)"AmstelLight  Control",WS_BORDER,rectControl1,
 (CWnd*)pMainWnd,1000)

Try this:
CWnd* pMainWnd = AfxGetMainWnd();

CWinLessX* pWinless=new CWinLessX;

 BOOL bSuccess = pWinless->Create((LPCTSTR)"AmstelLight  Control",WS_BORDER,rectControl1,
 (CWnd*)pMainWnd,1000);
if(!bSuccess )
  AfxMessageBox("No luck!!") ;


BTW: I am not sure that AfxGetMainWnd()
will return a window but if the above is the problem maybe it also works with NULL as paren window
0
georitaAuthor Commented:
Point taken.  Unfortunately, it had no effect on the outcome.  I know that there , technically, IS no mainwnd, but I really don't have a cwnd to pass it in the first place, because it is a dll.

So I added the instantiation of the 'pWinless' pointer, and the effect was that it still crashes on the 'Create' call.
0
NorbertCommented:
what kind of crash?
Assertion ? please tell me where the assertion occures

exception ? inside the debugger select
Debug->exception the exception what occures (you can see the number inside the outputwindow when the exception occures) and select stop always.
if the number does not exist just type it

if it occures at a place where only assembly code is visible try to look at the callstack
0
georitaAuthor Commented:
It throws an exception with the Abort, Retry, Ignore  Then it goes to the diassembly.  The call stack points to the COLEControl Create command.
0
NorbertCommented:
I would say it is an Assertion
It starts the debugger if you click retry.
So probably you have the code but
you see a window mixing assembly code and C++ code  
Switch of Disassembly
(debug toolbar Buttun with Tooltip disassembly)
may be you need to double click the top callstack function.
i am sure that you find a line beginning with
ASSERT(
the result of the condition inside the ASSERT statement must be TRUE.

if it is not true there you have the reason why it is not running like expected
figure out what goes wrong - may be the parent of NULL ?
if so create a parent.
Simplest way: Create a Dialog resource
create the dialog and use it as parent.
0
NorbertCommented:
Nothing heared for a long time.
Does it work now ?
0
NorbertCommented:
Actually I wrote a wrapper DLL for easy access to our OCX'es form C program without C++ or MFC and it works without any problem.
Difference to your problem is that the contol is not instanciated inside InitInstance it is created using an explicit call from the Main program so if creation does not work inside InitInstance try creation later (may be the first call from main program to the dll)
0
georitaAuthor Commented:
Can you elaborate on that proposed answer?
0
NorbertCommented:
>>Can you elaborate on that proposed answer?
It depends on how far I am doing my work

What I did:
Create a Dialog using recource editor
put the Control on the Dialog
set the dialog invisible.
starting class wizard creating a class for that dialog and adding a member variable for the control.
Classwizard ask to generate a wrapper class.
now I can create the dialog where ever I want. May be using the function below
CCtrlDlg* CreateCtrlDialog(CWnd Parent)
{
      CCtrlDlg* Dlg=new CCtrlDlg(Parent);
      CoInitialize(NULL);
      Dlg->Create(Dlg->IDD,Parent);
        return Dlg;
}
to destroy the dialog:
void DeleteCtrlDialog(CCtrlDlg* Dlg)
{
      Dlg->DestroyWindow();
      delete Dlg;
      CoUninitialize();
}

0

Experts Exchange Solution brought to you by

Your issues matter to us.

Facing a tech roadblock? Get the help and guidance you need from experienced professionals who care. Ask your question anytime, anywhere, with no hassle.

Start your 7-day free trial
georitaAuthor Commented:
good job!
0
NorbertCommented:
I assume it works now ?
0
It's more than this solution.Get answers and train to solve all your tech problems - anytime, anywhere.Try it for free Edge Out The Competitionfor your dream job with proven skills and certifications.Get started today Stand Outas the employee with proven skills.Start learning today for free Move Your Career Forwardwith certification training in the latest technologies.Start your trial today
C++

From novice to tech pro — start learning today.