1 /************************************************************************* 2 * 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * Copyright 2000, 2010 Oracle and/or its affiliates. 6 * 7 * OpenOffice.org - a multi-platform office productivity suite 8 * 9 * This file is part of OpenOffice.org. 10 * 11 * OpenOffice.org is free software: you can redistribute it and/or modify 12 * it under the terms of the GNU Lesser General Public License version 3 13 * only, as published by the Free Software Foundation. 14 * 15 * OpenOffice.org is distributed in the hope that it will be useful, 16 * but WITHOUT ANY WARRANTY; without even the implied warranty of 17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18 * GNU Lesser General Public License version 3 for more details 19 * (a copy is included in the LICENSE file that accompanied this code). 20 * 21 * You should have received a copy of the GNU Lesser General Public License 22 * version 3 along with OpenOffice.org. If not, see 23 * <http://www.openoffice.org/license.html> 24 * for a copy of the LGPLv3 License. 25 * 26 ************************************************************************/ 27 28 // MARKER(update_precomp.py): autogen include statement, do not remove 29 #include "precompiled_desktop.hxx" 30 31 #include "dp_gui_shared.hxx" 32 #include "dp_gui.h" 33 #include "dp_gui_theextmgr.hxx" 34 #include "cppuhelper/implbase2.hxx" 35 #include "cppuhelper/implementationentry.hxx" 36 #include "unotools/configmgr.hxx" 37 #include "comphelper/servicedecl.hxx" 38 #include "comphelper/unwrapargs.hxx" 39 #include <i18npool/mslangid.hxx> 40 #include "vcl/svapp.hxx" 41 #include "vcl/msgbox.hxx" 42 #include "com/sun/star/lang/XServiceInfo.hpp" 43 #include "com/sun/star/task/XJobExecutor.hpp" 44 #include "com/sun/star/ui/dialogs/XAsynchronousExecutableDialog.hpp" 45 46 #include "boost/bind.hpp" 47 #include "license_dialog.hxx" 48 #include "dp_gui_dialog2.hxx" 49 #include "dp_gui_extensioncmdqueue.hxx" 50 51 using namespace ::dp_misc; 52 using namespace ::com::sun::star; 53 using namespace ::com::sun::star::uno; 54 55 using ::rtl::OUString; 56 57 namespace css = ::com::sun::star; 58 namespace dp_gui { 59 60 //============================================================================== 61 class MyApp : public Application, private boost::noncopyable 62 { 63 public: 64 MyApp(); 65 virtual ~MyApp(); 66 67 // Application 68 virtual void Main(); 69 }; 70 71 //______________________________________________________________________________ 72 MyApp::~MyApp() 73 { 74 } 75 76 //______________________________________________________________________________ 77 MyApp::MyApp() 78 { 79 } 80 81 //______________________________________________________________________________ 82 void MyApp::Main() 83 { 84 } 85 86 //############################################################################## 87 88 namespace 89 { 90 struct ProductName 91 : public rtl::Static< String, ProductName > {}; 92 struct Version 93 : public rtl::Static< String, Version > {}; 94 struct AboutBoxVersion 95 : public rtl::Static< String, AboutBoxVersion > {}; 96 struct OOOVendor 97 : public rtl::Static< String, OOOVendor > {}; 98 struct Extension 99 : public rtl::Static< String, Extension > {}; 100 } 101 102 void ReplaceProductNameHookProc( String& rStr ) 103 { 104 static int nAll = 0, nPro = 0; 105 106 nAll++; 107 if ( rStr.SearchAscii( "%PRODUCT" ) != STRING_NOTFOUND ) 108 { 109 String &rProductName = ProductName::get(); 110 String &rVersion = Version::get(); 111 String &rAboutBoxVersion = AboutBoxVersion::get(); 112 String &rExtension = Extension::get(); 113 String &rOOOVendor = OOOVendor::get(); 114 115 if ( !rProductName.Len() ) 116 { 117 rtl::OUString aTmp; 118 Any aRet = ::utl::ConfigManager::GetDirectConfigProperty( ::utl::ConfigManager::PRODUCTNAME ); 119 aRet >>= aTmp; 120 rProductName = aTmp; 121 122 aRet = ::utl::ConfigManager::GetDirectConfigProperty( ::utl::ConfigManager::PRODUCTVERSION ); 123 aRet >>= aTmp; 124 rVersion = aTmp; 125 126 aRet = ::utl::ConfigManager::GetDirectConfigProperty( ::utl::ConfigManager::ABOUTBOXPRODUCTVERSION ); 127 aRet >>= aTmp; 128 rAboutBoxVersion = aTmp; 129 130 aRet = ::utl::ConfigManager::GetDirectConfigProperty( ::utl::ConfigManager::OOOVENDOR ); 131 aRet >>= aTmp; 132 rOOOVendor = aTmp; 133 134 if ( !rExtension.Len() ) 135 { 136 aRet = ::utl::ConfigManager::GetDirectConfigProperty( ::utl::ConfigManager::PRODUCTEXTENSION ); 137 aRet >>= aTmp; 138 rExtension = aTmp; 139 } 140 } 141 142 nPro++; 143 rStr.SearchAndReplaceAllAscii( "%PRODUCTNAME", rProductName ); 144 rStr.SearchAndReplaceAllAscii( "%PRODUCTVERSION", rVersion ); 145 rStr.SearchAndReplaceAllAscii( "%ABOUTBOXPRODUCTVERSION", rAboutBoxVersion ); 146 rStr.SearchAndReplaceAllAscii( "%OOOVENDOR", rOOOVendor ); 147 rStr.SearchAndReplaceAllAscii( "%PRODUCTEXTENSION", rExtension ); 148 } 149 } 150 151 //============================================================================== 152 class ServiceImpl 153 : public ::cppu::WeakImplHelper2<ui::dialogs::XAsynchronousExecutableDialog, 154 task::XJobExecutor> 155 { 156 Reference<XComponentContext> const m_xComponentContext; 157 boost::optional< Reference<awt::XWindow> > /* const */ m_parent; 158 boost::optional<OUString> /* const */ m_view; 159 /* if true then this service is running in an unopkg process and not in an office process */ 160 boost::optional<sal_Bool> /* const */ m_unopkg; 161 boost::optional<OUString> m_extensionURL; 162 OUString m_initialTitle; 163 bool m_bShowUpdateOnly; 164 165 public: 166 ServiceImpl( Sequence<Any> const & args, 167 Reference<XComponentContext> const & xComponentContext ); 168 169 // XAsynchronousExecutableDialog 170 virtual void SAL_CALL setDialogTitle( OUString const & aTitle ) 171 throw (RuntimeException); 172 virtual void SAL_CALL startExecuteModal( 173 Reference< ui::dialogs::XDialogClosedListener > const & xListener ) 174 throw (RuntimeException); 175 176 // XJobExecutor 177 virtual void SAL_CALL trigger( OUString const & event ) 178 throw (RuntimeException); 179 }; 180 181 //______________________________________________________________________________ 182 ServiceImpl::ServiceImpl( Sequence<Any> const& args, 183 Reference<XComponentContext> const& xComponentContext) 184 : m_xComponentContext(xComponentContext), 185 m_bShowUpdateOnly( false ) 186 { 187 try { 188 comphelper::unwrapArgs( args, m_parent, m_view, m_unopkg ); 189 return; 190 } catch (css::lang::IllegalArgumentException & ) { 191 } 192 try { 193 comphelper::unwrapArgs( args, m_extensionURL); 194 } catch (css::lang::IllegalArgumentException & ) { 195 } 196 197 ResHookProc pProc = ResMgr::GetReadStringHook(); 198 if ( !pProc ) 199 ResMgr::SetReadStringHook( ReplaceProductNameHookProc ); 200 } 201 202 // XAsynchronousExecutableDialog 203 //______________________________________________________________________________ 204 void ServiceImpl::setDialogTitle( OUString const & title ) 205 throw (RuntimeException) 206 { 207 if ( dp_gui::TheExtensionManager::s_ExtMgr.is() ) 208 { 209 const ::vos::OGuard guard( Application::GetSolarMutex() ); 210 ::rtl::Reference< ::dp_gui::TheExtensionManager > dialog( 211 ::dp_gui::TheExtensionManager::get( m_xComponentContext, 212 m_parent ? *m_parent : Reference<awt::XWindow>(), 213 m_extensionURL ? *m_extensionURL : OUString() ) ); 214 dialog->SetText( title ); 215 } 216 else 217 m_initialTitle = title; 218 } 219 220 //______________________________________________________________________________ 221 void ServiceImpl::startExecuteModal( 222 Reference< ui::dialogs::XDialogClosedListener > const & xListener ) 223 throw (RuntimeException) 224 { 225 bool bCloseDialog = true; // only used if m_bShowUpdateOnly is true 226 ::std::auto_ptr<Application> app; 227 //ToDo: synchronize access to s_dialog !!! 228 if (! dp_gui::TheExtensionManager::s_ExtMgr.is()) 229 { 230 const bool bAppUp = (GetpApp() != 0); 231 bool bOfficePipePresent; 232 try { 233 bOfficePipePresent = dp_misc::office_is_running(); 234 } 235 catch (Exception & exc) { 236 if (bAppUp) { 237 const vos::OGuard guard( Application::GetSolarMutex() ); 238 std::auto_ptr<ErrorBox> box( 239 new ErrorBox( Application::GetActiveTopWindow(), 240 WB_OK, exc.Message ) ); 241 box->Execute(); 242 } 243 throw; 244 } 245 246 if (! bOfficePipePresent) { 247 OSL_ASSERT( ! bAppUp ); 248 app.reset( new MyApp ); 249 if (! InitVCL( Reference<lang::XMultiServiceFactory>( 250 m_xComponentContext->getServiceManager(), 251 UNO_QUERY_THROW ) )) 252 throw RuntimeException( OUSTR("Cannot initialize VCL!"), 253 static_cast<OWeakObject *>(this) ); 254 AllSettings as = app->GetSettings(); 255 OUString slang; 256 if (! (::utl::ConfigManager::GetDirectConfigProperty( 257 ::utl::ConfigManager::LOCALE ) >>= slang)) 258 throw RuntimeException( OUSTR("Cannot determine language!"), 259 static_cast<OWeakObject *>(this) ); 260 as.SetUILanguage( MsLangId::convertIsoStringToLanguage( slang ) ); 261 app->SetSettings( as ); 262 String sTitle = ::utl::ConfigManager::GetDirectConfigProperty( 263 ::utl::ConfigManager::PRODUCTNAME).get<OUString>() 264 + String(static_cast<sal_Unicode>(' ')) 265 + ::utl::ConfigManager::GetDirectConfigProperty( 266 ::utl::ConfigManager::PRODUCTVERSION).get<OUString>(); 267 app->SetDisplayName(sTitle); 268 ExtensionCmdQueue::syncRepositories( m_xComponentContext ); 269 } 270 } 271 else 272 { 273 // When m_bShowUpdateOnly is set, we are inside the office and the user clicked 274 // the update notification icon in the menu bar. We must not close the extensions 275 // dialog after displaying the update dialog when it has been visible before 276 if ( m_bShowUpdateOnly ) 277 bCloseDialog = ! dp_gui::TheExtensionManager::s_ExtMgr->isVisible(); 278 } 279 280 { 281 const ::vos::OGuard guard( Application::GetSolarMutex() ); 282 ::rtl::Reference< ::dp_gui::TheExtensionManager > myExtMgr( 283 ::dp_gui::TheExtensionManager::get( 284 m_xComponentContext, 285 m_parent ? *m_parent : Reference<awt::XWindow>(), 286 m_extensionURL ? *m_extensionURL : OUString() ) ); 287 myExtMgr->createDialog( false ); 288 if (m_initialTitle.getLength() > 0) { 289 myExtMgr->SetText( m_initialTitle ); 290 m_initialTitle = OUString(); 291 } 292 if ( m_bShowUpdateOnly ) 293 { 294 myExtMgr->checkUpdates( true, !bCloseDialog ); 295 if ( bCloseDialog ) 296 myExtMgr->Close(); 297 else 298 myExtMgr->ToTop( TOTOP_RESTOREWHENMIN ); 299 } 300 else 301 { 302 myExtMgr->Show(); 303 myExtMgr->ToTop( TOTOP_RESTOREWHENMIN ); 304 } 305 } 306 307 if (app.get() != 0) { 308 Application::Execute(); 309 DeInitVCL(); 310 } 311 312 if (xListener.is()) 313 xListener->dialogClosed( 314 ui::dialogs::DialogClosedEvent( 315 static_cast< ::cppu::OWeakObject * >(this), 316 sal_Int16(0)) ); 317 } 318 319 // XJobExecutor 320 //______________________________________________________________________________ 321 void ServiceImpl::trigger( OUString const &rEvent ) throw (RuntimeException) 322 { 323 if ( rEvent == OUSTR("SHOW_UPDATE_DIALOG") ) 324 m_bShowUpdateOnly = true; 325 else 326 m_bShowUpdateOnly = false; 327 328 startExecuteModal( Reference< ui::dialogs::XDialogClosedListener >() ); 329 } 330 331 namespace sdecl = comphelper::service_decl; 332 sdecl::class_<ServiceImpl, sdecl::with_args<true> > serviceSI; 333 sdecl::ServiceDecl const serviceDecl( 334 serviceSI, 335 "com.sun.star.comp.deployment.ui.PackageManagerDialog", 336 "com.sun.star.deployment.ui.PackageManagerDialog" ); 337 338 sdecl::class_<LicenseDialog, sdecl::with_args<true> > licenseSI; 339 sdecl::ServiceDecl const licenseDecl( 340 licenseSI, 341 "com.sun.star.comp.deployment.ui.LicenseDialog", 342 "com.sun.star.deployment.ui.LicenseDialog" ); 343 344 sdecl::class_<UpdateRequiredDialogService, sdecl::with_args<true> > updateSI; 345 sdecl::ServiceDecl const updateDecl( 346 updateSI, 347 "com.sun.star.comp.deployment.ui.UpdateRequiredDialog", 348 "com.sun.star.deployment.ui.UpdateRequiredDialog" ); 349 } // namespace dp_gui 350 351 extern "C" { 352 353 void SAL_CALL component_getImplementationEnvironment( 354 const sal_Char ** ppEnvTypeName, uno_Environment ** ) 355 { 356 *ppEnvTypeName = CPPU_CURRENT_LANGUAGE_BINDING_NAME; 357 } 358 359 void * SAL_CALL component_getFactory( 360 sal_Char const * pImplName, 361 lang::XMultiServiceFactory * pServiceManager, 362 registry::XRegistryKey * pRegistryKey ) 363 { 364 return component_getFactoryHelper( 365 pImplName, pServiceManager, pRegistryKey, dp_gui::serviceDecl, dp_gui::licenseDecl, dp_gui::updateDecl ); 366 } 367 368 } // extern "C" 369