LibreOffice Module cui (master)  1
optpath.cxx
Go to the documentation of this file.
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3  * This file is part of the LibreOffice project.
4  *
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/.
8  *
9  * This file incorporates work covered by the following license notice:
10  *
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 .
18  */
19 
20 #include <svx/svxdlg.hxx>
21 #include <sfx2/filedlghelper.hxx>
22 #include <sfx2/app.hxx>
23 #include <tools/urlobj.hxx>
25 #include <unotools/pathoptions.hxx>
27 #include <unotools/viewoptions.hxx>
28 
29 #include <bitmaps.hlst>
30 #include <dialmgr.hxx>
31 #include <optpath.hxx>
32 #include <strings.hrc>
35 #include <comphelper/string.hxx>
36 #include <com/sun/star/uno/Exception.hpp>
37 #include <com/sun/star/beans/PropertyAttribute.hpp>
38 #include <com/sun/star/ui/dialogs/ExecutableDialogResults.hpp>
39 #include <com/sun/star/ui/dialogs/XAsynchronousExecutableDialog.hpp>
40 #include <com/sun/star/ui/dialogs/FolderPicker.hpp>
41 #include <com/sun/star/ui/dialogs/FilePicker.hpp>
42 #include <com/sun/star/ui/dialogs/TemplateDescription.hpp>
43 #include <com/sun/star/util/thePathSettings.hpp>
44 #include <officecfg/Office/Common.hxx>
45 #include <tools/diagnose_ex.h>
46 #include <sal/log.hxx>
47 
48 using namespace css;
49 using namespace css::beans;
50 using namespace css::lang;
51 using namespace css::ui::dialogs;
52 using namespace css::uno;
53 using namespace svx;
54 
55 // define ----------------------------------------------------------------
56 
57 #define POSTFIX_INTERNAL "_internal"
58 #define POSTFIX_USER "_user"
59 #define POSTFIX_WRITABLE "_writable"
60 #define VAR_ONE "%1"
61 #define IODLG_CONFIGNAME "FilePicker_Save"
62 
63 // struct OptPath_Impl ---------------------------------------------------
64 
66 {
68  OUString m_sMultiPathDlg;
69  Reference< css::util::XPathSettings > m_xPathSettings;
70 
72  : m_sMultiPathDlg(CuiResId(RID_SVXSTR_EDIT_PATHS))
73  {
74  }
75 };
76 
78 {
79  sal_uInt16 nRealId;
81  OUString sUserPath;
82  OUString sWritablePath;
83  bool bReadOnly;
84 
85  explicit PathUserData_Impl(sal_uInt16 nId)
86  : nRealId(nId)
87  , eState(SfxItemState::UNKNOWN)
88  , bReadOnly(false)
89  {
90  }
91 };
92 
94 {
95  sal_uInt16 m_nHandle;
96  const char* m_pCfgName;
97 };
98 
100 {
101  { SvtPathOptions::PATH_AUTOCORRECT, "AutoCorrect" },
102  { SvtPathOptions::PATH_AUTOTEXT, "AutoText" },
103  { SvtPathOptions::PATH_BACKUP, "Backup" },
104  { SvtPathOptions::PATH_GALLERY, "Gallery" },
105  { SvtPathOptions::PATH_GRAPHIC, "Graphic" },
106  { SvtPathOptions::PATH_TEMP, "Temp" },
107  { SvtPathOptions::PATH_TEMPLATE, "Template" },
108  { SvtPathOptions::PATH_WORK, "Work" },
109  { SvtPathOptions::PATH_DICTIONARY, "Dictionary" },
110  { SvtPathOptions::PATH_CLASSIFICATION, "Classification" },
111 #if OSL_DEBUG_LEVEL > 1
112  { SvtPathOptions::PATH_LINGUISTIC, "Linguistic" },
113 #endif
114  { USHRT_MAX, nullptr }
115 };
116 
117 static OUString getCfgName_Impl( sal_uInt16 _nHandle )
118 {
119  OUString sCfgName;
120  sal_uInt16 nIndex = 0;
121  while ( Hdl2CfgMap_Impl[ nIndex ].m_nHandle != USHRT_MAX )
122  {
123  if ( Hdl2CfgMap_Impl[ nIndex ].m_nHandle == _nHandle )
124  {
125  // config name found
126  sCfgName = OUString::createFromAscii( Hdl2CfgMap_Impl[ nIndex ].m_pCfgName );
127  break;
128  }
129  ++nIndex;
130  }
131 
132  return sCfgName;
133 }
134 
135 #define MULTIPATH_DELIMITER ';'
136 
137 static OUString Convert_Impl( const OUString& rValue )
138 {
139  if (rValue.isEmpty())
140  return OUString();
141 
142  sal_Int32 nPos = 0;
143  OUStringBuffer aReturn;
144  for (;;)
145  {
146  OUString aValue = rValue.getToken( 0, MULTIPATH_DELIMITER, nPos );
147  INetURLObject aObj( aValue );
148  if ( aObj.GetProtocol() == INetProtocol::File )
149  aReturn.append(aObj.PathToFileName());
150  if ( nPos < 0 )
151  break;
152  aReturn.append(MULTIPATH_DELIMITER);
153  }
154 
155  return aReturn.makeStringAndClear();
156 }
157 
158 // functions -------------------------------------------------------------
159 
160 static bool IsMultiPath_Impl( const sal_uInt16 nIndex )
161 {
162 #if OSL_DEBUG_LEVEL > 1
163  return ( SvtPathOptions::PATH_AUTOCORRECT == nIndex ||
164  SvtPathOptions::PATH_AUTOTEXT == nIndex ||
165  SvtPathOptions::PATH_BASIC == nIndex ||
166  SvtPathOptions::PATH_GALLERY == nIndex ||
167  SvtPathOptions::PATH_TEMPLATE == nIndex );
168 #else
169  return ( SvtPathOptions::PATH_AUTOCORRECT == nIndex ||
170  SvtPathOptions::PATH_AUTOTEXT == nIndex ||
171  SvtPathOptions::PATH_BASIC == nIndex ||
172  SvtPathOptions::PATH_GALLERY == nIndex ||
173  SvtPathOptions::PATH_TEMPLATE == nIndex ||
176 #endif
177 }
178 
179 // class SvxPathTabPage --------------------------------------------------
180 
182  : SfxTabPage( pPage, pController, "cui/ui/optpathspage.ui", "OptPathsPage", &rSet)
183  , pImpl(new OptPath_Impl)
184  , xDialogListener ( new ::svt::DialogClosedListener() )
185  , m_xStandardBtn(m_xBuilder->weld_button("default"))
186  , m_xPathBtn(m_xBuilder->weld_button("edit"))
187  , m_xPathBox(m_xBuilder->weld_tree_view("paths"))
188 {
189  m_xStandardBtn->connect_clicked(LINK(this, SvxPathTabPage, StandardHdl_Impl));
190  m_xPathBtn->connect_clicked( LINK( this, SvxPathTabPage, PathHdl_Impl ) );
191 
192  m_xPathBox->set_size_request(m_xPathBox->get_approximate_digit_width() * 60,
193  m_xPathBox->get_height_rows(20));
194 
195  m_xPathBox->connect_row_activated( LINK( this, SvxPathTabPage, DoubleClickPathHdl_Impl ) );
196  m_xPathBox->connect_changed( LINK( this, SvxPathTabPage, PathSelect_Impl ) );
197  m_xPathBox->set_selection_mode(SelectionMode::Multiple);
198 
199  xDialogListener->SetDialogClosedLink( LINK( this, SvxPathTabPage, DialogClosedHdl ) );
200 }
201 
203 {
204  for (int i = 0, nEntryCount = m_xPathBox->n_children(); i < nEntryCount; ++i)
205  delete reinterpret_cast<PathUserData_Impl*>(m_xPathBox->get_id(i).toInt64());
206 }
207 
208 std::unique_ptr<SfxTabPage> SvxPathTabPage::Create( weld::Container* pPage, weld::DialogController* pController,
209  const SfxItemSet* rAttrSet )
210 {
211  return std::make_unique<SvxPathTabPage>( pPage, pController, *rAttrSet );
212 }
213 
215 {
216  for (int i = 0, nEntryCount = m_xPathBox->n_children(); i < nEntryCount; ++i)
217  {
218  PathUserData_Impl* pPathImpl = reinterpret_cast<PathUserData_Impl*>(m_xPathBox->get_id(i).toInt64());
219  sal_uInt16 nRealId = pPathImpl->nRealId;
220  if (pPathImpl->eState == SfxItemState::SET)
221  SetPathList( nRealId, pPathImpl->sUserPath, pPathImpl->sWritablePath );
222  }
223  return true;
224 }
225 
227 {
228  m_xPathBox->clear();
229 
230  std::unique_ptr<weld::TreeIter> xIter = m_xPathBox->make_iterator();
231  for( sal_uInt16 i = 0; i <= sal_uInt16(SvtPathOptions::PATH_CLASSIFICATION); ++i )
232  {
233  // only writer uses autotext
236  continue;
237 
238  const char* pId = nullptr;
239 
240  switch (i)
241  {
243  pId = RID_SVXSTR_KEY_AUTOCORRECT_DIR;
244  break;
246  pId = RID_SVXSTR_KEY_GLOSSARY_PATH;
247  break;
249  pId = RID_SVXSTR_KEY_BACKUP_PATH;
250  break;
252  pId = RID_SVXSTR_KEY_GALLERY_DIR;
253  break;
255  pId = RID_SVXSTR_KEY_GRAPHICS_PATH;
256  break;
258  pId = RID_SVXSTR_KEY_TEMP_PATH;
259  break;
261  pId = RID_SVXSTR_KEY_TEMPLATE_PATH;
262  break;
264  pId = RID_SVXSTR_KEY_DICTIONARY_PATH;
265  break;
267  pId = RID_SVXSTR_KEY_CLASSIFICATION_PATH;
268  break;
269 #if OSL_DEBUG_LEVEL > 1
271  pId = RID_SVXSTR_KEY_LINGUISTIC_DIR;
272  break;
273 #endif
275  pId = RID_SVXSTR_KEY_WORK_PATH;
276  break;
277  }
278 
279  if (pId)
280  {
281  m_xPathBox->append(xIter.get());
282 
283  OUString aStr(CuiResId(pId));
284  m_xPathBox->set_text(*xIter, aStr, 0);
285 
286  OUString sInternal, sUser, sWritable;
287  bool bReadOnly = false;
288  GetPathList( i, sInternal, sUser, sWritable, bReadOnly );
289 
290  if (bReadOnly)
291  m_xPathBox->set_image(*xIter, RID_SVXBMP_LOCK);
292 
293  OUString sTmpPath = sUser;
294  if ( !sTmpPath.isEmpty() && !sWritable.isEmpty() )
295  sTmpPath += OUStringChar(MULTIPATH_DELIMITER);
296  sTmpPath += sWritable;
297  const OUString aValue = Convert_Impl( sTmpPath );
298 
299  m_xPathBox->set_text(*xIter, aValue, 1);
300 
301  const OUString aValueInternal = Convert_Impl( sInternal );
302 
303  m_xPathBox->set_text(*xIter, aValueInternal, 2);
304 
305  m_xPathBox->set_sensitive(*xIter, !bReadOnly, 0);
306  m_xPathBox->set_sensitive(*xIter, !bReadOnly, 1);
307  m_xPathBox->set_sensitive(*xIter, !bReadOnly, 2);
308 
309  PathUserData_Impl* pPathImpl = new PathUserData_Impl(i);
310  pPathImpl->sUserPath = sUser;
311  pPathImpl->sWritablePath = sWritable;
312  pPathImpl->bReadOnly = bReadOnly;
313 
314  OUString sId = OUString::number(reinterpret_cast<sal_Int64>(pPathImpl));
315  m_xPathBox->set_id(*xIter, sId);
316  }
317  }
318 
319  m_xPathBox->columns_autosize();
320  PathSelect_Impl(*m_xPathBox);
321 }
322 
324 {
325  bool bEnable = false;
326  int nEntry = m_xPathBox->get_selected_index();
327  if (nEntry != -1)
328  {
329  PathUserData_Impl* pPathImpl = reinterpret_cast<PathUserData_Impl*>(m_xPathBox->get_id(nEntry).toInt64());
330  bEnable = !pPathImpl->bReadOnly;
331  }
332  sal_uInt16 nSelCount = m_xPathBox->count_selected_rows();
333  m_xPathBtn->set_sensitive(1 == nSelCount && bEnable);
334  m_xStandardBtn->set_sensitive(nSelCount > 0 && bEnable);
335 }
336 
337 IMPL_LINK_NOARG(SvxPathTabPage, StandardHdl_Impl, weld::Button&, void)
338 {
339  m_xPathBox->selected_foreach([this](weld::TreeIter& rEntry){
340  PathUserData_Impl* pPathImpl = reinterpret_cast<PathUserData_Impl*>(m_xPathBox->get_id(rEntry).toInt64());
341  OUString aOldPath = pImpl->m_aDefOpt.GetDefaultPath( pPathImpl->nRealId );
342 
343  if ( !aOldPath.isEmpty() )
344  {
345  OUString sInternal, sUser, sWritable, sTemp;
346  bool bReadOnly = false;
347  GetPathList( pPathImpl->nRealId, sInternal, sUser, sWritable, bReadOnly );
348 
349  sal_Int32 nOldPos = 0;
350  do
351  {
352  bool bFound = false;
353  const OUString sOnePath = aOldPath.getToken( 0, MULTIPATH_DELIMITER, nOldPos );
354  if ( !sInternal.isEmpty() )
355  {
356  sal_Int32 nInternalPos = 0;
357  do
358  {
359  if ( sInternal.getToken( 0, MULTIPATH_DELIMITER, nInternalPos ) == sOnePath )
360  bFound = true;
361  }
362  while ( !bFound && nInternalPos >= 0 );
363  }
364  if ( !bFound )
365  {
366  if ( !sTemp.isEmpty() )
367  sTemp += OUStringChar(MULTIPATH_DELIMITER);
368  sTemp += sOnePath;
369  }
370  }
371  while ( nOldPos >= 0 );
372 
373  OUString sWritablePath;
374  OUStringBuffer sUserPath;
375  if ( !sTemp.isEmpty() )
376  {
377  sal_Int32 nNextPos = 0;
378  for (;;)
379  {
380  const OUString sToken = sTemp.getToken( 0, MULTIPATH_DELIMITER, nNextPos );
381  if ( nNextPos<0 )
382  {
383  // Last token need a different handling
384  sWritablePath = sToken;
385  break;
386  }
387  if ( !sUserPath.isEmpty() )
388  sUserPath.append(MULTIPATH_DELIMITER);
389  sUserPath.append(sToken);
390  }
391  }
392  m_xPathBox->set_text(rEntry, Convert_Impl(sTemp), 1);
393  pPathImpl->eState = SfxItemState::SET;
394  pPathImpl->sUserPath = sUserPath.makeStringAndClear();
395  pPathImpl->sWritablePath = sWritablePath;
396  }
397  return false;
398  });
399 }
400 
401 void SvxPathTabPage::ChangeCurrentEntry( const OUString& _rFolder )
402 {
403  int nEntry = m_xPathBox->get_cursor_index();
404  if (nEntry == -1)
405  {
406  SAL_WARN( "cui.options", "SvxPathTabPage::ChangeCurrentEntry(): no entry" );
407  return;
408  }
409 
410  OUString sInternal, sUser, sWritable;
411  PathUserData_Impl* pPathImpl = reinterpret_cast<PathUserData_Impl*>(m_xPathBox->get_id(nEntry).toInt64());
412  bool bReadOnly = false;
413  GetPathList( pPathImpl->nRealId, sInternal, sUser, sWritable, bReadOnly );
414  sUser = pPathImpl->sUserPath;
415  sWritable = pPathImpl->sWritablePath;
416 
417  // old path is a URL?
418  INetURLObject aObj( sWritable );
419  bool bURL = ( aObj.GetProtocol() != INetProtocol::NotValid );
420  INetURLObject aNewObj( _rFolder );
421  aNewObj.removeFinalSlash();
422 
423  // then the new path also a URL else system path
424  OUString sNewPathStr = bURL ? _rFolder : aNewObj.getFSysPath( FSysStyle::Detect );
425 
426  bool bChanged =
427 #ifdef UNX
428 // Unix is case sensitive
429  ( sNewPathStr != sWritable );
430 #else
431  !sNewPathStr.equalsIgnoreAsciiCase( sWritable );
432 #endif
433 
434  if ( bChanged )
435  {
436  m_xPathBox->set_text(nEntry, Convert_Impl(sNewPathStr), 1);
437  pPathImpl->eState = SfxItemState::SET;
438  pPathImpl->sWritablePath = sNewPathStr;
439  if ( SvtPathOptions::PATH_WORK == pPathImpl->nRealId )
440  {
441  // Remove view options entry so the new work path
442  // will be used for the next open dialog.
443  SvtViewOptions aDlgOpt( EViewType::Dialog, IODLG_CONFIGNAME );
444  aDlgOpt.Delete();
445  // Reset also last used dir in the sfx application instance
446  SfxApplication *pSfxApp = SfxGetpApp();
447  pSfxApp->ResetLastDir();
448 
449  // Set configuration flag to notify file picker that it's necessary
450  // to take over the path provided.
451  std::shared_ptr< comphelper::ConfigurationChanges > batch(
453  officecfg::Office::Common::Path::Info::WorkPathChanged::set(
454  true, batch);
455  batch->commit();
456  }
457  }
458 }
459 
460 IMPL_LINK_NOARG(SvxPathTabPage, DoubleClickPathHdl_Impl, weld::TreeView&, bool)
461 {
462  PathHdl_Impl(*m_xPathBtn);
463  return true;
464 }
465 
467 {
468  int nEntry = m_xPathBox->get_cursor_index();
469  PathUserData_Impl* pPathImpl = nEntry != -1 ? reinterpret_cast<PathUserData_Impl*>(m_xPathBox->get_id(nEntry).toInt64()) : nullptr;
470  if (!pPathImpl || pPathImpl->bReadOnly)
471  return;
472 
473  sal_uInt16 nPos = pPathImpl->nRealId;
474  OUString sInternal, sUser, sWritable;
475  bool bPickFile = false;
476  bool bReadOnly = false;
477  GetPathList( pPathImpl->nRealId, sInternal, sUser, sWritable, bReadOnly );
478  sUser = pPathImpl->sUserPath;
479  sWritable = pPathImpl->sWritablePath;
480  bPickFile = pPathImpl->nRealId == SvtPathOptions::PATH_CLASSIFICATION;
481 
482  if (IsMultiPath_Impl(nPos))
483  {
487 
488  OUString sPath( sUser );
489  if ( !sPath.isEmpty() )
490  sPath += OUStringChar(MULTIPATH_DELIMITER);
491  sPath += sWritable;
492  pMultiDlg->SetPath( sPath );
493 
494  const OUString sPathName = m_xPathBox->get_text(nEntry, 0);
495  const OUString sNewTitle = pImpl->m_sMultiPathDlg.replaceFirst( VAR_ONE, sPathName );
496  pMultiDlg->SetTitle( sNewTitle );
497 
498  if (pMultiDlg->Execute() == RET_OK)
499  {
500  sUser.clear();
501  sWritable.clear();
502  OUString sFullPath;
503  OUString sNewPath = pMultiDlg->GetPath();
504  if ( !sNewPath.isEmpty() )
505  {
506  sal_Int32 nNextPos = 0;
507  for (;;)
508  {
509  const OUString sToken(sNewPath.getToken( 0, MULTIPATH_DELIMITER, nNextPos ));
510  if ( nNextPos<0 )
511  {
512  // Last token need a different handling
513  sWritable = sToken;
514  break;
515  }
516  if ( !sUser.isEmpty() )
517  sUser += OUStringChar(MULTIPATH_DELIMITER);
518  sUser += sToken;
519  }
520  sFullPath = sUser;
521  if ( !sFullPath.isEmpty() )
522  sFullPath += OUStringChar(MULTIPATH_DELIMITER);
523  sFullPath += sWritable;
524  }
525 
526  m_xPathBox->set_text(nEntry, Convert_Impl(sFullPath), 1);
527  // save modified flag
528  pPathImpl->eState = SfxItemState::SET;
529  pPathImpl->sUserPath = sUser;
530  pPathImpl->sWritablePath = sWritable;
531  }
532  }
533  else if (!bPickFile)
534  {
535  try
536  {
538  xFolderPicker = FolderPicker::create(xContext);
539 
540  INetURLObject aURL( sWritable, INetProtocol::File );
541  xFolderPicker->setDisplayDirectory( aURL.GetMainURL( INetURLObject::DecodeMechanism::NONE ) );
542 
543  Reference< XAsynchronousExecutableDialog > xAsyncDlg( xFolderPicker, UNO_QUERY );
544  if ( xAsyncDlg.is() )
545  xAsyncDlg->startExecuteModal( xDialogListener.get() );
546  else
547  {
548  short nRet = xFolderPicker->execute();
549  if (ExecutableDialogResults::OK != nRet)
550  return;
551 
552  OUString sFolder(xFolderPicker->getDirectory());
553  ChangeCurrentEntry(sFolder);
554  }
555  }
556  catch( Exception const & )
557  {
558  TOOLS_WARN_EXCEPTION( "cui.options", "SvxPathTabPage::PathHdl_Impl: exception from folder picker" );
559  }
560  }
561  else
562  {
563  try
564  {
565  uno::Reference<uno::XComponentContext> xComponentContext(comphelper::getProcessComponentContext());
566  uno::Reference<ui::dialogs::XFilePicker3> xFilePicker = ui::dialogs::FilePicker::createWithMode(xComponentContext, ui::dialogs::TemplateDescription::FILEOPEN_SIMPLE);
567  xFilePicker->appendFilter(OUString(), "*.xml");
568  if (xFilePicker->execute() == ui::dialogs::ExecutableDialogResults::OK)
569  {
570  uno::Sequence<OUString> aPathSeq(xFilePicker->getSelectedFiles());
571  ChangeCurrentEntry(aPathSeq[0]);
572  }
573  }
574  catch (const uno::Exception&)
575  {
576  DBG_UNHANDLED_EXCEPTION("cui.options", "exception from file picker");
577  }
578  }
579 }
580 
581 IMPL_LINK( SvxPathTabPage, DialogClosedHdl, DialogClosedEvent*, pEvt, void )
582 {
583  if (RET_OK == pEvt->DialogResult)
584  {
585  assert(xFolderPicker.is() && "SvxPathTabPage::DialogClosedHdl(): no folder picker");
586  OUString sURL = xFolderPicker->getDirectory();
587  ChangeCurrentEntry( sURL );
588  }
589 }
590 
592  sal_uInt16 _nPathHandle, OUString& _rInternalPath,
593  OUString& _rUserPath, OUString& _rWritablePath, bool& _rReadOnly )
594 {
595  OUString sCfgName = getCfgName_Impl( _nPathHandle );
596 
597  try
598  {
599  // load PathSettings service if necessary
600  if ( !pImpl->m_xPathSettings.is() )
601  {
603  pImpl->m_xPathSettings = css::util::thePathSettings::get( xContext );
604  }
605 
606  // load internal paths
607  Any aAny = pImpl->m_xPathSettings->getPropertyValue(
608  sCfgName + POSTFIX_INTERNAL);
609  Sequence< OUString > aPathSeq;
610  if ( aAny >>= aPathSeq )
611  {
612  long i, nCount = aPathSeq.getLength();
613  const OUString* pPaths = aPathSeq.getConstArray();
614 
615  for ( i = 0; i < nCount; ++i )
616  {
617  if ( !_rInternalPath.isEmpty() )
618  _rInternalPath += ";";
619  _rInternalPath += pPaths[i];
620  }
621  }
622  // load user paths
623  aAny = pImpl->m_xPathSettings->getPropertyValue(
624  sCfgName + POSTFIX_USER);
625  if ( aAny >>= aPathSeq )
626  {
627  long i, nCount = aPathSeq.getLength();
628  const OUString* pPaths = aPathSeq.getConstArray();
629 
630  for ( i = 0; i < nCount; ++i )
631  {
632  if ( !_rUserPath.isEmpty() )
633  _rUserPath += ";";
634  _rUserPath += pPaths[i];
635  }
636  }
637  // then the writable path
638  aAny = pImpl->m_xPathSettings->getPropertyValue(
639  sCfgName + POSTFIX_WRITABLE);
640  OUString sWritablePath;
641  if ( aAny >>= sWritablePath )
642  _rWritablePath = sWritablePath;
643 
644  // and the readonly flag
645  Reference< XPropertySetInfo > xInfo = pImpl->m_xPathSettings->getPropertySetInfo();
646  Property aProp = xInfo->getPropertyByName(sCfgName);
647  _rReadOnly = ( ( aProp.Attributes & PropertyAttribute::READONLY ) == PropertyAttribute::READONLY );
648  }
649  catch( const Exception& )
650  {
651  OSL_FAIL( "SvxPathTabPage::GetPathList(): caught an exception!" );
652  }
653 }
654 
655 
657  sal_uInt16 _nPathHandle, const OUString& _rUserPath, const OUString& _rWritablePath )
658 {
659  OUString sCfgName = getCfgName_Impl( _nPathHandle );
660 
661  try
662  {
663  // load PathSettings service if necessary
664  if ( !pImpl->m_xPathSettings.is() )
665  {
667  pImpl->m_xPathSettings = css::util::thePathSettings::get( xContext );
668  }
669 
670  // save user paths
671  const sal_Int32 nCount = comphelper::string::getTokenCount(_rUserPath, MULTIPATH_DELIMITER);
672  Sequence< OUString > aPathSeq( nCount );
673  OUString* pArray = aPathSeq.getArray();
674  sal_Int32 nPos = 0;
675  for ( sal_Int32 i = 0; i < nCount; ++i )
676  pArray[i] = _rUserPath.getToken( 0, MULTIPATH_DELIMITER, nPos );
677  Any aValue( aPathSeq );
678  pImpl->m_xPathSettings->setPropertyValue(
679  sCfgName + POSTFIX_USER, aValue);
680 
681  // then the writable path
682  aValue <<= _rWritablePath;
683  pImpl->m_xPathSettings->setPropertyValue(
684  sCfgName + POSTFIX_WRITABLE, aValue);
685  }
686  catch( const Exception& )
687  {
688  TOOLS_WARN_EXCEPTION("cui.options", "");
689  }
690 }
691 
692 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
OUString sWritablePath
Definition: optpath.cxx:82
sal_uInt16 nRealId
Definition: optpath.cxx:79
#define VAR_ONE
Definition: optpath.cxx:60
OUString sUserPath
Definition: optpath.cxx:81
static SvxAbstractDialogFactory * Create()
bool IsModuleInstalled(EModule eModule) const
static OUString Convert_Impl(const OUString &rValue)
Definition: optpath.cxx:137
virtual bool FillItemSet(SfxItemSet *rSet) override
Definition: optpath.cxx:214
virtual VclPtr< AbstractSvxMultiPathDialog > CreateSvxMultiPathDialog(weld::Window *pParent)=0
SvxPathTabPage(weld::Container *pPage, weld::DialogController *pController, const SfxItemSet &rSet)
Definition: optpath.cxx:181
SfxApplication * SfxGetpApp()
OUString PathToFileName() const
Reference< css::util::XPathSettings > m_xPathSettings
Definition: optpath.cxx:69
std::unique_ptr< weld::TreeView > m_xPathBox
Definition: optpath.hxx:43
std::unique_ptr< weld::Button > m_xStandardBtn
Definition: optpath.hxx:41
IMPL_LINK_NOARG(SvxPathTabPage, PathSelect_Impl, weld::TreeView &, void)
Definition: optpath.cxx:323
IMPL_LINK(SvxPathTabPage, DialogClosedHdl, DialogClosedEvent *, pEvt, void)
Definition: optpath.cxx:581
#define POSTFIX_WRITABLE
Definition: optpath.cxx:59
static std::shared_ptr< ConfigurationChanges > create(css::uno::Reference< css::uno::XComponentContext > const &context=comphelper::getProcessComponentContext())
#define MULTIPATH_DELIMITER
Definition: optpath.cxx:135
UNKNOWN
#define DBG_UNHANDLED_EXCEPTION(...)
OUString getFSysPath(FSysStyle eStyle, sal_Unicode *pDelimiter=nullptr) const
#define TOOLS_WARN_EXCEPTION(area, stream)
void ResetLastDir()
virtual ~SvxPathTabPage() override
Definition: optpath.cxx:202
#define IODLG_CONFIGNAME
Definition: optpath.cxx:61
PathUserData_Impl(sal_uInt16 nId)
Definition: optpath.cxx:85
int i
OUString m_sMultiPathDlg
Definition: optpath.cxx:68
void GetPathList(sal_uInt16 _nPathHandle, OUString &_rInternalPath, OUString &_rUserPath, OUString &_rWritablePath, bool &_rReadOnly)
Definition: optpath.cxx:591
bool removeFinalSlash()
#define POSTFIX_USER
Definition: optpath.cxx:58
OUString CuiResId(const char *pKey)
Definition: cuiresmgr.cxx:23
OUString GetMainURL(DecodeMechanism eMechanism, rtl_TextEncoding eCharset=RTL_TEXTENCODING_UTF8) const
virtual void Reset(const SfxItemSet *rSet) override
Definition: optpath.cxx:226
SfxItemState
const char * m_pCfgName
Definition: optpath.cxx:96
rtl::Reference< ::svt::DialogClosedListener > xDialogListener
Definition: optpath.hxx:38
virtual void SetPath(const OUString &rPath)=0
const o3tl::enumarray< SvxAdjust, unsigned short > aSvxToUnoAdjust USHRT_MAX
INetProtocol GetProtocol() const
RET_OK
void ChangeCurrentEntry(const OUString &_rFolder)
Definition: optpath.cxx:401
void SetPathList(sal_uInt16 _nPathHandle, const OUString &_rUserPath, const OUString &_rWritablePath)
Definition: optpath.cxx:656
Reference< XComponentContext > getProcessComponentContext()
static Handle2CfgNameMapping_Impl const Hdl2CfgMap_Impl[]
Definition: optpath.cxx:99
#define POSTFIX_INTERNAL
Definition: optpath.cxx:57
#define SAL_WARN(area, stream)
SvtDefaultOptions m_aDefOpt
Definition: optpath.cxx:67
sal_Int32 getTokenCount(const OString &rIn, sal_Char cTok)
static bool IsMultiPath_Impl(const sal_uInt16 nIndex)
Definition: optpath.cxx:160
sal_Int32 nPos
static OUString getCfgName_Impl(sal_uInt16 _nHandle)
Definition: optpath.cxx:117
static std::unique_ptr< SfxTabPage > Create(weld::Container *pPage, weld::DialogController *pController, const SfxItemSet *rSet)
Definition: optpath.cxx:208
weld::Window * GetFrameWeld(const SfxFrame *pFrame)
aStr
std::unique_ptr< OptPath_Impl > pImpl
Definition: optpath.hxx:36
std::unique_ptr< weld::Button > m_xPathBtn
Definition: optpath.hxx:42
SfxItemState eState
Definition: optpath.cxx:80
OUString sId