From 8a673489c69cc65165b8af2061a05eba46cfc5e2 Mon Sep 17 00:00:00 2001 From: Oliver Bolte Date: Tue, 15 Mar 2005 11:55:54 +0000 Subject: INTEGRATION: CWS c01v005 (1.1.6); FILE ADDED 2005/03/08 08:48:33 as 1.1.6.3: #119880# reactivate HelpOnStartup job; fix some configuration issues; create new framework lib fwm 2005/03/07 13:33:14 cd 1.1.6.2: #119880# Fixed merge problems 2005/03/02 13:44:28 as 1.1.6.1: #119880# reactivate job --- framework/source/jobs/helponstartup.cxx | 506 ++++++++++++++++++++++++++++++++ 1 file changed, 506 insertions(+) create mode 100644 framework/source/jobs/helponstartup.cxx diff --git a/framework/source/jobs/helponstartup.cxx b/framework/source/jobs/helponstartup.cxx new file mode 100644 index 000000000000..8b5b98331984 --- /dev/null +++ b/framework/source/jobs/helponstartup.cxx @@ -0,0 +1,506 @@ +/************************************************************************* + * + * $RCSfile: helponstartup.cxx,v $ + * + * $Revision: 1.2 $ + * + * last change: $Author: obo $ $Date: 2005-03-15 12:55:54 $ + * + * The Contents of this file are made available subject to the terms of + * either of the following licenses + * + * - GNU Lesser General Public License Version 2.1 + * - Sun Industry Standards Source License Version 1.1 + * + * Sun Microsystems Inc., October, 2000 + * + * GNU Lesser General Public License Version 2.1 + * ============================================= + * Copyright 2000 by Sun Microsystems, Inc. + * 901 San Antonio Road, Palo Alto, CA 94303, USA + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License version 2.1, as published by the Free Software Foundation. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, + * MA 02111-1307 USA + * + * + * Sun Industry Standards Source License Version 1.1 + * ================================================= + * The contents of this file are subject to the Sun Industry Standards + * Source License Version 1.1 (the "License"); You may not use this file + * except in compliance with the License. You may obtain a copy of the + * License at http://www.openoffice.org/license.html. + * + * Software provided under this License is provided on an "AS IS" basis, + * WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, + * WITHOUT LIMITATION, WARRANTIES THAT THE SOFTWARE IS FREE OF DEFECTS, + * MERCHANTABLE, FIT FOR A PARTICULAR PURPOSE, OR NON-INFRINGING. + * See the License for the specific provisions governing your rights and + * obligations concerning the Software. + * + * The Initial Developer of the Original Code is: Sun Microsystems, Inc. + * + * Copyright: 2000 by Sun Microsystems, Inc. + * + * All Rights Reserved. + * + * Contributor(s): _______________________________________ + * + * + ************************************************************************/ + +//_______________________________________________ +// include own header + +#ifndef __FRAMEWORK_JOBS_HELPONSTARTUP_HXX_ +#include +#endif + +#ifndef __FRAMEWORK_THREADHELP_RESETABLEGUARD_HXX_ +#include +#endif + +#ifndef __FRAMEWORK_TARGETHELPER_HXX_ +#include +#endif + +#ifndef __FRAMEWORK_SERVICES_H_ +#include +#endif + +//_______________________________________________ +// include others + +#ifndef _COMPHELPER_CONFIGURATIONHELPER_HXX_ +#include +#endif + +#ifndef _COMPHELPER_SEQUENCEASHASHMAP_HXX_ +#include +#endif + +#ifndef _UTL_CONFIGMGR_HXX_ +#include +#endif + +#ifndef _SV_SVAPP_HXX +#include +#endif + +#ifndef _SV_HELP_HXX +#include +#endif + +#ifndef _RTL_USTRBUF_HXX_ +#include +#endif + +//_______________________________________________ +// include interfaces + +#ifndef _COM_SUN_STAR_FRAME_FRAMESEARCHFLAG_HPP_ +#include +#endif + +#ifndef _COM_SUN_STAR_FRAME_XFRAMESSUPPLIER_HPP_ +#include +#endif + +#ifndef _COM_SUN_STAR_FRAME_XDESKTOP_HPP_ +#include +#endif + +//_______________________________________________ +// namespace + +namespace framework{ + +//_______________________________________________ +// definitions + +// path to module config +static ::rtl::OUString CFG_PACKAGE_MODULES = ::rtl::OUString::createFromAscii("/org.openoffice.Setup/Office/Factories"); +static ::rtl::OUString CFG_PACKAGE_SETUP = ::rtl::OUString::createFromAscii("/org.openoffice.Setup" ); +static ::rtl::OUString CFG_PACKAGE_COMMON = ::rtl::OUString::createFromAscii("/org.openoffice.Office.Common" ); +static ::rtl::OUString CFG_PATH_L10N = ::rtl::OUString::createFromAscii("L10N" ); +static ::rtl::OUString CFG_PATH_HELP = ::rtl::OUString::createFromAscii("Help" ); +static ::rtl::OUString CFG_KEY_LOCALE = ::rtl::OUString::createFromAscii("ooLocale" ); +static ::rtl::OUString CFG_KEY_HELPSYSTEM = ::rtl::OUString::createFromAscii("System" ); + +// props of job environment +static ::rtl::OUString PROP_ENVIRONMENT = ::rtl::OUString::createFromAscii("Environment" ); +static ::rtl::OUString PROP_JOBCONFIG = ::rtl::OUString::createFromAscii("JobConfig" ); +static ::rtl::OUString PROP_ENVTYPE = ::rtl::OUString::createFromAscii("EnvType" ); +static ::rtl::OUString PROP_MODEL = ::rtl::OUString::createFromAscii("Model" ); + +// props of module config +static ::rtl::OUString PROP_HELP_BASEURL = ::rtl::OUString::createFromAscii("ooSetupFactoryHelpBaseURL" ); +static ::rtl::OUString PROP_AUTOMATIC_HELP = ::rtl::OUString::createFromAscii("ooSetupFactoryHelpOnOpen" ); + +// special value of job environment +static ::rtl::OUString ENVTYPE_DOCUMENTEVENT = ::rtl::OUString::createFromAscii("DOCUMENTEVENT" ); + +//----------------------------------------------- + +DEFINE_XINTERFACE_4(HelpOnStartup , + OWeakObject , + DIRECT_INTERFACE(css::lang::XTypeProvider ), + DIRECT_INTERFACE(css::lang::XServiceInfo ), + DIRECT_INTERFACE(css::task::XJob ), + DIRECT_INTERFACE(css::lang::XEventListener)) + +DEFINE_XTYPEPROVIDER_4(HelpOnStartup , + css::lang::XTypeProvider , + css::lang::XServiceInfo , + css::task::XJob , + css::lang::XEventListener) + +DEFINE_XSERVICEINFO_MULTISERVICE(HelpOnStartup , + ::cppu::OWeakObject , + SERVICENAME_JOB , + IMPLEMENTATIONNAME_HELPONSTARTUP) + +DEFINE_INIT_SERVICE(HelpOnStartup, + { + /* Attention + I think we don't need any mutex or lock here ... because we are called by our own static method impl_createInstance() + to create a new instance of this class by our own supported service factory. + see macro DEFINE_XSERVICEINFO_MULTISERVICE and "impl_initService()" for further informations! + */ + // create some needed uno services and cache it + m_xModuleManager = css::uno::Reference< css::frame::XModuleManager >( + m_xSMGR->createInstance(SERVICENAME_MODULEMANAGER), + css::uno::UNO_QUERY_THROW); + + m_xDesktop = css::uno::Reference< css::frame::XFrame >( + m_xSMGR->createInstance(SERVICENAME_DESKTOP), + css::uno::UNO_QUERY_THROW); + + m_xConfig = css::uno::Reference< css::container::XNameAccess >( + ::comphelper::ConfigurationHelper::openConfig( + m_xSMGR, + CFG_PACKAGE_MODULES, + ::comphelper::ConfigurationHelper::E_READONLY), + css::uno::UNO_QUERY_THROW); + + // ask for office locale + ::comphelper::ConfigurationHelper::readDirectKey( + m_xSMGR, + CFG_PACKAGE_SETUP, + CFG_PATH_L10N, + CFG_KEY_LOCALE, + ::comphelper::ConfigurationHelper::E_READONLY) >>= m_sLocale; + + // detect system + ::comphelper::ConfigurationHelper::readDirectKey( + m_xSMGR, + CFG_PACKAGE_COMMON, + CFG_PATH_HELP, + CFG_KEY_HELPSYSTEM, + ::comphelper::ConfigurationHelper::E_READONLY) >>= m_sSystem; + + // Start listening for disposing events of these services, + // so we can react e.g. for an office shutdown + css::uno::Reference< css::lang::XComponent > xComponent; + xComponent = css::uno::Reference< css::lang::XComponent >(m_xModuleManager, css::uno::UNO_QUERY); + if (xComponent.is()) + xComponent->addEventListener(static_cast< css::lang::XEventListener* >(this)); + xComponent = css::uno::Reference< css::lang::XComponent >(m_xDesktop, css::uno::UNO_QUERY); + if (xComponent.is()) + xComponent->addEventListener(static_cast< css::lang::XEventListener* >(this)); + xComponent = css::uno::Reference< css::lang::XComponent >(m_xConfig, css::uno::UNO_QUERY); + if (xComponent.is()) + xComponent->addEventListener(static_cast< css::lang::XEventListener* >(this)); + } + ) + +//----------------------------------------------- +HelpOnStartup::HelpOnStartup(const css::uno::Reference< css::lang::XMultiServiceFactory >& xSMGR) + : ThreadHelpBase( ) + , m_xSMGR (xSMGR) +{ +} + +//----------------------------------------------- +HelpOnStartup::~HelpOnStartup() +{ +} + +//----------------------------------------------- +// css.task.XJob +css::uno::Any SAL_CALL HelpOnStartup::execute(const css::uno::Sequence< css::beans::NamedValue >& lArguments) + throw(css::lang::IllegalArgumentException, + css::uno::Exception , + css::uno::RuntimeException ) +{ + // Analyze the given arguments; try to locate a model there and + // classify it's used application module. + ::rtl::OUString sModule = its_getModuleIdFromEnv(lArguments); + + // Attention: We are bound to events for openeing any document inside the office. + // That includes e.g. the help module itself. But we have to do nothing then! + if (!sModule.getLength()) + return css::uno::Any(); + + // check current state of the help module + // a) help isnt open => show default page for the detected module + // b) help shows any other default page(!) => show default page for the detected module + // c) help shows any other content => do nothing (user travelled to any other content and leaved the set of default pages) + ::rtl::OUString sCurrentHelpURL = its_getCurrentHelpURL(); + sal_Bool bCurrentHelpURLIsAnyDefaultURL = its_isHelpUrlADefaultOne(sCurrentHelpURL); + sal_Bool bShowIt = sal_False; + + // a) + if (!sCurrentHelpURL.getLength()) + bShowIt = sal_True; + else + // b) + if (bCurrentHelpURLIsAnyDefaultURL) + bShowIt = sal_True; + + if (bShowIt) + { + // retrieve the help URL for the detected application module + ::rtl::OUString sModuleDependendHelpURL = its_checkIfHelpEnabledAndGetURL(sModule); + if (sModuleDependendHelpURL.getLength()) + { + // Show this help page. + // Note: The help window brings itself to front ... + Help* pHelp = Application::GetHelp(); + if (pHelp) + pHelp->Start(sModuleDependendHelpURL, 0); + } + } + + return css::uno::Any(); +} + +//----------------------------------------------- +void SAL_CALL HelpOnStartup::disposing(const css::lang::EventObject& aEvent) + throw(css::uno::RuntimeException) +{ + // SAFE -> + ResetableGuard aLock(m_aLock); + + if (aEvent.Source == m_xModuleManager) + m_xModuleManager.clear(); + else + if (aEvent.Source == m_xDesktop) + m_xDesktop.clear(); + else + if (aEvent.Source == m_xConfig) + m_xConfig.clear(); + + aLock.unlock(); + // <- SAFE +} + +//----------------------------------------------- +::rtl::OUString HelpOnStartup::its_getModuleIdFromEnv(const css::uno::Sequence< css::beans::NamedValue >& lArguments) +{ + ::comphelper::SequenceAsHashMap lArgs (lArguments); + ::comphelper::SequenceAsHashMap lEnvironment = lArgs.getUnpackedValueOrDefault(PROP_ENVIRONMENT, css::uno::Sequence< css::beans::NamedValue >()); + ::comphelper::SequenceAsHashMap lJobConfig = lArgs.getUnpackedValueOrDefault(PROP_JOBCONFIG , css::uno::Sequence< css::beans::NamedValue >()); + + // check for right environment. + // If its not a DocumentEvent, which triggered this job, + // we cant work correctly! => return immediatly and do nothing + ::rtl::OUString sEnvType = lEnvironment.getUnpackedValueOrDefault(PROP_ENVTYPE, ::rtl::OUString()); + if (!sEnvType.equals(ENVTYPE_DOCUMENTEVENT)) + return ::rtl::OUString(); + + css::uno::Reference< css::frame::XModel > xDoc = lEnvironment.getUnpackedValueOrDefault(PROP_MODEL, css::uno::Reference< css::frame::XModel >()); + if (!xDoc.is()) + return ::rtl::OUString(); + + // be sure that we work on top level documents only, which are registered + // on the desktop instance. Ignore e.g. life previews, which are top frames too ... + // but not registered at this global desktop instance. + css::uno::Reference< css::frame::XDesktop > xDesktopCheck; + css::uno::Reference< css::frame::XFrame > xFrame ; + css::uno::Reference< css::frame::XController > xController = xDoc->getCurrentController(); + if (xController.is()) + xFrame = xController->getFrame(); + if (xFrame.is() && xFrame->isTop()) + xDesktopCheck = css::uno::Reference< css::frame::XDesktop >(xFrame->getCreator(), css::uno::UNO_QUERY); + if (!xDesktopCheck.is()) + return ::rtl::OUString(); + + // OK - now we are sure this document is a top level document. + // Classify it. + // SAFE -> + ResetableGuard aLock(m_aLock); + css::uno::Reference< css::frame::XModuleManager > xModuleManager = m_xModuleManager; + aLock.unlock(); + // <- SAFE + + if (!xModuleManager.is()) + return ::rtl::OUString(); + + ::rtl::OUString sModuleId; + try + { + sModuleId = xModuleManager->identify(xDoc); + } + catch(const css::uno::RuntimeException& exRun) + { throw exRun; } + catch(const css::uno::Exception&) + { sModuleId = ::rtl::OUString(); } + + return sModuleId; +} + +//----------------------------------------------- +::rtl::OUString HelpOnStartup::its_getCurrentHelpURL() +{ + // SAFE -> + ResetableGuard aLock(m_aLock); + css::uno::Reference< css::frame::XFrame > xDesktop = m_xDesktop; + aLock.unlock(); + // <- SAFE + + if (!xDesktop.is()) + return ::rtl::OUString(); + + css::uno::Reference< css::frame::XFrame > xHelp = xDesktop->findFrame(SPECIALTARGET_HELPTASK, css::frame::FrameSearchFlag::CHILDREN); + if (!xHelp.is()) + return ::rtl::OUString(); + + ::rtl::OUString sCurrentHelpURL; + try + { + css::uno::Reference< css::frame::XFramesSupplier > xHelpRoot (xHelp , css::uno::UNO_QUERY_THROW); + css::uno::Reference< css::container::XIndexAccess > xHelpChilds(xHelpRoot->getFrames(), css::uno::UNO_QUERY_THROW); + + css::uno::Reference< css::frame::XFrame > xHelpChild ; + css::uno::Reference< css::frame::XController > xHelpView ; + css::uno::Reference< css::frame::XModel > xHelpContent; + + xHelpChilds->getByIndex(0) >>= xHelpChild; + if (xHelpChild.is()) + xHelpView = xHelpChild->getController(); + if (xHelpView.is()) + xHelpContent = xHelpView->getModel(); + if (xHelpContent.is()) + sCurrentHelpURL = xHelpContent->getURL(); + } + catch(css::uno::RuntimeException& exRun) + { throw exRun; } + catch(css::uno::Exception&) + { sCurrentHelpURL = ::rtl::OUString(); } + + return sCurrentHelpURL; +} + +//----------------------------------------------- +::sal_Bool HelpOnStartup::its_isHelpUrlADefaultOne(const ::rtl::OUString& sHelpURL) +{ + if (!sHelpURL.getLength()) + return sal_False; + + // SAFE -> + ResetableGuard aLock(m_aLock); + css::uno::Reference< css::lang::XMultiServiceFactory > xSMGR (m_xSMGR, css::uno::UNO_QUERY_THROW); + css::uno::Reference< css::container::XNameAccess > xConfig = m_xConfig; + ::rtl::OUString sLocale = m_sLocale; + ::rtl::OUString sSystem = m_sSystem; + aLock.unlock(); + // <- SAFE + + if (!xConfig.is()) + return sal_False; + + // check given help url against all default ones + const css::uno::Sequence< ::rtl::OUString > lModules = xConfig->getElementNames(); + const ::rtl::OUString* pModules = lModules.getConstArray(); + ::sal_Int32 c = lModules.getLength(); + ::sal_Int32 i = 0; + + for (i=0; i xModuleConfig; + xConfig->getByName(pModules[i]) >>= xModuleConfig; + if (!xModuleConfig.is()) + continue; + + ::rtl::OUString sHelpBaseURL; + xModuleConfig->getByName(PROP_HELP_BASEURL) >>= sHelpBaseURL; + ::rtl::OUString sHelpURLForModule = HelpOnStartup::ist_createHelpURL(sHelpBaseURL, sLocale, sSystem); + if (sHelpURL.equals(sHelpURLForModule)) + return sal_True; + } + catch(const css::uno::RuntimeException& exRun) + { throw exRun; } + catch(const css::uno::Exception&) + {} + } + + return sal_False; +} + +//----------------------------------------------- +::rtl::OUString HelpOnStartup::its_checkIfHelpEnabledAndGetURL(const ::rtl::OUString& sModule) +{ + // SAFE -> + ResetableGuard aLock(m_aLock); + css::uno::Reference< css::container::XNameAccess > xConfig = m_xConfig; + ::rtl::OUString sLocale = m_sLocale; + ::rtl::OUString sSystem = m_sSystem; + aLock.unlock(); + // <- SAFE + + ::rtl::OUString sHelpURL; + + try + { + css::uno::Reference< css::container::XNameAccess > xModuleConfig; + if (xConfig.is()) + xConfig->getByName(sModule) >>= xModuleConfig; + + sal_Bool bHelpEnabled = sal_False; + if (xModuleConfig.is()) + xModuleConfig->getByName(PROP_AUTOMATIC_HELP) >>= bHelpEnabled; + + if (bHelpEnabled) + { + ::rtl::OUString sHelpBaseURL; + xModuleConfig->getByName(PROP_HELP_BASEURL) >>= sHelpBaseURL; + sHelpURL = HelpOnStartup::ist_createHelpURL(sHelpBaseURL, sLocale, sSystem); + } + } + catch(const css::uno::RuntimeException& exRun) + { throw exRun; } + catch(const css::uno::Exception&) + { sHelpURL = ::rtl::OUString(); } + + return sHelpURL; +} + +//----------------------------------------------- +::rtl::OUString HelpOnStartup::ist_createHelpURL(const ::rtl::OUString& sBaseURL, + const ::rtl::OUString& sLocale , + const ::rtl::OUString& sSystem ) +{ + ::rtl::OUStringBuffer sHelpURL(256); + sHelpURL.append (sBaseURL ); + sHelpURL.appendAscii("?Language="); + sHelpURL.append (sLocale ); + sHelpURL.appendAscii("&System=" ); + sHelpURL.append (sSystem ); + + return sHelpURL.makeStringAndClear(); +} + +} // namespace framework -- cgit