wined3d: TRACE fixes.
[wine.git] / programs / explorer / desktop.c
blob2b8502b56d882dc7f935e8d88c7992843f823ae9
1 /*
2 * Explorer desktop support
4 * Copyright 2006 Alexandre Julliard
5 * Copyright 2013 Hans Leidekker for CodeWeavers
7 * This library is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU Lesser General Public
9 * License as published by the Free Software Foundation; either
10 * version 2.1 of the License, or (at your option) any later version.
12 * This library is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * Lesser General Public License for more details.
17 * You should have received a copy of the GNU Lesser General Public
18 * License along with this library; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
22 #include "config.h"
23 #include "wine/port.h"
24 #include <stdio.h>
26 #define COBJMACROS
27 #define OEMRESOURCE
28 #include <windows.h>
29 #include <rpc.h>
30 #include <shlobj.h>
31 #include <shellapi.h>
32 #include "exdisp.h"
34 #include "wine/unicode.h"
35 #include "wine/debug.h"
36 #include "explorer_private.h"
38 WINE_DEFAULT_DEBUG_CHANNEL(explorer);
40 #define DESKTOP_CLASS_ATOM ((LPCWSTR)MAKEINTATOM(32769))
41 #define DESKTOP_ALL_ACCESS 0x01ff
43 #ifdef __APPLE__
44 static const WCHAR default_driver[] = {'m','a','c',',','x','1','1',0};
45 #else
46 static const WCHAR default_driver[] = {'x','1','1',0};
47 #endif
49 static BOOL using_root;
51 struct launcher
53 WCHAR *path;
54 HICON icon;
55 WCHAR *title;
58 static WCHAR *desktop_folder;
59 static WCHAR *desktop_folder_public;
61 static int icon_cx, icon_cy, icon_offset_cx, icon_offset_cy;
62 static int title_cx, title_cy, title_offset_cx, title_offset_cy;
63 static int desktop_width, launcher_size, launchers_per_row;
65 static struct launcher **launchers;
66 static unsigned int nb_launchers, nb_allocated;
68 static REFIID tid_ids[] =
70 &IID_IShellWindows,
71 &IID_IWebBrowser2
74 typedef enum
76 IShellWindows_tid,
77 IWebBrowser2_tid,
78 LAST_tid
79 } tid_t;
81 static ITypeLib *typelib;
82 static ITypeInfo *typeinfos[LAST_tid];
84 static HRESULT load_typelib(void)
86 HRESULT hres;
87 ITypeLib *tl;
89 hres = LoadRegTypeLib(&LIBID_SHDocVw, 1, 0, LOCALE_SYSTEM_DEFAULT, &tl);
90 if (FAILED(hres))
92 ERR("LoadRegTypeLib failed: %08x\n", hres);
93 return hres;
96 if (InterlockedCompareExchangePointer((void**)&typelib, tl, NULL))
97 ITypeLib_Release(tl);
98 return hres;
101 static HRESULT get_typeinfo(tid_t tid, ITypeInfo **typeinfo)
103 HRESULT hres;
105 if (!typelib)
106 hres = load_typelib();
107 if (!typelib)
108 return hres;
110 if (!typeinfos[tid]) {
111 ITypeInfo *ti;
113 hres = ITypeLib_GetTypeInfoOfGuid(typelib, tid_ids[tid], &ti);
114 if (FAILED(hres)) {
115 ERR("GetTypeInfoOfGuid(%s) failed: %08x\n", debugstr_guid(tid_ids[tid]), hres);
116 return hres;
119 if (InterlockedCompareExchangePointer((void**)(typeinfos+tid), ti, NULL))
120 ITypeInfo_Release(ti);
123 *typeinfo = typeinfos[tid];
124 ITypeInfo_AddRef(*typeinfo);
125 return S_OK;
128 struct shellwindows
130 IShellWindows IShellWindows_iface;
133 /* This is not limited to desktop itself, every file browser window that
134 explorer creates supports that. Desktop instance is special in some
135 aspects, for example navigation is not possible, you can't show/hide it,
136 or bring up a menu. CLSID_ShellBrowserWindow class could be used to
137 create instances like that, and they should be registered with
138 IShellWindows as well. */
139 struct shellbrowserwindow
141 IWebBrowser2 IWebBrowser2_iface;
142 IServiceProvider IServiceProvider_iface;
143 IShellBrowser IShellBrowser_iface;
144 IShellView *view;
147 static struct shellwindows shellwindows;
148 static struct shellbrowserwindow desktopshellbrowserwindow;
150 static inline struct shellwindows *impl_from_IShellWindows(IShellWindows *iface)
152 return CONTAINING_RECORD(iface, struct shellwindows, IShellWindows_iface);
155 static inline struct shellbrowserwindow *impl_from_IWebBrowser2(IWebBrowser2 *iface)
157 return CONTAINING_RECORD(iface, struct shellbrowserwindow, IWebBrowser2_iface);
160 static inline struct shellbrowserwindow *impl_from_IServiceProvider(IServiceProvider *iface)
162 return CONTAINING_RECORD(iface, struct shellbrowserwindow, IServiceProvider_iface);
165 static inline struct shellbrowserwindow *impl_from_IShellBrowser(IShellBrowser *iface)
167 return CONTAINING_RECORD(iface, struct shellbrowserwindow, IShellBrowser_iface);
170 static void shellwindows_init(void);
171 static void desktopshellbrowserwindow_init(void);
173 static RECT get_icon_rect( unsigned int index )
175 RECT rect;
176 unsigned int row = index / launchers_per_row;
177 unsigned int col = index % launchers_per_row;
179 rect.left = col * launcher_size + icon_offset_cx;
180 rect.right = rect.left + icon_cx;
181 rect.top = row * launcher_size + icon_offset_cy;
182 rect.bottom = rect.top + icon_cy;
183 return rect;
186 static RECT get_title_rect( unsigned int index )
188 RECT rect;
189 unsigned int row = index / launchers_per_row;
190 unsigned int col = index % launchers_per_row;
192 rect.left = col * launcher_size + title_offset_cx;
193 rect.right = rect.left + title_cx;
194 rect.top = row * launcher_size + title_offset_cy;
195 rect.bottom = rect.top + title_cy;
196 return rect;
199 static const struct launcher *launcher_from_point( int x, int y )
201 RECT icon, title;
202 unsigned int index;
204 if (!nb_launchers) return NULL;
205 index = x / launcher_size + (y / launcher_size) * launchers_per_row;
206 if (index >= nb_launchers) return NULL;
208 icon = get_icon_rect( index );
209 title = get_title_rect( index );
210 if ((x < icon.left || x > icon.right || y < icon.top || y > icon.bottom) &&
211 (x < title.left || x > title.right || y < title.top || y > title.bottom)) return NULL;
212 return launchers[index];
215 static void draw_launchers( HDC hdc, RECT update_rect )
217 COLORREF color = SetTextColor( hdc, RGB(255,255,255) ); /* FIXME: depends on background color */
218 int mode = SetBkMode( hdc, TRANSPARENT );
219 unsigned int i;
220 LOGFONTW lf;
221 HFONT font;
223 SystemParametersInfoW( SPI_GETICONTITLELOGFONT, sizeof(lf), &lf, 0 );
224 font = SelectObject( hdc, CreateFontIndirectW( &lf ) );
226 for (i = 0; i < nb_launchers; i++)
228 RECT dummy, icon = get_icon_rect( i ), title = get_title_rect( i );
230 if (IntersectRect( &dummy, &icon, &update_rect ))
231 DrawIconEx( hdc, icon.left, icon.top, launchers[i]->icon, icon_cx, icon_cy,
232 0, 0, DI_DEFAULTSIZE|DI_NORMAL );
234 if (IntersectRect( &dummy, &title, &update_rect ))
235 DrawTextW( hdc, launchers[i]->title, -1, &title,
236 DT_CENTER|DT_WORDBREAK|DT_EDITCONTROL|DT_END_ELLIPSIS );
239 SelectObject( hdc, font );
240 SetTextColor( hdc, color );
241 SetBkMode( hdc, mode );
244 static void do_launch( const struct launcher *launcher )
246 static const WCHAR openW[] = {'o','p','e','n',0};
247 ShellExecuteW( NULL, openW, launcher->path, NULL, NULL, 0 );
250 static WCHAR *append_path( const WCHAR *path, const WCHAR *filename, int len_filename )
252 int len_path = strlenW( path );
253 WCHAR *ret;
255 if (len_filename == -1) len_filename = strlenW( filename );
256 if (!(ret = HeapAlloc( GetProcessHeap(), 0, (len_path + len_filename + 2) * sizeof(WCHAR) )))
257 return NULL;
258 memcpy( ret, path, len_path * sizeof(WCHAR) );
259 ret[len_path] = '\\';
260 memcpy( ret + len_path + 1, filename, len_filename * sizeof(WCHAR) );
261 ret[len_path + 1 + len_filename] = 0;
262 return ret;
265 static IShellLinkW *load_shelllink( const WCHAR *path )
267 HRESULT hr;
268 IShellLinkW *link;
269 IPersistFile *file;
271 hr = CoCreateInstance( &CLSID_ShellLink, NULL, CLSCTX_INPROC_SERVER, &IID_IShellLinkW,
272 (void **)&link );
273 if (FAILED( hr )) return NULL;
275 hr = IShellLinkW_QueryInterface( link, &IID_IPersistFile, (void **)&file );
276 if (FAILED( hr ))
278 IShellLinkW_Release( link );
279 return NULL;
281 hr = IPersistFile_Load( file, path, 0 );
282 IPersistFile_Release( file );
283 if (FAILED( hr ))
285 IShellLinkW_Release( link );
286 return NULL;
288 return link;
291 static HICON extract_icon( IShellLinkW *link )
293 WCHAR tmp_path[MAX_PATH], icon_path[MAX_PATH], target_path[MAX_PATH];
294 HICON icon = NULL;
295 int index;
297 tmp_path[0] = 0;
298 IShellLinkW_GetIconLocation( link, tmp_path, MAX_PATH, &index );
299 ExpandEnvironmentStringsW( tmp_path, icon_path, MAX_PATH );
301 if (icon_path[0]) ExtractIconExW( icon_path, index, &icon, NULL, 1 );
302 if (!icon)
304 tmp_path[0] = 0;
305 IShellLinkW_GetPath( link, tmp_path, MAX_PATH, NULL, SLGP_RAWPATH );
306 ExpandEnvironmentStringsW( tmp_path, target_path, MAX_PATH );
307 ExtractIconExW( target_path, index, &icon, NULL, 1 );
309 return icon;
312 static WCHAR *build_title( const WCHAR *filename, int len )
314 const WCHAR *p;
315 WCHAR *ret;
317 if (len == -1) len = strlenW( filename );
318 for (p = filename + len - 1; p >= filename; p--)
320 if (*p == '.')
322 len = p - filename;
323 break;
326 if (!(ret = HeapAlloc( GetProcessHeap(), 0, (len + 1) * sizeof(WCHAR) ))) return NULL;
327 memcpy( ret, filename, len * sizeof(WCHAR) );
328 ret[len] = 0;
329 return ret;
332 static BOOL add_launcher( const WCHAR *folder, const WCHAR *filename, int len_filename )
334 struct launcher *launcher;
335 IShellLinkW *link;
337 if (nb_launchers == nb_allocated)
339 unsigned int count = nb_allocated * 2;
340 struct launcher **tmp = HeapReAlloc( GetProcessHeap(), 0, launchers, count * sizeof(*tmp) );
341 if (!tmp) return FALSE;
342 launchers = tmp;
343 nb_allocated = count;
346 if (!(launcher = HeapAlloc( GetProcessHeap(), 0, sizeof(*launcher) ))) return FALSE;
347 if (!(launcher->path = append_path( folder, filename, len_filename ))) goto error;
348 if (!(link = load_shelllink( launcher->path ))) goto error;
350 launcher->icon = extract_icon( link );
351 launcher->title = build_title( filename, len_filename );
352 IShellLinkW_Release( link );
353 if (launcher->icon && launcher->title)
355 launchers[nb_launchers++] = launcher;
356 return TRUE;
358 HeapFree( GetProcessHeap(), 0, launcher->title );
359 DestroyIcon( launcher->icon );
361 error:
362 HeapFree( GetProcessHeap(), 0, launcher->path );
363 HeapFree( GetProcessHeap(), 0, launcher );
364 return FALSE;
367 static void free_launcher( struct launcher *launcher )
369 DestroyIcon( launcher->icon );
370 HeapFree( GetProcessHeap(), 0, launcher->path );
371 HeapFree( GetProcessHeap(), 0, launcher->title );
372 HeapFree( GetProcessHeap(), 0, launcher );
375 static BOOL remove_launcher( const WCHAR *folder, const WCHAR *filename, int len_filename )
377 UINT i;
378 WCHAR *path;
379 BOOL ret = FALSE;
381 if (!(path = append_path( folder, filename, len_filename ))) return FALSE;
382 for (i = 0; i < nb_launchers; i++)
384 if (!strcmpiW( launchers[i]->path, path ))
386 free_launcher( launchers[i] );
387 if (--nb_launchers)
388 memmove( &launchers[i], &launchers[i + 1], sizeof(launchers[i]) * (nb_launchers - i) );
389 ret = TRUE;
390 break;
393 HeapFree( GetProcessHeap(), 0, path );
394 return ret;
397 static BOOL get_icon_text_metrics( HWND hwnd, TEXTMETRICW *tm )
399 BOOL ret;
400 HDC hdc;
401 LOGFONTW lf;
402 HFONT hfont;
404 hdc = GetDC( hwnd );
405 SystemParametersInfoW( SPI_GETICONTITLELOGFONT, sizeof(lf), &lf, 0 );
406 hfont = SelectObject( hdc, CreateFontIndirectW( &lf ) );
407 ret = GetTextMetricsW( hdc, tm );
408 SelectObject( hdc, hfont );
409 ReleaseDC( hwnd, hdc );
410 return ret;
413 static BOOL process_changes( const WCHAR *folder, char *buf )
415 FILE_NOTIFY_INFORMATION *info = (FILE_NOTIFY_INFORMATION *)buf;
416 BOOL ret = FALSE;
418 for (;;)
420 switch (info->Action)
422 case FILE_ACTION_ADDED:
423 case FILE_ACTION_RENAMED_NEW_NAME:
424 if (add_launcher( folder, info->FileName, info->FileNameLength / sizeof(WCHAR) ))
425 ret = TRUE;
426 break;
428 case FILE_ACTION_REMOVED:
429 case FILE_ACTION_RENAMED_OLD_NAME:
430 if (remove_launcher( folder, info->FileName, info->FileNameLength / sizeof(WCHAR) ))
431 ret = TRUE;
432 break;
434 default:
435 WARN( "unexpected action %u\n", info->Action );
436 break;
438 if (!info->NextEntryOffset) break;
439 info = (FILE_NOTIFY_INFORMATION *)((char *)info + info->NextEntryOffset);
441 return ret;
444 static DWORD CALLBACK watch_desktop_folders( LPVOID param )
446 HWND hwnd = param;
447 HRESULT init = CoInitialize( NULL );
448 HANDLE dir0, dir1, events[2];
449 OVERLAPPED ovl0, ovl1;
450 char *buf0 = NULL, *buf1 = NULL;
451 DWORD count, size = 4096, error = ERROR_OUTOFMEMORY;
452 BOOL ret, redraw;
454 dir0 = CreateFileW( desktop_folder, FILE_LIST_DIRECTORY|SYNCHRONIZE, FILE_SHARE_READ|FILE_SHARE_WRITE,
455 NULL, OPEN_EXISTING, FILE_FLAG_BACKUP_SEMANTICS|FILE_FLAG_OVERLAPPED, NULL );
456 if (dir0 == INVALID_HANDLE_VALUE) return GetLastError();
457 dir1 = CreateFileW( desktop_folder_public, FILE_LIST_DIRECTORY|SYNCHRONIZE, FILE_SHARE_READ|FILE_SHARE_WRITE,
458 NULL, OPEN_EXISTING, FILE_FLAG_BACKUP_SEMANTICS|FILE_FLAG_OVERLAPPED, NULL );
459 if (dir1 == INVALID_HANDLE_VALUE)
461 CloseHandle( dir0 );
462 return GetLastError();
464 if (!(ovl0.hEvent = events[0] = CreateEventW( NULL, FALSE, FALSE, NULL ))) goto error;
465 if (!(ovl1.hEvent = events[1] = CreateEventW( NULL, FALSE, FALSE, NULL ))) goto error;
466 if (!(buf0 = HeapAlloc( GetProcessHeap(), 0, size ))) goto error;
467 if (!(buf1 = HeapAlloc( GetProcessHeap(), 0, size ))) goto error;
469 for (;;)
471 ret = ReadDirectoryChangesW( dir0, buf0, size, FALSE, FILE_NOTIFY_CHANGE_FILE_NAME, NULL, &ovl0, NULL );
472 if (!ret)
474 error = GetLastError();
475 goto error;
477 ret = ReadDirectoryChangesW( dir1, buf1, size, FALSE, FILE_NOTIFY_CHANGE_FILE_NAME, NULL, &ovl1, NULL );
478 if (!ret)
480 error = GetLastError();
481 goto error;
484 redraw = FALSE;
485 switch ((error = WaitForMultipleObjects( 2, events, FALSE, INFINITE )))
487 case WAIT_OBJECT_0:
488 if (!GetOverlappedResult( dir0, &ovl0, &count, FALSE ) || !count) break;
489 if (process_changes( desktop_folder, buf0 )) redraw = TRUE;
490 break;
492 case WAIT_OBJECT_0 + 1:
493 if (!GetOverlappedResult( dir1, &ovl1, &count, FALSE ) || !count) break;
494 if (process_changes( desktop_folder_public, buf1 )) redraw = TRUE;
495 break;
497 default:
498 goto error;
500 if (redraw) InvalidateRect( hwnd, NULL, TRUE );
503 error:
504 CloseHandle( dir0 );
505 CloseHandle( dir1 );
506 CloseHandle( events[0] );
507 CloseHandle( events[1] );
508 HeapFree( GetProcessHeap(), 0, buf0 );
509 HeapFree( GetProcessHeap(), 0, buf1 );
510 if (SUCCEEDED( init )) CoUninitialize();
511 return error;
514 static void add_folder( const WCHAR *folder )
516 static const WCHAR lnkW[] = {'\\','*','.','l','n','k',0};
517 int len = strlenW( folder ) + strlenW( lnkW );
518 WIN32_FIND_DATAW data;
519 HANDLE handle;
520 WCHAR *glob;
522 if (!(glob = HeapAlloc( GetProcessHeap(), 0, (len + 1) * sizeof(WCHAR) ))) return;
523 strcpyW( glob, folder );
524 strcatW( glob, lnkW );
526 if ((handle = FindFirstFileW( glob, &data )) != INVALID_HANDLE_VALUE)
528 do { add_launcher( folder, data.cFileName, -1 ); } while (FindNextFileW( handle, &data ));
529 FindClose( handle );
531 HeapFree( GetProcessHeap(), 0, glob );
534 #define BORDER_SIZE 4
535 #define PADDING_SIZE 4
536 #define TITLE_CHARS 14
538 static void initialize_launchers( HWND hwnd )
540 HRESULT hr, init;
541 TEXTMETRICW tm;
542 int icon_size;
544 if (!(get_icon_text_metrics( hwnd, &tm ))) return;
546 icon_cx = GetSystemMetrics( SM_CXICON );
547 icon_cy = GetSystemMetrics( SM_CYICON );
548 icon_size = max( icon_cx, icon_cy );
549 title_cy = tm.tmHeight * 2;
550 title_cx = max( tm.tmAveCharWidth * TITLE_CHARS, icon_size + PADDING_SIZE + title_cy );
551 launcher_size = BORDER_SIZE + title_cx + BORDER_SIZE;
552 icon_offset_cx = (launcher_size - icon_cx) / 2;
553 icon_offset_cy = BORDER_SIZE + (icon_size - icon_cy) / 2;
554 title_offset_cx = BORDER_SIZE;
555 title_offset_cy = BORDER_SIZE + icon_size + PADDING_SIZE;
556 desktop_width = GetSystemMetrics( SM_CXSCREEN );
557 launchers_per_row = desktop_width / launcher_size;
559 hr = SHGetKnownFolderPath( &FOLDERID_Desktop, KF_FLAG_CREATE, NULL, &desktop_folder );
560 if (FAILED( hr ))
562 WINE_ERR("Could not get user desktop folder\n");
563 return;
565 hr = SHGetKnownFolderPath( &FOLDERID_PublicDesktop, KF_FLAG_CREATE, NULL, &desktop_folder_public );
566 if (FAILED( hr ))
568 WINE_ERR("Could not get public desktop folder\n");
569 CoTaskMemFree( desktop_folder );
570 return;
572 if ((launchers = HeapAlloc( GetProcessHeap(), 0, 2 * sizeof(launchers[0]) )))
574 nb_allocated = 2;
576 init = CoInitialize( NULL );
577 add_folder( desktop_folder );
578 add_folder( desktop_folder_public );
579 if (SUCCEEDED( init )) CoUninitialize();
581 CreateThread( NULL, 0, watch_desktop_folders, hwnd, 0, NULL );
585 /* screen saver handler */
586 static BOOL start_screensaver( void )
588 if (using_root)
590 const char *argv[3] = { "xdg-screensaver", "activate", NULL };
591 int pid = _spawnvp( _P_DETACH, argv[0], argv );
592 if (pid > 0)
594 WINE_TRACE( "started process %d\n", pid );
595 return TRUE;
598 return FALSE;
601 /* window procedure for the desktop window */
602 static LRESULT WINAPI desktop_wnd_proc( HWND hwnd, UINT message, WPARAM wp, LPARAM lp )
604 WINE_TRACE( "got msg %04x wp %lx lp %lx\n", message, wp, lp );
606 switch(message)
608 case WM_SYSCOMMAND:
609 switch(wp & 0xfff0)
611 case SC_CLOSE:
612 ExitWindows( 0, 0 );
613 break;
614 case SC_SCREENSAVE:
615 return start_screensaver();
617 return 0;
619 case WM_CLOSE:
620 PostQuitMessage(0);
621 return 0;
623 case WM_SETCURSOR:
624 return (LRESULT)SetCursor( LoadCursorA( 0, (LPSTR)IDC_ARROW ) );
626 case WM_NCHITTEST:
627 return HTCLIENT;
629 case WM_ERASEBKGND:
630 if (!using_root) PaintDesktop( (HDC)wp );
631 return TRUE;
633 case WM_SETTINGCHANGE:
634 if (wp == SPI_SETDESKWALLPAPER)
635 SystemParametersInfoW( SPI_SETDESKWALLPAPER, 0, NULL, FALSE );
636 return 0;
638 case WM_PARENTNOTIFY:
639 if (LOWORD(wp) == WM_DESTROY) cleanup_systray_window( (HWND)lp );
640 return 0;
642 case WM_LBUTTONDBLCLK:
643 if (!using_root)
645 const struct launcher *launcher = launcher_from_point( (short)LOWORD(lp), (short)HIWORD(lp) );
646 if (launcher) do_launch( launcher );
648 return 0;
650 case WM_PAINT:
652 PAINTSTRUCT ps;
653 BeginPaint( hwnd, &ps );
654 if (!using_root)
656 if (ps.fErase) PaintDesktop( ps.hdc );
657 draw_launchers( ps.hdc, ps.rcPaint );
659 EndPaint( hwnd, &ps );
661 return 0;
663 default:
664 return DefWindowProcW( hwnd, message, wp, lp );
668 /* create the desktop and the associated driver window, and make it the current desktop */
669 static BOOL create_desktop( HMODULE driver, const WCHAR *name, unsigned int width, unsigned int height )
671 static const WCHAR rootW[] = {'r','o','o','t',0};
672 BOOL ret = FALSE;
673 BOOL (CDECL *create_desktop_func)(unsigned int, unsigned int);
675 /* magic: desktop "root" means use the root window */
676 if (driver && strcmpiW( name, rootW ))
678 create_desktop_func = (void *)GetProcAddress( driver, "wine_create_desktop" );
679 if (create_desktop_func) ret = create_desktop_func( width, height );
681 return ret;
684 /* parse the desktop size specification */
685 static BOOL parse_size( const WCHAR *size, unsigned int *width, unsigned int *height )
687 WCHAR *end;
689 *width = strtoulW( size, &end, 10 );
690 if (end == size) return FALSE;
691 if (*end != 'x') return FALSE;
692 size = end + 1;
693 *height = strtoulW( size, &end, 10 );
694 return !*end;
697 /* retrieve the desktop name to use if not specified on the command line */
698 static const WCHAR *get_default_desktop_name(void)
700 static const WCHAR desktopW[] = {'D','e','s','k','t','o','p',0};
701 static const WCHAR defaultW[] = {'D','e','f','a','u','l','t',0};
702 static const WCHAR explorer_keyW[] = {'S','o','f','t','w','a','r','e','\\','W','i','n','e','\\',
703 'E','x','p','l','o','r','e','r',0};
704 static WCHAR buffer[MAX_PATH];
705 DWORD size = sizeof(buffer);
706 HDESK desk = GetThreadDesktop( GetCurrentThreadId() );
707 WCHAR *ret = NULL;
708 HKEY hkey;
710 if (desk && GetUserObjectInformationW( desk, UOI_NAME, buffer, sizeof(buffer)/sizeof(WCHAR), NULL ))
712 if (strcmpiW( buffer, defaultW )) return buffer;
715 /* @@ Wine registry key: HKCU\Software\Wine\Explorer */
716 if (!RegOpenKeyW( HKEY_CURRENT_USER, explorer_keyW, &hkey ))
718 if (!RegQueryValueExW( hkey, desktopW, 0, NULL, (LPBYTE)buffer, &size )) ret = buffer;
719 RegCloseKey( hkey );
721 return ret;
724 /* retrieve the default desktop size from the registry */
725 static BOOL get_default_desktop_size( const WCHAR *name, unsigned int *width, unsigned int *height )
727 static const WCHAR desktop_keyW[] = {'S','o','f','t','w','a','r','e','\\','W','i','n','e','\\',
728 'E','x','p','l','o','r','e','r','\\',
729 'D','e','s','k','t','o','p','s',0};
730 HKEY hkey;
731 WCHAR buffer[64];
732 DWORD size = sizeof(buffer);
733 BOOL found = FALSE;
735 *width = 800;
736 *height = 600;
738 /* @@ Wine registry key: HKCU\Software\Wine\Explorer\Desktops */
739 if (!RegOpenKeyW( HKEY_CURRENT_USER, desktop_keyW, &hkey ))
741 if (!RegQueryValueExW( hkey, name, 0, NULL, (LPBYTE)buffer, &size ))
743 found = TRUE;
744 if (!parse_size( buffer, width, height )) *width = *height = 0;
746 RegCloseKey( hkey );
748 return found;
751 static BOOL get_default_enable_shell( const WCHAR *name )
753 static const WCHAR desktop_keyW[] = {'S','o','f','t','w','a','r','e','\\','W','i','n','e','\\',
754 'E','x','p','l','o','r','e','r','\\',
755 'D','e','s','k','t','o','p','s',0};
756 static const WCHAR enable_shellW[] = {'E','n','a','b','l','e','S','h','e','l','l',0};
757 static const WCHAR shellW[] = {'s','h','e','l','l',0};
758 HKEY hkey;
759 BOOL found = FALSE;
760 BOOL result;
761 DWORD size = sizeof(result);
763 /* @@ Wine registry key: HKCU\Software\Wine\Explorer\Desktops */
764 if (!RegOpenKeyW( HKEY_CURRENT_USER, desktop_keyW, &hkey ))
766 if (!RegGetValueW( hkey, name, enable_shellW, RRF_RT_REG_DWORD, NULL, &result, &size ))
767 found = TRUE;
768 RegCloseKey( hkey );
770 /* Default off, except for the magic desktop name "shell" */
771 if (!found)
772 result = (lstrcmpiW( name, shellW ) == 0);
773 return result;
776 static HMODULE load_graphics_driver( const WCHAR *driver, const GUID *guid )
778 static const WCHAR device_keyW[] = {
779 'S','y','s','t','e','m','\\',
780 'C','u','r','r','e','n','t','C','o','n','t','r','o','l','S','e','t','\\',
781 'C','o','n','t','r','o','l','\\',
782 'V','i','d','e','o','\\',
783 '{','%','0','8','x','-','%','0','4','x','-','%','0','4','x','-',
784 '%','0','2','x','%','0','2','x','-','%','0','2','x','%','0','2','x','%','0','2','x',
785 '%','0','2','x','%','0','2','x','%','0','2','x','}','\\','0','0','0','0',0};
786 static const WCHAR graphics_driverW[] = {'G','r','a','p','h','i','c','s','D','r','i','v','e','r',0};
787 static const WCHAR driversW[] = {'S','o','f','t','w','a','r','e','\\',
788 'W','i','n','e','\\','D','r','i','v','e','r','s',0};
789 static const WCHAR graphicsW[] = {'G','r','a','p','h','i','c','s',0};
790 static const WCHAR drv_formatW[] = {'w','i','n','e','%','s','.','d','r','v',0};
792 WCHAR buffer[MAX_PATH], libname[32], *name, *next;
793 WCHAR key[sizeof(device_keyW)/sizeof(WCHAR) + 39];
794 HMODULE module = 0;
795 HKEY hkey;
796 char error[80];
798 if (!driver)
800 strcpyW( buffer, default_driver );
802 /* @@ Wine registry key: HKCU\Software\Wine\Drivers */
803 if (!RegOpenKeyW( HKEY_CURRENT_USER, driversW, &hkey ))
805 DWORD count = sizeof(buffer);
806 RegQueryValueExW( hkey, graphicsW, 0, NULL, (LPBYTE)buffer, &count );
807 RegCloseKey( hkey );
810 else lstrcpynW( buffer, driver, sizeof(buffer)/sizeof(WCHAR) );
812 name = buffer;
813 while (name)
815 next = strchrW( name, ',' );
816 if (next) *next++ = 0;
818 snprintfW( libname, sizeof(libname)/sizeof(WCHAR), drv_formatW, name );
819 if ((module = LoadLibraryW( libname )) != 0) break;
820 switch (GetLastError())
822 case ERROR_MOD_NOT_FOUND:
823 strcpy( error, "The graphics driver is missing. Check your build!" );
824 break;
825 case ERROR_DLL_INIT_FAILED:
826 strcpy( error, "Make sure that your X server is running and that $DISPLAY is set correctly." );
827 break;
828 default:
829 sprintf( error, "Unknown error (%u).", GetLastError() );
830 break;
832 name = next;
835 if (module)
837 GetModuleFileNameW( module, buffer, MAX_PATH );
838 TRACE( "display %s driver %s\n", debugstr_guid(guid), debugstr_w(buffer) );
841 sprintfW( key, device_keyW, guid->Data1, guid->Data2, guid->Data3,
842 guid->Data4[0], guid->Data4[1], guid->Data4[2], guid->Data4[3],
843 guid->Data4[4], guid->Data4[5], guid->Data4[6], guid->Data4[7] );
845 if (!RegCreateKeyExW( HKEY_LOCAL_MACHINE, key, 0, NULL,
846 REG_OPTION_VOLATILE, KEY_SET_VALUE, NULL, &hkey, NULL ))
848 if (module)
849 RegSetValueExW( hkey, graphics_driverW, 0, REG_SZ,
850 (BYTE *)buffer, (strlenW(buffer) + 1) * sizeof(WCHAR) );
851 else
852 RegSetValueExA( hkey, "DriverError", 0, REG_SZ, (BYTE *)error, strlen(error) + 1 );
853 RegCloseKey( hkey );
856 return module;
859 static void initialize_display_settings(void)
861 DEVMODEW dmW;
863 /* Store current display mode in the registry */
864 if (EnumDisplaySettingsExW( NULL, ENUM_CURRENT_SETTINGS, &dmW, 0 ))
866 WINE_TRACE( "Current display mode %ux%u %u bpp %u Hz\n", dmW.dmPelsWidth,
867 dmW.dmPelsHeight, dmW.dmBitsPerPel, dmW.dmDisplayFrequency );
868 ChangeDisplaySettingsExW( NULL, &dmW, 0,
869 CDS_GLOBAL | CDS_NORESET | CDS_UPDATEREGISTRY,
870 NULL );
874 static void set_desktop_window_title( HWND hwnd, const WCHAR *name )
876 static const WCHAR desktop_nameW[] = {'W','i','n','e',' ','d','e','s','k','t','o','p',0};
877 static const WCHAR desktop_name_separatorW[] = {' ', '-', ' ', 0};
878 WCHAR *window_titleW = NULL;
879 int window_title_len;
881 if (!name[0])
883 SetWindowTextW( hwnd, desktop_nameW );
884 return;
887 window_title_len = strlenW(name) * sizeof(WCHAR)
888 + sizeof(desktop_name_separatorW)
889 + sizeof(desktop_nameW);
890 window_titleW = HeapAlloc( GetProcessHeap(), 0, window_title_len );
891 if (!window_titleW)
893 SetWindowTextW( hwnd, desktop_nameW );
894 return;
897 strcpyW( window_titleW, name );
898 strcatW( window_titleW, desktop_name_separatorW );
899 strcatW( window_titleW, desktop_nameW );
901 SetWindowTextW( hwnd, window_titleW );
902 HeapFree( GetProcessHeap(), 0, window_titleW );
905 /* main desktop management function */
906 void manage_desktop( WCHAR *arg )
908 static const WCHAR messageW[] = {'M','e','s','s','a','g','e',0};
909 HDESK desktop = 0;
910 GUID guid;
911 MSG msg;
912 HWND hwnd;
913 HMODULE graphics_driver;
914 unsigned int width, height;
915 WCHAR *cmdline = NULL, *driver = NULL;
916 WCHAR *p = arg;
917 const WCHAR *name = NULL;
918 BOOL enable_shell = FALSE;
920 /* get the rest of the command line (if any) */
921 while (*p && !isspace(*p)) p++;
922 if (*p)
924 *p++ = 0;
925 while (*p && isspace(*p)) p++;
926 if (*p) cmdline = p;
929 /* parse the desktop option */
930 /* the option is of the form /desktop=name[,widthxheight[,driver]] */
931 if (*arg == '=' || *arg == ',')
933 arg++;
934 name = arg;
935 if ((p = strchrW( arg, ',' )))
937 *p++ = 0;
938 if ((driver = strchrW( p, ',' ))) *driver++ = 0;
940 if (!p || !parse_size( p, &width, &height ))
941 get_default_desktop_size( name, &width, &height );
943 else if ((name = get_default_desktop_name()))
945 if (!get_default_desktop_size( name, &width, &height )) width = height = 0;
948 if (name)
949 enable_shell = get_default_enable_shell( name );
951 if (name && width && height)
953 if (!(desktop = CreateDesktopW( name, NULL, NULL, 0, DESKTOP_ALL_ACCESS, NULL )))
955 WINE_ERR( "failed to create desktop %s error %d\n", wine_dbgstr_w(name), GetLastError() );
956 ExitProcess( 1 );
958 SetThreadDesktop( desktop );
961 UuidCreate( &guid );
962 TRACE( "display guid %s\n", debugstr_guid(&guid) );
963 graphics_driver = load_graphics_driver( driver, &guid );
965 /* create the desktop window */
966 hwnd = CreateWindowExW( 0, DESKTOP_CLASS_ATOM, NULL,
967 WS_POPUP | WS_CLIPSIBLINGS | WS_CLIPCHILDREN, 0, 0, 0, 0, 0, 0, 0, &guid );
969 if (hwnd)
971 /* create the HWND_MESSAGE parent */
972 CreateWindowExW( 0, messageW, NULL, WS_POPUP | WS_CLIPSIBLINGS | WS_CLIPCHILDREN,
973 0, 0, 100, 100, 0, 0, 0, NULL );
975 using_root = !desktop || !create_desktop( graphics_driver, name, width, height );
976 SetWindowLongPtrW( hwnd, GWLP_WNDPROC, (LONG_PTR)desktop_wnd_proc );
977 SendMessageW( hwnd, WM_SETICON, ICON_BIG, (LPARAM)LoadIconW( 0, MAKEINTRESOURCEW(OIC_WINLOGO)));
978 if (name) set_desktop_window_title( hwnd, name );
979 SetWindowPos( hwnd, 0, GetSystemMetrics(SM_XVIRTUALSCREEN), GetSystemMetrics(SM_YVIRTUALSCREEN),
980 GetSystemMetrics(SM_CXVIRTUALSCREEN), GetSystemMetrics(SM_CYVIRTUALSCREEN),
981 SWP_SHOWWINDOW );
982 SystemParametersInfoW( SPI_SETDESKWALLPAPER, 0, NULL, FALSE );
983 ClipCursor( NULL );
984 initialize_display_settings();
985 initialize_appbar();
987 if (graphics_driver)
989 HMODULE shell32;
990 void (WINAPI *pShellDDEInit)( BOOL );
992 if (using_root) enable_shell = FALSE;
994 initialize_systray( graphics_driver, using_root, enable_shell );
995 if (!using_root) initialize_launchers( hwnd );
997 if ((shell32 = LoadLibraryA( "shell32.dll" )) &&
998 (pShellDDEInit = (void *)GetProcAddress( shell32, (LPCSTR)188)))
1000 pShellDDEInit( TRUE );
1005 /* if we have a command line, execute it */
1006 if (cmdline)
1008 STARTUPINFOW si;
1009 PROCESS_INFORMATION pi;
1011 memset( &si, 0, sizeof(si) );
1012 si.cb = sizeof(si);
1013 WINE_TRACE( "starting %s\n", wine_dbgstr_w(cmdline) );
1014 if (CreateProcessW( NULL, cmdline, NULL, NULL, FALSE, 0, NULL, NULL, &si, &pi ))
1016 CloseHandle( pi.hThread );
1017 CloseHandle( pi.hProcess );
1021 desktopshellbrowserwindow_init();
1022 shellwindows_init();
1024 /* run the desktop message loop */
1025 if (hwnd)
1027 WINE_TRACE( "desktop message loop starting on hwnd %p\n", hwnd );
1028 while (GetMessageW( &msg, 0, 0, 0 )) DispatchMessageW( &msg );
1029 WINE_TRACE( "desktop message loop exiting for hwnd %p\n", hwnd );
1032 ExitProcess( 0 );
1035 /* IShellWindows implementation */
1036 static HRESULT WINAPI shellwindows_QueryInterface(IShellWindows *iface, REFIID riid, void **ppvObject)
1038 struct shellwindows *This = impl_from_IShellWindows(iface);
1040 TRACE("%s %p\n", debugstr_guid(riid), ppvObject);
1042 if (IsEqualGUID(riid, &IID_IShellWindows) ||
1043 IsEqualGUID(riid, &IID_IDispatch) ||
1044 IsEqualGUID(riid, &IID_IUnknown))
1046 *ppvObject = &This->IShellWindows_iface;
1048 else
1050 WARN("Unsupported interface %s\n", debugstr_guid(riid));
1051 *ppvObject = NULL;
1054 if (*ppvObject)
1056 IUnknown_AddRef((IUnknown*)*ppvObject);
1057 return S_OK;
1060 return E_NOINTERFACE;
1063 static ULONG WINAPI shellwindows_AddRef(IShellWindows *iface)
1065 return 2;
1068 static ULONG WINAPI shellwindows_Release(IShellWindows *iface)
1070 return 1;
1073 static HRESULT WINAPI shellwindows_GetTypeInfoCount(IShellWindows *iface, UINT *pctinfo)
1075 TRACE("%p\n", pctinfo);
1076 *pctinfo = 1;
1077 return S_OK;
1080 static HRESULT WINAPI shellwindows_GetTypeInfo(IShellWindows *iface,
1081 UINT iTInfo, LCID lcid, ITypeInfo **ppTInfo)
1083 TRACE("%d %d %p\n", iTInfo, lcid, ppTInfo);
1084 return get_typeinfo(IShellWindows_tid, ppTInfo);
1087 static HRESULT WINAPI shellwindows_GetIDsOfNames(IShellWindows *iface,
1088 REFIID riid, LPOLESTR *rgszNames, UINT cNames, LCID lcid,
1089 DISPID *rgDispId)
1091 ITypeInfo *typeinfo;
1092 HRESULT hr;
1094 TRACE("%s %p %d %d %p\n", debugstr_guid(riid), rgszNames, cNames,
1095 lcid, rgDispId);
1097 if (!rgszNames || cNames == 0 || !rgDispId)
1098 return E_INVALIDARG;
1100 hr = get_typeinfo(IShellWindows_tid, &typeinfo);
1101 if (SUCCEEDED(hr))
1103 hr = ITypeInfo_GetIDsOfNames(typeinfo, rgszNames, cNames, rgDispId);
1104 ITypeInfo_Release(typeinfo);
1107 return hr;
1110 static HRESULT WINAPI shellwindows_Invoke(IShellWindows *iface,
1111 DISPID dispIdMember, REFIID riid, LCID lcid, WORD wFlags,
1112 DISPPARAMS *pDispParams, VARIANT *pVarResult,
1113 EXCEPINFO *pExcepInfo, UINT *puArgErr)
1115 ITypeInfo *typeinfo;
1116 HRESULT hr;
1118 TRACE("%d %s %d %08x %p %p %p %p\n", dispIdMember, debugstr_guid(riid),
1119 lcid, wFlags, pDispParams, pVarResult, pExcepInfo, puArgErr);
1121 hr = get_typeinfo(IShellWindows_tid, &typeinfo);
1122 if (SUCCEEDED(hr))
1124 hr = ITypeInfo_Invoke(typeinfo, iface, dispIdMember, wFlags,
1125 pDispParams, pVarResult, pExcepInfo, puArgErr);
1126 ITypeInfo_Release(typeinfo);
1129 return hr;
1132 static HRESULT WINAPI shellwindows_get_Count(IShellWindows *iface, LONG *count)
1134 FIXME("%p\n", count);
1135 return E_NOTIMPL;
1138 static HRESULT WINAPI shellwindows_Item(IShellWindows *iface, VARIANT index,
1139 IDispatch **folder)
1141 FIXME("%s %p\n", debugstr_variant(&index), folder);
1142 return E_NOTIMPL;
1145 static HRESULT WINAPI shellwindows__NewEnum(IShellWindows *iface, IUnknown **ppunk)
1147 FIXME("%p\n", ppunk);
1148 return E_NOTIMPL;
1151 static HRESULT WINAPI shellwindows_Register(IShellWindows *iface,
1152 IDispatch *disp, LONG hWnd, int class, LONG *cookie)
1154 FIXME("%p 0x%x 0x%x %p\n", disp, hWnd, class, cookie);
1155 return E_NOTIMPL;
1158 static HRESULT WINAPI shellwindows_RegisterPending(IShellWindows *iface,
1159 LONG threadid, VARIANT *loc, VARIANT *root, int class, LONG *cookie)
1161 FIXME("0x%x %s %s 0x%x %p\n", threadid, debugstr_variant(loc), debugstr_variant(root),
1162 class, cookie);
1163 return E_NOTIMPL;
1166 static HRESULT WINAPI shellwindows_Revoke(IShellWindows *iface, LONG cookie)
1168 FIXME("0x%x\n", cookie);
1169 return E_NOTIMPL;
1172 static HRESULT WINAPI shellwindows_OnNavigate(IShellWindows *iface, LONG cookie, VARIANT *loc)
1174 FIXME("0x%x %s\n", cookie, debugstr_variant(loc));
1175 return E_NOTIMPL;
1178 static HRESULT WINAPI shellwindows_OnActivated(IShellWindows *iface, LONG cookie, VARIANT_BOOL active)
1180 FIXME("0x%x 0x%x\n", cookie, active);
1181 return E_NOTIMPL;
1184 static HRESULT WINAPI shellwindows_FindWindowSW(IShellWindows *iface, VARIANT *loc,
1185 VARIANT *root, int class, LONG *hwnd, int options, IDispatch **disp)
1187 TRACE("%s %s 0x%x %p 0x%x %p\n", debugstr_variant(loc), debugstr_variant(root),
1188 class, hwnd, options, disp);
1190 if (class != SWC_DESKTOP)
1192 WARN("only SWC_DESKTOP class supported.\n");
1193 return E_NOTIMPL;
1196 *hwnd = HandleToLong(GetDesktopWindow());
1197 if (options & SWFO_NEEDDISPATCH)
1199 *disp = (IDispatch*)&desktopshellbrowserwindow.IWebBrowser2_iface;
1200 IDispatch_AddRef(*disp);
1203 return S_OK;
1206 static HRESULT WINAPI shellwindows_OnCreated(IShellWindows *iface, LONG cookie, IUnknown *punk)
1208 FIXME("0x%x %p\n", cookie, punk);
1209 return E_NOTIMPL;
1212 static HRESULT WINAPI shellwindows_ProcessAttachDetach(IShellWindows *iface, VARIANT_BOOL attach)
1214 FIXME("0x%x\n", attach);
1215 return E_NOTIMPL;
1218 static const IShellWindowsVtbl shellwindowsvtbl =
1220 shellwindows_QueryInterface,
1221 shellwindows_AddRef,
1222 shellwindows_Release,
1223 shellwindows_GetTypeInfoCount,
1224 shellwindows_GetTypeInfo,
1225 shellwindows_GetIDsOfNames,
1226 shellwindows_Invoke,
1227 shellwindows_get_Count,
1228 shellwindows_Item,
1229 shellwindows__NewEnum,
1230 shellwindows_Register,
1231 shellwindows_RegisterPending,
1232 shellwindows_Revoke,
1233 shellwindows_OnNavigate,
1234 shellwindows_OnActivated,
1235 shellwindows_FindWindowSW,
1236 shellwindows_OnCreated,
1237 shellwindows_ProcessAttachDetach
1240 struct shellwindows_classfactory
1242 IClassFactory IClassFactory_iface;
1243 DWORD classreg;
1246 static inline struct shellwindows_classfactory *impl_from_IClassFactory(IClassFactory *iface)
1248 return CONTAINING_RECORD(iface, struct shellwindows_classfactory, IClassFactory_iface);
1251 static HRESULT WINAPI swclassfactory_QueryInterface(IClassFactory *iface, REFIID riid, void **ppvObject)
1253 struct shellwindows_classfactory *This = impl_from_IClassFactory(iface);
1255 TRACE("%s %p\n", debugstr_guid(riid), ppvObject);
1257 if (IsEqualGUID(riid, &IID_IUnknown) || IsEqualGUID(riid, &IID_IClassFactory))
1259 *ppvObject = &This->IClassFactory_iface;
1261 else
1263 WARN("Unsupported interface %s\n", debugstr_guid(riid));
1264 *ppvObject = NULL;
1267 if (*ppvObject)
1269 IUnknown_AddRef((IUnknown*)*ppvObject);
1270 return S_OK;
1273 return E_NOINTERFACE;
1276 static ULONG WINAPI swclassfactory_AddRef(IClassFactory *iface)
1278 return 2;
1281 static ULONG WINAPI swclassfactory_Release(IClassFactory *iface)
1283 return 1;
1286 static HRESULT WINAPI swclassfactory_CreateInstance(IClassFactory *iface,
1287 IUnknown *pUnkOuter, REFIID riid, void **ppvObject)
1289 TRACE("%p %s %p\n", pUnkOuter, debugstr_guid(riid), ppvObject);
1290 return IShellWindows_QueryInterface(&shellwindows.IShellWindows_iface, riid, ppvObject);
1293 static HRESULT WINAPI swclassfactory_LockServer(IClassFactory *iface, BOOL lock)
1295 TRACE("%u\n", lock);
1296 return E_NOTIMPL;
1299 static const IClassFactoryVtbl swclassfactoryvtbl =
1301 swclassfactory_QueryInterface,
1302 swclassfactory_AddRef,
1303 swclassfactory_Release,
1304 swclassfactory_CreateInstance,
1305 swclassfactory_LockServer
1308 static struct shellwindows_classfactory shellwindows_classfactory = { { &swclassfactoryvtbl } };
1310 static HRESULT WINAPI webbrowser_QueryInterface(IWebBrowser2 *iface, REFIID riid, void **ppv)
1312 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1314 *ppv = NULL;
1316 if (IsEqualGUID(&IID_IWebBrowser2, riid) ||
1317 IsEqualGUID(&IID_IWebBrowserApp, riid) ||
1318 IsEqualGUID(&IID_IWebBrowser, riid) ||
1319 IsEqualGUID(&IID_IDispatch, riid) ||
1320 IsEqualGUID(&IID_IUnknown, riid))
1322 *ppv = &This->IWebBrowser2_iface;
1324 else if (IsEqualGUID(&IID_IServiceProvider, riid))
1326 *ppv = &This->IServiceProvider_iface;
1329 if (*ppv)
1331 IUnknown_AddRef((IUnknown*)*ppv);
1332 return S_OK;
1335 FIXME("(%p)->(%s %p) interface not supported\n", This, debugstr_guid(riid), ppv);
1336 return E_NOINTERFACE;
1339 static ULONG WINAPI webbrowser_AddRef(IWebBrowser2 *iface)
1341 return 2;
1344 static ULONG WINAPI webbrowser_Release(IWebBrowser2 *iface)
1346 return 1;
1349 /* IDispatch methods */
1350 static HRESULT WINAPI webbrowser_GetTypeInfoCount(IWebBrowser2 *iface, UINT *pctinfo)
1352 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1353 TRACE("(%p)->(%p)\n", This, pctinfo);
1354 *pctinfo = 1;
1355 return S_OK;
1358 static HRESULT WINAPI webbrowser_GetTypeInfo(IWebBrowser2 *iface, UINT iTInfo, LCID lcid,
1359 LPTYPEINFO *ppTInfo)
1361 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1362 TRACE("(%p)->(%d %d %p)\n", This, iTInfo, lcid, ppTInfo);
1363 return get_typeinfo(IWebBrowser2_tid, ppTInfo);
1366 static HRESULT WINAPI webbrowser_GetIDsOfNames(IWebBrowser2 *iface, REFIID riid,
1367 LPOLESTR *rgszNames, UINT cNames,
1368 LCID lcid, DISPID *rgDispId)
1370 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1371 ITypeInfo *typeinfo;
1372 HRESULT hr;
1374 TRACE("(%p)->(%s %p %d %d %p)\n", This, debugstr_guid(riid), rgszNames, cNames,
1375 lcid, rgDispId);
1377 if(!rgszNames || cNames == 0 || !rgDispId)
1378 return E_INVALIDARG;
1380 hr = get_typeinfo(IWebBrowser2_tid, &typeinfo);
1381 if (SUCCEEDED(hr))
1383 hr = ITypeInfo_GetIDsOfNames(typeinfo, rgszNames, cNames, rgDispId);
1384 ITypeInfo_Release(typeinfo);
1387 return hr;
1390 static HRESULT WINAPI webbrowser_Invoke(IWebBrowser2 *iface, DISPID dispIdMember,
1391 REFIID riid, LCID lcid, WORD wFlags,
1392 DISPPARAMS *pDispParams, VARIANT *pVarResult,
1393 EXCEPINFO *pExcepInfo, UINT *puArgErr)
1395 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1396 ITypeInfo *typeinfo;
1397 HRESULT hr;
1399 TRACE("(%p)->(%d %s %d %08x %p %p %p %p)\n", This, dispIdMember, debugstr_guid(riid),
1400 lcid, wFlags, pDispParams, pVarResult, pExcepInfo, puArgErr);
1402 hr = get_typeinfo(IWebBrowser2_tid, &typeinfo);
1403 if (SUCCEEDED(hr))
1405 hr = ITypeInfo_Invoke(typeinfo, &This->IWebBrowser2_iface, dispIdMember, wFlags,
1406 pDispParams, pVarResult, pExcepInfo, puArgErr);
1407 ITypeInfo_Release(typeinfo);
1410 return hr;
1413 /* IWebBrowser methods */
1414 static HRESULT WINAPI webbrowser_GoBack(IWebBrowser2 *iface)
1416 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1417 FIXME("(%p): stub\n", This);
1418 return E_NOTIMPL;
1421 static HRESULT WINAPI webbrowser_GoForward(IWebBrowser2 *iface)
1423 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1424 FIXME("(%p): stub\n", This);
1425 return E_NOTIMPL;
1428 static HRESULT WINAPI webbrowser_GoHome(IWebBrowser2 *iface)
1430 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1431 FIXME("(%p): stub\n", This);
1432 return E_NOTIMPL;
1435 static HRESULT WINAPI webbrowser_GoSearch(IWebBrowser2 *iface)
1437 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1438 FIXME("(%p)\n", This);
1439 return E_NOTIMPL;
1442 static HRESULT WINAPI webbrowser_Navigate(IWebBrowser2 *iface, BSTR szUrl,
1443 VARIANT *Flags, VARIANT *TargetFrameName,
1444 VARIANT *PostData, VARIANT *Headers)
1446 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1447 FIXME("(%p)->(%s %s %s %s %s): stub\n", This, debugstr_w(szUrl), debugstr_variant(Flags),
1448 debugstr_variant(TargetFrameName), debugstr_variant(PostData),
1449 debugstr_variant(Headers));
1450 return E_NOTIMPL;
1453 static HRESULT WINAPI webbrowser_Refresh(IWebBrowser2 *iface)
1455 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1456 FIXME("(%p): stub\n", This);
1457 return E_NOTIMPL;
1460 static HRESULT WINAPI webbrowser_Refresh2(IWebBrowser2 *iface, VARIANT *Level)
1462 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1463 FIXME("(%p)->(%s): stub\n", This, debugstr_variant(Level));
1464 return E_NOTIMPL;
1467 static HRESULT WINAPI webbrowser_Stop(IWebBrowser2 *iface)
1469 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1470 FIXME("(%p): stub\n", This);
1471 return E_NOTIMPL;
1474 static HRESULT WINAPI webbrowser_get_Application(IWebBrowser2 *iface, IDispatch **ppDisp)
1476 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1478 TRACE("(%p)->(%p)\n", This, ppDisp);
1480 *ppDisp = (IDispatch*)iface;
1481 IDispatch_AddRef(*ppDisp);
1483 return S_OK;
1486 static HRESULT WINAPI webbrowser_get_Parent(IWebBrowser2 *iface, IDispatch **ppDisp)
1488 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1489 FIXME("(%p)->(%p)\n", This, ppDisp);
1490 return E_NOTIMPL;
1493 static HRESULT WINAPI webbrowser_get_Container(IWebBrowser2 *iface, IDispatch **ppDisp)
1495 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1496 FIXME("(%p)->(%p)\n", This, ppDisp);
1497 return E_NOTIMPL;
1500 static HRESULT WINAPI webbrowser_get_Document(IWebBrowser2 *iface, IDispatch **ppDisp)
1502 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1503 FIXME("(%p)->(%p)\n", This, ppDisp);
1504 return E_NOTIMPL;
1507 static HRESULT WINAPI webbrowser_get_TopLevelContainer(IWebBrowser2 *iface, VARIANT_BOOL *pBool)
1509 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1510 FIXME("(%p)->(%p)\n", This, pBool);
1511 return E_NOTIMPL;
1514 static HRESULT WINAPI webbrowser_get_Type(IWebBrowser2 *iface, BSTR *Type)
1516 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1517 FIXME("(%p)->(%p)\n", This, Type);
1518 return E_NOTIMPL;
1521 static HRESULT WINAPI webbrowser_get_Left(IWebBrowser2 *iface, LONG *pl)
1523 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1524 FIXME("(%p)->(%p)\n", This, pl);
1525 return E_NOTIMPL;
1528 static HRESULT WINAPI webbrowser_put_Left(IWebBrowser2 *iface, LONG Left)
1530 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1531 FIXME("(%p)->(%d)\n", This, Left);
1532 return E_NOTIMPL;
1535 static HRESULT WINAPI webbrowser_get_Top(IWebBrowser2 *iface, LONG *pl)
1537 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1538 FIXME("(%p)->(%p)\n", This, pl);
1539 return E_NOTIMPL;
1542 static HRESULT WINAPI webbrowser_put_Top(IWebBrowser2 *iface, LONG Top)
1544 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1545 FIXME("(%p)->(%d)\n", This, Top);
1546 return E_NOTIMPL;
1549 static HRESULT WINAPI webbrowser_get_Width(IWebBrowser2 *iface, LONG *pl)
1551 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1552 FIXME("(%p)->(%p)\n", This, pl);
1553 return E_NOTIMPL;
1556 static HRESULT WINAPI webbrowser_put_Width(IWebBrowser2 *iface, LONG Width)
1558 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1559 FIXME("(%p)->(%d)\n", This, Width);
1560 return E_NOTIMPL;
1563 static HRESULT WINAPI webbrowser_get_Height(IWebBrowser2 *iface, LONG *pl)
1565 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1566 FIXME("(%p)->(%p)\n", This, pl);
1567 return E_NOTIMPL;
1570 static HRESULT WINAPI webbrowser_put_Height(IWebBrowser2 *iface, LONG Height)
1572 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1573 FIXME("(%p)->(%d)\n", This, Height);
1574 return E_NOTIMPL;
1577 static HRESULT WINAPI webbrowser_get_LocationName(IWebBrowser2 *iface, BSTR *LocationName)
1579 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1580 FIXME("(%p)->(%p)\n", This, LocationName);
1581 return E_NOTIMPL;
1584 static HRESULT WINAPI webbrowser_get_LocationURL(IWebBrowser2 *iface, BSTR *LocationURL)
1586 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1587 FIXME("(%p)->(%p)\n", This, LocationURL);
1588 return E_NOTIMPL;
1591 static HRESULT WINAPI webbrowser_get_Busy(IWebBrowser2 *iface, VARIANT_BOOL *pBool)
1593 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1594 FIXME("(%p)->(%p)\n", This, pBool);
1595 return E_NOTIMPL;
1598 static HRESULT WINAPI webbrowser_Quit(IWebBrowser2 *iface)
1600 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1601 FIXME("(%p)\n", This);
1602 return E_NOTIMPL;
1605 static HRESULT WINAPI webbrowser_ClientToWindow(IWebBrowser2 *iface, int *pcx, int *pcy)
1607 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1608 FIXME("(%p)->(%p %p)\n", This, pcx, pcy);
1609 return E_NOTIMPL;
1612 static HRESULT WINAPI webbrowser_PutProperty(IWebBrowser2 *iface, BSTR szProperty, VARIANT vtValue)
1614 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1615 FIXME("(%p)->(%s %s)\n", This, debugstr_w(szProperty), debugstr_variant(&vtValue));
1616 return E_NOTIMPL;
1619 static HRESULT WINAPI webbrowser_GetProperty(IWebBrowser2 *iface, BSTR szProperty, VARIANT *pvtValue)
1621 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1622 FIXME("(%p)->(%s %s)\n", This, debugstr_w(szProperty), debugstr_variant(pvtValue));
1623 return E_NOTIMPL;
1626 static HRESULT WINAPI webbrowser_get_Name(IWebBrowser2 *iface, BSTR *Name)
1628 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1629 FIXME("(%p)->(%p)\n", This, Name);
1630 return E_NOTIMPL;
1633 static HRESULT WINAPI webbrowser_get_HWND(IWebBrowser2 *iface, SHANDLE_PTR *pHWND)
1635 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1636 FIXME("(%p)->(%p)\n", This, pHWND);
1637 return E_NOTIMPL;
1640 static HRESULT WINAPI webbrowser_get_FullName(IWebBrowser2 *iface, BSTR *FullName)
1642 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1643 FIXME("(%p)->(%p)\n", This, FullName);
1644 return E_NOTIMPL;
1647 static HRESULT WINAPI webbrowser_get_Path(IWebBrowser2 *iface, BSTR *Path)
1649 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1650 FIXME("(%p)->(%p)\n", This, Path);
1651 return E_NOTIMPL;
1654 static HRESULT WINAPI webbrowser_get_Visible(IWebBrowser2 *iface, VARIANT_BOOL *pBool)
1656 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1657 FIXME("(%p)->(%p)\n", This, pBool);
1658 return E_NOTIMPL;
1661 static HRESULT WINAPI webbrowser_put_Visible(IWebBrowser2 *iface, VARIANT_BOOL Value)
1663 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1664 FIXME("(%p)->(%x)\n", This, Value);
1665 return E_NOTIMPL;
1668 static HRESULT WINAPI webbrowser_get_StatusBar(IWebBrowser2 *iface, VARIANT_BOOL *pBool)
1670 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1671 FIXME("(%p)->(%p)\n", This, pBool);
1672 return E_NOTIMPL;
1675 static HRESULT WINAPI webbrowser_put_StatusBar(IWebBrowser2 *iface, VARIANT_BOOL Value)
1677 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1678 FIXME("(%p)->(%x)\n", This, Value);
1679 return E_NOTIMPL;
1682 static HRESULT WINAPI webbrowser_get_StatusText(IWebBrowser2 *iface, BSTR *StatusText)
1684 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1685 FIXME("(%p)->(%p)\n", This, StatusText);
1686 return E_NOTIMPL;
1689 static HRESULT WINAPI webbrowser_put_StatusText(IWebBrowser2 *iface, BSTR StatusText)
1691 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1692 FIXME("(%p)->(%s)\n", This, debugstr_w(StatusText));
1693 return E_NOTIMPL;
1696 static HRESULT WINAPI webbrowser_get_ToolBar(IWebBrowser2 *iface, int *Value)
1698 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1699 FIXME("(%p)->(%p)\n", This, Value);
1700 return E_NOTIMPL;
1703 static HRESULT WINAPI webbrowser_put_ToolBar(IWebBrowser2 *iface, int Value)
1705 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1706 FIXME("(%p)->(%x)\n", This, Value);
1707 return E_NOTIMPL;
1710 static HRESULT WINAPI webbrowser_get_MenuBar(IWebBrowser2 *iface, VARIANT_BOOL *Value)
1712 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1713 FIXME("(%p)->(%p)\n", This, Value);
1714 return E_NOTIMPL;
1717 static HRESULT WINAPI webbrowser_put_MenuBar(IWebBrowser2 *iface, VARIANT_BOOL Value)
1719 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1720 FIXME("(%p)->(%x)\n", This, Value);
1721 return E_NOTIMPL;
1724 static HRESULT WINAPI webbrowser_get_FullScreen(IWebBrowser2 *iface, VARIANT_BOOL *pbFullScreen)
1726 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1727 FIXME("(%p)->(%p)\n", This, pbFullScreen);
1728 return E_NOTIMPL;
1731 static HRESULT WINAPI webbrowser_put_FullScreen(IWebBrowser2 *iface, VARIANT_BOOL bFullScreen)
1733 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1734 FIXME("(%p)->(%x)\n", This, bFullScreen);
1735 return E_NOTIMPL;
1738 static HRESULT WINAPI webbrowser_Navigate2(IWebBrowser2 *iface, VARIANT *URL, VARIANT *Flags,
1739 VARIANT *TargetFrameName, VARIANT *PostData, VARIANT *Headers)
1741 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1742 FIXME("(%p)->(%s %s %s %s %s)\n", This, debugstr_variant(URL), debugstr_variant(Flags),
1743 debugstr_variant(TargetFrameName), debugstr_variant(PostData), debugstr_variant(Headers));
1744 return E_NOTIMPL;
1747 static HRESULT WINAPI webbrowser_QueryStatusWB(IWebBrowser2 *iface, OLECMDID cmdID, OLECMDF *pcmdf)
1749 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1750 FIXME("(%p)->(%d %p)\n", This, cmdID, pcmdf);
1751 return E_NOTIMPL;
1754 static HRESULT WINAPI webbrowser_ExecWB(IWebBrowser2 *iface, OLECMDID cmdID,
1755 OLECMDEXECOPT cmdexecopt, VARIANT *pvaIn, VARIANT *pvaOut)
1757 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1758 FIXME("(%p)->(%d %d %s %p)\n", This, cmdID, cmdexecopt, debugstr_variant(pvaIn), pvaOut);
1759 return E_NOTIMPL;
1762 static HRESULT WINAPI webbrowser_ShowBrowserBar(IWebBrowser2 *iface, VARIANT *pvaClsid,
1763 VARIANT *pvarShow, VARIANT *pvarSize)
1765 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1766 FIXME("(%p)->(%s %s %s)\n", This, debugstr_variant(pvaClsid), debugstr_variant(pvarShow),
1767 debugstr_variant(pvarSize));
1768 return E_NOTIMPL;
1771 static HRESULT WINAPI webbrowser_get_ReadyState(IWebBrowser2 *iface, READYSTATE *lpReadyState)
1773 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1774 FIXME("(%p)->(%p)\n", This, lpReadyState);
1775 return E_NOTIMPL;
1778 static HRESULT WINAPI webbrowser_get_Offline(IWebBrowser2 *iface, VARIANT_BOOL *pbOffline)
1780 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1781 FIXME("(%p)->(%p)\n", This, pbOffline);
1782 return E_NOTIMPL;
1785 static HRESULT WINAPI webbrowser_put_Offline(IWebBrowser2 *iface, VARIANT_BOOL bOffline)
1787 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1788 FIXME("(%p)->(%x)\n", This, bOffline);
1789 return E_NOTIMPL;
1792 static HRESULT WINAPI webbrowser_get_Silent(IWebBrowser2 *iface, VARIANT_BOOL *pbSilent)
1794 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1795 FIXME("(%p)->(%p)\n", This, pbSilent);
1796 return E_NOTIMPL;
1799 static HRESULT WINAPI webbrowser_put_Silent(IWebBrowser2 *iface, VARIANT_BOOL bSilent)
1801 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1802 FIXME("(%p)->(%x)\n", This, bSilent);
1803 return E_NOTIMPL;
1806 static HRESULT WINAPI webbrowser_get_RegisterAsBrowser(IWebBrowser2 *iface,
1807 VARIANT_BOOL *pbRegister)
1809 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1810 FIXME("(%p)->(%p)\n", This, pbRegister);
1811 return E_NOTIMPL;
1814 static HRESULT WINAPI webbrowser_put_RegisterAsBrowser(IWebBrowser2 *iface,
1815 VARIANT_BOOL bRegister)
1817 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1818 FIXME("(%p)->(%x)\n", This, bRegister);
1819 return E_NOTIMPL;
1822 static HRESULT WINAPI webbrowser_get_RegisterAsDropTarget(IWebBrowser2 *iface,
1823 VARIANT_BOOL *pbRegister)
1825 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1826 FIXME("(%p)->(%p)\n", This, pbRegister);
1827 return E_NOTIMPL;
1830 static HRESULT WINAPI webbrowser_put_RegisterAsDropTarget(IWebBrowser2 *iface,
1831 VARIANT_BOOL bRegister)
1833 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1834 FIXME("(%p)->(%x)\n", This, bRegister);
1835 return E_NOTIMPL;
1838 static HRESULT WINAPI webbrowser_get_TheaterMode(IWebBrowser2 *iface, VARIANT_BOOL *pbRegister)
1840 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1841 FIXME("(%p)->(%p)\n", This, pbRegister);
1842 return E_NOTIMPL;
1845 static HRESULT WINAPI webbrowser_put_TheaterMode(IWebBrowser2 *iface, VARIANT_BOOL bRegister)
1847 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1848 TRACE("(%p)->(%x)\n", This, bRegister);
1849 return E_NOTIMPL;
1852 static HRESULT WINAPI webbrowser_get_AddressBar(IWebBrowser2 *iface, VARIANT_BOOL *Value)
1854 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1855 FIXME("(%p)->(%p)\n", This, Value);
1856 return E_NOTIMPL;
1859 static HRESULT WINAPI webbrowser_put_AddressBar(IWebBrowser2 *iface, VARIANT_BOOL Value)
1861 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1862 FIXME("(%p)->(%x)\n", This, Value);
1863 return E_NOTIMPL;
1866 static HRESULT WINAPI webbrowser_get_Resizable(IWebBrowser2 *iface, VARIANT_BOOL *Value)
1868 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1869 FIXME("(%p)->(%p)\n", This, Value);
1870 return E_NOTIMPL;
1873 static HRESULT WINAPI webbrowser_put_Resizable(IWebBrowser2 *iface, VARIANT_BOOL Value)
1875 struct shellbrowserwindow *This = impl_from_IWebBrowser2(iface);
1876 FIXME("(%p)->(%x)\n", This, Value);
1877 return E_NOTIMPL;
1880 static const IWebBrowser2Vtbl webbrowser2vtbl =
1882 webbrowser_QueryInterface,
1883 webbrowser_AddRef,
1884 webbrowser_Release,
1885 webbrowser_GetTypeInfoCount,
1886 webbrowser_GetTypeInfo,
1887 webbrowser_GetIDsOfNames,
1888 webbrowser_Invoke,
1889 webbrowser_GoBack,
1890 webbrowser_GoForward,
1891 webbrowser_GoHome,
1892 webbrowser_GoSearch,
1893 webbrowser_Navigate,
1894 webbrowser_Refresh,
1895 webbrowser_Refresh2,
1896 webbrowser_Stop,
1897 webbrowser_get_Application,
1898 webbrowser_get_Parent,
1899 webbrowser_get_Container,
1900 webbrowser_get_Document,
1901 webbrowser_get_TopLevelContainer,
1902 webbrowser_get_Type,
1903 webbrowser_get_Left,
1904 webbrowser_put_Left,
1905 webbrowser_get_Top,
1906 webbrowser_put_Top,
1907 webbrowser_get_Width,
1908 webbrowser_put_Width,
1909 webbrowser_get_Height,
1910 webbrowser_put_Height,
1911 webbrowser_get_LocationName,
1912 webbrowser_get_LocationURL,
1913 webbrowser_get_Busy,
1914 webbrowser_Quit,
1915 webbrowser_ClientToWindow,
1916 webbrowser_PutProperty,
1917 webbrowser_GetProperty,
1918 webbrowser_get_Name,
1919 webbrowser_get_HWND,
1920 webbrowser_get_FullName,
1921 webbrowser_get_Path,
1922 webbrowser_get_Visible,
1923 webbrowser_put_Visible,
1924 webbrowser_get_StatusBar,
1925 webbrowser_put_StatusBar,
1926 webbrowser_get_StatusText,
1927 webbrowser_put_StatusText,
1928 webbrowser_get_ToolBar,
1929 webbrowser_put_ToolBar,
1930 webbrowser_get_MenuBar,
1931 webbrowser_put_MenuBar,
1932 webbrowser_get_FullScreen,
1933 webbrowser_put_FullScreen,
1934 webbrowser_Navigate2,
1935 webbrowser_QueryStatusWB,
1936 webbrowser_ExecWB,
1937 webbrowser_ShowBrowserBar,
1938 webbrowser_get_ReadyState,
1939 webbrowser_get_Offline,
1940 webbrowser_put_Offline,
1941 webbrowser_get_Silent,
1942 webbrowser_put_Silent,
1943 webbrowser_get_RegisterAsBrowser,
1944 webbrowser_put_RegisterAsBrowser,
1945 webbrowser_get_RegisterAsDropTarget,
1946 webbrowser_put_RegisterAsDropTarget,
1947 webbrowser_get_TheaterMode,
1948 webbrowser_put_TheaterMode,
1949 webbrowser_get_AddressBar,
1950 webbrowser_put_AddressBar,
1951 webbrowser_get_Resizable,
1952 webbrowser_put_Resizable
1955 static HRESULT WINAPI serviceprovider_QueryInterface(IServiceProvider *iface, REFIID riid, void **ppv)
1957 struct shellbrowserwindow *This = impl_from_IServiceProvider(iface);
1958 return IWebBrowser2_QueryInterface(&This->IWebBrowser2_iface, riid, ppv);
1961 static ULONG WINAPI serviceprovider_AddRef(IServiceProvider *iface)
1963 struct shellbrowserwindow *This = impl_from_IServiceProvider(iface);
1964 return IWebBrowser2_AddRef(&This->IWebBrowser2_iface);
1967 static ULONG WINAPI serviceprovider_Release(IServiceProvider *iface)
1969 struct shellbrowserwindow *This = impl_from_IServiceProvider(iface);
1970 return IWebBrowser2_Release(&This->IWebBrowser2_iface);
1973 static HRESULT WINAPI serviceprovider_QueryService(IServiceProvider *iface, REFGUID service,
1974 REFIID riid, void **ppv)
1976 struct shellbrowserwindow *This = impl_from_IServiceProvider(iface);
1978 TRACE("%s %s %p\n", debugstr_guid(service), debugstr_guid(riid), ppv);
1980 if (IsEqualGUID(service, &SID_STopLevelBrowser))
1981 return IShellBrowser_QueryInterface(&This->IShellBrowser_iface, riid, ppv);
1983 WARN("unknown service id %s\n", debugstr_guid(service));
1984 return E_NOTIMPL;
1987 static const IServiceProviderVtbl serviceprovidervtbl =
1989 serviceprovider_QueryInterface,
1990 serviceprovider_AddRef,
1991 serviceprovider_Release,
1992 serviceprovider_QueryService
1995 /* IShellBrowser */
1996 static HRESULT WINAPI shellbrowser_QueryInterface(IShellBrowser *iface, REFIID riid, void **ppv)
1998 TRACE("%s %p\n", debugstr_guid(riid), ppv);
2000 *ppv = NULL;
2002 if (IsEqualGUID(&IID_IShellBrowser, riid) ||
2003 IsEqualGUID(&IID_IOleWindow, riid) ||
2004 IsEqualGUID(&IID_IUnknown, riid))
2006 *ppv = iface;
2009 if (*ppv)
2011 IUnknown_AddRef((IUnknown*)*ppv);
2012 return S_OK;
2015 return E_NOINTERFACE;
2018 static ULONG WINAPI shellbrowser_AddRef(IShellBrowser *iface)
2020 struct shellbrowserwindow *This = impl_from_IShellBrowser(iface);
2021 return IWebBrowser2_AddRef(&This->IWebBrowser2_iface);
2024 static ULONG WINAPI shellbrowser_Release(IShellBrowser *iface)
2026 struct shellbrowserwindow *This = impl_from_IShellBrowser(iface);
2027 return IWebBrowser2_Release(&This->IWebBrowser2_iface);
2030 static HRESULT WINAPI shellbrowser_GetWindow(IShellBrowser *iface, HWND *phwnd)
2032 FIXME("%p\n", phwnd);
2033 return E_NOTIMPL;
2036 static HRESULT WINAPI shellbrowser_ContextSensitiveHelp(IShellBrowser *iface, BOOL mode)
2038 FIXME("%d\n", mode);
2039 return E_NOTIMPL;
2042 static HRESULT WINAPI shellbrowser_InsertMenusSB(IShellBrowser *iface, HMENU hmenuShared,
2043 OLEMENUGROUPWIDTHS *menuwidths)
2045 FIXME("%p %p\n", hmenuShared, menuwidths);
2046 return E_NOTIMPL;
2049 static HRESULT WINAPI shellbrowser_SetMenuSB(IShellBrowser *iface, HMENU hmenuShared,
2050 HOLEMENU holemenuReserved, HWND hwndActiveObject)
2052 FIXME("%p %p %p\n", hmenuShared, holemenuReserved, hwndActiveObject);
2053 return E_NOTIMPL;
2056 static HRESULT WINAPI shellbrowser_RemoveMenusSB(IShellBrowser *iface, HMENU hmenuShared)
2058 FIXME("%p\n", hmenuShared);
2059 return E_NOTIMPL;
2062 static HRESULT WINAPI shellbrowser_SetStatusTextSB(IShellBrowser *iface, LPCOLESTR text)
2064 FIXME("%s\n", debugstr_w(text));
2065 return E_NOTIMPL;
2068 static HRESULT WINAPI shellbrowser_EnableModelessSB(IShellBrowser *iface, BOOL enable)
2070 FIXME("%d\n", enable);
2071 return E_NOTIMPL;
2074 static HRESULT WINAPI shellbrowser_TranslateAcceleratorSB(IShellBrowser *iface, MSG *pmsg, WORD wID)
2076 FIXME("%p 0x%x\n", pmsg, wID);
2077 return E_NOTIMPL;
2080 static HRESULT WINAPI shellbrowser_BrowseObject(IShellBrowser *iface, LPCITEMIDLIST pidl, UINT flags)
2082 FIXME("%p %x\n", pidl, flags);
2083 return E_NOTIMPL;
2086 static HRESULT WINAPI shellbrowser_GetViewStateStream(IShellBrowser *iface, DWORD mode, IStream **stream)
2088 FIXME("0x%x %p\n", mode, stream);
2089 return E_NOTIMPL;
2092 static HRESULT WINAPI shellbrowser_GetControlWindow(IShellBrowser *iface, UINT id, HWND *phwnd)
2094 FIXME("%d %p\n", id, phwnd);
2095 return E_NOTIMPL;
2098 static HRESULT WINAPI shellbrowser_SendControlMsg(IShellBrowser *iface, UINT id, UINT uMsg,
2099 WPARAM wParam, LPARAM lParam, LRESULT *pret)
2101 FIXME("%d %d %lx %lx %p\n", id, uMsg, wParam, lParam, pret);
2102 return E_NOTIMPL;
2105 static HRESULT WINAPI shellbrowser_QueryActiveShellView(IShellBrowser *iface, IShellView **view)
2107 TRACE("%p\n", view);
2109 *view = desktopshellbrowserwindow.view;
2110 IShellView_AddRef(*view);
2111 return S_OK;
2114 static HRESULT WINAPI shellbrowser_OnViewWindowActive(IShellBrowser *iface, IShellView *view)
2116 FIXME("%p\n", view);
2117 return E_NOTIMPL;
2120 static HRESULT WINAPI shellbrowser_SetToolbarItems(IShellBrowser *iface, LPTBBUTTONSB buttons,
2121 UINT count, UINT flags)
2123 FIXME("%p %d 0x%x\n", buttons, count, flags);
2124 return E_NOTIMPL;
2127 static const IShellBrowserVtbl shellbrowservtbl = {
2128 shellbrowser_QueryInterface,
2129 shellbrowser_AddRef,
2130 shellbrowser_Release,
2131 shellbrowser_GetWindow,
2132 shellbrowser_ContextSensitiveHelp,
2133 shellbrowser_InsertMenusSB,
2134 shellbrowser_SetMenuSB,
2135 shellbrowser_RemoveMenusSB,
2136 shellbrowser_SetStatusTextSB,
2137 shellbrowser_EnableModelessSB,
2138 shellbrowser_TranslateAcceleratorSB,
2139 shellbrowser_BrowseObject,
2140 shellbrowser_GetViewStateStream,
2141 shellbrowser_GetControlWindow,
2142 shellbrowser_SendControlMsg,
2143 shellbrowser_QueryActiveShellView,
2144 shellbrowser_OnViewWindowActive,
2145 shellbrowser_SetToolbarItems
2148 static void desktopshellbrowserwindow_init(void)
2150 IShellFolder *folder;
2152 desktopshellbrowserwindow.IWebBrowser2_iface.lpVtbl = &webbrowser2vtbl;
2153 desktopshellbrowserwindow.IServiceProvider_iface.lpVtbl = &serviceprovidervtbl;
2154 desktopshellbrowserwindow.IShellBrowser_iface.lpVtbl = &shellbrowservtbl;
2156 if (FAILED(SHGetDesktopFolder(&folder)))
2157 return;
2159 IShellFolder_CreateViewObject(folder, NULL, &IID_IShellView, (void**)&desktopshellbrowserwindow.view);
2162 static void shellwindows_init(void)
2164 HRESULT hr;
2166 CoInitialize(NULL);
2168 shellwindows.IShellWindows_iface.lpVtbl = &shellwindowsvtbl;
2170 hr = CoRegisterClassObject(&CLSID_ShellWindows,
2171 (IUnknown*)&shellwindows_classfactory.IClassFactory_iface,
2172 CLSCTX_LOCAL_SERVER,
2173 REGCLS_MULTIPLEUSE,
2174 &shellwindows_classfactory.classreg);
2176 if (FAILED(hr))
2177 WARN("Failed to register ShellWindows object: %08x\n", hr);