1*d119d52dSAndrew Rist /**************************************************************
2cdf0e10cSrcweir *
3*d119d52dSAndrew Rist * Licensed to the Apache Software Foundation (ASF) under one
4*d119d52dSAndrew Rist * or more contributor license agreements. See the NOTICE file
5*d119d52dSAndrew Rist * distributed with this work for additional information
6*d119d52dSAndrew Rist * regarding copyright ownership. The ASF licenses this file
7*d119d52dSAndrew Rist * to you under the Apache License, Version 2.0 (the
8*d119d52dSAndrew Rist * "License"); you may not use this file except in compliance
9*d119d52dSAndrew Rist * with the License. You may obtain a copy of the License at
10*d119d52dSAndrew Rist *
11*d119d52dSAndrew Rist * http://www.apache.org/licenses/LICENSE-2.0
12*d119d52dSAndrew Rist *
13*d119d52dSAndrew Rist * Unless required by applicable law or agreed to in writing,
14*d119d52dSAndrew Rist * software distributed under the License is distributed on an
15*d119d52dSAndrew Rist * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16*d119d52dSAndrew Rist * KIND, either express or implied. See the License for the
17*d119d52dSAndrew Rist * specific language governing permissions and limitations
18*d119d52dSAndrew Rist * under the License.
19*d119d52dSAndrew Rist *
20*d119d52dSAndrew Rist *************************************************************/
21*d119d52dSAndrew Rist
22*d119d52dSAndrew Rist
23cdf0e10cSrcweir
24cdf0e10cSrcweir // MARKER(update_precomp.py): autogen include statement, do not remove
25cdf0e10cSrcweir #include "precompiled_sfx2.hxx"
26cdf0e10cSrcweir
27cdf0e10cSrcweir #ifdef WNT
28cdf0e10cSrcweir
29cdf0e10cSrcweir // necessary to include system headers without warnings
30cdf0e10cSrcweir #ifdef _MSC_VER
31cdf0e10cSrcweir #pragma warning(disable:4668 4917)
32cdf0e10cSrcweir #endif
33cdf0e10cSrcweir
34cdf0e10cSrcweir // Support Windows 95 too
35cdf0e10cSrcweir #undef WINVER
36cdf0e10cSrcweir #define WINVER 0x0400
37cdf0e10cSrcweir #define USE_APP_SHORTCUTS
38cdf0e10cSrcweir //
39cdf0e10cSrcweir // the systray icon is only available on windows
40cdf0e10cSrcweir //
41cdf0e10cSrcweir
42cdf0e10cSrcweir #include <unotools/moduleoptions.hxx>
43cdf0e10cSrcweir #include <unotools/dynamicmenuoptions.hxx>
44cdf0e10cSrcweir
45cdf0e10cSrcweir #include "shutdownicon.hxx"
46cdf0e10cSrcweir #include "app.hrc"
47cdf0e10cSrcweir #include <shlobj.h>
48cdf0e10cSrcweir #include <objidl.h>
49cdf0e10cSrcweir #include <stdio.h>
50cdf0e10cSrcweir #include <io.h>
51cdf0e10cSrcweir #include <osl/thread.h>
52cdf0e10cSrcweir #include <setup_native/qswin32.h>
53cdf0e10cSrcweir #include <comphelper/sequenceashashmap.hxx>
54cdf0e10cSrcweir #include <comphelper/processfactory.hxx>
55cdf0e10cSrcweir #include <com/sun/star/uno/Reference.h>
56cdf0e10cSrcweir #include <com/sun/star/lang/XMultiServiceFactory.hpp>
57cdf0e10cSrcweir #include <com/sun/star/task/XJob.hpp>
58cdf0e10cSrcweir #include <com/sun/star/beans/NamedValue.hpp>
59cdf0e10cSrcweir
60cdf0e10cSrcweir #include <set>
61cdf0e10cSrcweir
62cdf0e10cSrcweir using namespace ::rtl;
63cdf0e10cSrcweir using namespace ::com::sun::star::uno;
64cdf0e10cSrcweir using namespace ::com::sun::star::task;
65cdf0e10cSrcweir using namespace ::com::sun::star::lang;
66cdf0e10cSrcweir using namespace ::com::sun::star::beans;
67cdf0e10cSrcweir using namespace ::osl;
68cdf0e10cSrcweir
69cdf0e10cSrcweir
70cdf0e10cSrcweir #define EXECUTER_WINDOWCLASS "SO Executer Class"
71cdf0e10cSrcweir #define EXECUTER_WINDOWNAME "SO Executer Window"
72cdf0e10cSrcweir
73cdf0e10cSrcweir
74cdf0e10cSrcweir #define ID_QUICKSTART 1
75cdf0e10cSrcweir #define IDM_EXIT 2
76cdf0e10cSrcweir #if defined(USE_APP_SHORTCUTS)
77cdf0e10cSrcweir # define IDM_OPEN 3
78cdf0e10cSrcweir # define IDM_WRITER 4
79cdf0e10cSrcweir # define IDM_CALC 5
80cdf0e10cSrcweir # define IDM_IMPRESS 6
81cdf0e10cSrcweir # define IDM_DRAW 7
82cdf0e10cSrcweir # define IDM_BASE 8
83cdf0e10cSrcweir # define IDM_TEMPLATE 9
84cdf0e10cSrcweir # define IDM_MATH 12
85cdf0e10cSrcweir #endif
86cdf0e10cSrcweir #define IDM_INSTALL 10
87cdf0e10cSrcweir #define IDM_UNINSTALL 11
88cdf0e10cSrcweir
89cdf0e10cSrcweir
90cdf0e10cSrcweir #define ICON_SO_DEFAULT 1
91cdf0e10cSrcweir #define ICON_TEXT_DOCUMENT 2
92cdf0e10cSrcweir #define ICON_TEXT_TEMPLATE 3
93cdf0e10cSrcweir #define ICON_SPREADSHEET_DOCUMENT 4
94cdf0e10cSrcweir #define ICON_SPREADSHEET_TEMPLATE 5
95cdf0e10cSrcweir #define ICON_DRAWING_DOCUMENT 6
96cdf0e10cSrcweir #define ICON_DRAWING_TEMPLATE 7
97cdf0e10cSrcweir #define ICON_PRESENTATION_DOCUMENT 8
98cdf0e10cSrcweir #define ICON_PRESENTATION_TEMPLATE 9
99cdf0e10cSrcweir #define ICON_PRESENTATION_COMPRESSED 10
100cdf0e10cSrcweir #define ICON_GLOBAL_DOCUMENT 11
101cdf0e10cSrcweir #define ICON_HTML_DOCUMENT 12
102cdf0e10cSrcweir #define ICON_CHART_DOCUMENT 13
103cdf0e10cSrcweir #define ICON_DATABASE_DOCUMENT 14
104cdf0e10cSrcweir #define ICON_MATH_DOCUMENT 15
105cdf0e10cSrcweir #define ICON_TEMPLATE 16
106cdf0e10cSrcweir #define ICON_MACROLIBRARY 17
107cdf0e10cSrcweir #define ICON_CONFIGURATION 18
108cdf0e10cSrcweir #define ICON_OPEN 5 // See index of open folder icon in shell32.dll
109cdf0e10cSrcweir #define ICON_SETUP 500
110cdf0e10cSrcweir
111cdf0e10cSrcweir #define SFX_TASKBAR_NOTIFICATION WM_USER+1
112cdf0e10cSrcweir
113cdf0e10cSrcweir static HWND aListenerWindow = NULL;
114cdf0e10cSrcweir static HWND aExecuterWindow = NULL;
115cdf0e10cSrcweir static HMENU popupMenu = NULL;
116cdf0e10cSrcweir
117cdf0e10cSrcweir static void OnMeasureItem(HWND hwnd, LPMEASUREITEMSTRUCT lpmis);
118cdf0e10cSrcweir static void OnDrawItem(HWND hwnd, LPDRAWITEMSTRUCT lpdis);
119cdf0e10cSrcweir
120cdf0e10cSrcweir typedef struct tagMYITEM
121cdf0e10cSrcweir {
122cdf0e10cSrcweir OUString text;
123cdf0e10cSrcweir OUString module;
124cdf0e10cSrcweir UINT iconId;
125cdf0e10cSrcweir } MYITEM;
126cdf0e10cSrcweir
127cdf0e10cSrcweir // -------------------------------
128cdf0e10cSrcweir
isNT()129cdf0e10cSrcweir static bool isNT()
130cdf0e10cSrcweir {
131cdf0e10cSrcweir static bool bInitialized = false;
132cdf0e10cSrcweir static bool bWnt = false;
133cdf0e10cSrcweir
134cdf0e10cSrcweir if( !bInitialized )
135cdf0e10cSrcweir {
136cdf0e10cSrcweir bInitialized = true;
137cdf0e10cSrcweir
138cdf0e10cSrcweir OSVERSIONINFO aVerInfo;
139cdf0e10cSrcweir aVerInfo.dwOSVersionInfoSize = sizeof( aVerInfo );
140cdf0e10cSrcweir if ( GetVersionEx( &aVerInfo ) )
141cdf0e10cSrcweir {
142cdf0e10cSrcweir if ( aVerInfo.dwPlatformId == VER_PLATFORM_WIN32_NT )
143cdf0e10cSrcweir bWnt = true;
144cdf0e10cSrcweir }
145cdf0e10cSrcweir }
146cdf0e10cSrcweir return bWnt;
147cdf0e10cSrcweir }
148cdf0e10cSrcweir
149cdf0e10cSrcweir
150cdf0e10cSrcweir // -------------------------------
151cdf0e10cSrcweir
addMenuItem(HMENU hMenu,UINT id,UINT iconId,const OUString & text,int & pos,int bOwnerdraw,const OUString & module)152cdf0e10cSrcweir static void addMenuItem( HMENU hMenu, UINT id, UINT iconId, const OUString& text, int& pos, int bOwnerdraw, const OUString& module )
153cdf0e10cSrcweir {
154cdf0e10cSrcweir MENUITEMINFOW mi;
155cdf0e10cSrcweir memset( &mi, 0, sizeof( MENUITEMINFOW ) );
156cdf0e10cSrcweir
157cdf0e10cSrcweir mi.cbSize = sizeof( MENUITEMINFOW );
158cdf0e10cSrcweir if( id == -1 )
159cdf0e10cSrcweir {
160cdf0e10cSrcweir mi.fMask=MIIM_TYPE;
161cdf0e10cSrcweir mi.fType=MFT_SEPARATOR;
162cdf0e10cSrcweir }
163cdf0e10cSrcweir else
164cdf0e10cSrcweir {
165cdf0e10cSrcweir if( bOwnerdraw )
166cdf0e10cSrcweir {
167cdf0e10cSrcweir mi.fMask=MIIM_TYPE | MIIM_STATE | MIIM_ID | MIIM_DATA;
168cdf0e10cSrcweir mi.fType=MFT_OWNERDRAW;
169cdf0e10cSrcweir mi.fState=MFS_ENABLED;
170cdf0e10cSrcweir mi.wID = id;
171cdf0e10cSrcweir
172cdf0e10cSrcweir MYITEM *pMyItem = new MYITEM;
173cdf0e10cSrcweir pMyItem->text = text;
174cdf0e10cSrcweir pMyItem->iconId = iconId;
175cdf0e10cSrcweir pMyItem->module = module;
176cdf0e10cSrcweir mi.dwItemData = (DWORD) pMyItem;
177cdf0e10cSrcweir }
178cdf0e10cSrcweir else
179cdf0e10cSrcweir {
180cdf0e10cSrcweir mi.fMask=MIIM_TYPE | MIIM_STATE | MIIM_ID | MIIM_DATA;
181cdf0e10cSrcweir mi.fType=MFT_STRING;
182cdf0e10cSrcweir mi.fState=MFS_ENABLED;
183cdf0e10cSrcweir mi.wID = id;
184cdf0e10cSrcweir mi.dwTypeData = (LPWSTR) text.getStr();
185cdf0e10cSrcweir mi.cch = text.getLength();
186cdf0e10cSrcweir }
187cdf0e10cSrcweir
188cdf0e10cSrcweir #if defined(USE_APP_SHORTCUTS)
189cdf0e10cSrcweir if ( IDM_TEMPLATE == id )
190cdf0e10cSrcweir mi.fState |= MFS_DEFAULT;
191cdf0e10cSrcweir #endif
192cdf0e10cSrcweir }
193cdf0e10cSrcweir
194cdf0e10cSrcweir InsertMenuItemW( hMenu, pos++, TRUE, &mi );
195cdf0e10cSrcweir }
196cdf0e10cSrcweir
197cdf0e10cSrcweir // -------------------------------
198cdf0e10cSrcweir
createSystrayMenu()199cdf0e10cSrcweir static HMENU createSystrayMenu( )
200cdf0e10cSrcweir {
201cdf0e10cSrcweir SvtModuleOptions aModuleOptions;
202cdf0e10cSrcweir
203cdf0e10cSrcweir HMENU hMenu = CreatePopupMenu();
204cdf0e10cSrcweir int pos=0;
205cdf0e10cSrcweir
206cdf0e10cSrcweir ShutdownIcon *pShutdownIcon = ShutdownIcon::getInstance();
207cdf0e10cSrcweir OSL_ENSURE( pShutdownIcon, "ShutdownIcon instance empty!");
208cdf0e10cSrcweir
209cdf0e10cSrcweir if( !pShutdownIcon )
210cdf0e10cSrcweir return NULL;
211cdf0e10cSrcweir
212cdf0e10cSrcweir #if defined(USE_APP_SHORTCUTS)
213cdf0e10cSrcweir // collect the URLs of the entries in the File/New menu
214cdf0e10cSrcweir ::std::set< ::rtl::OUString > aFileNewAppsAvailable;
215cdf0e10cSrcweir SvtDynamicMenuOptions aOpt;
216cdf0e10cSrcweir Sequence < Sequence < PropertyValue > > aNewMenu = aOpt.GetMenu( E_NEWMENU );
217cdf0e10cSrcweir const ::rtl::OUString sURLKey( RTL_CONSTASCII_USTRINGPARAM( "URL" ) );
218cdf0e10cSrcweir
219cdf0e10cSrcweir const Sequence< PropertyValue >* pNewMenu = aNewMenu.getConstArray();
220cdf0e10cSrcweir const Sequence< PropertyValue >* pNewMenuEnd = aNewMenu.getConstArray() + aNewMenu.getLength();
221cdf0e10cSrcweir for ( ; pNewMenu != pNewMenuEnd; ++pNewMenu )
222cdf0e10cSrcweir {
223cdf0e10cSrcweir ::comphelper::SequenceAsHashMap aEntryItems( *pNewMenu );
224cdf0e10cSrcweir ::rtl::OUString sURL( aEntryItems.getUnpackedValueOrDefault( sURLKey, ::rtl::OUString() ) );
225cdf0e10cSrcweir if ( sURL.getLength() )
226cdf0e10cSrcweir aFileNewAppsAvailable.insert( sURL );
227cdf0e10cSrcweir }
228cdf0e10cSrcweir
229cdf0e10cSrcweir // describe the menu entries for launching the applications
230cdf0e10cSrcweir struct MenuEntryDescriptor
231cdf0e10cSrcweir {
232cdf0e10cSrcweir SvtModuleOptions::EModule eModuleIdentifier;
233cdf0e10cSrcweir UINT nMenuItemID;
234cdf0e10cSrcweir UINT nMenuIconID;
235cdf0e10cSrcweir const char* pAsciiURLDescription;
236cdf0e10cSrcweir } aMenuItems[] =
237cdf0e10cSrcweir {
238cdf0e10cSrcweir { SvtModuleOptions::E_SWRITER, IDM_WRITER, ICON_TEXT_DOCUMENT, WRITER_URL },
239cdf0e10cSrcweir { SvtModuleOptions::E_SCALC, IDM_CALC, ICON_SPREADSHEET_DOCUMENT, CALC_URL },
240cdf0e10cSrcweir { SvtModuleOptions::E_SIMPRESS, IDM_IMPRESS,ICON_PRESENTATION_DOCUMENT, IMPRESS_WIZARD_URL },
241cdf0e10cSrcweir { SvtModuleOptions::E_SDRAW, IDM_DRAW, ICON_DRAWING_DOCUMENT, DRAW_URL },
242cdf0e10cSrcweir { SvtModuleOptions::E_SDATABASE, IDM_BASE, ICON_DATABASE_DOCUMENT, BASE_URL },
243cdf0e10cSrcweir { SvtModuleOptions::E_SMATH, IDM_MATH, ICON_MATH_DOCUMENT, MATH_URL },
244cdf0e10cSrcweir };
245cdf0e10cSrcweir
246cdf0e10cSrcweir OUString aEmpty;
247cdf0e10cSrcweir
248cdf0e10cSrcweir // insert the menu entries for launching the applications
249cdf0e10cSrcweir for ( size_t i = 0; i < sizeof( aMenuItems ) / sizeof( aMenuItems[0] ); ++i )
250cdf0e10cSrcweir {
251cdf0e10cSrcweir if ( !aModuleOptions.IsModuleInstalled( aMenuItems[i].eModuleIdentifier ) )
252cdf0e10cSrcweir // the complete application is not even installed
253cdf0e10cSrcweir continue;
254cdf0e10cSrcweir
255cdf0e10cSrcweir ::rtl::OUString sURL( ::rtl::OUString::createFromAscii( aMenuItems[i].pAsciiURLDescription ) );
256cdf0e10cSrcweir
257cdf0e10cSrcweir if ( aFileNewAppsAvailable.find( sURL ) == aFileNewAppsAvailable.end() )
258cdf0e10cSrcweir // the application is installed, but the entry has been configured to *not* appear in the File/New
259cdf0e10cSrcweir // menu => also let not appear it in the quickstarter
260cdf0e10cSrcweir continue;
261cdf0e10cSrcweir
262cdf0e10cSrcweir addMenuItem( hMenu, aMenuItems[i].nMenuItemID, aMenuItems[i].nMenuIconID,
263cdf0e10cSrcweir pShutdownIcon->GetUrlDescription( sURL ), pos, true, aEmpty );
264cdf0e10cSrcweir }
265cdf0e10cSrcweir
266cdf0e10cSrcweir
267cdf0e10cSrcweir
268cdf0e10cSrcweir // insert the remaining menu entries
269cdf0e10cSrcweir addMenuItem( hMenu, IDM_TEMPLATE, ICON_TEMPLATE,
270cdf0e10cSrcweir pShutdownIcon->GetResString( STR_QUICKSTART_FROMTEMPLATE ), pos, true, aEmpty);
271cdf0e10cSrcweir addMenuItem( hMenu, static_cast< UINT >( -1 ), 0, OUString(), pos, false, aEmpty );
272cdf0e10cSrcweir addMenuItem( hMenu, IDM_OPEN, ICON_OPEN, pShutdownIcon->GetResString( STR_QUICKSTART_FILEOPEN ), pos, true, OUString::createFromAscii( "SHELL32" ));
273cdf0e10cSrcweir addMenuItem( hMenu, static_cast< UINT >( -1 ), 0, OUString(), pos, false, aEmpty );
274cdf0e10cSrcweir #endif
275cdf0e10cSrcweir addMenuItem( hMenu, IDM_INSTALL,0, pShutdownIcon->GetResString( STR_QUICKSTART_PRELAUNCH ), pos, false, aEmpty );
276cdf0e10cSrcweir addMenuItem( hMenu, static_cast< UINT >( -1 ), 0, OUString(), pos, false, aEmpty );
277cdf0e10cSrcweir addMenuItem( hMenu, IDM_EXIT, 0, pShutdownIcon->GetResString( STR_QUICKSTART_EXIT ), pos, false, aEmpty );
278cdf0e10cSrcweir
279cdf0e10cSrcweir // indicate status of autostart folder
280cdf0e10cSrcweir CheckMenuItem( hMenu, IDM_INSTALL, MF_BYCOMMAND | (ShutdownIcon::GetAutostart() ? MF_CHECKED : MF_UNCHECKED) );
281cdf0e10cSrcweir
282cdf0e10cSrcweir return hMenu;
283cdf0e10cSrcweir }
284cdf0e10cSrcweir
285cdf0e10cSrcweir // -------------------------------
286cdf0e10cSrcweir
deleteSystrayMenu(HMENU hMenu)287cdf0e10cSrcweir static void deleteSystrayMenu( HMENU hMenu )
288cdf0e10cSrcweir {
289cdf0e10cSrcweir if( !hMenu || !IsMenu( hMenu ))
290cdf0e10cSrcweir return;
291cdf0e10cSrcweir
292cdf0e10cSrcweir MENUITEMINFOW mi;
293cdf0e10cSrcweir MYITEM *pMyItem;
294cdf0e10cSrcweir int pos=0;
295cdf0e10cSrcweir memset( &mi, 0, sizeof( mi ) );
296cdf0e10cSrcweir mi.cbSize = sizeof( mi );
297cdf0e10cSrcweir mi.fMask = MIIM_DATA;
298cdf0e10cSrcweir
299cdf0e10cSrcweir while( GetMenuItemInfoW( hMenu, pos++, true, &mi ) )
300cdf0e10cSrcweir {
301cdf0e10cSrcweir pMyItem = (MYITEM*) mi.dwItemData;
302cdf0e10cSrcweir if( pMyItem )
303cdf0e10cSrcweir {
304cdf0e10cSrcweir pMyItem->text = OUString();
305cdf0e10cSrcweir delete pMyItem;
306cdf0e10cSrcweir }
307cdf0e10cSrcweir mi.fMask = MIIM_DATA;
308cdf0e10cSrcweir }
309cdf0e10cSrcweir }
310cdf0e10cSrcweir
311cdf0e10cSrcweir // -------------------------------
312cdf0e10cSrcweir
addTaskbarIcon(HWND hWnd)313cdf0e10cSrcweir static void addTaskbarIcon( HWND hWnd )
314cdf0e10cSrcweir {
315cdf0e10cSrcweir OUString strTip;
316cdf0e10cSrcweir if( ShutdownIcon::getInstance() )
317cdf0e10cSrcweir strTip = ShutdownIcon::getInstance()->GetResString( STR_QUICKSTART_TIP );
318cdf0e10cSrcweir
319cdf0e10cSrcweir // add taskbar icon
320cdf0e10cSrcweir NOTIFYICONDATAA nid;
321cdf0e10cSrcweir nid.hIcon = (HICON)LoadImageA( GetModuleHandle( NULL ), MAKEINTRESOURCE( ICON_SO_DEFAULT ),
322cdf0e10cSrcweir IMAGE_ICON, GetSystemMetrics( SM_CXSMICON ), GetSystemMetrics( SM_CYSMICON ),
323cdf0e10cSrcweir LR_DEFAULTCOLOR | LR_SHARED );
324cdf0e10cSrcweir
325cdf0e10cSrcweir // better use unicode wrapper here ?
326cdf0e10cSrcweir strncpy( nid.szTip, ( OUStringToOString(strTip, osl_getThreadTextEncoding()).getStr() ), 64 );
327cdf0e10cSrcweir
328cdf0e10cSrcweir nid.cbSize = sizeof(nid);
329cdf0e10cSrcweir nid.hWnd = hWnd;
330cdf0e10cSrcweir nid.uID = ID_QUICKSTART;
331cdf0e10cSrcweir nid.uCallbackMessage = SFX_TASKBAR_NOTIFICATION;
332cdf0e10cSrcweir nid.uFlags = NIF_MESSAGE|NIF_TIP|NIF_ICON;
333cdf0e10cSrcweir
334cdf0e10cSrcweir Shell_NotifyIconA(NIM_ADD, &nid);
335cdf0e10cSrcweir }
336cdf0e10cSrcweir
337cdf0e10cSrcweir // -------------------------------
338cdf0e10cSrcweir
339cdf0e10cSrcweir /*
340cdf0e10cSrcweir static void removeTaskbarIcon()
341cdf0e10cSrcweir {
342cdf0e10cSrcweir ShutdownIcon *pShutdownIcon = ShutdownIcon::getInstance();
343cdf0e10cSrcweir OSL_ENSURE( pShutdownIcon, "ShutdownIcon instance empty!");
344cdf0e10cSrcweir
345cdf0e10cSrcweir if( !pShutdownIcon )
346cdf0e10cSrcweir return;
347cdf0e10cSrcweir
348cdf0e10cSrcweir if ( IsWindow( aListenerWindow ))
349cdf0e10cSrcweir {
350cdf0e10cSrcweir deleteSystrayMenu( popupMenu );
351cdf0e10cSrcweir
352cdf0e10cSrcweir NOTIFYICONDATAA nid;
353cdf0e10cSrcweir nid.cbSize=sizeof(NOTIFYICONDATA);
354cdf0e10cSrcweir nid.hWnd = aListenerWindow;
355cdf0e10cSrcweir nid.uID = ID_QUICKSTART;
356cdf0e10cSrcweir Shell_NotifyIconA(NIM_DELETE, &nid);
357cdf0e10cSrcweir }
358cdf0e10cSrcweir }
359cdf0e10cSrcweir */
360cdf0e10cSrcweir
361cdf0e10cSrcweir // -------------------------------
362cdf0e10cSrcweir
listenerWndProc(HWND hWnd,UINT uMsg,WPARAM wParam,LPARAM lParam)363cdf0e10cSrcweir LRESULT CALLBACK listenerWndProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
364cdf0e10cSrcweir {
365cdf0e10cSrcweir static UINT s_uTaskbarRestart = 0;
366cdf0e10cSrcweir static UINT s_uMsgKillTray = 0;
367cdf0e10cSrcweir
368cdf0e10cSrcweir switch (uMsg)
369cdf0e10cSrcweir {
370cdf0e10cSrcweir case WM_NCCREATE:
371cdf0e10cSrcweir return TRUE;
372cdf0e10cSrcweir case WM_CREATE:
373cdf0e10cSrcweir {
374cdf0e10cSrcweir // request notfication when taskbar is recreated
375cdf0e10cSrcweir // we then have to add our icon again
376cdf0e10cSrcweir s_uTaskbarRestart = RegisterWindowMessage(TEXT("TaskbarCreated"));
377cdf0e10cSrcweir s_uMsgKillTray = RegisterWindowMessage( SHUTDOWN_QUICKSTART_MESSAGE );
378cdf0e10cSrcweir
379cdf0e10cSrcweir // create the menu
380cdf0e10cSrcweir if( !popupMenu )
381cdf0e10cSrcweir if( (popupMenu = createSystrayMenu( )) == NULL )
382cdf0e10cSrcweir return -1;
383cdf0e10cSrcweir
384cdf0e10cSrcweir // and the icon
385cdf0e10cSrcweir addTaskbarIcon( hWnd );
386cdf0e10cSrcweir
387cdf0e10cSrcweir // disable shutdown
388cdf0e10cSrcweir ShutdownIcon::getInstance()->SetVeto( true );
389cdf0e10cSrcweir ShutdownIcon::getInstance()->addTerminateListener();
390cdf0e10cSrcweir }
391cdf0e10cSrcweir return 0;
392cdf0e10cSrcweir
393cdf0e10cSrcweir case WM_MEASUREITEM:
394cdf0e10cSrcweir OnMeasureItem(hWnd, (LPMEASUREITEMSTRUCT) lParam);
395cdf0e10cSrcweir return TRUE;
396cdf0e10cSrcweir
397cdf0e10cSrcweir case WM_DRAWITEM:
398cdf0e10cSrcweir OnDrawItem(hWnd, (LPDRAWITEMSTRUCT) lParam);
399cdf0e10cSrcweir return TRUE;
400cdf0e10cSrcweir
401cdf0e10cSrcweir case SFX_TASKBAR_NOTIFICATION:
402cdf0e10cSrcweir switch( lParam )
403cdf0e10cSrcweir {
404cdf0e10cSrcweir case WM_LBUTTONDBLCLK:
405cdf0e10cSrcweir #if defined(USE_APP_SHORTCUTS)
406cdf0e10cSrcweir PostMessage( aExecuterWindow, WM_COMMAND, IDM_TEMPLATE, (LPARAM)hWnd );
407cdf0e10cSrcweir #endif
408cdf0e10cSrcweir break;
409cdf0e10cSrcweir
410cdf0e10cSrcweir case WM_RBUTTONDOWN:
411cdf0e10cSrcweir {
412cdf0e10cSrcweir POINT pt;
413cdf0e10cSrcweir GetCursorPos(&pt);
414cdf0e10cSrcweir SetForegroundWindow( hWnd );
415cdf0e10cSrcweir
416cdf0e10cSrcweir // update status before showing menu, could have been changed from option page
417cdf0e10cSrcweir CheckMenuItem( popupMenu, IDM_INSTALL, MF_BYCOMMAND| (ShutdownIcon::GetAutostart() ? MF_CHECKED : MF_UNCHECKED) );
418cdf0e10cSrcweir
419cdf0e10cSrcweir EnableMenuItem( popupMenu, IDM_EXIT, MF_BYCOMMAND | (ShutdownIcon::bModalMode ? MF_GRAYED : MF_ENABLED) );
420cdf0e10cSrcweir #if defined(USE_APP_SHORTCUTS)
421cdf0e10cSrcweir EnableMenuItem( popupMenu, IDM_OPEN, MF_BYCOMMAND | (ShutdownIcon::bModalMode ? MF_GRAYED : MF_ENABLED) );
422cdf0e10cSrcweir EnableMenuItem( popupMenu, IDM_TEMPLATE, MF_BYCOMMAND | (ShutdownIcon::bModalMode ? MF_GRAYED : MF_ENABLED) );
423cdf0e10cSrcweir #endif
424cdf0e10cSrcweir int m = TrackPopupMenuEx( popupMenu, TPM_RETURNCMD|TPM_LEFTALIGN|TPM_RIGHTBUTTON,
425cdf0e10cSrcweir pt.x, pt.y, hWnd, NULL );
426cdf0e10cSrcweir // BUGFIX: See Q135788 (PRB: Menus for Notification Icons Don't Work Correctly)
427cdf0e10cSrcweir PostMessage( hWnd, NULL, 0, 0 );
428cdf0e10cSrcweir switch( m )
429cdf0e10cSrcweir {
430cdf0e10cSrcweir #if defined(USE_APP_SHORTCUTS)
431cdf0e10cSrcweir case IDM_OPEN:
432cdf0e10cSrcweir case IDM_WRITER:
433cdf0e10cSrcweir case IDM_CALC:
434cdf0e10cSrcweir case IDM_IMPRESS:
435cdf0e10cSrcweir case IDM_DRAW:
436cdf0e10cSrcweir case IDM_TEMPLATE:
437cdf0e10cSrcweir case IDM_BASE:
438cdf0e10cSrcweir case IDM_MATH:
439cdf0e10cSrcweir break;
440cdf0e10cSrcweir #endif
441cdf0e10cSrcweir case IDM_INSTALL:
442cdf0e10cSrcweir CheckMenuItem( popupMenu, IDM_INSTALL, MF_BYCOMMAND| (ShutdownIcon::GetAutostart() ? MF_CHECKED : MF_UNCHECKED) );
443cdf0e10cSrcweir break;
444cdf0e10cSrcweir case IDM_EXIT:
445cdf0e10cSrcweir // delete taskbar icon
446cdf0e10cSrcweir NOTIFYICONDATAA nid;
447cdf0e10cSrcweir nid.cbSize=sizeof(NOTIFYICONDATA);
448cdf0e10cSrcweir nid.hWnd = hWnd;
449cdf0e10cSrcweir nid.uID = ID_QUICKSTART;
450cdf0e10cSrcweir Shell_NotifyIconA(NIM_DELETE, &nid);
451cdf0e10cSrcweir break;
452cdf0e10cSrcweir }
453cdf0e10cSrcweir
454cdf0e10cSrcweir PostMessage( aExecuterWindow, WM_COMMAND, m, (LPARAM)hWnd );
455cdf0e10cSrcweir }
456cdf0e10cSrcweir break;
457cdf0e10cSrcweir }
458cdf0e10cSrcweir break;
459cdf0e10cSrcweir case WM_DESTROY:
460cdf0e10cSrcweir deleteSystrayMenu( popupMenu );
461cdf0e10cSrcweir // We don't need the Systray Thread anymore
462cdf0e10cSrcweir PostQuitMessage( 0 );
463cdf0e10cSrcweir return DefWindowProc(hWnd, uMsg, wParam, lParam);
464cdf0e10cSrcweir default:
465cdf0e10cSrcweir if( uMsg == s_uTaskbarRestart )
466cdf0e10cSrcweir {
467cdf0e10cSrcweir // re-create taskbar icon
468cdf0e10cSrcweir addTaskbarIcon( hWnd );
469cdf0e10cSrcweir }
470cdf0e10cSrcweir else if ( uMsg == s_uMsgKillTray )
471cdf0e10cSrcweir {
472cdf0e10cSrcweir // delete taskbar icon
473cdf0e10cSrcweir NOTIFYICONDATAA nid;
474cdf0e10cSrcweir nid.cbSize=sizeof(NOTIFYICONDATA);
475cdf0e10cSrcweir nid.hWnd = hWnd;
476cdf0e10cSrcweir nid.uID = ID_QUICKSTART;
477cdf0e10cSrcweir Shell_NotifyIconA(NIM_DELETE, &nid);
478cdf0e10cSrcweir
479cdf0e10cSrcweir PostMessage( aExecuterWindow, WM_COMMAND, IDM_EXIT, (LPARAM)hWnd );
480cdf0e10cSrcweir }
481cdf0e10cSrcweir else
482cdf0e10cSrcweir return DefWindowProc(hWnd, uMsg, wParam, lParam);
483cdf0e10cSrcweir }
484cdf0e10cSrcweir return 0;
485cdf0e10cSrcweir }
486cdf0e10cSrcweir
487cdf0e10cSrcweir // -------------------------------
488cdf0e10cSrcweir
checkOEM()489cdf0e10cSrcweir static sal_Bool checkOEM() {
490cdf0e10cSrcweir Reference<XMultiServiceFactory> rFactory = ::comphelper::getProcessServiceFactory();
491cdf0e10cSrcweir Reference<XJob> rOemJob(rFactory->createInstance(
492cdf0e10cSrcweir OUString::createFromAscii("com.sun.star.office.OEMPreloadJob")),
493cdf0e10cSrcweir UNO_QUERY );
494cdf0e10cSrcweir Sequence<NamedValue> args;
495cdf0e10cSrcweir sal_Bool bResult = sal_False;
496cdf0e10cSrcweir if (rOemJob.is())
497cdf0e10cSrcweir {
498cdf0e10cSrcweir Any aResult = rOemJob->execute(args);
499cdf0e10cSrcweir aResult >>= bResult;
500cdf0e10cSrcweir } else bResult = sal_True;
501cdf0e10cSrcweir return bResult;
502cdf0e10cSrcweir }
503cdf0e10cSrcweir
executerWndProc(HWND hWnd,UINT uMsg,WPARAM wParam,LPARAM lParam)504cdf0e10cSrcweir LRESULT CALLBACK executerWndProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
505cdf0e10cSrcweir {
506cdf0e10cSrcweir switch (uMsg)
507cdf0e10cSrcweir {
508cdf0e10cSrcweir case WM_NCCREATE:
509cdf0e10cSrcweir return TRUE;
510cdf0e10cSrcweir case WM_CREATE:
511cdf0e10cSrcweir return 0;
512cdf0e10cSrcweir
513cdf0e10cSrcweir case WM_COMMAND:
514cdf0e10cSrcweir switch( LOWORD(wParam) )
515cdf0e10cSrcweir {
516cdf0e10cSrcweir #if defined(USE_APP_SHORTCUTS)
517cdf0e10cSrcweir case IDM_OPEN:
518cdf0e10cSrcweir if ( !ShutdownIcon::bModalMode && checkOEM() )
519cdf0e10cSrcweir ShutdownIcon::FileOpen();
520cdf0e10cSrcweir break;
521cdf0e10cSrcweir case IDM_WRITER:
522cdf0e10cSrcweir if (checkOEM())
523cdf0e10cSrcweir ShutdownIcon::OpenURL( OUString( RTL_CONSTASCII_USTRINGPARAM( WRITER_URL ) ), OUString( RTL_CONSTASCII_USTRINGPARAM( "_default" ) ) );
524cdf0e10cSrcweir break;
525cdf0e10cSrcweir case IDM_CALC:
526cdf0e10cSrcweir if (checkOEM())
527cdf0e10cSrcweir ShutdownIcon::OpenURL( OUString( RTL_CONSTASCII_USTRINGPARAM( CALC_URL ) ), OUString( RTL_CONSTASCII_USTRINGPARAM( "_default" ) ) );
528cdf0e10cSrcweir break;
529cdf0e10cSrcweir case IDM_IMPRESS:
530cdf0e10cSrcweir if (checkOEM())
531cdf0e10cSrcweir ShutdownIcon::OpenURL( OUString( RTL_CONSTASCII_USTRINGPARAM( IMPRESS_WIZARD_URL ) ), OUString( RTL_CONSTASCII_USTRINGPARAM( "_default" ) ) );
532cdf0e10cSrcweir break;
533cdf0e10cSrcweir case IDM_DRAW:
534cdf0e10cSrcweir if (checkOEM())
535cdf0e10cSrcweir ShutdownIcon::OpenURL( OUString( RTL_CONSTASCII_USTRINGPARAM( DRAW_URL ) ), OUString( RTL_CONSTASCII_USTRINGPARAM( "_default" ) ) );
536cdf0e10cSrcweir break;
537cdf0e10cSrcweir case IDM_BASE:
538cdf0e10cSrcweir if (checkOEM())
539cdf0e10cSrcweir ShutdownIcon::OpenURL( OUString( RTL_CONSTASCII_USTRINGPARAM( BASE_URL ) ), OUString( RTL_CONSTASCII_USTRINGPARAM( "_default" ) ) );
540cdf0e10cSrcweir break;
541cdf0e10cSrcweir case IDM_MATH:
542cdf0e10cSrcweir if (checkOEM())
543cdf0e10cSrcweir ShutdownIcon::OpenURL( OUString( RTL_CONSTASCII_USTRINGPARAM( MATH_URL ) ), OUString( RTL_CONSTASCII_USTRINGPARAM( "_default" ) ) );
544cdf0e10cSrcweir break;
545cdf0e10cSrcweir case IDM_TEMPLATE:
546cdf0e10cSrcweir if ( !ShutdownIcon::bModalMode && checkOEM())
547cdf0e10cSrcweir ShutdownIcon::FromTemplate();
548cdf0e10cSrcweir break;
549cdf0e10cSrcweir #endif
550cdf0e10cSrcweir case IDM_INSTALL:
551cdf0e10cSrcweir ShutdownIcon::SetAutostart( !ShutdownIcon::GetAutostart() );
552cdf0e10cSrcweir break;
553cdf0e10cSrcweir case IDM_EXIT:
554cdf0e10cSrcweir // remove listener and
555cdf0e10cSrcweir // terminate office if running in background
556cdf0e10cSrcweir if ( !ShutdownIcon::bModalMode )
557cdf0e10cSrcweir ShutdownIcon::terminateDesktop();
558cdf0e10cSrcweir break;
559cdf0e10cSrcweir }
560cdf0e10cSrcweir break;
561cdf0e10cSrcweir case WM_DESTROY:
562cdf0e10cSrcweir default:
563cdf0e10cSrcweir return DefWindowProc(hWnd, uMsg, wParam, lParam);
564cdf0e10cSrcweir }
565cdf0e10cSrcweir return 0;
566cdf0e10cSrcweir }
567cdf0e10cSrcweir
568cdf0e10cSrcweir // -------------------------------
569cdf0e10cSrcweir
570cdf0e10cSrcweir
SystrayThread(LPVOID)571cdf0e10cSrcweir DWORD WINAPI SystrayThread( LPVOID /*lpParam*/ )
572cdf0e10cSrcweir {
573cdf0e10cSrcweir aListenerWindow = CreateWindowExA(0,
574cdf0e10cSrcweir QUICKSTART_CLASSNAME, // registered class name
575cdf0e10cSrcweir QUICKSTART_WINDOWNAME, // window name
576cdf0e10cSrcweir 0, // window style
577cdf0e10cSrcweir CW_USEDEFAULT, // horizontal position of window
578cdf0e10cSrcweir CW_USEDEFAULT, // vertical position of window
579cdf0e10cSrcweir CW_USEDEFAULT, // window width
580cdf0e10cSrcweir CW_USEDEFAULT, // window height
581cdf0e10cSrcweir (HWND) NULL, // handle to parent or owner window
582cdf0e10cSrcweir NULL, // menu handle or child identifier
583cdf0e10cSrcweir (HINSTANCE) GetModuleHandle( NULL ), // handle to application instance
584cdf0e10cSrcweir NULL // window-creation data
585cdf0e10cSrcweir );
586cdf0e10cSrcweir
587cdf0e10cSrcweir MSG msg;
588cdf0e10cSrcweir
589cdf0e10cSrcweir while ( GetMessage( &msg, NULL, 0, 0 ) )
590cdf0e10cSrcweir {
591cdf0e10cSrcweir TranslateMessage( &msg );
592cdf0e10cSrcweir DispatchMessage( &msg );
593cdf0e10cSrcweir }
594cdf0e10cSrcweir
595cdf0e10cSrcweir return msg.wParam; // Exit code of WM_QUIT
596cdf0e10cSrcweir }
597cdf0e10cSrcweir
598cdf0e10cSrcweir // -------------------------------
599cdf0e10cSrcweir
win32_init_sys_tray()600cdf0e10cSrcweir void win32_init_sys_tray()
601cdf0e10cSrcweir {
602cdf0e10cSrcweir if ( ShutdownIcon::IsQuickstarterInstalled() )
603cdf0e10cSrcweir {
604cdf0e10cSrcweir WNDCLASSEXA listenerClass;
605cdf0e10cSrcweir listenerClass.cbSize = sizeof(WNDCLASSEX);
606cdf0e10cSrcweir listenerClass.style = 0;
607cdf0e10cSrcweir listenerClass.lpfnWndProc = listenerWndProc;
608cdf0e10cSrcweir listenerClass.cbClsExtra = 0;
609cdf0e10cSrcweir listenerClass.cbWndExtra = 0;
610cdf0e10cSrcweir listenerClass.hInstance = (HINSTANCE) GetModuleHandle( NULL );
611cdf0e10cSrcweir listenerClass.hIcon = NULL;
612cdf0e10cSrcweir listenerClass.hCursor = NULL;
613cdf0e10cSrcweir listenerClass.hbrBackground = NULL;
614cdf0e10cSrcweir listenerClass.lpszMenuName = NULL;
615cdf0e10cSrcweir listenerClass.lpszClassName = QUICKSTART_CLASSNAME;
616cdf0e10cSrcweir listenerClass.hIconSm = NULL;
617cdf0e10cSrcweir
618cdf0e10cSrcweir RegisterClassExA(&listenerClass);
619cdf0e10cSrcweir
620cdf0e10cSrcweir WNDCLASSEXA executerClass;
621cdf0e10cSrcweir executerClass.cbSize = sizeof(WNDCLASSEX);
622cdf0e10cSrcweir executerClass.style = 0;
623cdf0e10cSrcweir executerClass.lpfnWndProc = executerWndProc;
624cdf0e10cSrcweir executerClass.cbClsExtra = 0;
625cdf0e10cSrcweir executerClass.cbWndExtra = 0;
626cdf0e10cSrcweir executerClass.hInstance = (HINSTANCE) GetModuleHandle( NULL );
627cdf0e10cSrcweir executerClass.hIcon = NULL;
628cdf0e10cSrcweir executerClass.hCursor = NULL;
629cdf0e10cSrcweir executerClass.hbrBackground = NULL;
630cdf0e10cSrcweir executerClass.lpszMenuName = NULL;
631cdf0e10cSrcweir executerClass.lpszClassName = EXECUTER_WINDOWCLASS;
632cdf0e10cSrcweir executerClass.hIconSm = NULL;
633cdf0e10cSrcweir
634cdf0e10cSrcweir RegisterClassExA( &executerClass );
635cdf0e10cSrcweir
636cdf0e10cSrcweir aExecuterWindow = CreateWindowExA(0,
637cdf0e10cSrcweir EXECUTER_WINDOWCLASS, // registered class name
638cdf0e10cSrcweir EXECUTER_WINDOWNAME, // window name
639cdf0e10cSrcweir 0, // window style
640cdf0e10cSrcweir CW_USEDEFAULT, // horizontal position of window
641cdf0e10cSrcweir CW_USEDEFAULT, // vertical position of window
642cdf0e10cSrcweir CW_USEDEFAULT, // window width
643cdf0e10cSrcweir CW_USEDEFAULT, // window height
644cdf0e10cSrcweir (HWND) NULL, // handle to parent or owner window
645cdf0e10cSrcweir NULL, // menu handle or child identifier
646cdf0e10cSrcweir (HINSTANCE) GetModuleHandle( NULL ), // handle to application instance
647cdf0e10cSrcweir NULL // window-creation data
648cdf0e10cSrcweir );
649cdf0e10cSrcweir
650cdf0e10cSrcweir DWORD dwThreadId;
651cdf0e10cSrcweir CreateThread( NULL, 0, SystrayThread, NULL, 0, &dwThreadId );
652cdf0e10cSrcweir }
653cdf0e10cSrcweir }
654cdf0e10cSrcweir
655cdf0e10cSrcweir // -------------------------------
656cdf0e10cSrcweir
win32_shutdown_sys_tray()657cdf0e10cSrcweir void win32_shutdown_sys_tray()
658cdf0e10cSrcweir {
659cdf0e10cSrcweir if ( ShutdownIcon::IsQuickstarterInstalled() )
660cdf0e10cSrcweir {
661cdf0e10cSrcweir if( IsWindow( aListenerWindow ) )
662cdf0e10cSrcweir {
663cdf0e10cSrcweir DestroyWindow( aListenerWindow );
664cdf0e10cSrcweir aListenerWindow = NULL;
665cdf0e10cSrcweir DestroyWindow( aExecuterWindow );
666cdf0e10cSrcweir aExecuterWindow = NULL;
667cdf0e10cSrcweir }
668cdf0e10cSrcweir UnregisterClassA( QUICKSTART_CLASSNAME, GetModuleHandle( NULL ) );
669cdf0e10cSrcweir UnregisterClassA( EXECUTER_WINDOWCLASS, GetModuleHandle( NULL ) );
670cdf0e10cSrcweir }
671cdf0e10cSrcweir }
672cdf0e10cSrcweir
673cdf0e10cSrcweir
674cdf0e10cSrcweir
675cdf0e10cSrcweir // -------------------------------
676cdf0e10cSrcweir
OnMeasureItem(HWND hwnd,LPMEASUREITEMSTRUCT lpmis)677cdf0e10cSrcweir void OnMeasureItem(HWND hwnd, LPMEASUREITEMSTRUCT lpmis)
678cdf0e10cSrcweir {
679cdf0e10cSrcweir MYITEM *pMyItem = (MYITEM *) lpmis->itemData;
680cdf0e10cSrcweir HDC hdc = GetDC(hwnd);
681cdf0e10cSrcweir SIZE size;
682cdf0e10cSrcweir
683cdf0e10cSrcweir NONCLIENTMETRICS ncm;
684cdf0e10cSrcweir memset(&ncm, 0, sizeof(ncm));
685cdf0e10cSrcweir ncm.cbSize = sizeof(ncm);
686cdf0e10cSrcweir
687cdf0e10cSrcweir SystemParametersInfo(SPI_GETNONCLIENTMETRICS, 0, (PVOID) &ncm, 0);
688cdf0e10cSrcweir
689cdf0e10cSrcweir // Assume every menu item can be default and printed bold
690cdf0e10cSrcweir ncm.lfMenuFont.lfWeight = FW_BOLD;
691cdf0e10cSrcweir
692cdf0e10cSrcweir HFONT hfntOld = (HFONT) SelectObject(hdc, (HFONT) CreateFontIndirect( &ncm.lfMenuFont ));
693cdf0e10cSrcweir
694cdf0e10cSrcweir GetTextExtentPoint32W(hdc, reinterpret_cast<LPCWSTR>(pMyItem->text.getStr()),
695cdf0e10cSrcweir pMyItem->text.getLength(), &size);
696cdf0e10cSrcweir
697cdf0e10cSrcweir lpmis->itemWidth = size.cx + 4 + GetSystemMetrics( SM_CXSMICON );
698cdf0e10cSrcweir lpmis->itemHeight = (size.cy > GetSystemMetrics( SM_CYSMICON )) ? size.cy : GetSystemMetrics( SM_CYSMICON );
699cdf0e10cSrcweir lpmis->itemHeight += 4;
700cdf0e10cSrcweir
701cdf0e10cSrcweir DeleteObject( SelectObject(hdc, hfntOld) );
702cdf0e10cSrcweir ReleaseDC(hwnd, hdc);
703cdf0e10cSrcweir }
704cdf0e10cSrcweir
OnDrawItem(HWND,LPDRAWITEMSTRUCT lpdis)705cdf0e10cSrcweir void OnDrawItem(HWND /*hwnd*/, LPDRAWITEMSTRUCT lpdis)
706cdf0e10cSrcweir {
707cdf0e10cSrcweir MYITEM *pMyItem = (MYITEM *) lpdis->itemData;
708cdf0e10cSrcweir COLORREF clrPrevText, clrPrevBkgnd;
709cdf0e10cSrcweir HFONT hfntOld;
710cdf0e10cSrcweir HBRUSH hbrOld;
711cdf0e10cSrcweir int x, y;
712cdf0e10cSrcweir BOOL fSelected = lpdis->itemState & ODS_SELECTED;
713cdf0e10cSrcweir BOOL fDisabled = lpdis->itemState & (ODS_DISABLED | ODS_GRAYED);
714cdf0e10cSrcweir
715cdf0e10cSrcweir // Set the appropriate foreground and background colors.
716cdf0e10cSrcweir
717cdf0e10cSrcweir RECT aRect = lpdis->rcItem;
718cdf0e10cSrcweir
719cdf0e10cSrcweir clrPrevBkgnd = SetBkColor( lpdis->hDC, GetSysColor(COLOR_MENU) );
720cdf0e10cSrcweir
721cdf0e10cSrcweir if ( fDisabled )
722cdf0e10cSrcweir clrPrevText = SetTextColor( lpdis->hDC, GetSysColor( COLOR_GRAYTEXT ) );
723cdf0e10cSrcweir else
724cdf0e10cSrcweir clrPrevText = SetTextColor( lpdis->hDC, GetSysColor( fSelected ? COLOR_HIGHLIGHTTEXT : COLOR_MENUTEXT ) );
725cdf0e10cSrcweir
726cdf0e10cSrcweir if ( fSelected )
727cdf0e10cSrcweir clrPrevBkgnd = SetBkColor( lpdis->hDC, GetSysColor(COLOR_HIGHLIGHT) );
728cdf0e10cSrcweir else
729cdf0e10cSrcweir clrPrevBkgnd = SetBkColor( lpdis->hDC, GetSysColor(COLOR_MENU) );
730cdf0e10cSrcweir
731cdf0e10cSrcweir hbrOld = (HBRUSH)SelectObject( lpdis->hDC, CreateSolidBrush( GetBkColor( lpdis->hDC ) ) );
732cdf0e10cSrcweir
733cdf0e10cSrcweir // Fill background
734cdf0e10cSrcweir PatBlt(lpdis->hDC, aRect.left, aRect.top, aRect.right-aRect.left, aRect.bottom-aRect.top, PATCOPY);
735cdf0e10cSrcweir
736cdf0e10cSrcweir int height = aRect.bottom-aRect.top;
737cdf0e10cSrcweir
738cdf0e10cSrcweir x = aRect.left;
739cdf0e10cSrcweir y = aRect.top;
740cdf0e10cSrcweir
741cdf0e10cSrcweir int cx = GetSystemMetrics( SM_CXSMICON );
742cdf0e10cSrcweir int cy = GetSystemMetrics( SM_CYSMICON );
743cdf0e10cSrcweir HICON hIcon( 0 );
744cdf0e10cSrcweir HMODULE hModule( GetModuleHandle( NULL ) );
745cdf0e10cSrcweir
746cdf0e10cSrcweir if ( pMyItem->module.getLength() > 0 )
747cdf0e10cSrcweir {
748cdf0e10cSrcweir LPCWSTR pModuleName = reinterpret_cast<LPCWSTR>( pMyItem->module.getStr() );
749cdf0e10cSrcweir hModule = GetModuleHandleW( pModuleName );
750cdf0e10cSrcweir if ( hModule == NULL )
751cdf0e10cSrcweir {
752cdf0e10cSrcweir LoadLibraryW( pModuleName );
753cdf0e10cSrcweir hModule = GetModuleHandleW( pModuleName );
754cdf0e10cSrcweir }
755cdf0e10cSrcweir }
756cdf0e10cSrcweir
757cdf0e10cSrcweir hIcon = (HICON) LoadImageA( hModule, MAKEINTRESOURCE( pMyItem->iconId ),
758cdf0e10cSrcweir IMAGE_ICON, cx, cy,
759cdf0e10cSrcweir LR_DEFAULTCOLOR | LR_SHARED );
760cdf0e10cSrcweir
761cdf0e10cSrcweir // DrawIconEx( lpdis->hDC, x, y+(height-cy)/2, hIcon, cx, cy, 0, NULL, DI_NORMAL );
762cdf0e10cSrcweir
763cdf0e10cSrcweir HBRUSH hbrIcon = CreateSolidBrush( GetSysColor( COLOR_GRAYTEXT ) );
764cdf0e10cSrcweir
765cdf0e10cSrcweir DrawStateW( lpdis->hDC, (HBRUSH)hbrIcon, (DRAWSTATEPROC)NULL, (LPARAM)hIcon, (WPARAM)0, x, y+(height-cy)/2, 0, 0, DST_ICON | (fDisabled ? (fSelected ? DSS_MONO : DSS_DISABLED) : DSS_NORMAL) );
766cdf0e10cSrcweir
767cdf0e10cSrcweir DeleteObject( hbrIcon );
768cdf0e10cSrcweir
769cdf0e10cSrcweir x += cx + 4; // space for icon
770cdf0e10cSrcweir aRect.left = x;
771cdf0e10cSrcweir
772cdf0e10cSrcweir NONCLIENTMETRICS ncm;
773cdf0e10cSrcweir memset(&ncm, 0, sizeof(ncm));
774cdf0e10cSrcweir ncm.cbSize = sizeof(ncm);
775cdf0e10cSrcweir
776cdf0e10cSrcweir SystemParametersInfo(SPI_GETNONCLIENTMETRICS, 0, (PVOID) &ncm, 0);
777cdf0e10cSrcweir
778cdf0e10cSrcweir // Print default menu entry with bold font
779cdf0e10cSrcweir if ( lpdis->itemState & ODS_DEFAULT )
780cdf0e10cSrcweir ncm.lfMenuFont.lfWeight = FW_BOLD;
781cdf0e10cSrcweir
782cdf0e10cSrcweir hfntOld = (HFONT) SelectObject(lpdis->hDC, (HFONT) CreateFontIndirect( &ncm.lfMenuFont ));
783cdf0e10cSrcweir
784cdf0e10cSrcweir
785cdf0e10cSrcweir SIZE size;
786cdf0e10cSrcweir GetTextExtentPointW( lpdis->hDC, reinterpret_cast<LPCWSTR>(pMyItem->text.getStr()), pMyItem->text.getLength(), &size );
787cdf0e10cSrcweir
788cdf0e10cSrcweir DrawStateW( lpdis->hDC, (HBRUSH)NULL, (DRAWSTATEPROC)NULL, (LPARAM)pMyItem->text.getStr(), (WPARAM)0, aRect.left, aRect.top + (height - size.cy)/2, 0, 0, DST_TEXT | (fDisabled && !fSelected ? DSS_DISABLED : DSS_NORMAL) );
789cdf0e10cSrcweir
790cdf0e10cSrcweir // Restore the original font and colors.
791cdf0e10cSrcweir DeleteObject( SelectObject( lpdis->hDC, hbrOld ) );
792cdf0e10cSrcweir DeleteObject( SelectObject( lpdis->hDC, hfntOld) );
793cdf0e10cSrcweir SetTextColor(lpdis->hDC, clrPrevText);
794cdf0e10cSrcweir SetBkColor(lpdis->hDC, clrPrevBkgnd);
795cdf0e10cSrcweir }
796cdf0e10cSrcweir
797cdf0e10cSrcweir // -------------------------------
798cdf0e10cSrcweir // code from setup2 project
799cdf0e10cSrcweir // -------------------------------
800cdf0e10cSrcweir
_SHFree(void * pv)801cdf0e10cSrcweir void _SHFree( void *pv )
802cdf0e10cSrcweir {
803cdf0e10cSrcweir IMalloc *pMalloc;
804cdf0e10cSrcweir if( NOERROR == SHGetMalloc(&pMalloc) )
805cdf0e10cSrcweir {
806cdf0e10cSrcweir pMalloc->Free( pv );
807cdf0e10cSrcweir pMalloc->Release();
808cdf0e10cSrcweir }
809cdf0e10cSrcweir }
810cdf0e10cSrcweir
811cdf0e10cSrcweir #define ALLOC(type, n) ((type *) HeapAlloc(GetProcessHeap(), 0, sizeof(type) * n ))
812cdf0e10cSrcweir #define FREE(p) HeapFree(GetProcessHeap(), 0, p)
813cdf0e10cSrcweir
_SHGetSpecialFolder(int nFolderID)814cdf0e10cSrcweir static OUString _SHGetSpecialFolder( int nFolderID )
815cdf0e10cSrcweir {
816cdf0e10cSrcweir
817cdf0e10cSrcweir LPITEMIDLIST pidl;
818cdf0e10cSrcweir HRESULT hHdl = SHGetSpecialFolderLocation( NULL, nFolderID, &pidl );
819cdf0e10cSrcweir OUString aFolder;
820cdf0e10cSrcweir
821cdf0e10cSrcweir if( hHdl == NOERROR )
822cdf0e10cSrcweir {
823cdf0e10cSrcweir WCHAR *lpFolderA;
824cdf0e10cSrcweir lpFolderA = ALLOC( WCHAR, 16000 );
825cdf0e10cSrcweir
826cdf0e10cSrcweir SHGetPathFromIDListW( pidl, lpFolderA );
827cdf0e10cSrcweir aFolder = OUString( reinterpret_cast<const sal_Unicode*>(lpFolderA) );
828cdf0e10cSrcweir
829cdf0e10cSrcweir FREE( lpFolderA );
830cdf0e10cSrcweir _SHFree( pidl );
831cdf0e10cSrcweir }
832cdf0e10cSrcweir return aFolder;
833cdf0e10cSrcweir }
834cdf0e10cSrcweir
GetAutostartFolderNameW32()835cdf0e10cSrcweir OUString ShutdownIcon::GetAutostartFolderNameW32()
836cdf0e10cSrcweir {
837cdf0e10cSrcweir return _SHGetSpecialFolder(CSIDL_STARTUP);
838cdf0e10cSrcweir }
839cdf0e10cSrcweir
SHCoCreateInstance(LPVOID lpszReserved,REFCLSID clsid,LPUNKNOWN pUnkUnknown,REFIID iid,LPVOID * ppv)840cdf0e10cSrcweir static HRESULT WINAPI SHCoCreateInstance( LPVOID lpszReserved, REFCLSID clsid, LPUNKNOWN pUnkUnknown, REFIID iid, LPVOID *ppv )
841cdf0e10cSrcweir {
842cdf0e10cSrcweir HRESULT hResult = E_NOTIMPL;
843cdf0e10cSrcweir HMODULE hModShell = GetModuleHandle( "SHELL32" );
844cdf0e10cSrcweir
845cdf0e10cSrcweir if ( hModShell != NULL )
846cdf0e10cSrcweir {
847cdf0e10cSrcweir typedef HRESULT (WINAPI *SHCoCreateInstance_PROC)( LPVOID lpszReserved, REFCLSID clsid, LPUNKNOWN pUnkUnknwon, REFIID iid, LPVOID *ppv );
848cdf0e10cSrcweir
849cdf0e10cSrcweir SHCoCreateInstance_PROC lpfnSHCoCreateInstance = (SHCoCreateInstance_PROC)GetProcAddress( hModShell, MAKEINTRESOURCE(102) );
850cdf0e10cSrcweir
851cdf0e10cSrcweir if ( lpfnSHCoCreateInstance )
852cdf0e10cSrcweir hResult = lpfnSHCoCreateInstance( lpszReserved, clsid, pUnkUnknown, iid, ppv );
853cdf0e10cSrcweir }
854cdf0e10cSrcweir return hResult;
855cdf0e10cSrcweir }
856cdf0e10cSrcweir
CreateShortcut(const OUString & rAbsObject,const OUString & rAbsObjectPath,const OUString & rAbsShortcut,const OUString & rDescription,const OUString & rParameter)857cdf0e10cSrcweir BOOL CreateShortcut( const OUString& rAbsObject, const OUString& rAbsObjectPath,
858cdf0e10cSrcweir const OUString& rAbsShortcut, const OUString& rDescription, const OUString& rParameter )
859cdf0e10cSrcweir {
860cdf0e10cSrcweir HRESULT hres;
861cdf0e10cSrcweir IShellLink* psl;
862cdf0e10cSrcweir CLSID clsid_ShellLink = CLSID_ShellLink;
863cdf0e10cSrcweir CLSID clsid_IShellLink = IID_IShellLink;
864cdf0e10cSrcweir
865cdf0e10cSrcweir hres = CoCreateInstance( clsid_ShellLink, NULL, CLSCTX_INPROC_SERVER,
866cdf0e10cSrcweir clsid_IShellLink, (void**)&psl );
867cdf0e10cSrcweir if( FAILED(hres) )
868cdf0e10cSrcweir hres = SHCoCreateInstance( NULL, clsid_ShellLink, NULL, clsid_IShellLink, (void**)&psl );
869cdf0e10cSrcweir
870cdf0e10cSrcweir if( SUCCEEDED(hres) )
871cdf0e10cSrcweir {
872cdf0e10cSrcweir IPersistFile* ppf;
873cdf0e10cSrcweir psl->SetPath( OUStringToOString(rAbsObject, osl_getThreadTextEncoding()).getStr() );
874cdf0e10cSrcweir psl->SetWorkingDirectory( OUStringToOString(rAbsObjectPath, osl_getThreadTextEncoding()).getStr() );
875cdf0e10cSrcweir psl->SetDescription( OUStringToOString(rDescription, osl_getThreadTextEncoding()).getStr() );
876cdf0e10cSrcweir if( rParameter.getLength() )
877cdf0e10cSrcweir psl->SetArguments( OUStringToOString(rParameter, osl_getThreadTextEncoding()).getStr() );
878cdf0e10cSrcweir
879cdf0e10cSrcweir CLSID clsid_IPersistFile = IID_IPersistFile;
880cdf0e10cSrcweir hres = psl->QueryInterface( clsid_IPersistFile, (void**)&ppf );
881cdf0e10cSrcweir
882cdf0e10cSrcweir if( SUCCEEDED(hres) )
883cdf0e10cSrcweir {
884cdf0e10cSrcweir hres = ppf->Save( reinterpret_cast<LPCOLESTR>(rAbsShortcut.getStr()), TRUE );
885cdf0e10cSrcweir ppf->Release();
886cdf0e10cSrcweir } else return FALSE;
887cdf0e10cSrcweir psl->Release();
888cdf0e10cSrcweir } else return FALSE;
889cdf0e10cSrcweir return TRUE;
890cdf0e10cSrcweir }
891cdf0e10cSrcweir
892cdf0e10cSrcweir // ------------------
893cdf0e10cSrcweir // install/uninstall
894cdf0e10cSrcweir
FileExistsW(LPCWSTR lpPath)895cdf0e10cSrcweir static bool FileExistsW( LPCWSTR lpPath )
896cdf0e10cSrcweir {
897cdf0e10cSrcweir bool bExists = false;
898cdf0e10cSrcweir WIN32_FIND_DATAW aFindData;
899cdf0e10cSrcweir
900cdf0e10cSrcweir HANDLE hFind = FindFirstFileW( lpPath, &aFindData );
901cdf0e10cSrcweir
902cdf0e10cSrcweir if ( INVALID_HANDLE_VALUE != hFind )
903cdf0e10cSrcweir {
904cdf0e10cSrcweir bExists = true;
905cdf0e10cSrcweir FindClose( hFind );
906cdf0e10cSrcweir }
907cdf0e10cSrcweir
908cdf0e10cSrcweir return bExists;
909cdf0e10cSrcweir }
910cdf0e10cSrcweir
IsQuickstarterInstalled()911cdf0e10cSrcweir bool ShutdownIcon::IsQuickstarterInstalled()
912cdf0e10cSrcweir {
913cdf0e10cSrcweir wchar_t aPath[_MAX_PATH];
914cdf0e10cSrcweir if( isNT() )
915cdf0e10cSrcweir {
916cdf0e10cSrcweir GetModuleFileNameW( NULL, aPath, _MAX_PATH-1);
917cdf0e10cSrcweir }
918cdf0e10cSrcweir else
919cdf0e10cSrcweir {
920cdf0e10cSrcweir char szPathA[_MAX_PATH];
921cdf0e10cSrcweir GetModuleFileNameA( NULL, szPathA, _MAX_PATH-1);
922cdf0e10cSrcweir
923cdf0e10cSrcweir // calc the string wcstr len
924cdf0e10cSrcweir int nNeededWStrBuffSize = MultiByteToWideChar( CP_ACP, 0, szPathA, -1, NULL, 0 );
925cdf0e10cSrcweir
926cdf0e10cSrcweir // copy the string if necessary
927cdf0e10cSrcweir if ( nNeededWStrBuffSize > 0 )
928cdf0e10cSrcweir MultiByteToWideChar( CP_ACP, 0, szPathA, -1, aPath, nNeededWStrBuffSize );
929cdf0e10cSrcweir }
930cdf0e10cSrcweir
931cdf0e10cSrcweir OUString aOfficepath( reinterpret_cast<const sal_Unicode*>(aPath) );
932cdf0e10cSrcweir int i = aOfficepath.lastIndexOf((sal_Char) '\\');
933cdf0e10cSrcweir if( i != -1 )
934cdf0e10cSrcweir aOfficepath = aOfficepath.copy(0, i);
935cdf0e10cSrcweir
936cdf0e10cSrcweir OUString quickstartExe(aOfficepath);
937cdf0e10cSrcweir quickstartExe += OUString( RTL_CONSTASCII_USTRINGPARAM( "\\quickstart.exe" ) );
938cdf0e10cSrcweir
939cdf0e10cSrcweir return FileExistsW( reinterpret_cast<LPCWSTR>(quickstartExe.getStr()) );
940cdf0e10cSrcweir }
941cdf0e10cSrcweir
EnableAutostartW32(const rtl::OUString & aShortcut)942cdf0e10cSrcweir void ShutdownIcon::EnableAutostartW32( const rtl::OUString &aShortcut )
943cdf0e10cSrcweir {
944cdf0e10cSrcweir wchar_t aPath[_MAX_PATH];
945cdf0e10cSrcweir if( isNT() )
946cdf0e10cSrcweir GetModuleFileNameW( NULL, aPath, _MAX_PATH-1);
947cdf0e10cSrcweir else
948cdf0e10cSrcweir {
949cdf0e10cSrcweir char szPathA[_MAX_PATH];
950cdf0e10cSrcweir GetModuleFileNameA( NULL, szPathA, _MAX_PATH-1);
951cdf0e10cSrcweir
952cdf0e10cSrcweir // calc the string wcstr len
953cdf0e10cSrcweir int nNeededWStrBuffSize = MultiByteToWideChar( CP_ACP, 0, szPathA, -1, NULL, 0 );
954cdf0e10cSrcweir
955cdf0e10cSrcweir // copy the string if necessary
956cdf0e10cSrcweir if ( nNeededWStrBuffSize > 0 )
957cdf0e10cSrcweir MultiByteToWideChar( CP_ACP, 0, szPathA, -1, aPath, nNeededWStrBuffSize );
958cdf0e10cSrcweir }
959cdf0e10cSrcweir
960cdf0e10cSrcweir OUString aOfficepath( reinterpret_cast<const sal_Unicode*>(aPath) );
961cdf0e10cSrcweir int i = aOfficepath.lastIndexOf((sal_Char) '\\');
962cdf0e10cSrcweir if( i != -1 )
963cdf0e10cSrcweir aOfficepath = aOfficepath.copy(0, i);
964cdf0e10cSrcweir
965cdf0e10cSrcweir OUString quickstartExe(aOfficepath);
966cdf0e10cSrcweir quickstartExe += OUString( RTL_CONSTASCII_USTRINGPARAM( "\\quickstart.exe" ) );
967cdf0e10cSrcweir
968cdf0e10cSrcweir CreateShortcut( quickstartExe, aOfficepath, aShortcut, OUString(), OUString() );
969cdf0e10cSrcweir }
970cdf0e10cSrcweir
971cdf0e10cSrcweir #endif // WNT
972cdf0e10cSrcweir
973cdf0e10cSrcweir
974