/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
/*
* This file is part of the LibreOffice project.
*
* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
*
* This file incorporates work covered by the following license notice:
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed
* with this work for additional information regarding copyright
* ownership. The ASF licenses this file to you under the Apache
* License, Version 2.0 (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.apache.org/licenses/LICENSE-2.0 .
*/
#include <memory>
#include <string_view>
#include <config_features.h>
#include <config_feature_opencl.h>
#include <config_feature_desktop.h>
#include <config_gpgme.h>
#include <officecfg/Office/Common.hxx>
#include <officecfg/Office/Writer.hxx>
#include <svx/dialogs.hrc>
#include <svx/svxids.hrc>
#include <treeopt.hrc>
#include <helpids.h>
#include "cfgchart.hxx"
#include "connpoolconfig.hxx"
#include "connpooloptions.hxx"
#include <cuioptgenrl.hxx>
#include <dbregister.hxx>
#include "dbregisterednamesconfig.hxx"
#include <dialmgr.hxx>
#include "fontsubs.hxx"
#include "optaccessibility.hxx"
#include <optasian.hxx>
#include "optchart.hxx"
#include "optcolor.hxx"
#include "optctl.hxx"
#include "optfltr.hxx"
#include "optgdlg.hxx"
#include "opthtml.hxx"
#include "optinet2.hxx"
#include "optjava.hxx"
#include "optjsearch.hxx"
#include <optlingu.hxx>
#if HAVE_FEATURE_OPENCL
#include "optopencl.hxx"
#endif
#include <optpath.hxx>
#include "optsave.hxx"
#include "optupdt.hxx"
#include "personalization.hxx"
#include <treeopt.hxx>
#include "optbasic.hxx"
#include "optlanguagetool.hxx"
#include "optdeepl.hxx"
// include search util
#include <com/sun/star/util/SearchFlags.hpp>
#include <com/sun/star/util/SearchAlgorithms2.hpp>
#include <unotools/textsearch.hxx>
#include <com/sun/star/awt/XContainerWindowEventHandler.hpp>
#include <com/sun/star/awt/ContainerWindowProvider.hpp>
#include <com/sun/star/awt/XControl.hpp>
#include <com/sun/star/awt/PosSize.hpp>
#include <com/sun/star/frame/Desktop.hpp>
#include <com/sun/star/frame/ModuleManager.hpp>
#include <com/sun/star/frame/UnknownModuleException.hpp>
#include <com/sun/star/lang/XMultiServiceFactory.hpp>
#include <com/sun/star/linguistic2/LinguProperties.hpp>
#include <comphelper/getexpandeduri.hxx>
#include <comphelper/processfactory.hxx>
#include <editeng/langitem.hxx>
#include <editeng/optitems.hxx>
#include <editeng/unolingu.hxx>
#include <linguistic/misc.hxx>
#include <o3tl/deleter.hxx>
#include <officecfg/Office/OptionsDialog.hxx>
#include <sfx2/app.hxx>
#include <sfx2/dispatch.hxx>
#include <sfx2/module.hxx>
#include <sfx2/printopt.hxx>
#include <sfx2/shell.hxx>
#include <sfx2/viewsh.hxx>
#include <sfx2/viewfrm.hxx>
#include <svl/flagitem.hxx>
#include <svl/intitem.hxx>
#include <svl/cjkoptions.hxx>
#include <svl/ctloptions.hxx>
#include <svx/databaseregistrationui.hxx>
#include <toolkit/helper/vclunohelper.hxx>
#include <tools/urlobj.hxx>
#include <comphelper/diagnose_ex.hxx>
#include <unotools/configmgr.hxx>
#include <unotools/moduleoptions.hxx>
#include <unotools/optionsdlg.hxx>
#include <unotools/viewoptions.hxx>
#include <utility>
#include <vcl/help.hxx>
#include <vcl/svapp.hxx>
#include <vcl/weldutils.hxx>
#include <vcl/window.hxx>
#include <sal/log.hxx>
using namespace ::com::sun::star;
using namespace ::com::sun::star::container;
using namespace ::com::sun::star::frame;
using namespace ::com::sun::star::lang;
using namespace ::com::sun::star::linguistic2;
using namespace ::com::sun::star::uno;
using namespace ::com::sun::star::util;
LastPageSaver* OfaTreeOptionsDialog::pLastPageSaver = nullptr;
// some stuff for easier changes for SvtViewOptions
constexpr OUString VIEWOPT_DATANAME = u"page data"_ustr;
static void SetViewOptUserItem( SvtViewOptions& rOpt, const OUString& rData )
{
rOpt.SetUserItem( VIEWOPT_DATANAME, Any( rData ) );
}
static OUString GetViewOptUserItem( const SvtViewOptions& rOpt )
{
Any aAny( rOpt.GetUserItem( VIEWOPT_DATANAME ) );
OUString aUserData;
aAny >>= aUserData;
return aUserData;
}
namespace {
struct ModuleToGroupNameMap_Impl
{
std::u16string_view m_pModule;
OUString m_sGroupName;
sal_uInt16 m_nNodeId;
};
}
static ModuleToGroupNameMap_Impl ModuleMap[] =
{
{ u"ProductName", OUString(), SID_GENERAL_OPTIONS },
{ u"LanguageSettings", OUString(), SID_LANGUAGE_OPTIONS },
{ u"Internet", OUString(), SID_INET_DLG },
{ u"LoadSave", OUString(), SID_FILTER_DLG },
{ u"Writer", OUString(), SID_SW_EDITOPTIONS },
{ u"WriterWeb", OUString(), SID_SW_ONLINEOPTIONS },
{ u"Math", OUString(), SID_SM_EDITOPTIONS },
{ u"Calc", OUString(), SID_SC_EDITOPTIONS },
{ u"Impress", OUString(), SID_SD_EDITOPTIONS },
{ u"Draw", OUString(), SID_SD_GRAPHIC_OPTIONS },
{ u"Charts", OUString(), SID_SCH_EDITOPTIONS },
{ u"Base", OUString(), SID_SB_STARBASEOPTIONS },
};
static void setGroupName( std::u16string_view rModule, const OUString& rGroupName )
{
for (ModuleToGroupNameMap_Impl& rEntry : ModuleMap)
{
if ( rEntry.m_pModule == rModule )
{
rEntry.m_sGroupName = rGroupName;
break;
}
}
}
static OUString getGroupName( std::u16string_view rModule, bool bForced )
{
OUString sGroupName;
for (const ModuleToGroupNameMap_Impl& rEntry : ModuleMap)
{
if ( rEntry.m_pModule == rModule )
{
sGroupName = rEntry.m_sGroupName;
break;
}
}
if ( sGroupName.isEmpty() && bForced )
{
if ( rModule == u"Writer" )
sGroupName = CuiResId(SID_SW_EDITOPTIONS_RES[0].first);
else if ( rModule == u"WriterWeb" )
sGroupName = CuiResId(SID_SW_ONLINEOPTIONS_RES[0].first);
else if ( rModule == u"Calc" )
sGroupName = CuiResId(SID_SC_EDITOPTIONS_RES[0].first);
else if ( rModule == u"Impress" )
sGroupName = CuiResId(SID_SD_EDITOPTIONS_RES[0].first);
else if ( rModule == u"Draw" )
sGroupName = CuiResId(SID_SD_GRAPHIC_OPTIONS_RES[0].first);
else if ( rModule == u"Math" )
sGroupName = CuiResId(SID_SM_EDITOPTIONS_RES[0].first);
else if ( rModule == u"Base" )
sGroupName = CuiResId(SID_SB_STARBASEOPTIONS_RES[0].first);
}
return sGroupName;
}
static void deleteGroupNames()
{
for (ModuleToGroupNameMap_Impl& rEntry : ModuleMap)
rEntry.m_sGroupName.clear();
}
static sal_uInt16 getGroupNodeId( std::u16string_view rModule )
{
sal_uInt16 nNodeId = 0xFFFF;
for (const ModuleToGroupNameMap_Impl& rEntry : ModuleMap)
{
if ( rEntry.m_pModule == rModule )
{
nNodeId = rEntry.m_nNodeId;
break;
}
}
return nNodeId;
}
namespace {
bool MailMergeCfgIsEmailSupported()
{
std::optional<bool> b = officecfg::Office::Writer::MailMergeWizard::EMailSupported::get();
return b.has_value() && *b;
}
}
//typedef SfxTabPage* (*FNCreateTabPage)(weld::Container* pPage, weld::DialogController* pController, const SfxItemSet &rAttrSet);
static std::unique_ptr<SfxTabPage> CreateGeneralTabPage(sal_uInt16 nId, weld::Container* pPage, weld::DialogController* pController, const SfxItemSet& rSet)
{
CreateTabPage fnCreate = nullptr;
switch(nId)
{
case RID_SFXPAGE_SAVE: fnCreate = &SvxSaveTabPage::Create; break;
case RID_SFXPAGE_PATH: fnCreate = &SvxPathTabPage::Create; break;
case RID_SFXPAGE_GENERAL: fnCreate = &SvxGeneralTabPage::Create; break;
case RID_SFXPAGE_PRINTOPTIONS: fnCreate = &SfxCommonPrintOptionsTabPage::Create; break;
case OFA_TP_LANGUAGES: fnCreate = &OfaLanguagesTabPage::Create; break;
case RID_SFXPAGE_LINGU: fnCreate = &SvxLinguTabPage::Create; break;
case OFA_TP_VIEW: fnCreate = &OfaViewTabPage::Create; break;
case OFA_TP_MISC: fnCreate = &OfaMiscTabPage::Create; break;
case RID_SVXPAGE_ASIAN_LAYOUT: fnCreate = &SvxAsianLayoutPage::Create; break;
case RID_SVX_FONT_SUBSTITUTION: fnCreate = &SvxFontSubstTabPage::Create; break;
case RID_SVXPAGE_INET_PROXY: fnCreate = &SvxProxyTabPage::Create; break;
case RID_SVXPAGE_INET_SECURITY: fnCreate = &SvxSecurityTabPage::Create; break;
case RID_SVXPAGE_INET_MAIL: fnCreate = &SvxEMailTabPage::Create; break;
#if HAVE_FEATURE_DESKTOP
case RID_SVXPAGE_PERSONALIZATION: fnCreate = &SvxPersonalizationTabPage::Create; break;
#endif
case RID_SVXPAGE_COLORCONFIG: fnCreate = &SvxColorOptionsTabPage::Create; break;
case RID_OFAPAGE_HTMLOPT: fnCreate = &OfaHtmlTabPage::Create; break;
case SID_OPTFILTER_MSOFFICE: fnCreate = &OfaMSFilterTabPage::Create; break;
case RID_OFAPAGE_MSFILTEROPT2: fnCreate = &OfaMSFilterTabPage2::Create; break;
case RID_SVXPAGE_JSEARCH_OPTIONS: fnCreate = &SvxJSearchOptionsPage::Create ; break;
case SID_SB_CONNECTIONPOOLING: fnCreate = &::offapp::ConnectionPoolOptionsPage::Create; break;
case SID_SB_DBREGISTEROPTIONS: fnCreate = &svx::DbRegistrationOptionsPage::Create; break;
case RID_SVXPAGE_ACCESSIBILITYCONFIG: fnCreate = &SvxAccessibilityOptionsTabPage::Create; break;
case RID_SVXPAGE_OPTIONS_CTL: fnCreate = &SvxCTLOptionsPage::Create ; break;
case RID_SVXPAGE_LANGTOOL_OPTIONS: fnCreate = &OptLanguageToolTabPage::Create ; break;
case RID_SVXPAGE_DEEPL_OPTIONS: fnCreate = &OptDeeplTabPage::Create ; break;
case RID_SVXPAGE_OPTIONS_JAVA: fnCreate = &SvxJavaOptionsPage::Create ; break;
#if HAVE_FEATURE_OPENCL
case RID_SVXPAGE_OPENCL: fnCreate = &SvxOpenCLTabPage::Create ; break;
#endif
case RID_SVXPAGE_ONLINEUPDATE: fnCreate = &SvxOnlineUpdateTabPage::Create; break;
case RID_OPTPAGE_CHART_DEFCOLORS: fnCreate = &SvxDefaultColorOptPage::Create; break;
#if HAVE_FEATURE_SCRIPTING
case RID_SVXPAGE_BASICIDE_OPTIONS: fnCreate = &SvxBasicIDEOptionsPage::Create; break;
#endif
}
return fnCreate ? (*fnCreate)( pPage, pController, &rSet ) : nullptr;
}
namespace {
struct OptionsMapping_Impl
{
OUString m_aGroupName;
OUString m_aPageName;
sal_uInt16 m_nPageId;
};
}
constexpr OptionsMapping_Impl OptionsMap_Impl[]
{
// GROUP PAGE PAGE-ID
{ u"ProductName"_ustr, u""_ustr, SID_GENERAL_OPTIONS },
{ u"ProductName"_ustr, u"UserData"_ustr, RID_SFXPAGE_GENERAL },
{ u"ProductName"_ustr, u"General"_ustr, OFA_TP_MISC },
{ u"ProductName"_ustr, u"View"_ustr, OFA_TP_VIEW },
{ u"ProductName"_ustr, u"Print"_ustr, RID_SFXPAGE_PRINTOPTIONS },
{ u"ProductName"_ustr, u"Paths"_ustr, RID_SFXPAGE_PATH },
{ u"ProductName"_ustr, u"Fonts"_ustr, RID_SVX_FONT_SUBSTITUTION },
{ u"ProductName"_ustr, u"Security"_ustr, RID_SVXPAGE_INET_SECURITY },
{ u"ProductName"_ustr, u"Personalization"_ustr, RID_SVXPAGE_PERSONALIZATION },
{ u"ProductName"_ustr, u"Appearance"_ustr, RID_SVXPAGE_COLORCONFIG },
{ u"ProductName"_ustr, u"Accessibility"_ustr, RID_SVXPAGE_ACCESSIBILITYCONFIG },
{ u"ProductName"_ustr, u"Java"_ustr, RID_SVXPAGE_OPTIONS_JAVA },
{ u"ProductName"_ustr, u"BasicIDEOptions"_ustr, RID_SVXPAGE_BASICIDE_OPTIONS },
{ u"ProductName"_ustr, u"OnlineUpdate"_ustr, RID_SVXPAGE_ONLINEUPDATE },
{ u"LanguageSettings"_ustr, u""_ustr, SID_LANGUAGE_OPTIONS },
{ u"LanguageSettings"_ustr, u"Languages"_ustr, OFA_TP_LANGUAGES },
{ u"LanguageSettings"_ustr, u"WritingAids"_ustr, RID_SFXPAGE_LINGU },
{ u"LanguageSettings"_ustr, u"SearchingInJapanese"_ustr, RID_SVXPAGE_JSEARCH_OPTIONS },
{ u"LanguageSettings"_ustr, u"AsianLayout"_ustr, RID_SVXPAGE_ASIAN_LAYOUT },
{ u"LanguageSettings"_ustr, u"ComplexTextLayout"_ustr, RID_SVXPAGE_OPTIONS_CTL },
{ u"Internet"_ustr, u""_ustr, SID_INET_DLG },
{ u"Internet"_ustr, u"Proxy"_ustr, RID_SVXPAGE_INET_PROXY },
{ u"Internet"_ustr, u"Email"_ustr, RID_SVXPAGE_INET_MAIL },
{ u"LoadSave"_ustr, u""_ustr, SID_FILTER_DLG },
{ u"LoadSave"_ustr, u"General"_ustr, RID_SFXPAGE_SAVE },
{ u"LoadSave"_ustr, u"VBAProperties"_ustr, SID_OPTFILTER_MSOFFICE },
{ u"LoadSave"_ustr, u"MicrosoftOffice"_ustr, RID_OFAPAGE_MSFILTEROPT2 },
{ u"LoadSave"_ustr, u"HTMLCompatibility"_ustr, RID_OFAPAGE_HTMLOPT },
{ u"Writer"_ustr, u""_ustr, SID_SW_EDITOPTIONS },
{ u"Writer"_ustr, u"General"_ustr, RID_SW_TP_OPTLOAD_PAGE },
{ u"Writer"_ustr, u"View"_ustr, RID_SW_TP_CONTENT_OPT },
{ u"Writer"_ustr, u"FormattingAids"_ustr, RID_SW_TP_OPTSHDWCRSR },
{ u"Writer"_ustr, u"Grid"_ustr, RID_SVXPAGE_GRID },
{ u"Writer"_ustr, u"BasicFontsWestern"_ustr, RID_SW_TP_STD_FONT },
{ u"Writer"_ustr, u"BasicFontsAsian"_ustr, RID_SW_TP_STD_FONT_CJK },
{ u"Writer"_ustr, u"BasicFontsCTL"_ustr, RID_SW_TP_STD_FONT_CTL },
{ u"Writer"_ustr, u"Print"_ustr, RID_SW_TP_OPTPRINT_PAGE },
{ u"Writer"_ustr, u"Table"_ustr, RID_SW_TP_OPTTABLE_PAGE },
{ u"Writer"_ustr, u"Changes"_ustr, RID_SW_TP_REDLINE_OPT },
{ u"Writer"_ustr, u"Comparison"_ustr, RID_SW_TP_COMPARISON_OPT },
{ u"Writer"_ustr, u"Compatibility"_ustr, RID_SW_TP_OPTCOMPATIBILITY_PAGE },
{ u"Writer"_ustr, u"AutoCaption"_ustr, RID_SW_TP_OPTCAPTION_PAGE },
{ u"Writer"_ustr, u"MailMerge"_ustr, RID_SW_TP_MAILCONFIG },
{ u"WriterWeb"_ustr, u""_ustr, SID_SW_ONLINEOPTIONS },
{ u"WriterWeb"_ustr, u"View"_ustr, RID_SW_TP_HTML_CONTENT_OPT },
{ u"WriterWeb"_ustr, u"FormattingAids"_ustr, RID_SW_TP_HTML_OPTSHDWCRSR },
{ u"WriterWeb"_ustr, u"Grid"_ustr, RID_SW_TP_HTML_OPTGRID_PAGE },
{ u"WriterWeb"_ustr, u"Print"_ustr, RID_SW_TP_HTML_OPTPRINT_PAGE },
{ u"WriterWeb"_ustr, u"Table"_ustr, RID_SW_TP_HTML_OPTTABLE_PAGE },
{ u"WriterWeb"_ustr, u"Background"_ustr, RID_SW_TP_BACKGROUND },
{ u"Math"_ustr, u""_ustr, SID_SM_EDITOPTIONS },
{ u"Math"_ustr, u"Settings"_ustr, SID_SM_TP_PRINTOPTIONS },
{ u"Calc"_ustr, u""_ustr, SID_SC_EDITOPTIONS },
{ u"Calc"_ustr, u"General"_ustr, SID_SC_TP_LAYOUT },
{ u"Calc"_ustr, u"View"_ustr, SID_SC_TP_CONTENT },
{ u"Calc"_ustr, u"Calculate"_ustr, SID_SC_TP_CALC },
{ u"Calc"_ustr, u"Formula"_ustr, SID_SC_TP_FORMULA },
{ u"Calc"_ustr, u"SortLists"_ustr, SID_SC_TP_USERLISTS },
{ u"Calc"_ustr, u"Changes"_ustr, SID_SC_TP_CHANGES },
{ u"Calc"_ustr, u"Compatibility"_ustr, SID_SC_TP_COMPATIBILITY },
{ u"Calc"_ustr, u"Grid"_ustr, SID_SC_TP_GRID },
{ u"Calc"_ustr, u"Print"_ustr, RID_SC_TP_PRINT },
{ u"Impress"_ustr, u""_ustr, SID_SD_EDITOPTIONS },
{ u"Impress"_ustr, u"General"_ustr, SID_SI_TP_MISC },
{ u"Impress"_ustr, u"View"_ustr, SID_SI_TP_CONTENTS },
{ u"Impress"_ustr, u"Grid"_ustr, SID_SI_TP_SNAP },
{ u"Impress"_ustr, u"Print"_ustr, SID_SI_TP_PRINT },
{ u"Draw"_ustr, u""_ustr, SID_SD_GRAPHIC_OPTIONS },
{ u"Draw"_ustr, u"General"_ustr, SID_SD_TP_MISC },
{ u"Draw"_ustr, u"View"_ustr, SID_SD_TP_CONTENTS },
{ u"Draw"_ustr, u"Grid"_ustr, SID_SD_TP_SNAP },
{ u"Draw"_ustr, u"Print"_ustr, SID_SD_TP_PRINT },
{ u"Charts"_ustr, u""_ustr, SID_SCH_EDITOPTIONS },
{ u"Charts"_ustr, u"DefaultColors"_ustr, RID_OPTPAGE_CHART_DEFCOLORS },
{ u"Base"_ustr, u""_ustr, SID_SB_STARBASEOPTIONS },
{ u"Base"_ustr, u"Connections"_ustr, SID_SB_CONNECTIONPOOLING },
{ u"Base"_ustr, u"Databases"_ustr, SID_SB_DBREGISTEROPTIONS },
};
static bool lcl_getStringFromID( sal_uInt16 _nPageId, OUString& _rGroupName, OUString& _rPageName )
{
bool bRet = false;
for (const auto & rMapping : OptionsMap_Impl )
{
if ( _nPageId == rMapping.m_nPageId )
{
bRet = true;
_rGroupName = rMapping.m_aGroupName;
if ( !rMapping.m_aPageName.isEmpty() )
_rPageName = rMapping.m_aPageName;
break;
}
}
return bRet;
}
static bool lcl_isOptionHidden( sal_uInt16 _nPageId, const SvtOptionsDialogOptions& _rOptOptions )
{
bool bIsHidden = false;
OUString sGroupName, sPageName;
if ( lcl_getStringFromID( _nPageId, sGroupName, sPageName ) )
{
if ( sPageName.isEmpty() )
bIsHidden = _rOptOptions.IsGroupHidden( sGroupName );
else
bIsHidden = _rOptOptions.IsPageHidden( sPageName, sGroupName );
}
return bIsHidden;
}
struct OptionsPageInfo
{
std::unique_ptr<SfxTabPage> m_xPage;
sal_uInt16 m_nPageId;
OUString m_sPageURL;
OUString m_sEventHdl;
std::unique_ptr<ExtensionsTabPage> m_xExtPage;
explicit OptionsPageInfo( sal_uInt16 nId ) : m_nPageId( nId ) {}
};
struct OptionsGroupInfo
{
std::optional<SfxItemSet> m_pInItemSet;
std::unique_ptr<SfxItemSet> m_pOutItemSet;
SfxShell* m_pShell; // used to create the page
SfxModule* m_pModule; // used to create the ItemSet
sal_uInt16 m_nDialogId; // Id of the former dialog
OptionsGroupInfo( SfxShell* pSh, SfxModule* pMod, sal_uInt16 nId ) :
m_pShell( pSh ),
m_pModule( pMod ), m_nDialogId( nId ) {}
};
struct OptionsPageIdInfo
{
OUString m_sParentName;
OUString m_sPageName;
sal_uInt16 m_nParentId;
sal_uInt16 m_nPageId;
OptionsPageIdInfo(OUString sParentName, OUString sPageName, sal_uInt16 nParentId,
sal_uInt16 nPageId)
: m_sParentName(std::move(sParentName))
, m_sPageName(std::move(sPageName))
, m_nParentId(nParentId)
, m_nPageId(nPageId)
{
}
};
// Basic ctor with common initialization
OfaTreeOptionsDialog::OfaTreeOptionsDialog(weld::Window* pParent, bool fromExtensionManager)
: SfxOkDialogController(pParent, u"cui/ui/optionsdialog.ui"_ustr, u"OptionsDialog"_ustr)
, xOkPB(m_xBuilder->weld_button(u"ok"_ustr))
, xApplyPB(m_xBuilder->weld_button(u"apply"_ustr))
, xBackPB(m_xBuilder->weld_button(u"revert"_ustr))
, xTreeLB(m_xBuilder->weld_tree_view(u"pages"_ustr))
, xTabBox(m_xBuilder->weld_container(u"box"_ustr))
, m_xSearchEdit(m_xBuilder->weld_entry(u"searchEntry"_ustr))
, m_pParent(pParent)
, m_aUpdateDataTimer("OfaTreeOptionsDialog UpdateDataTimer")
, bIsFirtsInitialize(true)
, sTitle(m_xDialog->get_title())
, bForgetSelection(false)
, bIsFromExtensionManager(fromExtensionManager)
, bIsForSetDocumentLanguage(false)
, bNeedsRestart(false)
, eRestartReason(svtools::RESTART_REASON_NONE)
{
Size aSize(xTreeLB->get_approximate_digit_width() * 100, xTreeLB->get_height_rows(30));
xTabBox->set_size_request(aSize.Width(), aSize.Height());
xTreeLB->set_size_request(xTreeLB->get_approximate_digit_width() * 35, aSize.Height());
// Init tree and handler
xTreeLB->set_help_id(HID_OFADLG_TREELISTBOX);
xTreeLB->connect_changed(LINK(this, OfaTreeOptionsDialog, ShowPageHdl_Impl));
xBackPB->connect_clicked(LINK(this, OfaTreeOptionsDialog, BackHdl_Impl));
xApplyPB->connect_clicked(LINK(this, OfaTreeOptionsDialog, ApplyHdl_Impl));
xOkPB->connect_clicked(LINK(this, OfaTreeOptionsDialog, ApplyHdl_Impl));
m_xSearchEdit->connect_changed(LINK(this, OfaTreeOptionsDialog, SearchUpdateHdl));
m_xSearchEdit->connect_focus_out(LINK(this, OfaTreeOptionsDialog, FocusOut_Impl));
m_xDialog->connect_help(LINK(this, OfaTreeOptionsDialog, HelpHdl_Impl));
m_aUpdateDataTimer.SetInvokeHandler(LINK(this, OfaTreeOptionsDialog, ImplUpdateDataHdl));
m_aUpdateDataTimer.SetTimeout(EDIT_UPDATEDATA_TIMEOUT);
// Initialize search util
m_options.AlgorithmType2 = util::SearchAlgorithms2::ABSOLUTE;
m_options.transliterateFlags |= TransliterationFlags::IGNORE_CASE;
m_options.searchFlag
|= (util::SearchFlags::REG_NOT_BEGINOFLINE | util::SearchFlags::REG_NOT_ENDOFLINE);
xTreeLB->set_accessible_name(sTitle);
}
// Ctor() with Frame -----------------------------------------------------
OfaTreeOptionsDialog::OfaTreeOptionsDialog(weld::Window* pParent, const Reference< XFrame >& _xFrame, bool bActivateLastSelection)
: OfaTreeOptionsDialog(pParent, false)
{
Initialize( _xFrame );
LoadExtensionOptions( u"" );
if (bActivateLastSelection)
ActivateLastSelection();
}
// Ctor() with ExtensionId -----------------------------------------------
OfaTreeOptionsDialog::OfaTreeOptionsDialog(weld::Window* pParent, std::u16string_view rExtensionId)
: OfaTreeOptionsDialog(pParent, !rExtensionId.empty())
{
LoadExtensionOptions( rExtensionId );
ActivateLastSelection();
}
void OfaTreeOptionsDialog::ImplDestroy()
{
xCurrentPageEntry.reset();
std::unique_ptr<weld::TreeIter> xEntry = xTreeLB->make_iterator();
bool bEntry = xTreeLB->get_iter_first(*xEntry);
// first children
while (bEntry)
{
// if Child (has parent), then OptionsPageInfo
if (xTreeLB->get_iter_depth(*xEntry))
{
OptionsPageInfo *pPageInfo = weld::fromId<OptionsPageInfo*>(xTreeLB->get_id(*xEntry));
if(pPageInfo->m_xPage)
{
pPageInfo->m_xPage->FillUserData();
OUString aPageData(pPageInfo->m_xPage->GetUserData());
if ( !aPageData.isEmpty() )
{
SvtViewOptions aTabPageOpt( EViewType::TabPage, OUString::number( pPageInfo->m_nPageId) );
SetViewOptUserItem( aTabPageOpt, aPageData );
}
pPageInfo->m_xPage.reset();
}
if (pPageInfo->m_nPageId == RID_SFXPAGE_LINGU)
{
// write personal dictionaries
Reference< XSearchableDictionaryList > xDicList( LinguMgr::GetDictionaryList() );
if (xDicList.is())
{
linguistic::SaveDictionaries( xDicList );
}
}
pPageInfo->m_xExtPage.reset();
delete pPageInfo;
}
bEntry = xTreeLB->iter_next(*xEntry);
}
// and parents
bEntry = xTreeLB->get_iter_first(*xEntry);
while (bEntry)
{
if (!xTreeLB->get_iter_depth(*xEntry))
{
OptionsGroupInfo* pGroupInfo = weld::fromId<OptionsGroupInfo*>(xTreeLB->get_id(*xEntry));
delete pGroupInfo;
}
bEntry = xTreeLB->iter_next(*xEntry);
}
deleteGroupNames();
}
OfaTreeOptionsDialog::~OfaTreeOptionsDialog()
{
suppress_fun_call_w_exception(ImplDestroy());
}
OptionsPageInfo* OfaTreeOptionsDialog::AddTabPage(
sal_uInt16 nId, const OUString& rPageName, sal_uInt16 nGroup )
{
std::unique_ptr<weld::TreeIter> xParent = xTreeLB->make_iterator();
if (!xTreeLB->get_iter_first(*xParent))
return nullptr;
xTreeLB->iter_nth_sibling(*xParent, nGroup);
OptionsPageInfo* pPageInfo = new OptionsPageInfo( nId );
OUString sId(weld::toId(pPageInfo));
xTreeLB->insert(xParent.get(), -1, &rPageName, &sId, nullptr, nullptr, false, nullptr);
return pPageInfo;
}
// the ItemSet* is passed on to the dialog's ownership
sal_uInt16 OfaTreeOptionsDialog::AddGroup(const OUString& rGroupName,
SfxShell* pCreateShell,
SfxModule* pCreateModule,
sal_uInt16 nDialogId )
{
OptionsGroupInfo* pInfo =
new OptionsGroupInfo( pCreateShell, pCreateModule, nDialogId );
OUString sId(weld::toId(pInfo));
xTreeLB->append(sId, rGroupName);
sal_uInt16 nRet = 0;
std::unique_ptr<weld::TreeIter> xEntry = xTreeLB->make_iterator();
bool bEntry = xTreeLB->get_iter_first(*xEntry);
while (bEntry)
{
if (!xTreeLB->get_iter_depth(*xEntry))
nRet++;
bEntry = xTreeLB->iter_next(*xEntry);
}
return nRet - 1;
}
IMPL_LINK_NOARG(OfaTreeOptionsDialog, ShowPageHdl_Impl, weld::TreeView&, void)
{
SelectHdl_Impl();
}
void OfaTreeOptionsDialog::ResetCurrentPageFromConfig()
{
if (!(xCurrentPageEntry && xTreeLB->get_iter_depth(*xCurrentPageEntry)))
return;
OptionsPageInfo* pPageInfo = weld::fromId<OptionsPageInfo*>(xTreeLB->get_id(*xCurrentPageEntry));
if (pPageInfo->m_xPage)
{
std::unique_ptr<weld::TreeIter> xParent = xTreeLB->make_iterator(xCurrentPageEntry.get());
xTreeLB->iter_parent(*xParent);
OptionsGroupInfo* pGroupInfo =
weld::fromId<OptionsGroupInfo*>(xTreeLB->get_id(*xParent));
pPageInfo->m_xPage->Reset( &*pGroupInfo->m_pInItemSet );
}
else if ( pPageInfo->m_xExtPage )
pPageInfo->m_xExtPage->ResetPage();
}
IMPL_LINK_NOARG(OfaTreeOptionsDialog, BackHdl_Impl, weld::Button&, void)
{
ResetCurrentPageFromConfig();
}
void OfaTreeOptionsDialog::ApplyOptions()
{
std::unique_ptr<weld::TreeIter> xEntry = xTreeLB->make_iterator();
bool bEntry = xTreeLB->get_iter_first(*xEntry);
while (bEntry)
{
if (xTreeLB->get_iter_depth(*xEntry))
{
OptionsPageInfo* pPageInfo = weld::fromId<OptionsPageInfo*>(xTreeLB->get_id(*xEntry));
if ( pPageInfo->m_xPage && !pPageInfo->m_xPage->HasExchangeSupport() )
{
std::unique_ptr<weld::TreeIter> xParent = xTreeLB->make_iterator(xEntry.get());
xTreeLB->iter_parent(*xParent);
OptionsGroupInfo* pGroupInfo =
weld::fromId<OptionsGroupInfo*>(xTreeLB->get_id(*xParent));
pPageInfo->m_xPage->FillItemSet(pGroupInfo->m_pOutItemSet.get());
}
if ( pPageInfo->m_xExtPage )
{
pPageInfo->m_xExtPage->DeactivatePage();
pPageInfo->m_xExtPage->SavePage();
}
if ( pPageInfo->m_xPage && RID_OPTPAGE_CHART_DEFCOLORS == pPageInfo->m_nPageId )
{
SvxDefaultColorOptPage* pPage = static_cast<SvxDefaultColorOptPage *>(pPageInfo->m_xPage.get());
pPage->SaveChartOptions();
}
}
bEntry = xTreeLB->iter_next(*xEntry);
}
}
IMPL_LINK_NOARG(OfaTreeOptionsDialog, HelpHdl_Impl, weld::Widget&, bool)
{
Help* pHelp = Application::GetHelp();
if (pHelp && xCurrentPageEntry && xTreeLB->get_iter_depth(*xCurrentPageEntry))
{
OptionsPageInfo* pPageInfo = weld::fromId<OptionsPageInfo*>(xTreeLB->get_id(*xCurrentPageEntry));
if (pPageInfo->m_xPage)
{
OUString sHelpId(pPageInfo->m_xPage->GetHelpId());
pHelp->Start(sHelpId, m_xDialog.get());
return false;
}
}
return true;
}
IMPL_LINK(OfaTreeOptionsDialog, ApplyHdl_Impl, weld::Button&, rButton, void)
{
bool bOkPressed = &rButton == xOkPB.get();
OptionsGroupInfo* pGroupInfo = nullptr;
if (xCurrentPageEntry && xTreeLB->get_iter_depth(*xCurrentPageEntry))
{
OptionsPageInfo* pPageInfo = weld::fromId<OptionsPageInfo*>(xTreeLB->get_id(*xCurrentPageEntry));
if ( pPageInfo->m_xPage )
{
std::unique_ptr<weld::TreeIter> xParent = xTreeLB->make_iterator(xCurrentPageEntry.get());
xTreeLB->iter_parent(*xParent);
pGroupInfo = weld::fromId<OptionsGroupInfo*>(xTreeLB->get_id(*xParent));
if ( RID_SVXPAGE_COLOR != pPageInfo->m_nPageId
&& pPageInfo->m_xPage->HasExchangeSupport() )
{
DeactivateRC nLeave = pPageInfo->m_xPage->DeactivatePage(pGroupInfo->m_pOutItemSet.get());
if ( nLeave == DeactivateRC::KeepPage )
{
// the page mustn't be left, so return early
assert(xTreeLB->is_selected(*xCurrentPageEntry)); // presumably this must be true here
if (bOkPressed)
return;
}
}
}
}
ApplyOptions();
ApplyItemSets();
utl::ConfigManager::storeConfigItems();
if (bOkPressed)
m_xDialog->response(RET_OK);
else
{
// tdf#137930 rebuild the in and out itemsets to reflect the current
// post-apply state
if (pGroupInfo && pGroupInfo->m_pInItemSet)
{
// tdf#138596 seeing as the SfxTabPages keep pointers to the m_pInItemSet
// we update the contents of the existing SfxItemSets to match
// the current settings, rather than create new ones
auto xInItemSet = pGroupInfo->m_pShell
? pGroupInfo->m_pShell->CreateItemSet( pGroupInfo->m_nDialogId )
: CreateItemSet( pGroupInfo->m_nDialogId );
pGroupInfo->m_pInItemSet->Set(*xInItemSet, false);
pGroupInfo->m_pOutItemSet->ClearItem();
}
// for the Apply case, now that the settings are saved to config,
// reload the current page so it knows what the config now states
ResetCurrentPageFromConfig();
// reselect it to undo possible DeactivatePage above
xCurrentPageEntry.reset();
SelectHdl_Impl();
}
if (!bNeedsRestart)
return;
SolarMutexGuard aGuard;
weld::Window* pParent;
if (!bOkPressed)
pParent = m_xDialog.get();
else
{
m_xDialog->hide();
pParent = m_pParent;
}
bool bRestart = ::svtools::executeRestartDialog(comphelper::getProcessComponentContext(),
pParent, eRestartReason);
if (bRestart && !bOkPressed)
m_xDialog->response(RET_OK);
}
IMPL_LINK_NOARG(OfaTreeOptionsDialog, FocusOut_Impl, weld::Widget&, void)
{
if (m_aUpdateDataTimer.IsActive())
{
m_aUpdateDataTimer.Stop();
m_aUpdateDataTimer.Invoke();
}
}
IMPL_LINK_NOARG(OfaTreeOptionsDialog, SearchUpdateHdl, weld::Entry&, void)
{
m_aUpdateDataTimer.Start();
}
IMPL_LINK_NOARG(OfaTreeOptionsDialog, ImplUpdateDataHdl, Timer*, void)
{
// initializeAllDialogs() can take a long time, show wait cursor and disable input
m_xSearchEdit->set_editable(false);
m_xSearchEdit->set_busy_cursor(true);
// Pause redraw
xTreeLB->freeze();
if (bIsFirtsInitialize)
{
m_xSearchEdit->freeze();
xTreeLB->hide();
initializeAllDialogs();
m_xSearchEdit->thaw();
xTreeLB->show();
bIsFirtsInitialize = false;
}
// Apply the search filter
OUString aSearchTerm(m_xSearchEdit->get_text());
int nMatchFound = applySearchFilter(aSearchTerm);
// Resume redraw
xTreeLB->thaw();
// select first child of first node after the search done
if (nMatchFound != -1)
selectFirstEntry();
m_xSearchEdit->set_editable(true);
m_xSearchEdit->set_busy_cursor(false);
}
void OfaTreeOptionsDialog::selectFirstEntry()
{
std::unique_ptr<weld::TreeIter> xTemp = xTreeLB->make_iterator();
bool bTemp = xTreeLB->get_iter_first(*xTemp);
while (bTemp)
{
// select only the first child
if (xTreeLB->get_iter_depth(*xTemp) && xTreeLB->get_id(*xTemp).toInt64())
{
std::unique_ptr<weld::TreeIter> xEntry(xTreeLB->make_iterator(xTemp.get()));
std::unique_ptr<weld::TreeIter> xParent(xTreeLB->make_iterator(xEntry.get()));
xTreeLB->iter_parent(*xParent);
xTreeLB->expand_row(*xParent);
xTreeLB->scroll_to_row(*xParent);
xTreeLB->scroll_to_row(*xEntry);
xTreeLB->set_cursor(*xEntry);
xTreeLB->select(*xEntry);
SelectHdl_Impl();
break;
}
bTemp = xTreeLB->iter_next(*xTemp);
}
}
void OfaTreeOptionsDialog::initializeAllDialogs()
{
std::unique_ptr<weld::TreeIter> xEntry;
std::unique_ptr<weld::TreeIter> xTemp = xTreeLB->make_iterator();
bool bTemp = xTreeLB->get_iter_first(*xTemp);
while (bTemp)
{
if (xTreeLB->get_iter_depth(*xTemp) && xTreeLB->get_id(*xTemp).toInt64())
{
if (!(xEntry = xTreeLB->make_iterator(xTemp.get())))
{
xEntry = xTreeLB->make_iterator();
if (!xTreeLB->get_iter_first(*xEntry) || !xTreeLB->iter_next(*xEntry))
xEntry.reset();
}
if (!xEntry)
return;
OptionsPageInfo* pPageInfo = weld::fromId<OptionsPageInfo*>(xTreeLB->get_id(*xEntry));
if (TreeOptHelper::getStringsFromDialog(pPageInfo->m_nPageId).isEmpty())
{
SolarMutexGuard aGuard;
initializeCurrentDialog(pPageInfo, xEntry);
}
}
bTemp = xTreeLB->iter_next(*xTemp);
}
}
void OfaTreeOptionsDialog::clearOptionsDialog()
{
// clear and reset
std::unique_ptr<weld::TreeIter> xEntry = xTreeLB->make_iterator();
bool bEntry = xTreeLB->get_iter_first(*xEntry);
while (bEntry)
{
if (xTreeLB->get_iter_depth(*xEntry))
{
OptionsPageInfo* pPageInfo = weld::fromId<OptionsPageInfo*>(xTreeLB->get_id(*xEntry));
if (pPageInfo->m_xPage)
pPageInfo->m_xPage.reset();
}
bEntry = xTreeLB->iter_next(*xEntry);
}
xCurrentPageEntry.reset();
}
// store Options tree with their page names
void OfaTreeOptionsDialog::storeOptionsTree()
{
m_aTreePageIds.clear();
sal_uInt16 aParentId = 0;
OUString sParentName;
std::unique_ptr<weld::TreeIter> xEntry = xTreeLB->make_iterator();
bool bEntry = xTreeLB->get_iter_first(*xEntry);
while (bEntry)
{
OptionsGroupInfo* pGroupInfo = weld::fromId<OptionsGroupInfo*>(xTreeLB->get_id(*xEntry));
bool bIsParentNode = !xTreeLB->get_iter_depth(*xEntry);
if (bIsParentNode)
{
// Parent node
sParentName = xTreeLB->get_text(*xEntry);
aParentId = pGroupInfo->m_nDialogId;
m_aTreePageIds.push_back(new OptionsPageIdInfo(sParentName, sParentName, aParentId, 0));
}
else
{
// Child node
OUString sChildName = xTreeLB->get_text(*xEntry);
OptionsPageInfo* pPageInfo = weld::fromId<OptionsPageInfo*>(xTreeLB->get_id(*xEntry));
m_aTreePageIds.push_back(
new OptionsPageIdInfo(sParentName, sChildName, aParentId, pPageInfo->m_nPageId));
}
bEntry = xTreeLB->iter_next(*xEntry);
}
}
int OfaTreeOptionsDialog::applySearchFilter(const OUString& rSearchTerm)
{
if (rSearchTerm.isEmpty())
{
clearOptionsDialog();
xTreeLB->clear();
Initialize(m_xFrame);
return 0;
}
m_options.searchString = rSearchTerm;
utl::TextSearch textSearch(m_options);
clearOptionsDialog();
if (xTreeLB->n_children() > 0)
xTreeLB->clear();
std::vector<std::pair<sal_uInt16, std::vector<sal_uInt16>>> aFoundIdsVector;
for (std::size_t i = 0; i < m_aTreePageIds.size(); ++i)
{
const OUString sParentName = m_aTreePageIds[i]->m_sParentName;
const OUString sPageName = m_aTreePageIds[i]->m_sPageName;
const sal_uInt16 nParentId = m_aTreePageIds[i]->m_nParentId;
const sal_uInt16 nPageId = m_aTreePageIds[i]->m_nPageId;
const OUString sPageStrings = TreeOptHelper::getStringsFromDialog(nPageId);
const OUString sPageNameAndStrings = sParentName + " " + sPageName + " " + sPageStrings;
sal_Int32 aStartPos = 0;
sal_Int32 aEndPos = sPageNameAndStrings.getLength();
// check if rSearchTerm matches with sPageNameAndStrings
if (textSearch.SearchForward(sPageNameAndStrings, &aStartPos, &aEndPos))
{
bool isFound = false;
for (auto& aEntryId : aFoundIdsVector)
{
if (aEntryId.first == nParentId)
{
isFound = true;
aEntryId.second.push_back(nPageId);
}
}
if (!isFound)
aFoundIdsVector.push_back({ nParentId, { nPageId } });
}
}
showDialog(aFoundIdsVector);
// if treeview is empty, return -1
return xTreeLB->n_children() ? 0 : -1;
}
void OfaTreeOptionsDialog::showDialog(VectorOfMatchedIds& pSearchIds)
{
//
// void generalOptions(); // SID_GENERAL_OPTIONS
// void loadAndSaveOptions(); // SID_FILTER_DLG
// void languageOptions(); // SID_LANGUAGE_OPTIONS
// void writerOptions(); // SID_SW_EDITOPTIONS
// void writerWebOptions(); // SID_SW_ONLINEOPTIONS
// void calcOptions(); // SID_SC_EDITOPTIONS
// void impressOptions(); // SID_SD_EDITOPTIONS
// void drawOptions(); // SID_SD_GRAPHIC_OPTIONS
// void mathOptions(); // SID_SM_EDITOPTIONS
// void databaseOptions(); // SID_SB_STARBASEOPTIONS
// void chartOptions(); // SID_SCH_EDITOPTIONS
// void internetOptions(); // SID_INET_DLG
//
for (auto& aEntryId : pSearchIds)
{
switch (aEntryId.first)
{
case SID_GENERAL_OPTIONS:
generalOptions(aEntryId.second);
break;
case SID_FILTER_DLG:
loadAndSaveOptions(aEntryId.second);
break;
case SID_LANGUAGE_OPTIONS:
languageOptions(aEntryId.second);
break;
case SID_SW_EDITOPTIONS:
writerOptions(aEntryId.second);
break;
case SID_SW_ONLINEOPTIONS:
writerWebOptions(aEntryId.second);
break;
case SID_SC_EDITOPTIONS:
calcOptions(aEntryId.second);
break;
case SID_SD_EDITOPTIONS:
impressOptions(aEntryId.second);
break;
case SID_SD_GRAPHIC_OPTIONS:
drawOptions(aEntryId.second);
break;
case SID_SM_EDITOPTIONS:
mathOptions(aEntryId.second);
break;
case SID_SB_STARBASEOPTIONS:
databaseOptions(aEntryId.second);
break;
case SID_SCH_EDITOPTIONS:
chartOptions(aEntryId.second);
break;
case SID_INET_DLG:
internetOptions(aEntryId.second);
break;
default:
break;
}
}
}
void OfaTreeOptionsDialog::ApplyItemSets()
{
std::unique_ptr<weld::TreeIter> xEntry = xTreeLB->make_iterator();
bool bEntry = xTreeLB->get_iter_first(*xEntry);
while (bEntry)
{
if (!xTreeLB->get_iter_depth(*xEntry))
{
OptionsGroupInfo* pGroupInfo = weld::fromId<OptionsGroupInfo*>(xTreeLB->get_id(*xEntry));
if(pGroupInfo->m_pOutItemSet)
{
if(pGroupInfo->m_pShell)
pGroupInfo->m_pShell->ApplyItemSet( pGroupInfo->m_nDialogId, *pGroupInfo->m_pOutItemSet);
else
ApplyItemSet( pGroupInfo->m_nDialogId, *pGroupInfo->m_pOutItemSet);
}
}
bEntry = xTreeLB->iter_next(*xEntry);
}
}
void OfaTreeOptionsDialog::ActivatePage( sal_uInt16 nResId )
{
bIsForSetDocumentLanguage = false;
if ( nResId == OFA_TP_LANGUAGES_FOR_SET_DOCUMENT_LANGUAGE )
{
bIsForSetDocumentLanguage = true;
nResId = OFA_TP_LANGUAGES;
}
DBG_ASSERT( !bIsFromExtensionManager, "OfaTreeOptionsDialog::ActivatePage(): call from extension manager" );
if ( !pLastPageSaver )
pLastPageSaver = new LastPageSaver;
bForgetSelection = true;
sal_uInt16 nTemp = pLastPageSaver->m_nLastPageId;
pLastPageSaver->m_nLastPageId = nResId;
ActivateLastSelection();
pLastPageSaver->m_nLastPageId = nTemp;
}
void OfaTreeOptionsDialog::ActivatePage( const OUString& rPageURL )
{
DBG_ASSERT( !bIsFromExtensionManager, "OfaTreeOptionsDialog::ActivatePage(): call from extension manager" );
if ( !pLastPageSaver )
pLastPageSaver = new LastPageSaver;
bForgetSelection = true;
pLastPageSaver->m_nLastPageId = 0;
pLastPageSaver->m_sLastPageURL_Tools = rPageURL;
ActivateLastSelection();
}
void OfaTreeOptionsDialog::ActivateLastSelection()
{
std::unique_ptr<weld::TreeIter> xEntry;
if (pLastPageSaver)
{
OUString sLastURL = bIsFromExtensionManager ? pLastPageSaver->m_sLastPageURL_ExtMgr
: pLastPageSaver->m_sLastPageURL_Tools;
if ( sLastURL.isEmpty() )
{
sLastURL = !bIsFromExtensionManager ? pLastPageSaver->m_sLastPageURL_ExtMgr
: pLastPageSaver->m_sLastPageURL_Tools;
}
bool bMustExpand = ( INetURLObject( sLastURL ).GetProtocol() == INetProtocol::File );
std::unique_ptr<weld::TreeIter> xTemp = xTreeLB->make_iterator();
bool bTemp = xTreeLB->get_iter_first(*xTemp);
while (bTemp)
{
// restore only selection of a leaf
if (xTreeLB->get_iter_depth(*xTemp) && xTreeLB->get_id(*xTemp).toInt64())
{
OptionsPageInfo* pPageInfo = weld::fromId<OptionsPageInfo*>(xTreeLB->get_id(*xTemp));
OUString sPageURL = pPageInfo->m_sPageURL;
if ( bMustExpand )
{
sPageURL = comphelper::getExpandedUri(
comphelper::getProcessComponentContext(), sPageURL);
}
if ( ( !bIsFromExtensionManager
&& pPageInfo->m_nPageId && pPageInfo->m_nPageId == pLastPageSaver->m_nLastPageId )
|| ( !pPageInfo->m_nPageId && sLastURL == sPageURL ) )
{
xEntry = xTreeLB->make_iterator(xTemp.get());
break;
}
}
bTemp = xTreeLB->iter_next(*xTemp);
}
}
if (!xEntry)
{
xEntry = xTreeLB->make_iterator();
if (!xTreeLB->get_iter_first(*xEntry) || !xTreeLB->iter_next(*xEntry))
xEntry.reset();
}
if (!xEntry)
return;
std::unique_ptr<weld::TreeIter> xParent(xTreeLB->make_iterator(xEntry.get()));
xTreeLB->iter_parent(*xParent);
xTreeLB->expand_row(*xParent);
xTreeLB->scroll_to_row(*xParent);
xTreeLB->scroll_to_row(*xEntry);
xTreeLB->set_cursor(*xEntry);
xTreeLB->select(*xEntry);
m_xSearchEdit->grab_focus();
SelectHdl_Impl();
}
void OfaTreeOptionsDialog::InitItemSets(OptionsGroupInfo& rGroupInfo)
{
if (!rGroupInfo.m_pInItemSet)
rGroupInfo.m_pInItemSet.emplace( rGroupInfo.m_pShell
? *rGroupInfo.m_pShell->CreateItemSet( rGroupInfo.m_nDialogId )
: *CreateItemSet( rGroupInfo.m_nDialogId ) );
if (!rGroupInfo.m_pOutItemSet)
rGroupInfo.m_pOutItemSet = std::make_unique<SfxItemSet>(
*rGroupInfo.m_pInItemSet->GetPool(),
rGroupInfo.m_pInItemSet->GetRanges());
}
void OfaTreeOptionsDialog::initializeCurrentDialog(OptionsPageInfo*& pPageInfo,
std::unique_ptr<weld::TreeIter>& xEntry)
{
std::unique_ptr<weld::TreeIter> xParent(xTreeLB->make_iterator(xEntry.get()));
bool bParent = xTreeLB->iter_parent(*xParent);
if (!bParent)
return;
if (pPageInfo->m_xPage)
{
TreeOptHelper::storeStringsOfDialog(pPageInfo->m_nPageId,
pPageInfo->m_xPage->GetAllStrings());
return;
}
OptionsGroupInfo* pGroupInfo = weld::fromId<OptionsGroupInfo*>(xTreeLB->get_id(*xParent));
if (!pPageInfo->m_xPage && pPageInfo->m_nPageId > 0)
{
InitItemSets(*pGroupInfo);
pPageInfo->m_xPage = ::CreateGeneralTabPage(pPageInfo->m_nPageId, xTabBox.get(), this,
*pGroupInfo->m_pInItemSet);
if (!pPageInfo->m_xPage && pGroupInfo->m_pModule)
pPageInfo->m_xPage = pGroupInfo->m_pModule->CreateTabPage(
pPageInfo->m_nPageId, xTabBox.get(), this, *pGroupInfo->m_pInItemSet);
DBG_ASSERT(pPageInfo->m_xPage, "tabpage could not created");
if (pPageInfo->m_xPage)
{
SvtViewOptions aTabPageOpt(EViewType::TabPage, OUString::number(pPageInfo->m_nPageId));
pPageInfo->m_xPage->SetUserData(GetViewOptUserItem(aTabPageOpt));
pPageInfo->m_xPage->SetFrame(m_xFrame);
pPageInfo->m_xPage->Reset(&*pGroupInfo->m_pInItemSet);
}
TreeOptHelper::storeStringsOfDialog(pPageInfo->m_nPageId,
pPageInfo->m_xPage->GetAllStrings());
pPageInfo->m_xPage->set_visible(false);
}
else if (0 == pPageInfo->m_nPageId && !pPageInfo->m_xExtPage)
{
if (!m_xContainerWinProvider.is())
m_xContainerWinProvider
= awt::ContainerWindowProvider::create(::comphelper::getProcessComponentContext());
pPageInfo->m_xExtPage = std::make_unique<ExtensionsTabPage>(
xTabBox.get(), pPageInfo->m_sPageURL, pPageInfo->m_sEventHdl, m_xContainerWinProvider);
pPageInfo->m_xExtPage->Hide();
}
BuilderPage* pNewPage = pPageInfo->m_xPage.get();
// fdo#58170 use current page's layout child HelpId, unless there isn't a current page
OUString sHelpId(pNewPage ? pNewPage->GetHelpId() : OUString());
if (sHelpId.isEmpty())
sHelpId = HID_OFADLG_TREELISTBOX;
xTreeLB->set_help_id(sHelpId);
}
void OfaTreeOptionsDialog::SelectHdl_Impl()
{
std::unique_ptr<weld::TreeIter> xEntry(xTreeLB->make_iterator());
if (!xTreeLB->get_cursor(xEntry.get()))
return;
if (xCurrentPageEntry && xCurrentPageEntry->equal(*xEntry))
return;
std::unique_ptr<weld::TreeIter> xParent(xTreeLB->make_iterator(xEntry.get()));
bool bParent = xTreeLB->iter_parent(*xParent);
// If the user has selected a category, automatically switch to a suitable
// default sub-page instead.
if (!bParent)
return;
BuilderPage* pNewPage = nullptr;
OptionsPageInfo* pOptPageInfo = (xCurrentPageEntry && xTreeLB->get_iter_depth(*xCurrentPageEntry))
? weld::fromId<OptionsPageInfo*>(xTreeLB->get_id(*xCurrentPageEntry)) : nullptr;
if (pOptPageInfo && pOptPageInfo->m_xPage && pOptPageInfo->m_xPage->IsVisible())
{
std::unique_ptr<weld::TreeIter> xCurParent(xTreeLB->make_iterator(xCurrentPageEntry.get()));
xTreeLB->iter_parent(*xCurParent);
OptionsGroupInfo* pGroupInfo = weld::fromId<OptionsGroupInfo*>(xTreeLB->get_id(*xCurParent));
DeactivateRC nLeave = DeactivateRC::LeavePage;
if ( RID_SVXPAGE_COLOR != pOptPageInfo->m_nPageId && pOptPageInfo->m_xPage->HasExchangeSupport() )
nLeave = pOptPageInfo->m_xPage->DeactivatePage( pGroupInfo->m_pOutItemSet.get() );
if ( nLeave == DeactivateRC::KeepPage )
{
// we cannot leave this page, this is may be from a user clicking a different entry
// in the tree so reselect the current page
xTreeLB->select(*xCurrentPageEntry);
return;
}
else
pOptPageInfo->m_xPage->set_visible(false);
}
else if ( pOptPageInfo && pOptPageInfo->m_xExtPage )
{
pOptPageInfo->m_xExtPage->Hide();
pOptPageInfo->m_xExtPage->DeactivatePage();
}
OptionsPageInfo *pPageInfo = weld::fromId<OptionsPageInfo*>(xTreeLB->get_id(*xEntry));
OptionsGroupInfo* pGroupInfo = weld::fromId<OptionsGroupInfo*>(xTreeLB->get_id(*xParent));
if(!pPageInfo->m_xPage && pPageInfo->m_nPageId > 0)
{
InitItemSets(*pGroupInfo);
pPageInfo->m_xPage = ::CreateGeneralTabPage(pPageInfo->m_nPageId, xTabBox.get(), this, *pGroupInfo->m_pInItemSet);
if(!pPageInfo->m_xPage && pGroupInfo->m_pModule)
pPageInfo->m_xPage = pGroupInfo->m_pModule->CreateTabPage(pPageInfo->m_nPageId, xTabBox.get(), this, *pGroupInfo->m_pInItemSet);
DBG_ASSERT( pPageInfo->m_xPage, "tabpage could not created");
if ( pPageInfo->m_xPage )
{
SvtViewOptions aTabPageOpt( EViewType::TabPage, OUString::number( pPageInfo->m_nPageId) );
pPageInfo->m_xPage->SetUserData( GetViewOptUserItem( aTabPageOpt ) );
pPageInfo->m_xPage->SetFrame( m_xFrame );
pPageInfo->m_xPage->Reset( &*pGroupInfo->m_pInItemSet );
}
}
else if ( 0 == pPageInfo->m_nPageId && !pPageInfo->m_xExtPage )
{
if ( !m_xContainerWinProvider.is() )
{
m_xContainerWinProvider = awt::ContainerWindowProvider::create( ::comphelper::getProcessComponentContext() );
}
pPageInfo->m_xExtPage = std::make_unique<ExtensionsTabPage>(
xTabBox.get(), pPageInfo->m_sPageURL, pPageInfo->m_sEventHdl, m_xContainerWinProvider);
}
if ( pPageInfo->m_xPage )
{
if ( RID_SVXPAGE_COLOR != pPageInfo->m_nPageId &&
pPageInfo->m_xPage->HasExchangeSupport())
{
pPageInfo->m_xPage->ActivatePage(*pGroupInfo->m_pOutItemSet);
}
pPageInfo->m_xPage->set_visible(true);
}
else if ( pPageInfo->m_xExtPage )
{
pPageInfo->m_xExtPage->Show();
pPageInfo->m_xExtPage->ActivatePage();
}
{
OUString sTitleText = sTitle
+ " - " + xTreeLB->get_text(*xParent)
+ " - " + xTreeLB->get_text(*xEntry);
m_xDialog->set_title(sTitleText);
}
xCurrentPageEntry = std::move(xEntry);
if ( !bForgetSelection )
{
if ( !pLastPageSaver )
pLastPageSaver = new LastPageSaver;
if ( !bIsFromExtensionManager )
pLastPageSaver->m_nLastPageId = pPageInfo->m_nPageId;
if ( pPageInfo->m_xExtPage )
{
if ( bIsFromExtensionManager )
pLastPageSaver->m_sLastPageURL_ExtMgr = pPageInfo->m_sPageURL;
else
pLastPageSaver->m_sLastPageURL_Tools = pPageInfo->m_sPageURL;
}
}
pNewPage = pPageInfo->m_xPage.get();
// fdo#58170 use current page's layout child HelpId, unless there isn't a current page
OUString sHelpId(pNewPage ? pNewPage->GetHelpId() : OUString());
if (sHelpId.isEmpty())
sHelpId = HID_OFADLG_TREELISTBOX;
xTreeLB->set_help_id(sHelpId);
}
std::optional<SfxItemSet> OfaTreeOptionsDialog::CreateItemSet( sal_uInt16 nId )
{
Reference< XLinguProperties > xProp( LinguMgr::GetLinguPropertySet() );
std::optional<SfxItemSet> pRet;
switch(nId)
{
case SID_GENERAL_OPTIONS:
{
pRet.emplace(
SfxGetpApp()->GetPool(),
svl::Items<
SID_HTML_MODE, SID_HTML_MODE,
SID_ATTR_METRIC, SID_ATTR_METRIC,
SID_AUTOSPELL_CHECK, SID_AUTOSPELL_CHECK,
SID_ATTR_QUICKLAUNCHER, SID_ATTR_QUICKLAUNCHER,
SID_ATTR_YEAR2000, SID_ATTR_YEAR2000> );
SfxItemSetFixed<SID_ATTR_QUICKLAUNCHER, SID_ATTR_QUICKLAUNCHER> aOptSet( SfxGetpApp()->GetPool() );
SfxApplication::GetOptions(aOptSet);
pRet->Put(aOptSet);
SfxViewFrame* pViewFrame = SfxViewFrame::Current();
if ( pViewFrame )
{
SfxPoolItemHolder aResult;
const SfxItemState aState(pViewFrame->GetDispatcher()->QueryState(SID_ATTR_YEAR2000, aResult));
const SfxUInt16Item* pItem(static_cast<const SfxUInt16Item*>(aResult.getItem()));
// miscellaneous - Year2000
if(SfxItemState::DEFAULT <= aState && nullptr != pItem)
pRet->Put( SfxUInt16Item( SID_ATTR_YEAR2000, pItem->GetValue() ) );
else
pRet->Put( SfxUInt16Item( SID_ATTR_YEAR2000, officecfg::Office::Common::DateFormat::TwoDigitYear::get() ) );
}
else
pRet->Put( SfxUInt16Item( SID_ATTR_YEAR2000, officecfg::Office::Common::DateFormat::TwoDigitYear::get() ) );
// miscellaneous - Tabulator
pRet->Put(SfxBoolItem(SID_PRINTER_NOTFOUND_WARN, officecfg::Office::Common::Print::Warning::NotFound::get()));
SfxPrinterChangeFlags nFlag = officecfg::Office::Common::Print::Warning::PaperSize::get() ? SfxPrinterChangeFlags::CHG_SIZE : SfxPrinterChangeFlags::NONE;
nFlag |= officecfg::Office::Common::Print::Warning::PaperOrientation::get() ? SfxPrinterChangeFlags::CHG_ORIENTATION : SfxPrinterChangeFlags::NONE;
pRet->Put( SfxFlagItem( SID_PRINTER_CHANGESTODOC, static_cast<int>(nFlag) ));
}
break;
case SID_LANGUAGE_OPTIONS :
{
pRet.emplace(
SfxGetpApp()->GetPool(),
svl::Items<
SID_ATTR_CHAR_CJK_LANGUAGE, SID_ATTR_CHAR_CJK_LANGUAGE,
SID_ATTR_CHAR_CTL_LANGUAGE, SID_ATTR_CHAR_CTL_LANGUAGE,
SID_SET_DOCUMENT_LANGUAGE, SID_SET_DOCUMENT_LANGUAGE,
SID_ATTR_LANGUAGE, SID_ATTR_LANGUAGE,
SID_AUTOSPELL_CHECK, SID_AUTOSPELL_CHECK,
SID_OPT_LOCALE_CHANGED, SID_OPT_LOCALE_CHANGED>);
// for linguistic
SfxHyphenRegionItem aHyphen( SID_ATTR_HYPHENREGION );
sal_Int16 nMinLead = 2,
nMinTrail = 2;
if (xProp.is())
{
nMinLead = xProp->getHyphMinLeading();
nMinTrail = xProp->getHyphMinTrailing();
}
aHyphen.GetMinLead() = static_cast<sal_uInt8>(nMinLead);
aHyphen.GetMinTrail() = static_cast<sal_uInt8>(nMinTrail);
SfxViewFrame* pViewFrame = SfxViewFrame::Current();
if ( pViewFrame )
{
SfxPoolItemHolder aResult;
SfxDispatcher* pDispatch(pViewFrame->GetDispatcher());
SfxItemState aState(pDispatch->QueryState(SID_ATTR_LANGUAGE, aResult));
if(SfxItemState::DEFAULT <= aState)
pRet->Put(*aResult.getItem());
aState = pDispatch->QueryState(SID_ATTR_CHAR_CJK_LANGUAGE, aResult);
if(SfxItemState::DEFAULT <= aState)
pRet->Put(*aResult.getItem());
aState = pDispatch->QueryState(SID_ATTR_CHAR_CTL_LANGUAGE, aResult);
if(SfxItemState::DEFAULT <= aState)
pRet->Put(*aResult.getItem());
pRet->Put(aHyphen);
aState = pDispatch->QueryState(SID_AUTOSPELL_CHECK, aResult);
if(SfxItemState::DEFAULT <= aState)
{
pRet->Put(*aResult.getItem()); // allow share/refcounting
// pRet->Put(std::unique_ptr<SfxPoolItem>(aResult.getItem()->Clone()));
}
else
{
bool bVal = false;
if (xProp.is())
{
bVal = xProp->getIsSpellAuto();
}
pRet->Put(SfxBoolItem(SID_AUTOSPELL_CHECK, bVal));
}
}
pRet->Put( SfxBoolItem( SID_SET_DOCUMENT_LANGUAGE, bIsForSetDocumentLanguage ) );
}
break;
case SID_INET_DLG :
pRet.emplace( SfxGetpApp()->GetPool(),
svl::Items<
//SID_OPTIONS_START - ..END
SID_SAVEREL_INET, SID_SAVEREL_FSYS,
SID_INET_NOPROXY, SID_INET_HTTP_PROXY_PORT,
SID_SECURE_URL, SID_SECURE_URL> );
SfxApplication::GetOptions(*pRet);
break;
case SID_FILTER_DLG:
pRet.emplace(
SfxGetpApp()->GetPool(),
svl::Items<
SID_ATTR_WARNALIENFORMAT, SID_ATTR_WARNALIENFORMAT,
SID_ATTR_DOCINFO, SID_ATTR_AUTOSAVEMINUTE,
SID_SAVEREL_INET, SID_SAVEREL_FSYS,
SID_ATTR_PRETTYPRINTING, SID_ATTR_PRETTYPRINTING> );
SfxApplication::GetOptions(*pRet);
break;
case SID_SB_STARBASEOPTIONS:
pRet.emplace( SfxGetpApp()->GetPool(),
svl::Items<SID_SB_POOLING_ENABLED, SID_SB_DB_REGISTER> );
::offapp::ConnectionPoolConfig::GetOptions(*pRet);
svx::DbRegisteredNamesConfig::GetOptions(*pRet);
break;
case SID_SCH_EDITOPTIONS:
{
pRet.emplace( SfxGetpApp()->GetPool(), svl::Items<SID_SCH_EDITOPTIONS, SID_SCH_EDITOPTIONS> );
pRet->Put( SvxChartColorTableItem( SID_SCH_EDITOPTIONS, SvxChartOptions::GetDefaultColors() ) );
break;
}
}
return pRet;
}
void OfaTreeOptionsDialog::ApplyItemSet( sal_uInt16 nId, const SfxItemSet& rSet )
{
switch(nId)
{
case SID_GENERAL_OPTIONS:
{
std::shared_ptr<comphelper::ConfigurationChanges> batch(comphelper::ConfigurationChanges::create());
SfxItemSetFixed<SID_ATTR_QUICKLAUNCHER, SID_ATTR_QUICKLAUNCHER> aOptSet(SfxGetpApp()->GetPool());
aOptSet.Put(rSet);
if(aOptSet.Count())
SfxApplication::SetOptions( aOptSet );
// get dispatcher anew, because SetOptions() might have destroyed the dispatcher
SfxViewFrame *pViewFrame = SfxViewFrame::Current();
// evaluate Year2000
sal_uInt16 nY2K = USHRT_MAX;
const SfxUInt16Item* pYearItem = rSet.GetItemIfSet( SID_ATTR_YEAR2000, false );
if( pYearItem )
nY2K = pYearItem->GetValue();
if( USHRT_MAX != nY2K )
{
if ( pViewFrame )
{
SfxDispatcher* pDispatch = pViewFrame->GetDispatcher();
pDispatch->ExecuteList(SID_ATTR_YEAR2000,
SfxCallMode::ASYNCHRON, { pYearItem });
}
officecfg::Office::Common::DateFormat::TwoDigitYear::set(nY2K, batch);
}
// evaluate print
if(const SfxBoolItem* pWarnItem = rSet.GetItemIfSet(SID_PRINTER_NOTFOUND_WARN, false))
officecfg::Office::Common::Print::Warning::NotFound::set(pWarnItem->GetValue(), batch);
if(const SfxFlagItem* pFlag = rSet.GetItemIfSet(SID_PRINTER_CHANGESTODOC, false))
{
bool bPaperSizeWarning = bool(static_cast<SfxPrinterChangeFlags>(pFlag->GetValue()) & SfxPrinterChangeFlags::CHG_SIZE);
officecfg::Office::Common::Print::Warning::PaperSize::set(bPaperSizeWarning, batch);
bool bPaperOrientationWarning = bool(static_cast<SfxPrinterChangeFlags>(pFlag->GetValue()) & SfxPrinterChangeFlags::CHG_ORIENTATION);
officecfg::Office::Common::Print::Warning::PaperOrientation::set(bPaperOrientationWarning, batch);
}
// evaluate help options
bool bHelpTips = officecfg::Office::Common::Help::Tip::get();
if ( bHelpTips != Help::IsQuickHelpEnabled() )
bHelpTips ? Help::EnableQuickHelp() : Help::DisableQuickHelp();
bool bExtendedHelp = officecfg::Office::Common::Help::ExtendedTip::get();
if ( bExtendedHelp != Help::IsBalloonHelpEnabled() )
bExtendedHelp ? Help::EnableBalloonHelp() : Help::DisableBalloonHelp();
batch->commit();
}
break;
case SID_LANGUAGE_OPTIONS :
{
OfaTreeOptionsDialog::ApplyLanguageOptions(rSet);
}
break;
case SID_INET_DLG :
case SID_FILTER_DLG:
SfxApplication::SetOptions( rSet );
break;
case SID_SB_STARBASEOPTIONS:
::offapp::ConnectionPoolConfig::SetOptions( rSet );
svx::DbRegisteredNamesConfig::SetOptions(rSet);
break;
case SID_SCH_EDITOPTIONS:
// nothing to do. Chart options only apply to newly created charts
break;
default:
{
SAL_WARN("cui.options", "Unhandled option in ApplyItemSet");
}
break;
}
}
void OfaTreeOptionsDialog::ApplyLanguageOptions(const SfxItemSet& rSet)
{
bool bSaveSpellCheck = false;
const SfxPoolItem* pItem = nullptr;
const Reference< XComponentContext >& xContext( ::comphelper::getProcessComponentContext() );
Reference< XLinguProperties > xProp = LinguProperties::create( xContext );
if ( const SfxHyphenRegionItem* pHyphenItem = rSet.GetItemIfSet(SID_ATTR_HYPHENREGION, false ) )
{
xProp->setHyphMinLeading( static_cast<sal_Int16>(pHyphenItem->GetMinLead()) );
xProp->setHyphMinTrailing( static_cast<sal_Int16>(pHyphenItem->GetMinTrail()) );
bSaveSpellCheck = true;
}
SfxViewFrame *pViewFrame = SfxViewFrame::Current();
if ( pViewFrame )
{
SfxDispatcher* pDispatch = pViewFrame->GetDispatcher();
pItem = nullptr;
if(SfxItemState::SET == rSet.GetItemState( SID_ATTR_LANGUAGE, false, &pItem ))
{
pDispatch->ExecuteList(pItem->Which(), SfxCallMode::SYNCHRON, { pItem });
bSaveSpellCheck = true;
}
if(SfxItemState::SET == rSet.GetItemState( SID_ATTR_CHAR_CTL_LANGUAGE, false, &pItem ))
{
pDispatch->ExecuteList(pItem->Which(), SfxCallMode::SYNCHRON, { pItem });
bSaveSpellCheck = true;
}
if(SfxItemState::SET == rSet.GetItemState( SID_ATTR_CHAR_CJK_LANGUAGE, false, &pItem ))
{
pDispatch->ExecuteList(pItem->Which(), SfxCallMode::SYNCHRON, { pItem });
bSaveSpellCheck = true;
}
if( SfxItemState::SET == rSet.GetItemState(SID_AUTOSPELL_CHECK, false, &pItem ))
{
bool bOnlineSpelling = static_cast<const SfxBoolItem*>(pItem)->GetValue();
pDispatch->ExecuteList(SID_AUTOSPELL_CHECK,
SfxCallMode::ASYNCHRON|SfxCallMode::RECORD, { pItem });
xProp->setIsSpellAuto( bOnlineSpelling );
}
if( bSaveSpellCheck )
{
//! the config item has changed since we modified the
//! property set it uses
pDispatch->Execute(SID_SPELLCHECKER_CHANGED, SfxCallMode::ASYNCHRON);
}
}
if( SfxItemState::SET == rSet.GetItemState(SID_OPT_LOCALE_CHANGED, false, &pItem ))
{
SfxViewFrame* _pViewFrame = SfxViewFrame::GetFirst();
while ( _pViewFrame )
{
_pViewFrame->GetDispatcher()->ExecuteList(pItem->Which(),
SfxCallMode::ASYNCHRON, { pItem });
_pViewFrame = SfxViewFrame::GetNext( *_pViewFrame );
}
}
}
OUString OfaTreeOptionsDialog::getCurrentFactory_Impl( const Reference< XFrame >& _xFrame )
{
OUString sIdentifier;
Reference < XFrame > xCurrentFrame( _xFrame );
Reference < XModuleManager2 > xModuleManager = ModuleManager::create(::comphelper::getProcessComponentContext());
if ( !xCurrentFrame.is() )
{
Reference< XDesktop2 > xDesktop = Desktop::create( ::comphelper::getProcessComponentContext() );
xCurrentFrame = xDesktop->getCurrentFrame();
}
if ( xCurrentFrame.is() )
{
try
{
sIdentifier = xModuleManager->identify( xCurrentFrame );
}
catch ( css::frame::UnknownModuleException& )
{
SAL_INFO( "cui.options", "unknown module" );
}
catch ( Exception const & )
{
TOOLS_WARN_EXCEPTION( "cui.options", "getActiveModule_Impl(): exception of XModuleManager::identify()" );
}
}
return sIdentifier;
}
void OfaTreeOptionsDialog::generalOptions(const std::vector<sal_uInt16>& vPageId)
{
sal_uInt16 nGroup = 0;
SvtOptionsDialogOptions aOptionsDlgOpt;
sal_uInt16 nPageId = 0;
if ( !lcl_isOptionHidden( SID_GENERAL_OPTIONS, aOptionsDlgOpt ) )
{
setGroupName(u"ProductName", CuiResId(SID_GENERAL_OPTIONS_RES[0].first));
nGroup = AddGroup(CuiResId(SID_GENERAL_OPTIONS_RES[0].first), nullptr, nullptr, SID_GENERAL_OPTIONS );
const sal_uInt16 nEnd = static_cast<sal_uInt16>(std::size(SID_GENERAL_OPTIONS_RES));
for (sal_uInt16 i = 1; i < nEnd; ++i)
{
OUString sNewTitle = CuiResId(SID_GENERAL_OPTIONS_RES[i].first);
nPageId = SID_GENERAL_OPTIONS_RES[i].second;
if ( lcl_isOptionHidden( nPageId, aOptionsDlgOpt ) )
continue;
// Disable Online Update page if neither mode is available
if( RID_SVXPAGE_ONLINEUPDATE == nPageId
&& !(SvxOnlineUpdateTabPage::isTraditionalOnlineUpdateAvailable()
|| SvxOnlineUpdateTabPage::isMarOnlineUpdateAvailable()) )
{
continue;
}
if (!vPageId.empty())
{
if (std::find(vPageId.begin(), vPageId.end(), nPageId) != vPageId.end())
AddTabPage(nPageId, sNewTitle, nGroup);
}
else
AddTabPage(nPageId, sNewTitle, nGroup);
}
}
}
void OfaTreeOptionsDialog::loadAndSaveOptions(const std::vector<sal_uInt16>& vPageId)
{
sal_uInt16 nGroup = 0;
SvtOptionsDialogOptions aOptionsDlgOpt;
sal_uInt16 nPageId = 0;
if ( !lcl_isOptionHidden( SID_FILTER_DLG, aOptionsDlgOpt ) )
{
setGroupName( u"LoadSave", CuiResId(SID_FILTER_DLG_RES[0].first) );
nGroup = AddGroup( CuiResId(SID_FILTER_DLG_RES[0].first), nullptr, nullptr, SID_FILTER_DLG );
for ( size_t i = 1; i < std::size(SID_FILTER_DLG_RES); ++i )
{
nPageId = static_cast<sal_uInt16>(SID_FILTER_DLG_RES[i].second);
if ( !lcl_isOptionHidden( nPageId, aOptionsDlgOpt ) )
{
if (!vPageId.empty())
{
if (std::find(vPageId.begin(), vPageId.end(), nPageId) != vPageId.end())
AddTabPage(nPageId, CuiResId(SID_FILTER_DLG_RES[i].first), nGroup);
}
else
AddTabPage(nPageId, CuiResId(SID_FILTER_DLG_RES[i].first), nGroup);
}
}
}
}
void OfaTreeOptionsDialog::languageOptions(const std::vector<sal_uInt16>& vPageId)
{
sal_uInt16 nGroup = 0;
SvtOptionsDialogOptions aOptionsDlgOpt;
sal_uInt16 nPageId = 0;
SvtCTLOptions aCTLLanguageOptions;
if ( !lcl_isOptionHidden( SID_LANGUAGE_OPTIONS, aOptionsDlgOpt ) )
{
setGroupName(u"LanguageSettings", CuiResId(SID_LANGUAGE_OPTIONS_RES[0].first));
nGroup = AddGroup(CuiResId(SID_LANGUAGE_OPTIONS_RES[0].first), nullptr, nullptr, SID_LANGUAGE_OPTIONS );
for (size_t i = 1; i < std::size(SID_LANGUAGE_OPTIONS_RES); ++i)
{
nPageId = static_cast<sal_uInt16>(SID_LANGUAGE_OPTIONS_RES[i].second);
if ( lcl_isOptionHidden( nPageId, aOptionsDlgOpt ) )
continue;
// Disable DeepL translation settings, if experimental mode is not enabled
if( RID_SVXPAGE_DEEPL_OPTIONS == nPageId )
{
if( ! officecfg::Office::Common::Misc::ExperimentalMode::get() )
continue;
}
if ( ( RID_SVXPAGE_JSEARCH_OPTIONS != nPageId || SvtCJKOptions::IsJapaneseFindEnabled() ) &&
( RID_SVXPAGE_ASIAN_LAYOUT != nPageId || SvtCJKOptions::IsAsianTypographyEnabled() ) &&
( RID_SVXPAGE_OPTIONS_CTL != nPageId || SvtCTLOptions::IsCTLFontEnabled() ) )
{
if (!vPageId.empty())
{
if (std::find(vPageId.begin(), vPageId.end(), nPageId) != vPageId.end())
AddTabPage(nPageId, CuiResId(SID_LANGUAGE_OPTIONS_RES[i].first), nGroup);
}
else
AddTabPage(nPageId, CuiResId(SID_LANGUAGE_OPTIONS_RES[i].first), nGroup);
}
}
}
}
void OfaTreeOptionsDialog::writerOptions(const std::vector<sal_uInt16>& vPageId)
{
sal_uInt16 nGroup = 0;
SvtOptionsDialogOptions aOptionsDlgOpt;
sal_uInt16 nPageId = 0;
OUString aFactory = getCurrentFactory_Impl( m_xFrame );
DBG_ASSERT( GetModuleIdentifier( m_xFrame ) == aFactory, "This should not happen" );
SvtModuleOptions aModuleOpt;
if ( aModuleOpt.IsModuleInstalled( SvtModuleOptions::EModule::WRITER ) )
{
// text document
if ( aFactory == "com.sun.star.text.TextDocument"
|| aFactory == "com.sun.star.text.WebDocument"
|| aFactory == "com.sun.star.text.GlobalDocument" )
{
SfxModule* pSwMod = SfxApplication::GetModule(SfxToolsModule::Writer);
if ( !lcl_isOptionHidden( SID_SW_EDITOPTIONS, aOptionsDlgOpt ) )
{
if ( aFactory == "com.sun.star.text.WebDocument" )
setGroupName( u"WriterWeb", CuiResId(SID_SW_EDITOPTIONS_RES[0].first) );
else
setGroupName( u"Writer", CuiResId(SID_SW_EDITOPTIONS_RES[0].first) );
nGroup = AddGroup(CuiResId(SID_SW_EDITOPTIONS_RES[0].first), pSwMod, pSwMod, SID_SW_EDITOPTIONS );
SvtCTLOptions aCTLLanguageOptions;
for ( size_t i = 1; i < std::size(SID_SW_EDITOPTIONS_RES); ++i )
{
nPageId = static_cast<sal_uInt16>(SID_SW_EDITOPTIONS_RES[i].second);
if ( lcl_isOptionHidden( nPageId, aOptionsDlgOpt ) )
continue;
if ( ( RID_SW_TP_STD_FONT_CJK != nPageId || SvtCJKOptions::IsCJKFontEnabled() ) &&
( RID_SW_TP_STD_FONT_CTL != nPageId || SvtCTLOptions::IsCTLFontEnabled() ) &&
( RID_SW_TP_MAILCONFIG != nPageId || MailMergeCfgIsEmailSupported() ) )
{
if (!vPageId.empty())
{
if (std::find(vPageId.begin(), vPageId.end(), nPageId) != vPageId.end())
AddTabPage(nPageId, CuiResId(SID_SW_EDITOPTIONS_RES[i].first),
nGroup);
}
else
AddTabPage(nPageId, CuiResId(SID_SW_EDITOPTIONS_RES[i].first), nGroup);
}
}
#ifdef DBG_UTIL
if (!vPageId.empty())
{
if (std::find(vPageId.begin(), vPageId.end(), RID_SW_TP_OPTTEST_PAGE)
!= vPageId.end())
AddTabPage(RID_SW_TP_OPTTEST_PAGE, u"Internal Test"_ustr, nGroup);
}
else
AddTabPage(RID_SW_TP_OPTTEST_PAGE, u"Internal Test"_ustr, nGroup);
#endif
}
}
}
}
void OfaTreeOptionsDialog::writerWebOptions(const std::vector<sal_uInt16>& vPageId)
{
sal_uInt16 nGroup = 0;
SvtOptionsDialogOptions aOptionsDlgOpt;
sal_uInt16 nPageId = 0;
OUString aFactory = getCurrentFactory_Impl( m_xFrame );
DBG_ASSERT( GetModuleIdentifier( m_xFrame ) == aFactory, "This should not happen" );
SvtModuleOptions aModuleOpt;
if ( aModuleOpt.IsModuleInstalled( SvtModuleOptions::EModule::WRITER ) )
{
// text document
if ( aFactory == "com.sun.star.text.TextDocument"
|| aFactory == "com.sun.star.text.WebDocument"
|| aFactory == "com.sun.star.text.GlobalDocument" )
{
SfxModule* pSwMod = SfxApplication::GetModule(SfxToolsModule::Writer);
// HTML documents
if ( !lcl_isOptionHidden( SID_SW_ONLINEOPTIONS, aOptionsDlgOpt ) )
{
nGroup = AddGroup(CuiResId(SID_SW_ONLINEOPTIONS_RES[0].first), pSwMod, pSwMod, SID_SW_ONLINEOPTIONS );
for( size_t i = 1; i < std::size(SID_SW_ONLINEOPTIONS_RES); ++i )
{
nPageId = static_cast<sal_uInt16>(SID_SW_ONLINEOPTIONS_RES[i].second);
if ( !lcl_isOptionHidden( nPageId, aOptionsDlgOpt ) )
{
if (!vPageId.empty())
{
if (std::find(vPageId.begin(), vPageId.end(), nPageId) != vPageId.end())
AddTabPage(nPageId, CuiResId(SID_SW_ONLINEOPTIONS_RES[i].first),
nGroup);
}
else
AddTabPage(nPageId, CuiResId(SID_SW_ONLINEOPTIONS_RES[i].first),
nGroup);
}
}
#ifdef DBG_UTIL
if (!vPageId.empty())
{
if (std::find(vPageId.begin(), vPageId.end(), RID_SW_TP_OPTTEST_PAGE)
!= vPageId.end())
AddTabPage(RID_SW_TP_OPTTEST_PAGE, u"Internal Test"_ustr, nGroup);
}
else
AddTabPage(RID_SW_TP_OPTTEST_PAGE, u"Internal Test"_ustr, nGroup);
#endif
}
}
}
}
void OfaTreeOptionsDialog::calcOptions(const std::vector<sal_uInt16>& vPageId)
{
sal_uInt16 nGroup = 0;
SvtOptionsDialogOptions aOptionsDlgOpt;
sal_uInt16 nPageId = 0;
OUString aFactory = getCurrentFactory_Impl( m_xFrame );
DBG_ASSERT( GetModuleIdentifier( m_xFrame ) == aFactory, "This should not happen" );
SvtModuleOptions aModuleOpt;
// Calc options
if ( aModuleOpt.IsModuleInstalled( SvtModuleOptions::EModule::CALC ) )
{
if ( aFactory == "com.sun.star.sheet.SpreadsheetDocument" )
{
if ( !lcl_isOptionHidden( SID_SC_EDITOPTIONS, aOptionsDlgOpt ) )
{
SfxModule* pScMod = SfxApplication::GetModule( SfxToolsModule::Calc );
setGroupName( u"Calc", CuiResId(SID_SC_EDITOPTIONS_RES[0].first) );
nGroup = AddGroup( CuiResId(SID_SC_EDITOPTIONS_RES[0].first), pScMod, pScMod, SID_SC_EDITOPTIONS );
const sal_uInt16 nCount = static_cast<sal_uInt16>(std::size(SID_SC_EDITOPTIONS_RES));
for ( sal_uInt16 i = 1; i < nCount; ++i )
{
nPageId = static_cast<sal_uInt16>(SID_SC_EDITOPTIONS_RES[i].second);
if ( lcl_isOptionHidden( nPageId, aOptionsDlgOpt ) )
continue;
if (!vPageId.empty())
{
if (std::find(vPageId.begin(), vPageId.end(), nPageId) != vPageId.end())
AddTabPage(nPageId, CuiResId(SID_SC_EDITOPTIONS_RES[i].first), nGroup);
}
else
AddTabPage(nPageId, CuiResId(SID_SC_EDITOPTIONS_RES[i].first), nGroup);
}
}
}
}
}
void OfaTreeOptionsDialog::impressOptions(const std::vector<sal_uInt16>& vPageId)
{
sal_uInt16 nGroup = 0;
SvtOptionsDialogOptions aOptionsDlgOpt;
sal_uInt16 nPageId = 0;
OUString aFactory = getCurrentFactory_Impl( m_xFrame );
DBG_ASSERT( GetModuleIdentifier( m_xFrame ) == aFactory, "This should not happen" );
SvtModuleOptions aModuleOpt;
// Impress options
SfxModule* pSdMod = SfxApplication::GetModule( SfxToolsModule::Draw );
if ( aModuleOpt.IsModuleInstalled( SvtModuleOptions::EModule::IMPRESS ) )
{
if ( aFactory == "com.sun.star.presentation.PresentationDocument" )
{
if ( !lcl_isOptionHidden( SID_SD_EDITOPTIONS, aOptionsDlgOpt ) )
{
setGroupName( u"Impress", CuiResId(SID_SD_EDITOPTIONS_RES[0].first) );
nGroup = AddGroup( CuiResId(SID_SD_EDITOPTIONS_RES[0].first), pSdMod, pSdMod, SID_SD_EDITOPTIONS );
const sal_uInt16 nCount = static_cast<sal_uInt16>(std::size(SID_SD_EDITOPTIONS_RES));
for ( sal_uInt16 i = 1; i < nCount; ++i )
{
nPageId = static_cast<sal_uInt16>(SID_SD_EDITOPTIONS_RES[i].second);
if ( lcl_isOptionHidden( nPageId, aOptionsDlgOpt ) )
continue;
if (!vPageId.empty())
{
if (std::find(vPageId.begin(), vPageId.end(), nPageId) != vPageId.end())
AddTabPage(nPageId, CuiResId(SID_SD_EDITOPTIONS_RES[i].first), nGroup);
}
else
AddTabPage(nPageId, CuiResId(SID_SD_EDITOPTIONS_RES[i].first), nGroup);
}
}
}
}
}
void OfaTreeOptionsDialog::drawOptions(const std::vector<sal_uInt16>& vPageId)
{
sal_uInt16 nGroup = 0;
SvtOptionsDialogOptions aOptionsDlgOpt;
sal_uInt16 nPageId = 0;
OUString aFactory = getCurrentFactory_Impl( m_xFrame );
DBG_ASSERT( GetModuleIdentifier( m_xFrame ) == aFactory, "This should not happen" );
SvtModuleOptions aModuleOpt;
// Draw options
SfxModule* pSdMod = SfxApplication::GetModule(SfxToolsModule::Draw);
if ( aModuleOpt.IsModuleInstalled( SvtModuleOptions::EModule::DRAW ) )
{
if ( aFactory == "com.sun.star.drawing.DrawingDocument" )
{
if ( !lcl_isOptionHidden( SID_SD_GRAPHIC_OPTIONS, aOptionsDlgOpt ) )
{
setGroupName( u"Draw", CuiResId(SID_SD_GRAPHIC_OPTIONS_RES[0].first) );
nGroup = AddGroup( CuiResId(SID_SD_GRAPHIC_OPTIONS_RES[0].first), pSdMod, pSdMod, SID_SD_GRAPHIC_OPTIONS );
const sal_uInt16 nCount = static_cast<sal_uInt16>(std::size(SID_SD_GRAPHIC_OPTIONS_RES));
for ( sal_uInt16 i = 1; i < nCount; ++i )
{
nPageId = static_cast<sal_uInt16>(SID_SD_GRAPHIC_OPTIONS_RES[i].second);
if ( lcl_isOptionHidden( nPageId, aOptionsDlgOpt ) )
continue;
if (!vPageId.empty())
{
if (std::find(vPageId.begin(), vPageId.end(), nPageId) != vPageId.end())
AddTabPage(nPageId, CuiResId(SID_SD_GRAPHIC_OPTIONS_RES[i].first),
nGroup);
}
else
AddTabPage(nPageId, CuiResId(SID_SD_GRAPHIC_OPTIONS_RES[i].first), nGroup);
}
}
}
}
}
void OfaTreeOptionsDialog::mathOptions(const std::vector<sal_uInt16>& vPageId)
{
sal_uInt16 nGroup = 0;
SvtOptionsDialogOptions aOptionsDlgOpt;
sal_uInt16 nPageId = 0;
OUString aFactory = getCurrentFactory_Impl( m_xFrame );
DBG_ASSERT( GetModuleIdentifier( m_xFrame ) == aFactory, "This should not happen" );
SvtModuleOptions aModuleOpt;
// Math options
if ( aModuleOpt.IsModuleInstalled( SvtModuleOptions::EModule::MATH ) )
{
if ( aFactory == "com.sun.star.formula.FormulaProperties" )
{
if ( !lcl_isOptionHidden( SID_SM_EDITOPTIONS, aOptionsDlgOpt ) )
{
SfxModule* pSmMod = SfxApplication::GetModule(SfxToolsModule::Math);
setGroupName( u"Math", CuiResId(SID_SM_EDITOPTIONS_RES[0].first) );
nGroup = AddGroup(CuiResId(SID_SM_EDITOPTIONS_RES[0].first), pSmMod, pSmMod, SID_SM_EDITOPTIONS );
for ( size_t i = 1; i < std::size(SID_SM_EDITOPTIONS_RES); ++i )
{
nPageId = static_cast<sal_uInt16>(SID_SM_EDITOPTIONS_RES[i].second);
if ( !lcl_isOptionHidden( nPageId, aOptionsDlgOpt ) )
{
if (!vPageId.empty())
{
if (std::find(vPageId.begin(), vPageId.end(), nPageId) != vPageId.end())
AddTabPage(nPageId, CuiResId(SID_SM_EDITOPTIONS_RES[i].first),
nGroup);
}
else
AddTabPage(nPageId, CuiResId(SID_SM_EDITOPTIONS_RES[i].first), nGroup);
}
}
}
}
}
}
void OfaTreeOptionsDialog::databaseOptions(const std::vector<sal_uInt16>& vPageId)
{
sal_uInt16 nGroup = 0;
SvtOptionsDialogOptions aOptionsDlgOpt;
sal_uInt16 nPageId = 0;
SvtModuleOptions aModuleOpt;
// Database - needed only if there is an application which integrates with databases
if ( !lcl_isOptionHidden( SID_SB_STARBASEOPTIONS, aOptionsDlgOpt ) &&
( aModuleOpt.IsModuleInstalled( SvtModuleOptions::EModule::DATABASE )
|| aModuleOpt.IsModuleInstalled( SvtModuleOptions::EModule::WRITER )
|| aModuleOpt.IsModuleInstalled( SvtModuleOptions::EModule::CALC )
) )
{
setGroupName( u"Base", CuiResId(SID_SB_STARBASEOPTIONS_RES[0].first) );
nGroup = AddGroup( CuiResId(SID_SB_STARBASEOPTIONS_RES[0].first), nullptr, nullptr, SID_SB_STARBASEOPTIONS );
for ( size_t i = 1; i < std::size(SID_SB_STARBASEOPTIONS_RES); ++i )
{
nPageId = static_cast<sal_uInt16>(SID_SB_STARBASEOPTIONS_RES[i].second);
if ( !lcl_isOptionHidden( nPageId, aOptionsDlgOpt ) )
{
if (!vPageId.empty())
{
if (std::find(vPageId.begin(), vPageId.end(), nPageId) != vPageId.end())
AddTabPage(nPageId, CuiResId(SID_SB_STARBASEOPTIONS_RES[i].first), nGroup);
}
else
AddTabPage(nPageId, CuiResId(SID_SB_STARBASEOPTIONS_RES[i].first), nGroup);
}
}
}
}
void OfaTreeOptionsDialog::chartOptions(const std::vector<sal_uInt16>& vPageId)
{
sal_uInt16 nGroup = 0;
SvtOptionsDialogOptions aOptionsDlgOpt;
sal_uInt16 nPageId = 0;
if ( !lcl_isOptionHidden( SID_SCH_EDITOPTIONS, aOptionsDlgOpt ) )
{
setGroupName( u"Charts", CuiResId(SID_SCH_EDITOPTIONS_RES[0].first) );
nGroup = AddGroup( CuiResId(SID_SCH_EDITOPTIONS_RES[0].first), nullptr, nullptr, SID_SCH_EDITOPTIONS );
for ( size_t i = 1; i < std::size(SID_SCH_EDITOPTIONS_RES); ++i )
{
nPageId = static_cast<sal_uInt16>(SID_SCH_EDITOPTIONS_RES[i].second);
if ( !lcl_isOptionHidden( nPageId, aOptionsDlgOpt ) )
{
if (!vPageId.empty())
{
if (std::find(vPageId.begin(), vPageId.end(), nPageId) != vPageId.end())
AddTabPage(nPageId, CuiResId(SID_SCH_EDITOPTIONS_RES[i].first), nGroup);
}
else
AddTabPage(nPageId, CuiResId(SID_SCH_EDITOPTIONS_RES[i].first), nGroup);
}
}
}
}
void OfaTreeOptionsDialog::internetOptions(const std::vector<sal_uInt16>& vPageId)
{
sal_uInt16 nGroup = 0;
SvtOptionsDialogOptions aOptionsDlgOpt;
sal_uInt16 nPageId = 0;
if ( lcl_isOptionHidden( SID_INET_DLG, aOptionsDlgOpt ) )
return;
setGroupName(u"Internet", CuiResId(SID_INET_DLG_RES[0].first));
nGroup = AddGroup(CuiResId(SID_INET_DLG_RES[0].first), nullptr, nullptr, SID_INET_DLG );
for ( size_t i = 1; i < std::size(SID_INET_DLG_RES); ++i )
{
nPageId = static_cast<sal_uInt16>(SID_INET_DLG_RES[i].second);
if ( lcl_isOptionHidden( nPageId, aOptionsDlgOpt ) )
continue;
#if defined(_WIN32)
// Disable E-mail tab-page on Windows
if ( nPageId == RID_SVXPAGE_INET_MAIL )
continue;
#endif
if (!vPageId.empty())
{
if (std::find(vPageId.begin(), vPageId.end(), nPageId) != vPageId.end())
AddTabPage(nPageId, CuiResId(SID_INET_DLG_RES[i].first), nGroup);
}
else
AddTabPage(nPageId, CuiResId(SID_INET_DLG_RES[i].first), nGroup);
}
}
void OfaTreeOptionsDialog::Initialize(const Reference<XFrame>& _xFrame)
{
m_xFrame = _xFrame;
// %PRODUCTNAME options
generalOptions();
// Load and Save options
loadAndSaveOptions();
// Language options
languageOptions();
// Writer and Writer/Web options
writerOptions();
writerWebOptions();
// Calc options
calcOptions();
// Impress options
impressOptions();
// Draw options
drawOptions();
// Math options
mathOptions();
// Database - needed only if there is an application which integrates with databases
databaseOptions();
// Chart options (always installed and active)
chartOptions();
// Internet options
internetOptions();
// store Options Dialogs with their page names and strings
// in order to use them when searching
storeOptionsTree();
}
static bool isNodeActive( OptionsNode const * pNode, Module* pModule )
{
if ( !pNode )
return false;
// Node for all modules active?
if ( pNode->m_bAllModules )
return true;
// OOo-Nodes (Writer, Calc, Impress...) are active if node is already inserted
if ( !getGroupName( pNode->m_sId, false ).isEmpty() )
return true;
// no module -> not active
if ( !pModule )
return false;
// search node in active module
if ( pModule->m_bActive )
{
for (auto const& j : pModule->m_aNodeList)
if ( j->m_sId == pNode->m_sId )
return true;
}
return false;
}
void OfaTreeOptionsDialog::LoadExtensionOptions( std::u16string_view rExtensionId )
{
std::unique_ptr<Module> pModule;
// when called by Tools - Options then load nodes of active module
if ( rExtensionId.empty() )
{
pModule = LoadModule( GetModuleIdentifier( Reference< XFrame >() ) );
}
VectorOfNodes aNodeList = LoadNodes( pModule.get(), rExtensionId );
InsertNodes( aNodeList );
}
OUString OfaTreeOptionsDialog::GetModuleIdentifier( const Reference< XFrame >& rFrame )
{
OUString sModule;
Reference < XFrame > xCurrentFrame( rFrame );
const Reference< XComponentContext >& xContext = comphelper::getProcessComponentContext();
Reference < XModuleManager2 > xModuleManager = ModuleManager::create(xContext);
if ( !xCurrentFrame.is() )
{
Reference < XDesktop2 > xDesktop = Desktop::create( xContext );
xCurrentFrame = xDesktop->getCurrentFrame();
}
if ( xCurrentFrame.is() )
{
try
{
sModule = xModuleManager->identify( xCurrentFrame );
}
catch ( css::frame::UnknownModuleException& )
{
SAL_INFO( "cui.options", "unknown module" );
}
catch ( Exception const & )
{
TOOLS_WARN_EXCEPTION( "cui.options", "OfaTreeOptionsDialog::GetModuleIdentifier(): exception of XModuleManager::identify()");
}
}
return sModule;
}
std::unique_ptr<Module> OfaTreeOptionsDialog::LoadModule(
std::u16string_view rModuleIdentifier )
{
std::unique_ptr<Module> pModule;
Reference< XNameAccess > xSet(
officecfg::Office::OptionsDialog::Modules::get());
const Sequence< OUString > seqNames = xSet->getElementNames();
for ( const OUString& rModule : seqNames )
{
if ( rModuleIdentifier == rModule )
{
// current active module found
pModule.reset(new Module);
pModule->m_bActive = true;
Reference< XNameAccess > xModAccess;
xSet->getByName( rModule ) >>= xModAccess;
if ( xModAccess.is() )
{
// load the nodes of this module
Reference< XNameAccess > xNodeAccess;
xModAccess->getByName( u"Nodes"_ustr ) >>= xNodeAccess;
if ( xNodeAccess.is() )
{
const Sequence< OUString > xTemp = xNodeAccess->getElementNames();
Reference< XNameAccess > xAccess;
sal_Int32 nIndex = -1;
for ( const OUString& rNode : xTemp)
{
xNodeAccess->getByName( rNode ) >>= xAccess;
if ( xAccess.is() )
{
xAccess->getByName( u"Index"_ustr ) >>= nIndex;
if ( nIndex < 0 )
// append nodes with index < 0
pModule->m_aNodeList.push_back(
std::unique_ptr<OrderedEntry>(new OrderedEntry(nIndex, rNode)));
else
{
// search position of the node
std::vector<OrderedEntry *>::size_type y = 0;
for ( ; y < pModule->m_aNodeList.size(); ++y )
{
sal_Int32 nNodeIdx = pModule->m_aNodeList[y]->m_nIndex;
if ( nNodeIdx < 0 || nNodeIdx > nIndex )
break;
}
// and insert the node on this position
pModule->m_aNodeList.insert(
pModule->m_aNodeList.begin() + y,
std::unique_ptr<OrderedEntry>(new OrderedEntry( nIndex, rNode )) );
}
}
}
}
}
break;
}
}
return pModule;
}
VectorOfNodes OfaTreeOptionsDialog::LoadNodes(
Module* pModule, std::u16string_view rExtensionId)
{
VectorOfNodes aOutNodeList;
Reference< XNameAccess > xSet(
officecfg::Office::OptionsDialog::Nodes::get());
VectorOfNodes aNodeList;
const Sequence< OUString > seqNames = xSet->getElementNames();
for ( OUString const & sGroupName : seqNames )
{
Reference< XNameAccess > xNodeAccess;
xSet->getByName( sGroupName ) >>= xNodeAccess;
if ( xNodeAccess.is() )
{
OUString sNodeId, sLabel, sPageURL;
bool bAllModules = false;
sNodeId = sGroupName;
xNodeAccess->getByName( u"Label"_ustr ) >>= sLabel;
xNodeAccess->getByName( u"OptionsPage"_ustr ) >>= sPageURL;
xNodeAccess->getByName( u"AllModules"_ustr ) >>= bAllModules;
if ( sLabel.isEmpty() )
sLabel = sGroupName;
OUString sTemp = getGroupName( sLabel, !rExtensionId.empty() );
if ( !sTemp.isEmpty() )
sLabel = sTemp;
std::unique_ptr<OptionsNode> pNode(new OptionsNode(sNodeId, sLabel, bAllModules));
if ( rExtensionId.empty() && !isNodeActive( pNode.get(), pModule ) )
{
continue;
}
Reference< XNameAccess > xLeavesSet;
xNodeAccess->getByName( u"Leaves"_ustr ) >>= xLeavesSet;
if ( xLeavesSet.is() )
{
const Sequence< OUString > seqLeaves = xLeavesSet->getElementNames();
for ( OUString const & leafName : seqLeaves )
{
Reference< XNameAccess > xLeaveAccess;
xLeavesSet->getByName( leafName ) >>= xLeaveAccess;
if ( xLeaveAccess.is() )
{
OUString sId, sLeafLabel, sEventHdl, sLeafURL, sLeafGrpId;
sal_Int32 nLeafGrpIdx = 0;
xLeaveAccess->getByName( u"Id"_ustr ) >>= sId;
xLeaveAccess->getByName( u"Label"_ustr ) >>= sLeafLabel;
xLeaveAccess->getByName( u"OptionsPage"_ustr ) >>= sLeafURL;
xLeaveAccess->getByName( u"EventHandlerService"_ustr ) >>= sEventHdl;
xLeaveAccess->getByName( u"GroupId"_ustr ) >>= sLeafGrpId;
xLeaveAccess->getByName( u"GroupIndex"_ustr ) >>= nLeafGrpIdx;
if ( rExtensionId.empty() || sId == rExtensionId )
{
std::unique_ptr<OptionsLeaf> pLeaf(new OptionsLeaf(
sLeafLabel, sLeafURL, sEventHdl, sLeafGrpId, nLeafGrpIdx ));
if ( !sLeafGrpId.isEmpty() )
{
bool bAlreadyOpened = false;
if ( !pNode->m_aGroupedLeaves.empty() )
{
for (auto & rGroup : pNode->m_aGroupedLeaves)
{
if ( !rGroup.empty() &&
rGroup[0]->m_sGroupId == sLeafGrpId )
{
std::vector<std::unique_ptr<OptionsLeaf>>::size_type l = 0;
for ( ; l < rGroup.size(); ++l )
{
if ( rGroup[l]->m_nGroupIndex >= nLeafGrpIdx )
break;
}
rGroup.insert( rGroup.begin() + l, std::move(pLeaf) );
bAlreadyOpened = true;
break;
}
}
}
if ( !bAlreadyOpened )
{
std::vector< std::unique_ptr<OptionsLeaf> > aGroupedLeaves;
aGroupedLeaves.push_back( std::move(pLeaf) );
pNode->m_aGroupedLeaves.push_back( std::move(aGroupedLeaves) );
}
}
else
pNode->m_aLeaves.push_back( std::move(pLeaf) );
}
}
}
}
// do not insert nodes without leaves
if ( !pNode->m_aLeaves.empty() || !pNode->m_aGroupedLeaves.empty() )
{
pModule ? aNodeList.push_back( std::move(pNode) ) : aOutNodeList.push_back( std::move(pNode) );
}
}
}
if ( pModule && !aNodeList.empty() )
{
for ( auto const & i: pModule->m_aNodeList )
{
OUString sNodeId = i->m_sId;
for ( auto j = aNodeList.begin(); j != aNodeList.end(); ++j )
{
if ( (*j)->m_sId == sNodeId )
{
aOutNodeList.push_back( std::move(*j) );
aNodeList.erase( j );
break;
}
}
}
for ( auto & i: aNodeList )
aOutNodeList.push_back( std::move(i) );
}
return aOutNodeList;
}
static sal_uInt16 lcl_getGroupId( std::u16string_view rGroupName, const weld::TreeView& rTreeLB )
{
sal_uInt16 nRet = 0;
std::unique_ptr<weld::TreeIter> xEntry = rTreeLB.make_iterator();
bool bEntry = rTreeLB.get_iter_first(*xEntry);
while (bEntry)
{
if (!rTreeLB.get_iter_depth(*xEntry))
{
OUString sTemp(rTreeLB.get_text(*xEntry));
if (sTemp == rGroupName)
return nRet;
nRet++;
}
bEntry = rTreeLB.iter_next(*xEntry);
}
return USHRT_MAX;
}
static void lcl_insertLeaf(
OfaTreeOptionsDialog* pDlg, OptionsNode const * pNode, OptionsLeaf const * pLeaf, const weld::TreeView& rTreeLB )
{
sal_uInt16 nGrpId = lcl_getGroupId( pNode->m_sLabel, rTreeLB );
if ( USHRT_MAX == nGrpId )
{
sal_uInt16 nNodeGrpId = getGroupNodeId( pNode->m_sId );
nGrpId = pDlg->AddGroup( pNode->m_sLabel, nullptr, nullptr, nNodeGrpId );
}
OptionsPageInfo* pInfo = pDlg->AddTabPage( 0, pLeaf->m_sLabel, nGrpId );
pInfo->m_sPageURL = pLeaf->m_sPageURL;
pInfo->m_sEventHdl = pLeaf->m_sEventHdl;
}
void OfaTreeOptionsDialog::InsertNodes( const VectorOfNodes& rNodeList )
{
for (auto const& node : rNodeList)
{
if ( !node->m_aLeaves.empty() || !node->m_aGroupedLeaves.empty() )
{
for ( auto const & j: node->m_aGroupedLeaves )
{
for ( size_t k = 0; k < j.size(); ++k )
{
lcl_insertLeaf( this, node.get(), j[k].get(), *xTreeLB );
}
}
for ( auto const & j: node->m_aLeaves )
{
lcl_insertLeaf( this, node.get(), j.get(), *xTreeLB );
}
}
}
}
void OfaTreeOptionsDialog::SetNeedsRestart( svtools::RestartReason eReason)
{
bNeedsRestart = true;
eRestartReason = eReason;
}
short OfaTreeOptionsDialog::run()
{
std::unique_ptr< SvxDicListChgClamp > pClamp;
if ( !bIsFromExtensionManager )
{
// collect all DictionaryList Events while the dialog is executed
pClamp.reset(new SvxDicListChgClamp(LinguMgr::GetDictionaryList()));
}
return SfxOkDialogController::run();
}
// class ExtensionsTabPage -----------------------------------------------
ExtensionsTabPage::ExtensionsTabPage(
weld::Container* pParent, OUString aPageURL,
OUString aEvtHdl, const Reference< awt::XContainerWindowProvider >& rProvider )
: m_pContainer(pParent)
, m_sPageURL(std::move(aPageURL))
, m_sEventHdl(std::move(aEvtHdl))
, m_xWinProvider(rProvider)
{
}
ExtensionsTabPage::~ExtensionsTabPage()
{
Hide();
DeactivatePage();
if ( m_xPage.is() )
{
try
{
m_xPage->dispose();
}
catch (const Exception&)
{
}
m_xPage.clear();
}
if ( m_xPageParent.is() )
{
try
{
m_xPageParent->dispose();
}
catch (const Exception&)
{
}
m_xPageParent.clear();
}
}
void ExtensionsTabPage::CreateDialogWithHandler()
{
try
{
bool bWithHandler = !m_sEventHdl.isEmpty();
if ( bWithHandler )
{
Reference < XMultiServiceFactory > xFactory( ::comphelper::getProcessServiceFactory() );
m_xEventHdl.set( xFactory->createInstance( m_sEventHdl ), UNO_QUERY );
}
if ( !bWithHandler || m_xEventHdl.is() )
{
m_xPageParent = m_pContainer->CreateChildFrame();
Reference<awt::XWindowPeer> xParent(m_xPageParent, UNO_QUERY);
m_xPage =
m_xWinProvider->createContainerWindow(
m_sPageURL, OUString(), xParent, m_xEventHdl );
Reference< awt::XControl > xPageControl( m_xPage, UNO_QUERY );
if ( xPageControl.is() )
{
Reference< awt::XWindowPeer > xWinPeer( xPageControl->getPeer() );
if ( xWinPeer.is() )
{
VclPtr<vcl::Window> pWindow = VCLUnoHelper::GetWindow( xWinPeer );
if ( pWindow )
pWindow->SetStyle( pWindow->GetStyle() | WB_DIALOGCONTROL | WB_CHILDDLGCTRL );
}
}
}
}
catch (const Exception&)
{
TOOLS_WARN_EXCEPTION( "cui.options", "ExtensionsTabPage::CreateDialogWithHandler(): exception of XDialogProvider2::createDialogWithHandler()");
}
}
bool ExtensionsTabPage::DispatchAction( const OUString& rAction )
{
bool bRet = false;
if ( m_xEventHdl.is() )
{
try
{
bRet = m_xEventHdl->callHandlerMethod( m_xPage, Any( rAction ), u"external_event"_ustr );
}
catch ( Exception const & )
{
TOOLS_WARN_EXCEPTION( "cui.options", "ExtensionsTabPage::DispatchAction(): exception of XDialogEventHandler::callHandlerMethod()" );
}
}
return bRet;
}
void ExtensionsTabPage::Show()
{
if (!m_xPageParent.is())
return;
VclPtr<vcl::Window> xPageParent = VCLUnoHelper::GetWindow(m_xPageParent);
if (xPageParent)
{
// NoActivate otherwise setVisible will call Window::Show which will grab
// focus to the page by default
xPageParent->Show(true, ShowFlags::NoActivate);
}
m_xPageParent->setVisible(true);
}
void ExtensionsTabPage::Hide()
{
if (!m_xPageParent.is())
return;
m_xPageParent->setVisible(false);
}
void ExtensionsTabPage::ActivatePage()
{
if ( !m_xPage.is() )
{
CreateDialogWithHandler();
if ( m_xPage.is() )
{
auto aWindowRect = m_xPageParent->getPosSize();
m_xPage->setPosSize(0, 0, aWindowRect.Width, aWindowRect.Height, awt::PosSize::POSSIZE);
if ( !m_sEventHdl.isEmpty() )
DispatchAction( u"initialize"_ustr );
}
}
if ( m_xPage.is() )
{
m_xPage->setVisible( true );
}
}
void ExtensionsTabPage::DeactivatePage()
{
if ( m_xPage.is() )
m_xPage->setVisible( false );
}
void ExtensionsTabPage::ResetPage()
{
DispatchAction( u"back"_ustr );
ActivatePage();
}
void ExtensionsTabPage::SavePage()
{
DispatchAction( u"ok"_ustr );
}
/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
↑ V530 The return value of function 'ExecuteList' is required to be utilized.
↑ V530 The return value of function 'ExecuteList' is required to be utilized.
↑ V530 The return value of function 'ExecuteList' is required to be utilized.
↑ V530 The return value of function 'ExecuteList' is required to be utilized.
↑ V530 The return value of function 'ExecuteList' is required to be utilized.
↑ V530 The return value of function 'Execute' is required to be utilized.
↑ V530 The return value of function 'ExecuteList' is required to be utilized.
↑ V547 Expression 'nIndex < 0' is always true.
↑ V560 A part of conditional expression is always true: !pPageInfo->m_xPage.
↑ V560 A part of conditional expression is always true: 0 == pPageInfo->m_nPageId.
↑ V1001 The 'aAny' variable is assigned but is not used by the end of the function.
↑ V1004 The 'pPageInfo->m_xPage' pointer was used unsafely after it was verified against nullptr. Check lines: 1229, 1238.