include: Add definition of IKsControl interface in dmksctrl.h.
[wine] / dlls / atl / atl_ax.c
1 /*
2  * Active Template Library ActiveX functions (atl.dll)
3  *
4  * Copyright 2006 Andrey Turkin
5  *
6  * This library is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Lesser General Public
8  * License as published by the Free Software Foundation; either
9  * version 2.1 of the License, or (at your option) any later version.
10  *
11  * This library is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14  * Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with this library; if not, write to the Free Software
18  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
19  */
20
21 #include <stdarg.h>
22 #include <stdio.h>
23
24 #define COBJMACROS
25
26 #include "windef.h"
27 #include "winbase.h"
28 #include "winerror.h"
29 #include "winuser.h"
30 #include "wine/debug.h"
31 #include "objbase.h"
32 #include "objidl.h"
33 #include "ole2.h"
34 #include "exdisp.h"
35 #include "atlbase.h"
36 #include "atliface.h"
37 #include "atlwin.h"
38
39 #include "wine/unicode.h"
40
41 WINE_DEFAULT_DEBUG_CHANNEL(atl);
42
43 typedef struct IOCS {
44     IOleClientSite            IOleClientSite_iface;
45     IOleContainer             IOleContainer_iface;
46     IOleInPlaceSiteWindowless IOleInPlaceSiteWindowless_iface;
47     IOleInPlaceFrame          IOleInPlaceFrame_iface;
48     IOleControlSite           IOleControlSite_iface;
49
50     LONG ref;
51     HWND hWnd;
52     IOleObject *control;
53     RECT size;
54     WNDPROC OrigWndProc;
55     BOOL fActive, fInPlace, fWindowless;
56 } IOCS;
57
58 /**********************************************************************
59  * AtlAxWin class window procedure
60  */
61 static LRESULT CALLBACK AtlAxWin_wndproc( HWND hWnd, UINT wMsg, WPARAM wParam, LPARAM lParam )
62 {
63     if ( wMsg == WM_CREATE )
64     {
65             DWORD len = GetWindowTextLengthW( hWnd ) + 1;
66             WCHAR *ptr = HeapAlloc( GetProcessHeap(), 0, len*sizeof(WCHAR) );
67             if (!ptr)
68                 return 1;
69             GetWindowTextW( hWnd, ptr, len );
70             AtlAxCreateControlEx( ptr, hWnd, NULL, NULL, NULL, NULL, NULL );
71             HeapFree( GetProcessHeap(), 0, ptr );
72             return 0;
73     }
74     return DefWindowProcW( hWnd, wMsg, wParam, lParam );
75 }
76
77 /***********************************************************************
78  *           AtlAxWinInit          [ATL.@]
79  * Initializes the control-hosting code: registering the AtlAxWin,
80  * AtlAxWin7 and AtlAxWinLic7 window classes and some messages.
81  *
82  * RETURNS
83  *  TRUE or FALSE
84  */
85
86 BOOL WINAPI AtlAxWinInit(void)
87 {
88     WNDCLASSEXW wcex;
89     const WCHAR AtlAxWin[] = {'A','t','l','A','x','W','i','n',0};
90
91     FIXME("semi-stub\n");
92
93     if ( FAILED( OleInitialize(NULL) ) )
94         return FALSE;
95
96     wcex.cbSize        = sizeof(wcex);
97     wcex.style         = 0;
98     wcex.cbClsExtra    = 0;
99     wcex.cbWndExtra    = 0;
100     wcex.hInstance     = GetModuleHandleW( NULL );
101     wcex.hIcon         = NULL;
102     wcex.hCursor       = NULL;
103     wcex.hbrBackground = NULL;
104     wcex.lpszMenuName  = NULL;
105     wcex.hIconSm       = 0;
106
107     wcex.lpfnWndProc   = AtlAxWin_wndproc;
108     wcex.lpszClassName = AtlAxWin;
109     if ( !RegisterClassExW( &wcex ) )
110         return FALSE;
111
112     return TRUE;
113 }
114
115 /***********************************************************************
116  *  Atl container component implementation
117  */
118
119
120 static ULONG IOCS_AddRef(IOCS *This)
121 {
122     ULONG ref = InterlockedIncrement(&This->ref);
123
124     TRACE( "(%p) : AddRef from %d\n", This, ref - 1 );
125
126     return ref;
127 }
128
129 static HRESULT IOCS_QueryInterface(IOCS *This, REFIID riid, void **ppv)
130 {
131     *ppv = NULL;
132
133     if ( IsEqualIID( &IID_IUnknown, riid )
134       || IsEqualIID( &IID_IOleClientSite, riid ) )
135     {
136         *ppv = &This->IOleClientSite_iface;
137     } else if ( IsEqualIID( &IID_IOleContainer, riid ) )
138     {
139         *ppv = &This->IOleContainer_iface;
140     } else if ( IsEqualIID( &IID_IOleInPlaceSite, riid ) || IsEqualIID( &IID_IOleInPlaceSiteEx, riid ) || IsEqualIID( &IID_IOleInPlaceSiteWindowless, riid ) )
141     {
142         *ppv = &This->IOleInPlaceSiteWindowless_iface;
143     } else if ( IsEqualIID( &IID_IOleInPlaceFrame, riid ) )
144     {
145         *ppv = &This->IOleInPlaceFrame_iface;
146     } else if ( IsEqualIID( &IID_IOleControlSite, riid ) )
147     {
148         *ppv = &This->IOleControlSite_iface;
149     }
150
151     if (*ppv)
152     {
153         IOCS_AddRef( This );
154         return S_OK;
155     }
156
157     WARN("unsupported interface %s\n", debugstr_guid( riid ) );
158     *ppv = NULL;
159     return E_NOINTERFACE;
160 }
161
162 static HRESULT IOCS_Detach( IOCS *This );
163 static ULONG IOCS_Release(IOCS *This)
164 {
165     ULONG ref = InterlockedDecrement(&This->ref);
166
167     TRACE( "(%p) : ReleaseRef to %d\n", This, ref );
168
169     if (!ref)
170     {
171         IOCS_Detach( This );
172         HeapFree( GetProcessHeap(), 0, This );
173     }
174
175     return ref;
176 }
177
178 /******      IOleClientSite    *****/
179 static inline IOCS *impl_from_IOleClientSite(IOleClientSite *iface)
180 {
181     return CONTAINING_RECORD(iface, IOCS, IOleClientSite_iface);
182 }
183
184 static HRESULT WINAPI OleClientSite_QueryInterface(IOleClientSite *iface, REFIID riid, void **ppv)
185 {
186     IOCS *This = impl_from_IOleClientSite(iface);
187     return IOCS_QueryInterface(This, riid, ppv);
188 }
189
190 static ULONG WINAPI OleClientSite_AddRef(IOleClientSite *iface)
191 {
192     IOCS *This = impl_from_IOleClientSite(iface);
193     return IOCS_AddRef(This);
194 }
195
196 static ULONG WINAPI OleClientSite_Release(IOleClientSite *iface)
197 {
198     IOCS *This = impl_from_IOleClientSite(iface);
199     return IOCS_Release(This);
200 }
201
202 static HRESULT WINAPI OleClientSite_SaveObject(IOleClientSite *iface)
203 {
204     IOCS *This = impl_from_IOleClientSite(iface);
205     FIXME( "(%p) - stub\n", This );
206     return E_NOTIMPL;
207 }
208
209 static HRESULT WINAPI OleClientSite_GetMoniker(IOleClientSite *iface, DWORD dwAssign, DWORD dwWhichMoniker, IMoniker **ppmk)
210 {
211     IOCS *This = impl_from_IOleClientSite(iface);
212
213     FIXME( "(%p, 0x%x, 0x%x, %p)\n", This, dwAssign, dwWhichMoniker, ppmk );
214     return E_NOTIMPL;
215 }
216
217 static HRESULT WINAPI OleClientSite_GetContainer(IOleClientSite *iface, IOleContainer **ppContainer)
218 {
219     IOCS *This = impl_from_IOleClientSite(iface);
220     TRACE( "(%p, %p)\n", This, ppContainer );
221     return OleClientSite_QueryInterface( iface, &IID_IOleContainer, (void**)ppContainer );
222 }
223
224 static HRESULT WINAPI OleClientSite_ShowObject(IOleClientSite *iface)
225 {
226     IOCS *This = impl_from_IOleClientSite(iface);
227     FIXME( "(%p) - stub\n", This );
228     return S_OK;
229 }
230
231 static HRESULT WINAPI OleClientSite_OnShowWindow(IOleClientSite *iface, BOOL fShow)
232 {
233     IOCS *This = impl_from_IOleClientSite(iface);
234     FIXME( "(%p, %s) - stub\n", This, fShow ? "TRUE" : "FALSE" );
235     return E_NOTIMPL;
236 }
237
238 static HRESULT WINAPI OleClientSite_RequestNewObjectLayout(IOleClientSite *iface)
239 {
240     IOCS *This = impl_from_IOleClientSite(iface);
241     FIXME( "(%p) - stub\n", This );
242     return E_NOTIMPL;
243 }
244
245
246 /******      IOleContainer     *****/
247 static inline IOCS *impl_from_IOleContainer(IOleContainer *iface)
248 {
249     return CONTAINING_RECORD(iface, IOCS, IOleContainer_iface);
250 }
251
252 static HRESULT WINAPI OleContainer_QueryInterface( IOleContainer* iface, REFIID riid, void** ppv)
253 {
254     IOCS *This = impl_from_IOleContainer(iface);
255     return IOCS_QueryInterface( This, riid, ppv );
256 }
257
258 static ULONG WINAPI OleContainer_AddRef(IOleContainer* iface)
259 {
260     IOCS *This = impl_from_IOleContainer(iface);
261     return IOCS_AddRef(This);
262 }
263
264 static ULONG WINAPI OleContainer_Release(IOleContainer* iface)
265 {
266     IOCS *This = impl_from_IOleContainer(iface);
267     return IOCS_Release(This);
268 }
269
270 static HRESULT WINAPI OleContainer_ParseDisplayName(IOleContainer* iface, IBindCtx* pbc,
271         LPOLESTR pszDisplayName, ULONG* pchEaten, IMoniker** ppmkOut)
272 {
273     IOCS *This = impl_from_IOleContainer(iface);
274     FIXME( "(%p,%p,%s,%p,%p) - stub\n", This, pbc, debugstr_w(pszDisplayName), pchEaten, ppmkOut );
275     return E_NOTIMPL;
276 }
277
278 static HRESULT WINAPI OleContainer_EnumObjects(IOleContainer* iface, DWORD grfFlags, IEnumUnknown** ppenum)
279 {
280     IOCS *This = impl_from_IOleContainer(iface);
281     FIXME( "(%p, %u, %p) - stub\n", This, grfFlags, ppenum );
282     return E_NOTIMPL;
283 }
284
285 static HRESULT WINAPI OleContainer_LockContainer(IOleContainer* iface, BOOL fLock)
286 {
287     IOCS *This = impl_from_IOleContainer(iface);
288     FIXME( "(%p, %s) - stub\n", This, fLock?"TRUE":"FALSE" );
289     return E_NOTIMPL;
290 }
291
292
293 /******    IOleInPlaceSiteWindowless   *******/
294 static inline IOCS *impl_from_IOleInPlaceSiteWindowless(IOleInPlaceSiteWindowless *iface)
295 {
296     return CONTAINING_RECORD(iface, IOCS, IOleInPlaceSiteWindowless_iface);
297 }
298
299 static HRESULT WINAPI OleInPlaceSiteWindowless_QueryInterface(IOleInPlaceSiteWindowless *iface, REFIID riid, void **ppv)
300 {
301     IOCS *This = impl_from_IOleInPlaceSiteWindowless(iface);
302     return IOCS_QueryInterface(This, riid, ppv);
303 }
304
305 static ULONG WINAPI OleInPlaceSiteWindowless_AddRef(IOleInPlaceSiteWindowless *iface)
306 {
307     IOCS *This = impl_from_IOleInPlaceSiteWindowless(iface);
308     return IOCS_AddRef(This);
309 }
310
311 static ULONG WINAPI OleInPlaceSiteWindowless_Release(IOleInPlaceSiteWindowless *iface)
312 {
313     IOCS *This = impl_from_IOleInPlaceSiteWindowless(iface);
314     return IOCS_Release(This);
315 }
316
317 static HRESULT WINAPI OleInPlaceSiteWindowless_GetWindow(IOleInPlaceSiteWindowless* iface, HWND* phwnd)
318 {
319     IOCS *This = impl_from_IOleInPlaceSiteWindowless(iface);
320
321     TRACE("(%p,%p)\n", This, phwnd);
322     *phwnd = This->hWnd;
323     return S_OK;
324 }
325
326 static HRESULT WINAPI OleInPlaceSiteWindowless_ContextSensitiveHelp(IOleInPlaceSiteWindowless* iface, BOOL fEnterMode)
327 {
328     IOCS *This = impl_from_IOleInPlaceSiteWindowless(iface);
329     FIXME("(%p,%d) - stub\n", This, fEnterMode);
330     return E_NOTIMPL;
331 }
332
333 static HRESULT WINAPI OleInPlaceSiteWindowless_CanInPlaceActivate(IOleInPlaceSiteWindowless *iface)
334 {
335     IOCS *This = impl_from_IOleInPlaceSiteWindowless(iface);
336     TRACE("(%p)\n", This);
337     return S_OK;
338 }
339
340 static HRESULT WINAPI OleInPlaceSiteWindowless_OnInPlaceActivate(IOleInPlaceSiteWindowless *iface)
341 {
342     IOCS *This = impl_from_IOleInPlaceSiteWindowless(iface);
343
344     TRACE("(%p)\n", This);
345
346     This->fInPlace = TRUE;
347     return S_OK;
348 }
349
350 static HRESULT WINAPI OleInPlaceSiteWindowless_OnUIActivate(IOleInPlaceSiteWindowless *iface)
351 {
352     IOCS *This = impl_from_IOleInPlaceSiteWindowless(iface);
353
354     TRACE("(%p)\n", This);
355
356     return S_OK;
357 }
358 static HRESULT WINAPI OleInPlaceSiteWindowless_GetWindowContext(IOleInPlaceSiteWindowless *iface,
359         IOleInPlaceFrame **ppFrame, IOleInPlaceUIWindow **ppDoc, LPRECT lprcPosRect,
360         LPRECT lprcClipRect, LPOLEINPLACEFRAMEINFO lpFrameInfo)
361 {
362     IOCS *This = impl_from_IOleInPlaceSiteWindowless(iface);
363
364     TRACE("(%p,%p,%p,%p,%p,%p)\n", This, ppFrame, ppDoc, lprcPosRect, lprcClipRect, lpFrameInfo);
365
366     if ( lprcClipRect )
367         *lprcClipRect = This->size;
368     if ( lprcPosRect )
369         *lprcPosRect = This->size;
370
371     if ( ppFrame )
372     {
373         IOCS_QueryInterface( This, &IID_IOleInPlaceFrame, (void**) ppFrame );
374     }
375
376     if ( ppDoc )
377         *ppDoc = NULL;
378
379     if ( lpFrameInfo )
380     {
381         lpFrameInfo->fMDIApp = FALSE;
382         lpFrameInfo->hwndFrame = This->hWnd;
383         lpFrameInfo->haccel = NULL;
384         lpFrameInfo->cAccelEntries = 0;
385     }
386
387     return S_OK;
388 }
389
390 static HRESULT WINAPI OleInPlaceSiteWindowless_Scroll(IOleInPlaceSiteWindowless *iface, SIZE scrollExtent)
391 {
392     IOCS *This = impl_from_IOleInPlaceSiteWindowless(iface);
393     FIXME("(%p) - stub\n", This);
394     return E_NOTIMPL;
395 }
396
397 static HRESULT WINAPI OleInPlaceSiteWindowless_OnUIDeactivate(IOleInPlaceSiteWindowless *iface, BOOL fUndoable)
398 {
399     IOCS *This = impl_from_IOleInPlaceSiteWindowless(iface);
400     FIXME("(%p,%d) - stub\n", This, fUndoable);
401     return E_NOTIMPL;
402 }
403
404 static HRESULT WINAPI OleInPlaceSiteWindowless_OnInPlaceDeactivate(IOleInPlaceSiteWindowless *iface)
405 {
406     IOCS *This = impl_from_IOleInPlaceSiteWindowless(iface);
407
408     TRACE("(%p)\n", This);
409
410     This->fInPlace = This->fWindowless = FALSE;
411     return S_OK;
412 }
413
414 static HRESULT WINAPI OleInPlaceSiteWindowless_DiscardUndoState(IOleInPlaceSiteWindowless *iface)
415 {
416     IOCS *This = impl_from_IOleInPlaceSiteWindowless(iface);
417     FIXME("(%p) - stub\n", This);
418     return E_NOTIMPL;
419 }
420
421 static HRESULT WINAPI OleInPlaceSiteWindowless_DeactivateAndUndo(IOleInPlaceSiteWindowless *iface)
422 {
423     IOCS *This = impl_from_IOleInPlaceSiteWindowless(iface);
424     FIXME("(%p) - stub\n", This);
425     return E_NOTIMPL;
426 }
427
428 static HRESULT WINAPI OleInPlaceSiteWindowless_OnPosRectChange(IOleInPlaceSiteWindowless *iface, LPCRECT lprcPosRect)
429 {
430     IOCS *This = impl_from_IOleInPlaceSiteWindowless(iface);
431     FIXME("(%p,%p) - stub\n", This, lprcPosRect);
432     return E_NOTIMPL;
433 }
434
435 static HRESULT WINAPI OleInPlaceSiteWindowless_OnInPlaceActivateEx( IOleInPlaceSiteWindowless *iface, BOOL* pfNoRedraw, DWORD dwFlags)
436 {
437     IOCS *This = impl_from_IOleInPlaceSiteWindowless(iface);
438
439     TRACE("\n");
440
441     This->fActive = This->fInPlace = TRUE;
442     if ( dwFlags & ACTIVATE_WINDOWLESS )
443         This->fWindowless = TRUE;
444     return S_OK;
445 }
446
447 static HRESULT WINAPI OleInPlaceSiteWindowless_OnInPlaceDeactivateEx( IOleInPlaceSiteWindowless *iface, BOOL fNoRedraw)
448 {
449     IOCS *This = impl_from_IOleInPlaceSiteWindowless(iface);
450
451     TRACE("\n");
452
453     This->fActive = This->fInPlace = This->fWindowless = FALSE;
454     return S_OK;
455 }
456 static HRESULT WINAPI OleInPlaceSiteWindowless_RequestUIActivate( IOleInPlaceSiteWindowless *iface)
457 {
458     FIXME("\n");
459     return E_NOTIMPL;
460 }
461 static HRESULT WINAPI OleInPlaceSiteWindowless_CanWindowlessActivate( IOleInPlaceSiteWindowless *iface)
462 {
463     FIXME("\n");
464     return S_OK;
465 }
466 static HRESULT WINAPI OleInPlaceSiteWindowless_GetCapture( IOleInPlaceSiteWindowless *iface)
467 {
468     FIXME("\n");
469     return E_NOTIMPL;
470 }
471 static HRESULT WINAPI OleInPlaceSiteWindowless_SetCapture( IOleInPlaceSiteWindowless *iface, BOOL fCapture)
472 {
473     FIXME("\n");
474     return E_NOTIMPL;
475 }
476 static HRESULT WINAPI OleInPlaceSiteWindowless_GetFocus( IOleInPlaceSiteWindowless *iface)
477 {
478     FIXME("\n");
479     return E_NOTIMPL;
480 }
481 static HRESULT WINAPI OleInPlaceSiteWindowless_SetFocus( IOleInPlaceSiteWindowless *iface, BOOL fFocus)
482 {
483     FIXME("\n");
484     return E_NOTIMPL;
485 }
486 static HRESULT WINAPI OleInPlaceSiteWindowless_GetDC( IOleInPlaceSiteWindowless *iface, LPCRECT pRect, DWORD grfFlags, HDC* phDC)
487 {
488     FIXME("\n");
489     return E_NOTIMPL;
490 }
491 static HRESULT WINAPI OleInPlaceSiteWindowless_ReleaseDC( IOleInPlaceSiteWindowless *iface, HDC hDC)
492 {
493     FIXME("\n");
494     return E_NOTIMPL;
495 }
496 static HRESULT WINAPI OleInPlaceSiteWindowless_InvalidateRect( IOleInPlaceSiteWindowless *iface, LPCRECT pRect, BOOL fErase)
497 {
498     FIXME("\n");
499     return E_NOTIMPL;
500 }
501 static HRESULT WINAPI OleInPlaceSiteWindowless_InvalidateRgn( IOleInPlaceSiteWindowless *iface, HRGN hRGN, BOOL fErase)
502 {
503     FIXME("\n");
504     return E_NOTIMPL;
505 }
506 static HRESULT WINAPI OleInPlaceSiteWindowless_ScrollRect( IOleInPlaceSiteWindowless *iface, INT dx, INT dy, LPCRECT pRectScroll, LPCRECT pRectClip)
507 {
508     FIXME("\n");
509     return E_NOTIMPL;
510 }
511 static HRESULT WINAPI OleInPlaceSiteWindowless_AdjustRect( IOleInPlaceSiteWindowless *iface, LPRECT prc)
512 {
513     FIXME("\n");
514     return E_NOTIMPL;
515 }
516 static HRESULT WINAPI OleInPlaceSiteWindowless_OnDefWindowMessage( IOleInPlaceSiteWindowless *iface, UINT msg, WPARAM wParam, LPARAM lParam, LRESULT* plResult)
517 {
518     FIXME("\n");
519     return E_NOTIMPL;
520 }
521
522
523 /******    IOleInPlaceFrame   *******/
524 static inline IOCS *impl_from_IOleInPlaceFrame(IOleInPlaceFrame *iface)
525 {
526     return CONTAINING_RECORD(iface, IOCS, IOleInPlaceFrame_iface);
527 }
528
529 static HRESULT WINAPI OleInPlaceFrame_QueryInterface(IOleInPlaceFrame *iface, REFIID riid, void **ppv)
530 {
531     IOCS *This = impl_from_IOleInPlaceFrame(iface);
532     return IOCS_QueryInterface(This, riid, ppv);
533 }
534
535 static ULONG WINAPI OleInPlaceFrame_AddRef(IOleInPlaceFrame *iface)
536 {
537     IOCS *This = impl_from_IOleInPlaceFrame(iface);
538     return IOCS_AddRef(This);
539 }
540
541 static ULONG WINAPI OleInPlaceFrame_Release(IOleInPlaceFrame *iface)
542 {
543     IOCS *This = impl_from_IOleInPlaceFrame(iface);
544     return IOCS_Release(This);
545 }
546
547 static HRESULT WINAPI OleInPlaceFrame_GetWindow(IOleInPlaceFrame *iface, HWND *phWnd)
548 {
549     IOCS *This = impl_from_IOleInPlaceFrame(iface);
550
551     TRACE( "(%p,%p)\n", This, phWnd );
552
553     *phWnd = This->hWnd;
554     return S_OK;
555 }
556
557 static HRESULT WINAPI OleInPlaceFrame_ContextSensitiveHelp(IOleInPlaceFrame *iface, BOOL fEnterMode)
558 {
559     IOCS *This = impl_from_IOleInPlaceFrame(iface);
560
561     FIXME( "(%p,%d) - stub\n", This, fEnterMode );
562     return E_NOTIMPL;
563 }
564
565 static HRESULT WINAPI OleInPlaceFrame_GetBorder(IOleInPlaceFrame *iface, LPRECT lprectBorder)
566 {
567     IOCS *This = impl_from_IOleInPlaceFrame(iface);
568
569     FIXME( "(%p,%p) - stub\n", This, lprectBorder );
570     return E_NOTIMPL;
571 }
572
573 static HRESULT WINAPI OleInPlaceFrame_RequestBorderSpace(IOleInPlaceFrame *iface, LPCBORDERWIDTHS pborderwidths)
574 {
575     IOCS *This = impl_from_IOleInPlaceFrame(iface);
576
577     FIXME( "(%p,%p) - stub\n", This, pborderwidths );
578     return E_NOTIMPL;
579 }
580
581 static HRESULT WINAPI OleInPlaceFrame_SetBorderSpace(IOleInPlaceFrame *iface, LPCBORDERWIDTHS pborderwidths)
582 {
583     IOCS *This = impl_from_IOleInPlaceFrame(iface);
584
585     FIXME( "(%p,%p) - stub\n", This, pborderwidths );
586     return E_NOTIMPL;
587 }
588
589 static HRESULT WINAPI OleInPlaceFrame_SetActiveObject(IOleInPlaceFrame *iface, IOleInPlaceActiveObject *pActiveObject, LPCOLESTR pszObjName)
590 {
591     IOCS *This = impl_from_IOleInPlaceFrame(iface);
592
593     FIXME( "(%p,%p,%s) - stub\n", This, pActiveObject, debugstr_w(pszObjName) );
594     return S_OK;
595 }
596
597 static HRESULT WINAPI OleInPlaceFrame_InsertMenus(IOleInPlaceFrame *iface, HMENU hmenuShared, LPOLEMENUGROUPWIDTHS lpMenuWidths)
598 {
599     IOCS *This = impl_from_IOleInPlaceFrame(iface);
600
601     FIXME( "(%p,%p,%p) - stub\n", This, hmenuShared, lpMenuWidths );
602     return E_NOTIMPL;
603 }
604
605 static HRESULT WINAPI OleInPlaceFrame_SetMenu(IOleInPlaceFrame *iface, HMENU hmenuShared, HOLEMENU holemenu, HWND hwndActiveObject)
606 {
607     IOCS *This = impl_from_IOleInPlaceFrame(iface);
608
609     FIXME( "(%p,%p,%p,%p) - stub\n", This, hmenuShared, holemenu, hwndActiveObject );
610     return E_NOTIMPL;
611 }
612
613 static HRESULT WINAPI OleInPlaceFrame_RemoveMenus(IOleInPlaceFrame *iface, HMENU hmenuShared)
614 {
615     IOCS *This = impl_from_IOleInPlaceFrame(iface);
616
617     FIXME( "(%p, %p) - stub\n", This, hmenuShared );
618     return E_NOTIMPL;
619 }
620
621 static HRESULT WINAPI OleInPlaceFrame_SetStatusText(IOleInPlaceFrame *iface, LPCOLESTR pszStatusText)
622 {
623     IOCS *This = impl_from_IOleInPlaceFrame(iface);
624
625     FIXME( "(%p, %s) - stub\n", This, debugstr_w( pszStatusText ) );
626     return E_NOTIMPL;
627 }
628
629 static HRESULT WINAPI OleInPlaceFrame_EnableModeless(IOleInPlaceFrame *iface, BOOL fEnable)
630 {
631     IOCS *This = impl_from_IOleInPlaceFrame(iface);
632
633     FIXME( "(%p, %d) - stub\n", This, fEnable );
634     return E_NOTIMPL;
635 }
636
637 static HRESULT WINAPI OleInPlaceFrame_TranslateAccelerator(IOleInPlaceFrame *iface, LPMSG lpmsg, WORD wID)
638 {
639     IOCS *This = impl_from_IOleInPlaceFrame(iface);
640
641     FIXME( "(%p, %p, %x) - stub\n", This, lpmsg, wID );
642     return E_NOTIMPL;
643 }
644
645
646 /******    IOleControlSite    *******/
647 static inline IOCS *impl_from_IOleControlSite(IOleControlSite *iface)
648 {
649     return CONTAINING_RECORD(iface, IOCS, IOleControlSite_iface);
650 }
651
652 static HRESULT WINAPI OleControlSite_QueryInterface(IOleControlSite *iface, REFIID riid, void **ppv)
653 {
654     IOCS *This = impl_from_IOleControlSite(iface);
655     return IOCS_QueryInterface(This, riid, ppv);
656 }
657
658 static ULONG WINAPI OleControlSite_AddRef(IOleControlSite *iface)
659 {
660     IOCS *This = impl_from_IOleControlSite(iface);
661     return IOCS_AddRef(This);
662 }
663
664 static ULONG WINAPI OleControlSite_Release(IOleControlSite *iface)
665 {
666     IOCS *This = impl_from_IOleControlSite(iface);
667     return IOCS_Release(This);
668 }
669
670 static HRESULT WINAPI OleControlSite_OnControlInfoChanged( IOleControlSite* This)
671 {
672     FIXME( "\n" );
673     return E_NOTIMPL;
674 }
675 static HRESULT WINAPI OleControlSite_LockInPlaceActive( IOleControlSite* This, BOOL fLock)
676 {
677     FIXME( "\n" );
678     return E_NOTIMPL;
679 }
680 static HRESULT WINAPI OleControlSite_GetExtendedControl( IOleControlSite* This, IDispatch** ppDisp)
681 {
682     FIXME( "\n" );
683     return E_NOTIMPL;
684 }
685 static HRESULT WINAPI OleControlSite_TransformCoords( IOleControlSite* This, POINTL* pPtlHimetric, POINTF* pPtfContainer, DWORD dwFlags)
686 {
687     FIXME( "\n" );
688     return E_NOTIMPL;
689 }
690 static HRESULT WINAPI OleControlSite_TranslateAccelerator( IOleControlSite* This, MSG* pMsg, DWORD grfModifiers)
691 {
692     FIXME( "\n" );
693     return E_NOTIMPL;
694 }
695 static HRESULT WINAPI OleControlSite_OnFocus( IOleControlSite* This, BOOL fGotFocus)
696 {
697     FIXME( "\n" );
698     return E_NOTIMPL;
699 }
700 static HRESULT WINAPI OleControlSite_ShowPropertyFrame( IOleControlSite* This)
701 {
702     FIXME( "\n" );
703     return E_NOTIMPL;
704 }
705
706
707 static const IOleClientSiteVtbl OleClientSite_vtbl = {
708     OleClientSite_QueryInterface,
709     OleClientSite_AddRef,
710     OleClientSite_Release,
711     OleClientSite_SaveObject,
712     OleClientSite_GetMoniker,
713     OleClientSite_GetContainer,
714     OleClientSite_ShowObject,
715     OleClientSite_OnShowWindow,
716     OleClientSite_RequestNewObjectLayout
717 };
718 static const IOleContainerVtbl OleContainer_vtbl = {
719     OleContainer_QueryInterface,
720     OleContainer_AddRef,
721     OleContainer_Release,
722     OleContainer_ParseDisplayName,
723     OleContainer_EnumObjects,
724     OleContainer_LockContainer
725 };
726 static const IOleInPlaceSiteWindowlessVtbl OleInPlaceSiteWindowless_vtbl = {
727     OleInPlaceSiteWindowless_QueryInterface,
728     OleInPlaceSiteWindowless_AddRef,
729     OleInPlaceSiteWindowless_Release,
730     OleInPlaceSiteWindowless_GetWindow,
731     OleInPlaceSiteWindowless_ContextSensitiveHelp,
732     OleInPlaceSiteWindowless_CanInPlaceActivate,
733     OleInPlaceSiteWindowless_OnInPlaceActivate,
734     OleInPlaceSiteWindowless_OnUIActivate,
735     OleInPlaceSiteWindowless_GetWindowContext,
736     OleInPlaceSiteWindowless_Scroll,
737     OleInPlaceSiteWindowless_OnUIDeactivate,
738     OleInPlaceSiteWindowless_OnInPlaceDeactivate,
739     OleInPlaceSiteWindowless_DiscardUndoState,
740     OleInPlaceSiteWindowless_DeactivateAndUndo,
741     OleInPlaceSiteWindowless_OnPosRectChange,
742     OleInPlaceSiteWindowless_OnInPlaceActivateEx,
743     OleInPlaceSiteWindowless_OnInPlaceDeactivateEx,
744     OleInPlaceSiteWindowless_RequestUIActivate,
745     OleInPlaceSiteWindowless_CanWindowlessActivate,
746     OleInPlaceSiteWindowless_GetCapture,
747     OleInPlaceSiteWindowless_SetCapture,
748     OleInPlaceSiteWindowless_GetFocus,
749     OleInPlaceSiteWindowless_SetFocus,
750     OleInPlaceSiteWindowless_GetDC,
751     OleInPlaceSiteWindowless_ReleaseDC,
752     OleInPlaceSiteWindowless_InvalidateRect,
753     OleInPlaceSiteWindowless_InvalidateRgn,
754     OleInPlaceSiteWindowless_ScrollRect,
755     OleInPlaceSiteWindowless_AdjustRect,
756     OleInPlaceSiteWindowless_OnDefWindowMessage
757 };
758 static const IOleInPlaceFrameVtbl OleInPlaceFrame_vtbl =
759 {
760     OleInPlaceFrame_QueryInterface,
761     OleInPlaceFrame_AddRef,
762     OleInPlaceFrame_Release,
763     OleInPlaceFrame_GetWindow,
764     OleInPlaceFrame_ContextSensitiveHelp,
765     OleInPlaceFrame_GetBorder,
766     OleInPlaceFrame_RequestBorderSpace,
767     OleInPlaceFrame_SetBorderSpace,
768     OleInPlaceFrame_SetActiveObject,
769     OleInPlaceFrame_InsertMenus,
770     OleInPlaceFrame_SetMenu,
771     OleInPlaceFrame_RemoveMenus,
772     OleInPlaceFrame_SetStatusText,
773     OleInPlaceFrame_EnableModeless,
774     OleInPlaceFrame_TranslateAccelerator
775 };
776 static const IOleControlSiteVtbl OleControlSite_vtbl =
777 {
778     OleControlSite_QueryInterface,
779     OleControlSite_AddRef,
780     OleControlSite_Release,
781     OleControlSite_OnControlInfoChanged,
782     OleControlSite_LockInPlaceActive,
783     OleControlSite_GetExtendedControl,
784     OleControlSite_TransformCoords,
785     OleControlSite_TranslateAccelerator,
786     OleControlSite_OnFocus,
787     OleControlSite_ShowPropertyFrame
788 };
789
790 static HRESULT IOCS_Detach( IOCS *This ) /* remove subclassing */
791 {
792     if ( This->hWnd )
793     {
794         SetWindowLongPtrW( This->hWnd, GWLP_WNDPROC, (ULONG_PTR) This->OrigWndProc );
795         SetWindowLongPtrW( This->hWnd, GWLP_USERDATA, 0 );
796         This->hWnd = NULL;
797     }
798     if ( This->control )
799     {
800         IOleObject *control = This->control;
801
802         This->control = NULL;
803         IOleObject_Close( control, OLECLOSE_NOSAVE );
804         IOleObject_SetClientSite( control, NULL );
805         IOleObject_Release( control );
806     }
807     return S_OK;
808 }
809
810 static void IOCS_OnSize( IOCS* This, LPCRECT rect )
811 {
812     SIZEL inPix, inHi;
813
814     This->size.left = rect->left; This->size.right = rect->right; This->size.top = rect->top; This->size.bottom = rect->bottom;
815
816     if ( !This->control )
817         return;
818
819     inPix.cx = rect->right - rect->left;
820     inPix.cy = rect->bottom - rect->top;
821     AtlPixelToHiMetric( &inPix, &inHi );
822     IOleObject_SetExtent( This->control, DVASPECT_CONTENT, &inHi );
823
824     if ( This->fInPlace )
825     {
826         IOleInPlaceObject *wl;
827
828         if ( SUCCEEDED( IOleObject_QueryInterface( This->control, &IID_IOleInPlaceObject, (void**)&wl ) ) )
829         {
830             IOleInPlaceObject_SetObjectRects( wl, rect, rect );
831             IOleInPlaceObject_Release( wl );
832         }
833     }
834 }
835
836 static void IOCS_OnShow( IOCS *This, BOOL fShow )
837 {
838     if (!This->control || This->fActive || !fShow )
839         return;
840
841     This->fActive = TRUE;
842 }
843
844 static void IOCS_OnDraw( IOCS *This )
845 {
846     IViewObject *view;
847
848     if ( !This->control || !This->fWindowless )
849         return;
850
851     if ( SUCCEEDED( IOleObject_QueryInterface( This->control, &IID_IViewObject, (void**)&view ) ) )
852     {
853         HDC dc = GetDC( This->hWnd );
854         RECTL rect;
855
856         rect.left = This->size.left; rect.top = This->size.top;
857         rect.bottom = This->size.bottom; rect.right = This->size.right;
858
859         IViewObject_Draw( view, DVASPECT_CONTENT, ~0, NULL, NULL, 0, dc, &rect, &rect, NULL, 0 );
860         IViewObject_Release( view );
861         ReleaseDC( This->hWnd, dc );
862     }
863 }
864
865 static LRESULT IOCS_OnWndProc( IOCS *This, HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam )
866 {
867     WNDPROC OrigWndProc = This->OrigWndProc;
868
869     switch( uMsg )
870     {
871         case WM_DESTROY:
872             IOCS_Detach( This );
873             break;
874         case WM_SIZE:
875             {
876                 RECT r;
877                 r.left = r.top = 0;
878                 r.right = LOWORD( lParam );
879                 r.bottom = HIWORD( lParam );
880                 IOCS_OnSize( This, &r );
881             }
882             break;
883         case WM_SHOWWINDOW:
884             IOCS_OnShow( This, (BOOL) wParam );
885             break;
886         case WM_PAINT:
887             IOCS_OnDraw( This );
888             break;
889     }
890
891     return CallWindowProcW( OrigWndProc, hWnd, uMsg, wParam, lParam );
892 }
893
894 static LRESULT CALLBACK AtlHost_wndproc( HWND hWnd, UINT wMsg, WPARAM wParam, LPARAM lParam )
895 {
896     IOCS *This = (IOCS*) GetWindowLongPtrW( hWnd, GWLP_USERDATA );
897     return IOCS_OnWndProc( This, hWnd, wMsg, wParam, lParam );
898 }
899
900 static HRESULT IOCS_Attach( IOCS *This, HWND hWnd, IUnknown *pUnkControl ) /* subclass hWnd */
901 {
902     This->hWnd = hWnd;
903     IUnknown_QueryInterface( pUnkControl, &IID_IOleObject, (void**)&This->control );
904     IOleObject_SetClientSite( This->control, &This->IOleClientSite_iface );
905     SetWindowLongPtrW( hWnd, GWLP_USERDATA, (ULONG_PTR) This );
906     This->OrigWndProc = (WNDPROC)SetWindowLongPtrW( hWnd, GWLP_WNDPROC, (ULONG_PTR) AtlHost_wndproc );
907
908     return S_OK;
909 }
910
911 static HRESULT IOCS_Init( IOCS *This )
912 {
913     RECT rect;
914     static const WCHAR AXWIN[] = {'A','X','W','I','N',0};
915
916     IOleObject_SetHostNames( This->control, AXWIN, AXWIN );
917
918     GetClientRect( This->hWnd, &rect );
919     IOCS_OnSize( This, &rect );
920     IOleObject_DoVerb( This->control, OLEIVERB_INPLACEACTIVATE, NULL, &This->IOleClientSite_iface,
921                        0, This->hWnd, &rect );
922
923     return S_OK;
924 }
925
926 /**********************************************************************
927  * Create new instance of Atl host component and attach it to window  *
928  */
929 static HRESULT IOCS_Create( HWND hWnd, IUnknown *pUnkControl, IOCS **ppSite )
930 {
931     HRESULT hr;
932     IOCS *This;
933
934     *ppSite = NULL;
935     This = HeapAlloc(GetProcessHeap(), 0, sizeof(IOCS));
936
937     if (!This)
938         return E_OUTOFMEMORY;
939
940     This->IOleClientSite_iface.lpVtbl = &OleClientSite_vtbl;
941     This->IOleContainer_iface.lpVtbl = &OleContainer_vtbl;
942     This->IOleInPlaceSiteWindowless_iface.lpVtbl = &OleInPlaceSiteWindowless_vtbl;
943     This->IOleInPlaceFrame_iface.lpVtbl = &OleInPlaceFrame_vtbl;
944     This->IOleControlSite_iface.lpVtbl = &OleControlSite_vtbl;
945     This->ref = 1;
946
947     This->OrigWndProc = NULL;
948     This->hWnd = NULL;
949     This->fWindowless = This->fActive = This->fInPlace = FALSE;
950
951     hr = IOCS_Attach( This, hWnd, pUnkControl );
952     if ( SUCCEEDED( hr ) )
953         hr = IOCS_Init( This );
954     if ( SUCCEEDED( hr ) )
955         *ppSite = This;
956     else
957         IOCS_Release( This );
958
959     return hr;
960 }
961
962
963 /***********************************************************************
964  *           AtlAxCreateControl           [ATL.@]
965  */
966 HRESULT WINAPI AtlAxCreateControl(LPCOLESTR lpszName, HWND hWnd,
967         IStream *pStream, IUnknown **ppUnkContainer)
968 {
969     return AtlAxCreateControlEx( lpszName, hWnd, pStream, ppUnkContainer,
970             NULL, NULL, NULL );
971 }
972
973 /***********************************************************************
974  *           AtlAxCreateControlEx            [ATL.@]
975  *
976  * REMARKS
977  *   See http://www.codeproject.com/com/cwebpage.asp for some background
978  *
979  */
980 HRESULT WINAPI AtlAxCreateControlEx(LPCOLESTR lpszName, HWND hWnd,
981         IStream *pStream, IUnknown **ppUnkContainer, IUnknown **ppUnkControl,
982         REFIID iidSink, IUnknown *punkSink)
983 {
984     CLSID controlId;
985     HRESULT hRes;
986     IOleObject *pControl;
987     IUnknown *pUnkControl;
988     IPersistStreamInit *pPSInit;
989     IUnknown *pContainer;
990     enum {IsGUID=0,IsHTML=1,IsURL=2} content;
991
992     TRACE("(%s %p %p %p %p %p %p)\n", debugstr_w(lpszName), hWnd, pStream, 
993             ppUnkContainer, ppUnkControl, iidSink, punkSink);
994
995     hRes = CLSIDFromString( lpszName, &controlId );
996     if ( FAILED(hRes) )
997         hRes = CLSIDFromProgID( lpszName, &controlId );
998     if ( SUCCEEDED( hRes ) )
999         content = IsGUID;
1000     else {
1001         /* FIXME - check for MSHTML: prefix! */
1002         content = IsURL;
1003         controlId = CLSID_WebBrowser;
1004     }
1005
1006     hRes = CoCreateInstance( &controlId, 0, CLSCTX_ALL, &IID_IOleObject, 
1007             (void**) &pControl );
1008     if ( FAILED( hRes ) )
1009     {
1010         WARN( "cannot create ActiveX control %s instance - error 0x%08x\n",
1011                 debugstr_guid( &controlId ), hRes );
1012         return hRes;
1013     }
1014
1015     hRes = IOleObject_QueryInterface( pControl, &IID_IPersistStreamInit, (void**) &pPSInit );
1016     if ( SUCCEEDED( hRes ) )
1017     {
1018         if (!pStream)
1019             IPersistStreamInit_InitNew( pPSInit );
1020         else
1021             IPersistStreamInit_Load( pPSInit, pStream );
1022         IPersistStreamInit_Release( pPSInit );
1023     } else
1024         WARN("cannot get IID_IPersistStreamInit out of control\n");
1025
1026     IOleObject_QueryInterface( pControl, &IID_IUnknown, (void**) &pUnkControl );
1027     IOleObject_Release( pControl );
1028      
1029
1030     hRes = AtlAxAttachControl( pUnkControl, hWnd, &pContainer );
1031     if ( FAILED( hRes ) )
1032         WARN("cannot attach control to window\n");
1033
1034     if ( content == IsURL )
1035     {
1036         IWebBrowser2 *browser;
1037
1038         hRes = IOleObject_QueryInterface( pControl, &IID_IWebBrowser2, (void**) &browser );
1039         if ( !browser )
1040             WARN( "Cannot query IWebBrowser2 interface: %08x\n", hRes );
1041         else {
1042             VARIANT url;
1043             
1044             IWebBrowser2_put_Visible( browser, VARIANT_TRUE ); /* it seems that native does this on URL (but do not on MSHTML:! why? */
1045
1046             V_VT(&url) = VT_BSTR;
1047             V_BSTR(&url) = SysAllocString( lpszName );
1048
1049             hRes = IWebBrowser2_Navigate2( browser, &url, NULL, NULL, NULL, NULL );
1050             if ( FAILED( hRes ) )
1051                 WARN( "IWebBrowser2::Navigate2 failed: %08x\n", hRes );
1052             SysFreeString( V_BSTR(&url) );
1053
1054             IWebBrowser2_Release( browser );
1055         }
1056     }
1057
1058     if (ppUnkContainer)
1059     {
1060         *ppUnkContainer = pContainer;
1061         if ( pContainer )
1062             IUnknown_AddRef( pContainer );
1063     }
1064     if (ppUnkControl)
1065     {
1066         *ppUnkControl = pUnkControl;
1067         if ( pUnkControl )
1068             IUnknown_AddRef( pUnkControl );
1069     }
1070
1071     if ( pUnkControl )
1072         IUnknown_Release( pUnkControl );
1073     if ( pContainer )
1074         IUnknown_Release( pContainer );
1075
1076     return S_OK;
1077 }
1078
1079 /***********************************************************************
1080  *           AtlAxAttachControl           [ATL.@]
1081  */
1082 HRESULT WINAPI AtlAxAttachControl(IUnknown* pControl, HWND hWnd, IUnknown** ppUnkContainer)
1083 {
1084     IOCS *pUnkContainer;
1085     HRESULT hr;
1086
1087     TRACE( "%p %p %p\n", pControl, hWnd, ppUnkContainer );
1088
1089     if (!pControl)
1090         return E_INVALIDARG;
1091
1092     hr = IOCS_Create( hWnd, pControl, &pUnkContainer );
1093     if ( SUCCEEDED( hr ) && ppUnkContainer)
1094     {
1095         *ppUnkContainer = (IUnknown*) pUnkContainer;
1096     }
1097
1098     if(!hWnd)
1099         return S_FALSE;
1100
1101     return hr;
1102 }
1103
1104 /**********************************************************************
1105  * Helper function for AX_ConvertDialogTemplate
1106  */
1107 static inline BOOL advance_array(WORD **pptr, DWORD *palloc, DWORD *pfilled, const WORD *data, DWORD size)
1108 {
1109     if ( (*pfilled + size) > *palloc )
1110     {
1111         *palloc = ((*pfilled+size) + 0xFF) & ~0xFF;
1112         *pptr = HeapReAlloc( GetProcessHeap(), 0, *pptr, *palloc * sizeof(WORD) );
1113         if (!*pptr)
1114             return FALSE;
1115     }
1116     RtlMoveMemory( *pptr+*pfilled, data, size * sizeof(WORD) );
1117     *pfilled += size;
1118     return TRUE;
1119 }
1120
1121 /**********************************************************************
1122  * Convert ActiveX control templates to AtlAxWin class instances
1123  */
1124 static LPDLGTEMPLATEW AX_ConvertDialogTemplate(LPCDLGTEMPLATEW src_tmpl)
1125 {
1126 #define GET_WORD(x)  (*(const  WORD *)(x))
1127 #define GET_DWORD(x) (*(const DWORD *)(x))
1128 #define PUT_BLOCK(x,y) do {if (!advance_array(&output, &allocated, &filled, (x), (y))) return NULL;} while (0)
1129 #define PUT_WORD(x)  do {WORD w = (x);PUT_BLOCK(&w, 1);} while(0)
1130 #define PUT_DWORD(x)  do {DWORD w = (x);PUT_BLOCK(&w, 2);} while(0)
1131     const WORD *tmp, *src = (const WORD *)src_tmpl;
1132     WORD *output; 
1133     DWORD allocated, filled; /* in WORDs */
1134     BOOL ext;
1135     WORD signature, dlgver, rescount;
1136     DWORD style;
1137
1138     filled = 0; allocated = 256;
1139     output = HeapAlloc( GetProcessHeap(), 0, allocated * sizeof(WORD) );
1140     if (!output)
1141         return NULL;
1142     
1143     /* header */
1144     tmp = src;
1145     signature = GET_WORD(src);
1146     dlgver = GET_WORD(src + 1);
1147     if (signature == 1 && dlgver == 0xFFFF)
1148     {
1149         ext = TRUE;
1150         src += 6;
1151         style = GET_DWORD(src);
1152         src += 2;
1153         rescount = GET_WORD(src++);
1154         src += 4;
1155         if ( GET_WORD(src) == 0xFFFF ) /* menu */
1156             src += 2;
1157         else
1158             src += strlenW(src) + 1;
1159         if ( GET_WORD(src) == 0xFFFF ) /* class */
1160             src += 2;
1161         else
1162             src += strlenW(src) + 1;
1163         src += strlenW(src) + 1; /* title */
1164         if ( style & (DS_SETFONT | DS_SHELLFONT) )
1165         {
1166             src += 3;
1167             src += strlenW(src) + 1;
1168         }
1169     } else {
1170         ext = FALSE;
1171         style = GET_DWORD(src);
1172         src += 4;
1173         rescount = GET_WORD(src++);
1174         src += 4;
1175         if ( GET_WORD(src) == 0xFFFF ) /* menu */
1176             src += 2;
1177         else
1178             src += strlenW(src) + 1;
1179         if ( GET_WORD(src) == 0xFFFF ) /* class */
1180             src += 2;
1181         else
1182             src += strlenW(src) + 1;
1183         src += strlenW(src) + 1; /* title */
1184         if ( style & DS_SETFONT )
1185         {
1186             src++;
1187             src += strlenW(src) + 1;
1188         }
1189     }
1190     PUT_BLOCK(tmp, src-tmp);
1191
1192     while(rescount--)
1193     {
1194         src = (const WORD *)( ( ((ULONG_PTR)src) + 3) & ~3); /* align on DWORD boundary */
1195         filled = (filled + 1) & ~1; /* depends on DWORD-aligned allocation unit */
1196
1197         tmp = src;
1198         if (ext)
1199             src += 12;
1200         else
1201             src += 9;
1202         PUT_BLOCK(tmp, src-tmp);
1203
1204         tmp = src;
1205         if ( GET_WORD(src) == 0xFFFF ) /* class */
1206         {
1207             src += 2;
1208         } else
1209         {
1210             src += strlenW(src) + 1;
1211         }
1212         src += strlenW(src) + 1; /* title */
1213         if ( GET_WORD(tmp) == '{' ) /* all this mess created because of this line */
1214         {
1215             static const WCHAR AtlAxWin[] = {'A','t','l','A','x','W','i','n', 0};
1216             PUT_BLOCK(AtlAxWin, sizeof(AtlAxWin)/sizeof(WCHAR));
1217             PUT_BLOCK(tmp, strlenW(tmp)+1);
1218         } else
1219             PUT_BLOCK(tmp, src-tmp);
1220
1221         if ( GET_WORD(src) )
1222         {
1223             WORD size = (GET_WORD(src)+sizeof(WORD)-1) / sizeof(WORD); /* quite ugly :( Maybe use BYTE* instead of WORD* everywhere ? */
1224             PUT_BLOCK(src, size);
1225             src+=size;
1226         }
1227         else
1228         {
1229             PUT_WORD(0);
1230             src++;
1231         }
1232     }
1233     return (LPDLGTEMPLATEW) output;
1234 }
1235
1236 /***********************************************************************
1237  *           AtlAxCreateDialogA           [ATL.@]
1238  *
1239  * Creates a dialog window
1240  *
1241  * PARAMS
1242  *  hInst   [I] Application instance
1243  *  name    [I] Dialog box template name
1244  *  owner   [I] Dialog box parent HWND
1245  *  dlgProc [I] Dialog box procedure
1246  *  param   [I] This value will be passed to dlgProc as WM_INITDIALOG's message lParam 
1247  *
1248  * RETURNS
1249  *  Window handle of dialog window.
1250  */
1251 HWND WINAPI AtlAxCreateDialogA(HINSTANCE hInst, LPCSTR name, HWND owner, DLGPROC dlgProc ,LPARAM param)
1252 {
1253     HWND res = NULL;
1254     int length;
1255     WCHAR *nameW;
1256
1257     if (IS_INTRESOURCE(name))
1258         return AtlAxCreateDialogW( hInst, (LPCWSTR) name, owner, dlgProc, param );
1259
1260     length = MultiByteToWideChar( CP_ACP, 0, name, -1, NULL, 0 );
1261     nameW = HeapAlloc( GetProcessHeap(), 0, length * sizeof(WCHAR) );
1262     if (nameW)
1263     {
1264         MultiByteToWideChar( CP_ACP, 0, name, -1, nameW, length );
1265         res = AtlAxCreateDialogW( hInst, nameW, owner, dlgProc, param );
1266         HeapFree( GetProcessHeap(), 0, nameW );
1267     }
1268     return res;
1269 }
1270
1271 /***********************************************************************
1272  *           AtlAxCreateDialogW           [ATL.@]
1273  *
1274  * See AtlAxCreateDialogA
1275  *
1276  */
1277 HWND WINAPI AtlAxCreateDialogW(HINSTANCE hInst, LPCWSTR name, HWND owner, DLGPROC dlgProc ,LPARAM param)
1278 {
1279     HRSRC hrsrc;
1280     HGLOBAL hgl;
1281     LPCDLGTEMPLATEW ptr;
1282     LPDLGTEMPLATEW newptr;
1283     HWND res;
1284
1285     TRACE("(%p %s %p %p %lx)\n", hInst, debugstr_w(name), owner, dlgProc, param);
1286
1287     hrsrc = FindResourceW( hInst, name, (LPWSTR)RT_DIALOG );
1288     if ( !hrsrc )
1289         return NULL;
1290     hgl = LoadResource (hInst, hrsrc);
1291     if ( !hgl )
1292         return NULL;
1293     ptr = LockResource ( hgl );
1294     if (!ptr)
1295     {
1296         FreeResource( hgl );
1297         return NULL;
1298     }
1299     newptr = AX_ConvertDialogTemplate( ptr );
1300     if ( newptr )
1301     {
1302             res = CreateDialogIndirectParamW( hInst, newptr, owner, dlgProc, param );
1303             HeapFree( GetProcessHeap(), 0, newptr );
1304     } else
1305         res = NULL;
1306     FreeResource ( hrsrc );
1307     return res;
1308 }
1309
1310 /***********************************************************************
1311  *           AtlAxGetHost                 [ATL.@]
1312  *
1313  */
1314 HRESULT WINAPI AtlAxGetHost(HWND hWnd, IUnknown **pUnk)
1315 {
1316     IOCS *This;
1317
1318     TRACE( "(%p, %p)\n", hWnd, pUnk );
1319
1320     *pUnk = NULL;
1321
1322     This = (IOCS*) GetWindowLongPtrW( hWnd, GWLP_USERDATA );
1323     if ( !This )
1324     {
1325         WARN("No container attached to %p\n", hWnd );
1326         return E_FAIL;
1327     }
1328
1329     return IOCS_QueryInterface( This, &IID_IUnknown, (void**) pUnk );
1330 }
1331
1332 /***********************************************************************
1333  *           AtlAxGetControl              [ATL.@]
1334  *
1335  */
1336 HRESULT WINAPI AtlAxGetControl(HWND hWnd, IUnknown **pUnk)
1337 {
1338     IOCS *This;
1339
1340     TRACE( "(%p, %p)\n", hWnd, pUnk );
1341
1342     *pUnk = NULL;
1343
1344     This = (IOCS*) GetWindowLongPtrW( hWnd, GWLP_USERDATA );
1345     if ( !This || !This->control )
1346     {
1347         WARN("No control attached to %p\n", hWnd );
1348         return E_FAIL;
1349     }
1350
1351     return IOleObject_QueryInterface( This->control, &IID_IUnknown, (void**) pUnk );
1352 }