Use correct object
[LibreOffice.git] / cui / source / options / optpath.cxx
blob29c554fe8ffb70ba97a6897769bd41dc799374c7
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3 * This file is part of the LibreOffice project.
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 * This file incorporates work covered by the following license notice:
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
20 #include <svx/svxdlg.hxx>
21 #include <sfx2/filedlghelper.hxx>
22 #include <sfx2/app.hxx>
23 #include <tools/urlobj.hxx>
24 #include <unotools/defaultoptions.hxx>
25 #include <unotools/pathoptions.hxx>
26 #include <unotools/moduleoptions.hxx>
27 #include <unotools/viewoptions.hxx>
29 #include <bitmaps.hlst>
30 #include <dialmgr.hxx>
31 #include <optpath.hxx>
32 #include <strings.hrc>
33 #include <comphelper/processfactory.hxx>
34 #include <comphelper/string.hxx>
35 #include <com/sun/star/uno/Exception.hpp>
36 #include <com/sun/star/beans/PropertyAttribute.hpp>
37 #include <com/sun/star/ui/dialogs/ExecutableDialogResults.hpp>
38 #include <com/sun/star/ui/dialogs/XAsynchronousExecutableDialog.hpp>
39 #include <com/sun/star/ui/dialogs/XFolderPicker2.hpp>
40 #include <com/sun/star/ui/dialogs/XFilePicker3.hpp>
41 #include <com/sun/star/ui/dialogs/TemplateDescription.hpp>
42 #include <com/sun/star/util/thePathSettings.hpp>
43 #include <comphelper/diagnose_ex.hxx>
44 #include <sal/log.hxx>
45 #include <o3tl/string_view.hxx>
47 using namespace css;
48 using namespace css::beans;
49 using namespace css::ui::dialogs;
50 using namespace css::uno;
51 using namespace svx;
53 // define ----------------------------------------------------------------
55 constexpr OUStringLiteral POSTFIX_INTERNAL = u"_internal";
56 constexpr OUString POSTFIX_USER = u"_user"_ustr;
57 constexpr OUString POSTFIX_WRITABLE = u"_writable"_ustr;
58 constexpr OUStringLiteral VAR_ONE = u"%1";
59 constexpr OUStringLiteral IODLG_CONFIGNAME = u"FilePicker_Save";
61 // struct OptPath_Impl ---------------------------------------------------
63 struct OptPath_Impl
65 OUString m_sMultiPathDlg;
66 Reference< css::util::XPathSettings > m_xPathSettings;
68 OptPath_Impl()
69 : m_sMultiPathDlg(CuiResId(RID_CUISTR_EDIT_PATHS))
74 namespace {
76 struct PathUserData_Impl
78 SvtPathOptions::Paths nRealId;
79 bool bItemStateSet;
80 OUString sUserPath;
81 OUString sWritablePath;
82 bool bReadOnly;
84 explicit PathUserData_Impl(SvtPathOptions::Paths nId)
85 : nRealId(nId)
86 , bItemStateSet(false)
87 , bReadOnly(false)
92 struct Handle2CfgNameMapping_Impl
94 SvtPathOptions::Paths m_nHandle;
95 OUString m_aCfgName;
100 constexpr Handle2CfgNameMapping_Impl Hdl2CfgMap_Impl[]
102 { SvtPathOptions::Paths::AutoCorrect, u"AutoCorrect"_ustr },
103 { SvtPathOptions::Paths::AutoText, u"AutoText"_ustr },
104 { SvtPathOptions::Paths::Backup, u"Backup"_ustr },
105 { SvtPathOptions::Paths::Gallery, u"Gallery"_ustr },
106 { SvtPathOptions::Paths::Graphic, u"Graphic"_ustr },
107 { SvtPathOptions::Paths::Temp, u"Temp"_ustr },
108 { SvtPathOptions::Paths::Template, u"Template"_ustr },
109 { SvtPathOptions::Paths::Work, u"Work"_ustr },
110 { SvtPathOptions::Paths::Dictionary, u"Dictionary"_ustr },
111 { SvtPathOptions::Paths::Classification, u"Classification"_ustr },
112 #if OSL_DEBUG_LEVEL > 1
113 { SvtPathOptions::Paths::Linguistic, u"Linguistic"_ustr },
114 #endif
117 static OUString getCfgName_Impl( SvtPathOptions::Paths _nHandle )
119 OUString sCfgName;
120 for (const auto & rMapping : Hdl2CfgMap_Impl)
122 if ( rMapping.m_nHandle == _nHandle )
124 // config name found
125 sCfgName = rMapping.m_aCfgName;
126 break;
130 return sCfgName;
133 #define MULTIPATH_DELIMITER ';'
135 static OUString Convert_Impl( std::u16string_view rValue )
137 if (rValue.empty())
138 return OUString();
140 sal_Int32 nPos = 0;
141 OUStringBuffer aReturn;
142 for (;;)
144 OUString aValue( o3tl::getToken(rValue, 0, MULTIPATH_DELIMITER, nPos ) );
145 INetURLObject aObj( aValue );
146 if ( aObj.GetProtocol() == INetProtocol::File )
147 aReturn.append(aObj.PathToFileName());
148 if ( nPos < 0 )
149 break;
150 aReturn.append(MULTIPATH_DELIMITER);
153 return aReturn.makeStringAndClear();
156 // functions -------------------------------------------------------------
158 static bool IsMultiPath_Impl( const SvtPathOptions::Paths nIndex )
160 #if OSL_DEBUG_LEVEL > 1
161 return ( SvtPathOptions::Paths::AutoCorrect == nIndex ||
162 SvtPathOptions::Paths::AutoText == nIndex ||
163 SvtPathOptions::Paths::Basic == nIndex ||
164 SvtPathOptions::Paths::Gallery == nIndex ||
165 SvtPathOptions::Paths::Template == nIndex );
166 #else
167 return ( SvtPathOptions::Paths::AutoCorrect == nIndex ||
168 SvtPathOptions::Paths::AutoText == nIndex ||
169 SvtPathOptions::Paths::Basic == nIndex ||
170 SvtPathOptions::Paths::Gallery == nIndex ||
171 SvtPathOptions::Paths::Template == nIndex ||
172 SvtPathOptions::Paths::Linguistic == nIndex ||
173 SvtPathOptions::Paths::Dictionary == nIndex );
174 #endif
177 // class SvxPathTabPage --------------------------------------------------
179 SvxPathTabPage::SvxPathTabPage(weld::Container* pPage, weld::DialogController* pController, const SfxItemSet& rSet)
180 : SfxTabPage( pPage, pController, u"cui/ui/optpathspage.ui"_ustr, u"OptPathsPage"_ustr, &rSet)
181 , pImpl(new OptPath_Impl)
182 , xDialogListener ( new ::svt::DialogClosedListener() )
183 , m_xStandardBtn(m_xBuilder->weld_button(u"default"_ustr))
184 , m_xPathBtn(m_xBuilder->weld_button(u"edit"_ustr))
185 , m_xPathBox(m_xBuilder->weld_tree_view(u"paths"_ustr))
187 m_xStandardBtn->connect_clicked(LINK(this, SvxPathTabPage, StandardHdl_Impl));
188 m_xPathBtn->connect_clicked( LINK( this, SvxPathTabPage, PathHdl_Impl ) );
190 m_xPathBox->set_size_request(m_xPathBox->get_approximate_digit_width() * 60,
191 m_xPathBox->get_height_rows(20));
193 m_xPathBox->connect_row_activated( LINK( this, SvxPathTabPage, DoubleClickPathHdl_Impl ) );
194 m_xPathBox->connect_column_clicked(LINK(this, SvxPathTabPage, HeaderBarClick));
195 m_xPathBox->connect_selection_changed(LINK(this, SvxPathTabPage, PathSelect_Impl));
196 m_xPathBox->set_selection_mode(SelectionMode::Multiple);
198 xDialogListener->SetDialogClosedLink( LINK( this, SvxPathTabPage, DialogClosedHdl ) );
201 IMPL_LINK(SvxPathTabPage, HeaderBarClick, int, nColumn, void)
203 bool bSortAtoZ = !m_xPathBox->get_sort_order();
204 m_xPathBox->set_sort_order(bSortAtoZ);
205 m_xPathBox->set_sort_indicator(bSortAtoZ ? TRISTATE_TRUE : TRISTATE_FALSE, nColumn);
208 SvxPathTabPage::~SvxPathTabPage()
210 for (int i = 0, nEntryCount = m_xPathBox->n_children(); i < nEntryCount; ++i)
211 delete weld::fromId<PathUserData_Impl*>(m_xPathBox->get_id(i));
214 std::unique_ptr<SfxTabPage> SvxPathTabPage::Create( weld::Container* pPage, weld::DialogController* pController,
215 const SfxItemSet* rAttrSet )
217 return std::make_unique<SvxPathTabPage>( pPage, pController, *rAttrSet );
220 OUString SvxPathTabPage::GetAllStrings()
222 OUString sAllStrings;
223 if (const auto pString = m_xBuilder->weld_label(u"label1"_ustr))
224 sAllStrings += pString->get_label() + " ";
225 return sAllStrings.replaceAll("_", "");
228 bool SvxPathTabPage::FillItemSet( SfxItemSet* )
230 for (int i = 0, nEntryCount = m_xPathBox->n_children(); i < nEntryCount; ++i)
232 PathUserData_Impl* pPathImpl = weld::fromId<PathUserData_Impl*>(m_xPathBox->get_id(i));
233 SvtPathOptions::Paths nRealId = pPathImpl->nRealId;
234 if (pPathImpl->bItemStateSet )
235 SetPathList( nRealId, pPathImpl->sUserPath, pPathImpl->sWritablePath );
237 return true;
240 void SvxPathTabPage::Reset( const SfxItemSet* )
242 m_xPathBox->clear();
243 m_xPathBox->make_unsorted();
245 std::unique_ptr<weld::TreeIter> xIter = m_xPathBox->make_iterator();
246 for( sal_uInt16 i = 0; i <= sal_uInt16(SvtPathOptions::Paths::Classification); ++i )
248 // only writer uses autotext
249 if ( static_cast<SvtPathOptions::Paths>(i) == SvtPathOptions::Paths::AutoText
250 && !SvtModuleOptions().IsWriterInstalled())
251 continue;
253 TranslateId pId;
255 switch (static_cast<SvtPathOptions::Paths>(i))
257 case SvtPathOptions::Paths::AutoCorrect:
258 pId = RID_CUISTR_KEY_AUTOCORRECT_DIR;
259 break;
260 case SvtPathOptions::Paths::AutoText:
261 pId = RID_CUISTR_KEY_GLOSSARY_PATH;
262 break;
263 case SvtPathOptions::Paths::Backup:
264 pId = RID_CUISTR_KEY_BACKUP_PATH;
265 break;
266 case SvtPathOptions::Paths::Gallery:
267 pId = RID_CUISTR_KEY_GALLERY_DIR;
268 break;
269 case SvtPathOptions::Paths::Graphic:
270 pId = RID_CUISTR_KEY_GRAPHICS_PATH;
271 break;
272 case SvtPathOptions::Paths::Temp:
273 pId = RID_CUISTR_KEY_TEMP_PATH;
274 break;
275 case SvtPathOptions::Paths::Template:
276 pId = RID_CUISTR_KEY_TEMPLATE_PATH;
277 break;
278 case SvtPathOptions::Paths::Dictionary:
279 pId = RID_CUISTR_KEY_DICTIONARY_PATH;
280 break;
281 case SvtPathOptions::Paths::Classification:
282 pId = RID_CUISTR_KEY_CLASSIFICATION_PATH;
283 break;
284 #if OSL_DEBUG_LEVEL > 1
285 case SvtPathOptions::Paths::Linguistic:
286 pId = RID_CUISTR_KEY_LINGUISTIC_DIR;
287 break;
288 #endif
289 case SvtPathOptions::Paths::Work:
290 pId = RID_CUISTR_KEY_WORK_PATH;
291 break;
292 default: break;
295 if (pId)
297 m_xPathBox->append(xIter.get());
299 OUString aStr(CuiResId(pId));
300 m_xPathBox->set_text(*xIter, aStr, 0);
302 OUString sInternal, sUser, sWritable;
303 bool bReadOnly = false;
304 GetPathList( static_cast<SvtPathOptions::Paths>(i), sInternal, sUser, sWritable, bReadOnly );
306 if (bReadOnly)
307 m_xPathBox->set_image(*xIter, RID_SVXBMP_LOCK);
309 OUString sTmpPath = sUser;
310 if ( !sTmpPath.isEmpty() && !sWritable.isEmpty() )
311 sTmpPath += OUStringChar(MULTIPATH_DELIMITER);
312 sTmpPath += sWritable;
313 const OUString aValue = Convert_Impl( sTmpPath );
315 m_xPathBox->set_text(*xIter, aValue, 1);
317 const OUString aValueInternal = Convert_Impl( sInternal );
319 m_xPathBox->set_text(*xIter, aValueInternal, 2);
321 m_xPathBox->set_sensitive(*xIter, !bReadOnly, 0);
322 m_xPathBox->set_sensitive(*xIter, !bReadOnly, 1);
323 m_xPathBox->set_sensitive(*xIter, !bReadOnly, 2);
325 PathUserData_Impl* pPathImpl = new PathUserData_Impl(static_cast<SvtPathOptions::Paths>(i));
326 pPathImpl->sUserPath = sUser;
327 pPathImpl->sWritablePath = sWritable;
328 pPathImpl->bReadOnly = bReadOnly;
330 OUString sId = weld::toId(pPathImpl);
331 m_xPathBox->set_id(*xIter, sId);
335 m_xPathBox->columns_autosize();
336 m_xPathBox->make_sorted();
337 PathSelect_Impl(*m_xPathBox);
340 IMPL_LINK_NOARG(SvxPathTabPage, PathSelect_Impl, weld::TreeView&, void)
342 bool bEnable = false;
343 int nEntry = m_xPathBox->get_selected_index();
344 if (nEntry != -1)
346 PathUserData_Impl* pPathImpl = weld::fromId<PathUserData_Impl*>(m_xPathBox->get_id(nEntry));
347 bEnable = !pPathImpl->bReadOnly;
349 sal_uInt16 nSelCount = m_xPathBox->count_selected_rows();
350 m_xPathBtn->set_sensitive(1 == nSelCount && bEnable);
351 m_xStandardBtn->set_sensitive(nSelCount > 0 && bEnable);
354 IMPL_LINK_NOARG(SvxPathTabPage, StandardHdl_Impl, weld::Button&, void)
356 m_xPathBox->selected_foreach([this](weld::TreeIter& rEntry){
357 PathUserData_Impl* pPathImpl = weld::fromId<PathUserData_Impl*>(m_xPathBox->get_id(rEntry));
358 OUString aOldPath = SvtDefaultOptions::GetDefaultPath( pPathImpl->nRealId );
360 if ( !aOldPath.isEmpty() )
362 OUString sInternal, sUser, sWritable, sTemp;
363 bool bReadOnly = false;
364 GetPathList( pPathImpl->nRealId, sInternal, sUser, sWritable, bReadOnly );
366 sal_Int32 nOldPos = 0;
369 bool bFound = false;
370 const std::u16string_view sOnePath = o3tl::getToken(aOldPath, 0, MULTIPATH_DELIMITER, nOldPos );
371 if ( !sInternal.isEmpty() )
373 sal_Int32 nInternalPos = 0;
376 if ( o3tl::getToken(sInternal, 0, MULTIPATH_DELIMITER, nInternalPos ) == sOnePath )
377 bFound = true;
379 while ( !bFound && nInternalPos >= 0 );
381 if ( !bFound )
383 if ( !sTemp.isEmpty() )
384 sTemp += OUStringChar(MULTIPATH_DELIMITER);
385 sTemp += sOnePath;
388 while ( nOldPos >= 0 );
390 OUString sWritablePath;
391 OUStringBuffer sUserPath;
392 if ( !sTemp.isEmpty() )
394 sal_Int32 nNextPos = 0;
395 for (;;)
397 const OUString sToken = sTemp.getToken( 0, MULTIPATH_DELIMITER, nNextPos );
398 if ( nNextPos<0 )
400 // Last token need a different handling
401 sWritablePath = sToken;
402 break;
404 if ( !sUserPath.isEmpty() )
405 sUserPath.append(MULTIPATH_DELIMITER);
406 sUserPath.append(sToken);
409 m_xPathBox->set_text(rEntry, Convert_Impl(sTemp), 1);
410 pPathImpl->bItemStateSet = true;
411 pPathImpl->sUserPath = sUserPath.makeStringAndClear();
412 pPathImpl->sWritablePath = sWritablePath;
414 return false;
418 void SvxPathTabPage::ChangeCurrentEntry( const OUString& _rFolder )
420 int nEntry = m_xPathBox->get_cursor_index();
421 if (nEntry == -1)
423 SAL_WARN( "cui.options", "SvxPathTabPage::ChangeCurrentEntry(): no entry" );
424 return;
427 OUString sInternal, sUser, sWritable;
428 PathUserData_Impl* pPathImpl = weld::fromId<PathUserData_Impl*>(m_xPathBox->get_id(nEntry));
429 bool bReadOnly = false;
430 GetPathList( pPathImpl->nRealId, sInternal, sUser, sWritable, bReadOnly );
431 sUser = pPathImpl->sUserPath;
432 sWritable = pPathImpl->sWritablePath;
434 // old path is a URL?
435 INetURLObject aObj( sWritable );
436 bool bURL = ( aObj.GetProtocol() != INetProtocol::NotValid );
437 INetURLObject aNewObj( _rFolder );
438 aNewObj.removeFinalSlash();
440 // then the new path also a URL else system path
441 OUString sNewPathStr = bURL ? _rFolder : aNewObj.getFSysPath( FSysStyle::Detect );
443 bool bChanged =
444 #ifdef UNX
445 // Unix is case sensitive
446 ( sNewPathStr != sWritable );
447 #else
448 !sNewPathStr.equalsIgnoreAsciiCase( sWritable );
449 #endif
451 if ( !bChanged )
452 return;
454 m_xPathBox->set_text(nEntry, Convert_Impl(sNewPathStr), 1);
455 pPathImpl->bItemStateSet = true;
456 pPathImpl->sWritablePath = sNewPathStr;
457 if ( SvtPathOptions::Paths::Work == pPathImpl->nRealId )
459 // Remove view options entry so the new work path
460 // will be used for the next open dialog.
461 SvtViewOptions aDlgOpt( EViewType::Dialog, IODLG_CONFIGNAME );
462 aDlgOpt.Delete();
463 // Reset also last used dir in the sfx application instance
464 SfxApplication *pSfxApp = SfxGetpApp();
465 pSfxApp->ResetLastDir();
469 IMPL_LINK_NOARG(SvxPathTabPage, DoubleClickPathHdl_Impl, weld::TreeView&, bool)
471 PathHdl_Impl(*m_xPathBtn);
472 return true;
475 IMPL_LINK_NOARG(SvxPathTabPage, PathHdl_Impl, weld::Button&, void)
477 int nEntry = m_xPathBox->get_cursor_index();
478 PathUserData_Impl* pPathImpl = nEntry != -1 ? weld::fromId<PathUserData_Impl*>(m_xPathBox->get_id(nEntry)) : nullptr;
479 if (!pPathImpl || pPathImpl->bReadOnly)
480 return;
482 SvtPathOptions::Paths nPos = pPathImpl->nRealId;
483 OUString sInternal, sUser, sWritable;
484 bool bPickFile = false;
485 bool bReadOnly = false;
486 GetPathList( pPathImpl->nRealId, sInternal, sUser, sWritable, bReadOnly );
487 sUser = pPathImpl->sUserPath;
488 sWritable = pPathImpl->sWritablePath;
489 bPickFile = pPathImpl->nRealId == SvtPathOptions::Paths::Classification;
491 if (IsMultiPath_Impl(nPos))
493 SvxAbstractDialogFactory* pFact = SvxAbstractDialogFactory::Create();
494 ScopedVclPtr<AbstractSvxMultiPathDialog> pMultiDlg(
495 pFact->CreateSvxMultiPathDialog(GetFrameWeld()));
497 OUString sPath( sUser );
498 if ( !sPath.isEmpty() )
499 sPath += OUStringChar(MULTIPATH_DELIMITER);
500 sPath += sWritable;
501 pMultiDlg->SetPath( sPath );
503 const OUString sPathName = m_xPathBox->get_text(nEntry, 0);
504 const OUString sNewTitle = pImpl->m_sMultiPathDlg.replaceFirst( VAR_ONE, sPathName );
505 pMultiDlg->SetTitle( sNewTitle );
507 if (pMultiDlg->Execute() == RET_OK)
509 sUser.clear();
510 sWritable.clear();
511 OUString sFullPath;
512 OUString sNewPath = pMultiDlg->GetPath();
513 if ( !sNewPath.isEmpty() )
515 sal_Int32 nNextPos = 0;
516 for (;;)
518 const OUString sToken(sNewPath.getToken( 0, MULTIPATH_DELIMITER, nNextPos ));
519 if ( nNextPos<0 )
521 // Last token need a different handling
522 sWritable = sToken;
523 break;
525 if ( !sUser.isEmpty() )
526 sUser += OUStringChar(MULTIPATH_DELIMITER);
527 sUser += sToken;
529 sFullPath = sUser;
530 if ( !sFullPath.isEmpty() )
531 sFullPath += OUStringChar(MULTIPATH_DELIMITER);
532 sFullPath += sWritable;
535 m_xPathBox->set_text(nEntry, Convert_Impl(sFullPath), 1);
536 // save modified flag
537 pPathImpl->bItemStateSet = true;
538 pPathImpl->sUserPath = sUser;
539 pPathImpl->sWritablePath = sWritable;
542 else if (!bPickFile)
546 const Reference < XComponentContext >& xContext( ::comphelper::getProcessComponentContext() );
547 xFolderPicker = sfx2::createFolderPicker(xContext, GetFrameWeld());
549 INetURLObject aURL( sWritable, INetProtocol::File );
550 xFolderPicker->setDisplayDirectory( aURL.GetMainURL( INetURLObject::DecodeMechanism::NONE ) );
552 Reference< XAsynchronousExecutableDialog > xAsyncDlg( xFolderPicker, UNO_QUERY );
553 if ( xAsyncDlg.is() )
554 xAsyncDlg->startExecuteModal( xDialogListener );
555 else
557 short nRet = xFolderPicker->execute();
558 if (ExecutableDialogResults::OK != nRet)
559 return;
561 OUString sFolder(xFolderPicker->getDirectory());
562 ChangeCurrentEntry(sFolder);
565 catch( Exception const & )
567 TOOLS_WARN_EXCEPTION( "cui.options", "SvxPathTabPage::PathHdl_Impl: exception from folder picker" );
570 else
574 sfx2::FileDialogHelper aHelper(ui::dialogs::TemplateDescription::FILEOPEN_SIMPLE, FileDialogFlags::NONE, GetFrameWeld());
575 const uno::Reference<ui::dialogs::XFilePicker3>& xFilePicker = aHelper.GetFilePicker();
576 xFilePicker->appendFilter(OUString(), u"*.xml"_ustr);
577 if (xFilePicker->execute() == ui::dialogs::ExecutableDialogResults::OK)
579 uno::Sequence<OUString> aPathSeq(xFilePicker->getSelectedFiles());
580 ChangeCurrentEntry(aPathSeq[0]);
583 catch (const uno::Exception&)
585 DBG_UNHANDLED_EXCEPTION("cui.options", "exception from file picker");
590 IMPL_LINK( SvxPathTabPage, DialogClosedHdl, DialogClosedEvent*, pEvt, void )
592 if (RET_OK == pEvt->DialogResult)
594 assert(xFolderPicker.is() && "SvxPathTabPage::DialogClosedHdl(): no folder picker");
595 OUString sURL = xFolderPicker->getDirectory();
596 ChangeCurrentEntry( sURL );
600 void SvxPathTabPage::GetPathList(
601 SvtPathOptions::Paths _nPathHandle, OUString& _rInternalPath,
602 OUString& _rUserPath, OUString& _rWritablePath, bool& _rReadOnly )
604 OUString sCfgName = getCfgName_Impl( _nPathHandle );
608 // load PathSettings service if necessary
609 if ( !pImpl->m_xPathSettings.is() )
611 const Reference< XComponentContext >& xContext = comphelper::getProcessComponentContext();
612 pImpl->m_xPathSettings = css::util::thePathSettings::get( xContext );
615 // load internal paths
616 Any aAny = pImpl->m_xPathSettings->getPropertyValue(
617 sCfgName + POSTFIX_INTERNAL);
618 Sequence< OUString > aPathSeq;
619 if ( aAny >>= aPathSeq )
621 for (auto& path : aPathSeq)
623 if ( !_rInternalPath.isEmpty() )
624 _rInternalPath += ";";
625 _rInternalPath += path;
628 // load user paths
629 aAny = pImpl->m_xPathSettings->getPropertyValue(
630 sCfgName + POSTFIX_USER);
631 if ( aAny >>= aPathSeq )
633 for (auto& path : aPathSeq)
635 if ( !_rUserPath.isEmpty() )
636 _rUserPath += ";";
637 _rUserPath += path;
640 // then the writable path
641 aAny = pImpl->m_xPathSettings->getPropertyValue(
642 sCfgName + POSTFIX_WRITABLE);
643 OUString sWritablePath;
644 if ( aAny >>= sWritablePath )
645 _rWritablePath = sWritablePath;
647 // and the readonly flag
648 Reference< XPropertySetInfo > xInfo = pImpl->m_xPathSettings->getPropertySetInfo();
649 Property aProp = xInfo->getPropertyByName(sCfgName);
650 _rReadOnly = ( ( aProp.Attributes & PropertyAttribute::READONLY ) == PropertyAttribute::READONLY );
652 catch( const Exception& )
654 TOOLS_WARN_EXCEPTION( "cui.options", "SvxPathTabPage::GetPathList()" );
659 void SvxPathTabPage::SetPathList(
660 SvtPathOptions::Paths _nPathHandle, std::u16string_view _rUserPath, const OUString& _rWritablePath )
662 OUString sCfgName = getCfgName_Impl( _nPathHandle );
666 // load PathSettings service if necessary
667 if ( !pImpl->m_xPathSettings.is() )
669 const Reference< XComponentContext >& xContext = comphelper::getProcessComponentContext();
670 pImpl->m_xPathSettings = css::util::thePathSettings::get( xContext );
673 // save user paths
674 const sal_Int32 nCount = comphelper::string::getTokenCount(_rUserPath, MULTIPATH_DELIMITER);
675 Sequence< OUString > aPathSeq( nCount );
676 OUString* pArray = aPathSeq.getArray();
677 sal_Int32 nPos = 0;
678 for ( sal_Int32 i = 0; i < nCount; ++i )
679 pArray[i] = o3tl::getToken(_rUserPath, 0, MULTIPATH_DELIMITER, nPos );
680 Any aValue( aPathSeq );
681 pImpl->m_xPathSettings->setPropertyValue(
682 sCfgName + POSTFIX_USER, aValue);
684 // then the writable path
685 aValue <<= _rWritablePath;
686 pImpl->m_xPathSettings->setPropertyValue(
687 sCfgName + POSTFIX_WRITABLE, aValue);
689 catch( const Exception& )
691 TOOLS_WARN_EXCEPTION("cui.options", "");
695 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */