LibreOffice Module cui (master)  1
SvxToolbarConfigPage.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 <sal/config.h>
21 #include <sal/log.hxx>
22 
23 #include <vcl/event.hxx>
24 #include <vcl/weld.hxx>
25 #include <vcl/svapp.hxx>
26 
27 #include <sfx2/sfxsids.hrc>
28 #include <svl/stritem.hxx>
29 #include <tools/diagnose_ex.h>
30 
31 #include <algorithm>
32 #include <helpids.h>
33 #include <strings.hrc>
34 
35 #include <cfg.hxx>
36 #include <SvxToolbarConfigPage.hxx>
37 #include <SvxConfigPageHelper.hxx>
38 #include <dialmgr.hxx>
39 
41 #include <com/sun/star/ui/ImageType.hpp>
42 
43 #include <dlgname.hxx>
44 
46  : SvxConfigPage(pPage, pController, rSet)
47 {
48  m_xGearBtn = m_xBuilder->weld_menu_button("toolbargearbtn");
49  m_xGearBtn->show();
51 
52  m_xContentsListBox.reset(new SvxToolbarEntriesListBox(m_xBuilder->weld_tree_view("toolcontents"), this));
54 
55  std::vector<int> aWidths;
56  weld::TreeView& rTreeView = m_xContentsListBox->get_widget();
57  Size aSize(m_xFunctions->get_size_request());
58  rTreeView.set_size_request(aSize.Width(), aSize.Height());
59 
60  int nExpectedSize = 16;
61 
62  int nStandardImageColWidth = rTreeView.get_checkbox_column_width();
63  int nMargin = nStandardImageColWidth - nExpectedSize;
64  if (nMargin < 16)
65  nMargin = 16;
66 
67  if (SvxConfigPageHelper::GetImageType() & css::ui::ImageType::SIZE_LARGE)
68  nExpectedSize = 24;
69  else if (SvxConfigPageHelper::GetImageType() & css::ui::ImageType::SIZE_32)
70  nExpectedSize = 32;
71 
72  int nImageColWidth = nExpectedSize + nMargin;
73 
74  aWidths.push_back(nStandardImageColWidth);
75  aWidths.push_back(nImageColWidth);
76  rTreeView.set_column_fixed_widths(aWidths);
77 
78  rTreeView.set_hexpand(true);
79  rTreeView.set_vexpand(true);
81  rTreeView.show();
82 
83  rTreeView.connect_changed(
84  LINK( this, SvxToolbarConfigPage, SelectToolbarEntry ) );
85 
87  m_xSaveInListBox->set_help_id( HID_SVX_SAVE_IN );
90  m_xDescriptionField->set_help_id ( HID_SVX_DESCFIELD );
91 
92  m_xCommandCategoryListBox->connect_changed(
93  LINK( this, SvxToolbarConfigPage, SelectCategory ) );
94 
95  m_xGearBtn->connect_selected(
96  LINK( this, SvxToolbarConfigPage, GearHdl ) );
97 
98  m_xMoveUpButton->connect_clicked( LINK( this, SvxToolbarConfigPage, MoveHdl) );
99  m_xMoveDownButton->connect_clicked( LINK( this, SvxToolbarConfigPage, MoveHdl) );
100  // Always enable Up and Down buttons
101  // added for issue i53677 by shizhoubo
102  m_xMoveDownButton->set_sensitive(true);
103  m_xMoveUpButton->set_sensitive(true);
104 
105  m_xAddCommandButton->connect_clicked( LINK( this, SvxToolbarConfigPage, AddCommandHdl ) );
106  m_xRemoveCommandButton->connect_clicked( LINK( this, SvxToolbarConfigPage, RemoveCommandHdl ) );
107 
108  m_xInsertBtn->connect_selected(
109  LINK( this, SvxToolbarConfigPage, InsertHdl ) );
110  m_xModifyBtn->connect_selected(
111  LINK( this, SvxToolbarConfigPage, ModifyItemHdl ) );
112  m_xResetBtn->connect_clicked(
113  LINK( this, SvxToolbarConfigPage, ResetToolbarHdl ) );
114 
115  // "Insert Submenu" is irrelevant to the toolbars
116  m_xInsertBtn->remove_item("insertsubmenu");
117 
118  // Gear menu's "Move" action is irrelevant to the toolbars
119  m_xGearBtn->set_item_sensitive("toolbar_gear_move", false);
120 
121  // default toolbar to select is standardbar unless a different one
122  // has been passed in
124  m_aURLToSelect += "standardbar";
125 
126  const SfxPoolItem* pItem =
127  rSet.GetItem( rSet.GetPool()->GetWhich( SID_CONFIG ) );
128 
129  if ( pItem )
130  {
131  OUString text = static_cast<const SfxStringItem*>(pItem)->GetValue();
132  if (text.startsWith( ITEM_TOOLBAR_URL ))
133  {
134  m_aURLToSelect = text.copy( 0 );
135  }
136  }
137 }
138 
140 {
141  // regenerate with the current ordering within the list
142  SvxEntries* pEntries = GetTopLevelSelection()->GetEntries();
143  pEntries->clear();
144 
145  for (int i = 0; i < m_xContentsListBox->n_children(); ++i)
146  pEntries->push_back(reinterpret_cast<SvxConfigEntry*>(m_xContentsListBox->get_id(i).toInt64()));
147 
150 
151  SvxConfigEntry* pToolbar = GetTopLevelSelection();
152  if ( pToolbar )
153  static_cast<ToolbarSaveInData*>(GetSaveInData())->ApplyToolbar( pToolbar );
154 }
155 
157 {
158  for (int i = 0, nCount = m_xSaveInListBox->get_count(); i < nCount; ++i)
159  {
161  reinterpret_cast<ToolbarSaveInData*>(m_xSaveInListBox->get_id(i).toInt64());
162  delete pData;
163  }
164  m_xSaveInListBox->clear();
165 }
166 
168 {
169  const sal_Int32 nSelectionPos = m_xTopLevelListBox->get_active();
170  ToolbarSaveInData* pSaveInData = static_cast<ToolbarSaveInData*>( GetSaveInData() );
171  pSaveInData->RemoveToolbar( GetTopLevelSelection() );
172 
173  int nCount = m_xTopLevelListBox->get_count();
174  if (nCount > 1)
175  {
176  // select next entry after the one being deleted
177  // selection position is indexed from 0 so need to
178  // subtract one from the entry count
179  if (nSelectionPos != nCount - 1)
180  {
181  m_xTopLevelListBox->set_active(nSelectionPos + 1);
182  }
183  else
184  {
185  m_xTopLevelListBox->set_active(nSelectionPos - 1);
186  }
187  SelectElement();
188 
189  // and now remove the entry
190  m_xTopLevelListBox->remove(nSelectionPos);
191  }
192  else
193  {
195  }
196 }
197 
199 {
200  int nActEntry = m_xContentsListBox->get_selected_index();
201 
202  if (nActEntry != -1)
203  {
204  // get currently selected entry
205  SvxConfigEntry* pEntry =
206  reinterpret_cast<SvxConfigEntry*>(m_xContentsListBox->get_id(nActEntry).toInt64());
207 
208  SvxConfigEntry* pToolbar = GetTopLevelSelection();
209 
210  // remove entry from the list for this toolbar
211  SvxConfigPageHelper::RemoveEntry( pToolbar->GetEntries(), pEntry );
212 
213  // remove toolbar entry from UI
214  m_xContentsListBox->remove(nActEntry);
215 
216  // delete data for toolbar entry
217  delete pEntry;
218 
219  static_cast<ToolbarSaveInData*>(GetSaveInData())->ApplyToolbar( pToolbar );
221 
222  // if this is the last entry in the toolbar and it is a user
223  // defined toolbar pop up a dialog asking the user if they
224  // want to delete the toolbar
225  if ( m_xContentsListBox->n_children() == 0 &&
227  {
228  std::unique_ptr<weld::MessageDialog> xQueryBox(Application::CreateMessageDialog(GetFrameWeld(),
229  VclMessageType::Question, VclButtonsType::YesNo,
230  CuiResId(RID_SXVSTR_CONFIRM_DELETE_TOOLBAR)));
231  if (xQueryBox->run() == RET_YES)
232  {
234  }
235  }
236  }
237 }
238 
239 IMPL_LINK( SvxToolbarConfigPage, MoveHdl, weld::Button&, rButton, void )
240 {
241  MoveEntry(&rButton == m_xMoveUpButton.get());
242 }
243 
245 {
246  SvxConfigPage::MoveEntry( bMoveUp );
247 
248  // Apply change to currently selected toolbar
249  SvxConfigEntry* pToolbar = GetTopLevelSelection();
250  if ( pToolbar )
251  static_cast<ToolbarSaveInData*>(GetSaveInData())->ApplyToolbar( pToolbar );
252  else
253  {
254  SAL_WARN( "cui.customize", "SvxToolbarConfigPage::MoveEntry(): no entry" );
256  }
257 }
258 
260 {
261  // ensure that the UI is cleared before populating it
262  m_xTopLevelListBox->clear();
263  m_xContentsListBox->clear();
264 
266 
267  sal_Int32 nPos = 0;
268  if ( !m_aURLToSelect.isEmpty() )
269  {
270  for (sal_Int32 i = 0, nCount = m_xTopLevelListBox->get_count(); i < nCount; ++i)
271  {
273  reinterpret_cast<SvxConfigEntry*>(m_xTopLevelListBox->get_id(i).toInt64());
274 
275  if ( pData->GetCommand().equals( m_aURLToSelect ) )
276  {
277  nPos = i;
278  break;
279  }
280  }
281 
282  // in future select the default toolbar: Standard
284  m_aURLToSelect += "standardbar";
285  }
286 
287  m_xTopLevelListBox->set_active(nPos);
288  SelectElement();
289 
293  m_xCommandCategoryListBox->categorySelected(m_xFunctions.get(), OUString(), GetSaveInData());
294 }
295 
297  const css::uno::Reference< css::ui::XUIConfigurationManager >& xCfgMgr,
298  const css::uno::Reference< css::ui::XUIConfigurationManager >& xParentCfgMgr,
299  const OUString& aModuleId,
300  bool bDocConfig )
301 {
302  return static_cast< SaveInData* >(
303  new ToolbarSaveInData( xCfgMgr, xParentCfgMgr, aModuleId, bDocConfig ));
304 }
305 
307 {
308  UpdateButtonStates();
309 }
310 
311 IMPL_LINK( SvxToolbarConfigPage, GearHdl, const OString&, rIdent, void )
312 {
313  SvxConfigEntry* pCurrentToolbar = GetTopLevelSelection();
314 
315  if (rIdent == "toolbar_gear_add")
316  {
317  OUString prefix = CuiResId( RID_SVXSTR_NEW_TOOLBAR );
318 
319  OUString aNewName =
320  SvxConfigPageHelper::generateCustomName( prefix, GetSaveInData()->GetEntries() );
321 
322  OUString aNewURL =
323  SvxConfigPageHelper::generateCustomURL( GetSaveInData()->GetEntries() );
324 
325  SvxNewToolbarDialog aNameDialog(GetFrameWeld(), aNewName);
326 
327  // Reflect the actual m_xSaveInListBox into the new toolbar dialog
328  for (int i = 0, nCount = m_xSaveInListBox->get_count(); i < nCount; ++i)
329  aNameDialog.m_xSaveInListBox->append_text(m_xSaveInListBox->get_text(i));
330 
331  aNameDialog.m_xSaveInListBox->set_active(m_xSaveInListBox->get_active());
332 
333  if (aNameDialog.run() == RET_OK)
334  {
335  aNewName = aNameDialog.GetName();
336 
337  // Where to save the new toolbar? (i.e. Modulewise or documentwise)
338  int nInsertPos = aNameDialog.m_xSaveInListBox->get_active();
339 
341  reinterpret_cast<ToolbarSaveInData*>(
342  m_xSaveInListBox->get_id(nInsertPos).toInt64() );
343 
344  if ( GetSaveInData() != pData )
345  {
346  m_xSaveInListBox->set_active(nInsertPos);
347  SelectSaveInLocation(*m_xSaveInListBox);
348  }
349 
350  SvxConfigEntry* pToolbar =
351  new SvxConfigEntry( aNewName, aNewURL, true, false );
352 
353  pToolbar->SetUserDefined();
354  pToolbar->SetMain();
355 
356  pData->CreateToolbar( pToolbar );
357 
358  OUString sId(OUString::number(reinterpret_cast<sal_Int64>(pToolbar)));
359  m_xTopLevelListBox->append(sId, pToolbar->GetName());
360  m_xTopLevelListBox->set_active_id(sId);
361  SelectElement();
362 
363  pData->SetModified();
364  }
365  }
366  else if (rIdent == "toolbar_gear_delete")
367  {
368  if ( pCurrentToolbar && pCurrentToolbar->IsDeletable() )
369  {
370  DeleteSelectedTopLevel();
371  UpdateButtonStates();
372  }
373  }
374  else if (rIdent == "toolbar_gear_rename")
375  {
376  sal_Int32 nSelectionPos = m_xTopLevelListBox->get_active();
377  SvxConfigEntry* pToolbar =
378  reinterpret_cast<SvxConfigEntry*>(m_xTopLevelListBox->get_id(nSelectionPos).toInt64());
379  ToolbarSaveInData* pSaveInData = static_cast<ToolbarSaveInData*>( GetSaveInData() );
380 
381  //Rename the toolbar
382  OUString sCurrentName( SvxConfigPageHelper::stripHotKey( pToolbar->GetName() ) );
383  OUString sDesc = CuiResId( RID_SVXSTR_LABEL_NEW_NAME );
384 
385  SvxNameDialog aNameDialog(GetFrameWeld(), sCurrentName, sDesc);
387  aNameDialog.set_title(CuiResId(RID_SVXSTR_RENAME_TOOLBAR));
388 
389  if ( aNameDialog.run() == RET_OK )
390  {
391  OUString sNewName = aNameDialog.GetName();
392 
393  if (sCurrentName == sNewName)
394  return;
395 
396  pToolbar->SetName( sNewName );
397  pSaveInData->ApplyToolbar( pToolbar );
398 
399  // have to use remove and insert to change the name
400  m_xTopLevelListBox->remove(nSelectionPos);
401  OUString sId(OUString::number(reinterpret_cast<sal_Int64>(pToolbar)));
402  m_xTopLevelListBox->insert(nSelectionPos, sNewName, &sId, nullptr, nullptr);
403  m_xTopLevelListBox->set_active_id(sId);
404  }
405  }
406  else if (rIdent == "toolbar_gear_iconOnly" || rIdent == "toolbar_gear_textOnly" || rIdent == "toolbar_gear_iconAndText")
407  {
408  ToolbarSaveInData* pSaveInData = static_cast<ToolbarSaveInData*>( GetSaveInData() );
409 
410  if (pCurrentToolbar == nullptr || pSaveInData == nullptr)
411  {
412  SAL_WARN("cui.customize", "NULL toolbar or savein data");
413  return;
414  }
415 
416  sal_Int32 nStyle = 0;
417  if (rIdent == "toolbar_gear_iconOnly")
418  nStyle = 0;
419  else if (rIdent == "toolbar_gear_textOnly")
420  nStyle = 1;
421  else if (rIdent == "toolbar_gear_iconAndText")
422  nStyle = 2;
423 
424  pCurrentToolbar->SetStyle( nStyle );
425  pSaveInData->SetSystemStyle( m_xFrame, pCurrentToolbar->GetCommand(), nStyle );
426 
427  SelectElement();
428  }
429  else
430  {
431  //This block should never be reached
432  SAL_WARN("cui.customize", "Unknown gear menu option: " << rIdent);
433  return;
434  }
435 }
436 
438 {
439  OUString aSearchTerm(m_xSearchEdit->get_text());
440 
441  m_xCommandCategoryListBox->categorySelected(m_xFunctions.get(), aSearchTerm, GetSaveInData());
442 }
443 
445 {
446  AddFunction();
447 }
448 
450 {
451  DeleteSelectedContent();
452 }
453 
454 IMPL_LINK(SvxToolbarConfigPage, InsertHdl, const OString&, rIdent, void)
455 {
456  if (rIdent == "insertseparator")
457  {
458  // Get the currently selected toolbar
459  SvxConfigEntry* pToolbar = GetTopLevelSelection();
460 
461  SvxConfigEntry* pNewEntryData = new SvxConfigEntry;
462  pNewEntryData->SetUserDefined();
463 
464  int nPos = AppendEntry(pNewEntryData, -1);
465  InsertEntryIntoUI(pNewEntryData, m_xContentsListBox->get_widget(), nPos, 1);
466 
467  static_cast<ToolbarSaveInData*>( GetSaveInData())->ApplyToolbar( pToolbar );
468 
469  UpdateButtonStates();
470  }
471  else
472  {
473  //This block should never be reached
474  SAL_WARN("cui.customize", "Unknown insert option: " << rIdent);
475  return;
476  }
477 }
478 
479 IMPL_LINK(SvxToolbarConfigPage, ModifyItemHdl, const OString&, rIdent, void)
480 {
481  bool bNeedsApply = false;
482 
483  // get currently selected toolbar
484  SvxConfigEntry* pToolbar = GetTopLevelSelection();
485 
486  if (rIdent.isEmpty() || pToolbar == nullptr)
487  {
488  SAL_WARN("cui.customize", "No toolbar selected, or empty rIdent!");
489  return;
490  }
491 
492  if (rIdent == "renameItem")
493  {
494  int nActEntry = m_xContentsListBox->get_selected_index();
495  SvxConfigEntry* pEntry =
496  reinterpret_cast<SvxConfigEntry*>(m_xContentsListBox->get_id(nActEntry).toInt64());
497 
498  OUString aNewName( SvxConfigPageHelper::stripHotKey( pEntry->GetName() ) );
499  OUString aDesc = CuiResId( RID_SVXSTR_LABEL_NEW_NAME );
500 
501  SvxNameDialog aNameDialog(GetFrameWeld(), aNewName, aDesc);
503  aNameDialog.set_title(CuiResId(RID_SVXSTR_RENAME_TOOLBAR));
504 
505  if (aNameDialog.run() == RET_OK)
506  {
507  aNewName = aNameDialog.GetName();
508 
509  if( aNewName.isEmpty() ) // tdf#80758 - Accelerator character ("~") is passed as
510  pEntry->SetName( "~" ); // the button name in case of empty values.
511  else
512  pEntry->SetName( aNewName );
513 
514  m_xContentsListBox->set_text(nActEntry, aNewName, 2);
515  bNeedsApply = true;
516  }
517  }
518  else if (rIdent == "changeIcon")
519  {
520  int nActEntry = m_xContentsListBox->get_selected_index();
521  SvxConfigEntry* pEntry =
522  reinterpret_cast<SvxConfigEntry*>(m_xContentsListBox->get_id(nActEntry).toInt64());
523 
524  SvxIconSelectorDialog aIconDialog(GetFrameWeld(),
525  GetSaveInData()->GetImageManager(),
526  GetSaveInData()->GetParentImageManager());
527 
528  if (aIconDialog.run() == RET_OK)
529  {
530  css::uno::Reference< css::graphic::XGraphic > newgraphic =
531  aIconDialog.GetSelectedIcon();
532 
533  if ( newgraphic.is() )
534  {
535  css::uno::Sequence< css::uno::Reference< css::graphic::XGraphic > >
536  aGraphicSeq( 1 );
537 
538  css::uno::Sequence<OUString> aURLSeq { pEntry->GetCommand() };
539 
540  if ( !pEntry->GetBackupGraphic().is() )
541  {
542  css::uno::Reference< css::graphic::XGraphic > backup =
543  SvxConfigPageHelper::GetGraphic(GetSaveInData()->GetImageManager(),
544  aURLSeq[0]);
545 
546  if ( backup.is() )
547  {
548  pEntry->SetBackupGraphic(backup);
549  }
550  }
551 
552  aGraphicSeq[ 0 ] = newgraphic;
553  try
554  {
555  GetSaveInData()->GetImageManager()->replaceImages(
556  SvxConfigPageHelper::GetImageType(), aURLSeq, aGraphicSeq );
557 
558  m_xContentsListBox->remove(nActEntry);
559 
560  OUString sId(OUString::number(reinterpret_cast<sal_Int64>(pEntry)));
561  m_xContentsListBox->insert(nActEntry, sId);
562  m_xContentsListBox->set_toggle(nActEntry, pEntry->IsVisible() ? TRISTATE_TRUE : TRISTATE_FALSE, 0);
563  InsertEntryIntoUI(pEntry, m_xContentsListBox->get_widget(), nActEntry, 1);
564 
565  m_xContentsListBox->select(nActEntry);
566  m_xContentsListBox->scroll_to_row(nActEntry);
567 
568  GetSaveInData()->PersistChanges(
569  GetSaveInData()->GetImageManager() );
570  }
571  catch ( const css::uno::Exception&)
572  {
573  TOOLS_WARN_EXCEPTION("cui.customize", "Error replacing image");
574  }
575  }
576  }
577  }
578  else if (rIdent == "resetIcon")
579  {
580  int nActEntry = m_xContentsListBox->get_selected_index();
581  SvxConfigEntry* pEntry =
582  reinterpret_cast<SvxConfigEntry*>(m_xContentsListBox->get_id(nActEntry).toInt64());
583 
584  css::uno::Reference< css::graphic::XGraphic > backup =
585  pEntry->GetBackupGraphic();
586 
587  css::uno::Sequence< css::uno::Reference< css::graphic::XGraphic > >
588  aGraphicSeq( 1 );
589  aGraphicSeq[ 0 ] = backup;
590 
591  css::uno::Sequence<OUString> aURLSeq { pEntry->GetCommand() };
592 
593  try
594  {
595  GetSaveInData()->GetImageManager()->replaceImages(
596  SvxConfigPageHelper::GetImageType(), aURLSeq, aGraphicSeq );
597 
598  m_xContentsListBox->remove(nActEntry);
599 
600  OUString sId(OUString::number(reinterpret_cast<sal_Int64>(pEntry)));
601  m_xContentsListBox->insert(nActEntry, sId);
602  m_xContentsListBox->set_toggle(nActEntry, pEntry->IsVisible() ? TRISTATE_TRUE : TRISTATE_FALSE, 0);
603  InsertEntryIntoUI(pEntry, m_xContentsListBox->get_widget(), nActEntry, 1);
604 
605  m_xContentsListBox->select(nActEntry);
606  m_xContentsListBox->scroll_to_row(nActEntry);
607 
608  // reset backup in entry
609  pEntry->SetBackupGraphic(
610  css::uno::Reference< css::graphic::XGraphic >() );
611 
612  GetSaveInData()->PersistChanges(
613  GetSaveInData()->GetImageManager() );
614  }
615  catch ( const css::uno::Exception& )
616  {
617  TOOLS_WARN_EXCEPTION("cui.customize", "Error resetting image");
618  }
619  }
620  else if (rIdent == "restoreItem")
621  {
622  int nActEntry = m_xContentsListBox->get_selected_index();
623  SvxConfigEntry* pEntry =
624  reinterpret_cast<SvxConfigEntry*>(m_xContentsListBox->get_id(nActEntry).toInt64());
625 
626  ToolbarSaveInData* pSaveInData =
627  static_cast<ToolbarSaveInData*>( GetSaveInData() );
628 
629  OUString aSystemName =
630  pSaveInData->GetSystemUIName( pEntry->GetCommand() );
631 
632  if ( !pEntry->GetName().equals( aSystemName ) )
633  {
634  pEntry->SetName( aSystemName );
635  m_xContentsListBox->set_text(
636  nActEntry, SvxConfigPageHelper::stripHotKey(aSystemName), 2);
637  bNeedsApply = true;
638  }
639 
640  css::uno::Sequence<OUString> aURLSeq { pEntry->GetCommand() };
641 
642  try
643  {
644  GetSaveInData()->GetImageManager()->removeImages(
646 
647  // reset backup in entry
648  pEntry->SetBackupGraphic(
649  css::uno::Reference< css::graphic::XGraphic >() );
650 
651  GetSaveInData()->PersistChanges(
652  GetSaveInData()->GetImageManager() );
653 
654  m_xContentsListBox->remove(nActEntry);
655 
656  OUString sId(OUString::number(reinterpret_cast<sal_Int64>(pEntry)));
657  m_xContentsListBox->insert(nActEntry, sId);
658  m_xContentsListBox->set_toggle(nActEntry,
659  pEntry->IsVisible() ? TRISTATE_TRUE : TRISTATE_FALSE, 0);
660  InsertEntryIntoUI(pEntry, m_xContentsListBox->get_widget(), nActEntry, 1);
661 
662  m_xContentsListBox->select(nActEntry);
663  m_xContentsListBox->scroll_to_row(nActEntry);
664 
665  bNeedsApply = true;
666  }
667  catch ( const css::uno::Exception& )
668  {
669  TOOLS_WARN_EXCEPTION("cui.customize", "Error restoring image");
670  }
671  }
672  else
673  {
674  //This block should never be reached
675  SAL_WARN("cui.customize", "Unknown insert option: " << rIdent);
676  return;
677  }
678 
679  if ( bNeedsApply )
680  {
681  static_cast<ToolbarSaveInData*>( GetSaveInData())->ApplyToolbar( pToolbar );
682  UpdateButtonStates();
683  }
684 }
685 
687 {
688  sal_Int32 nSelectionPos = m_xTopLevelListBox->get_active();
689 
690  SvxConfigEntry* pToolbar =
691  reinterpret_cast<SvxConfigEntry*>(m_xTopLevelListBox->get_id(nSelectionPos).toInt64());
692 
693  std::unique_ptr<weld::MessageDialog> xQueryBox(Application::CreateMessageDialog(GetFrameWeld(),
694  VclMessageType::Question, VclButtonsType::YesNo,
695  CuiResId(RID_SVXSTR_CONFIRM_RESTORE_DEFAULT)));
696  if (xQueryBox->run() == RET_YES)
697  {
698  ToolbarSaveInData* pSaveInData =
699  static_cast<ToolbarSaveInData*>(GetSaveInData());
700 
701  pSaveInData->RestoreToolbar( pToolbar );
702 
703  SelectElement();
704  }
705 }
706 
708 {
709  SvxConfigEntry* pToolbar = GetTopLevelSelection();
710  int selection = m_xContentsListBox->get_selected_index();
711 
712  bool bIsSeparator =
713  selection != -1 && reinterpret_cast<SvxConfigEntry*>(m_xContentsListBox->get_id(selection).toInt64())->IsSeparator();
714  bool bIsValidSelection =
715  !(m_xContentsListBox->n_children() == 0 || selection == -1);
716 
717  m_xMoveUpButton->set_sensitive( bIsValidSelection );
718  m_xMoveDownButton->set_sensitive( bIsValidSelection );
719 
720  m_xRemoveCommandButton->set_sensitive( bIsValidSelection );
721 
722  m_xModifyBtn->set_sensitive( bIsValidSelection && !bIsSeparator );
723 
724  // Handle the gear button
725  // "toolbar_gear_add" option is always enabled
726  m_xGearBtn->set_item_sensitive("toolbar_gear_delete", pToolbar && pToolbar->IsDeletable());
727  m_xGearBtn->set_item_sensitive("toolbar_gear_rename", pToolbar && pToolbar->IsRenamable());
728 }
729 
731 {
732  OUString msg = CuiResId( RID_SVXSTR_CONFIRM_TOOLBAR_RESET );
733 
734  OUString saveInName = m_xSaveInListBox->get_active_text();
735 
736  OUString label = SvxConfigPageHelper::replaceSaveInName( msg, saveInName );
737 
738  std::unique_ptr<weld::MessageDialog> xQueryBox(Application::CreateMessageDialog(GetFrameWeld(),
739  VclMessageType::Question, VclButtonsType::YesNo,
740  label));
741  return xQueryBox->run();
742 }
743 
745 {
746  m_xContentsListBox->clear();
747 
748  SvxConfigEntry* pToolbar = GetTopLevelSelection();
749  if ( pToolbar == nullptr )
750  {
751  //TODO: Disable related buttons
752  m_xInsertBtn->set_sensitive( false );
753  m_xResetBtn->set_sensitive( false );
754  m_xGearBtn->set_sensitive( false );
755 
756  return;
757  }
758  else
759  {
760  m_xInsertBtn->set_sensitive(true);
761  m_xResetBtn->set_sensitive(true);
762  m_xGearBtn->set_sensitive(true);
763  }
764 
765  switch (pToolbar->GetStyle())
766  {
767  case 0:
768  {
769  m_xGearBtn->set_item_active("toolbar_gear_iconOnly", true);
770  break;
771  }
772  case 1:
773  {
774  m_xGearBtn->set_item_active("toolbar_gear_textOnly", true);
775  break;
776  }
777  case 2:
778  {
779  m_xGearBtn->set_item_active("toolbar_gear_iconAndText", true);
780  break;
781  }
782  }
783 
784  int i = 0;
785  SvxEntries* pEntries = pToolbar->GetEntries();
786  for (auto const& entry : *pEntries)
787  {
788  OUString sId(OUString::number(reinterpret_cast<sal_Int64>(entry)));
789  m_xContentsListBox->insert(i, sId);
790  if (entry->IsBinding() && !entry->IsSeparator())
791  m_xContentsListBox->set_toggle(i, entry->IsVisible() ? TRISTATE_TRUE : TRISTATE_FALSE, 0);
792  InsertEntryIntoUI(entry, m_xContentsListBox->get_widget(), i, 1);
793  ++i;
794  }
795 
797 }
798 
800 {
801  SvxConfigEntry* pToolbar = GetTopLevelSelection();
802 
803  if (pToolbar == nullptr)
804  return;
805 
806  // Add the command to the contents listbox of the selected toolbar
807  int nNewLBEntry =
808  SvxConfigPage::AddFunction(nTarget, true/*bAllowDuplicates*/);
809 
810  if (nNewLBEntry == -1)
811  return;
812 
813  SvxConfigEntry* pEntry = reinterpret_cast<SvxConfigEntry*>(m_xContentsListBox->get_id(nNewLBEntry).toInt64());
814 
815  if ( pEntry->IsBinding() ) //TODO sep ?
816  {
817  pEntry->SetVisible(true);
818  m_xContentsListBox->set_toggle(nNewLBEntry, TRISTATE_TRUE, 0);
819  }
820 
821  InsertEntryIntoUI(pEntry, m_xContentsListBox->get_widget(), nNewLBEntry, 1);
822 
823  // Changes are not visible on the toolbar until this point
824  // TODO: Figure out a way to show the changes on the toolbar, but revert if
825  // the dialog is closed by pressing "Cancel"
826  // get currently selected toolbar and apply change
827  if ( pToolbar != nullptr )
828  {
829  static_cast<ToolbarSaveInData*>( GetSaveInData() )->ApplyToolbar( pToolbar );
830  }
831 }
832 
833 SvxToolbarEntriesListBox::SvxToolbarEntriesListBox(std::unique_ptr<weld::TreeView> xParent, SvxToolbarConfigPage* pPg)
834  : SvxMenuEntriesListBox(std::move(xParent), pPg)
835 {
836  m_xControl->connect_toggled(LINK(this, SvxToolbarEntriesListBox, CheckButtonHdl));
837  m_xControl->connect_key_press(Link<const KeyEvent&, bool>()); //acknowledge we first remove the old one
838  m_xControl->connect_key_press(LINK(this, SvxToolbarEntriesListBox, KeyInputHdl)); // then add the new one
839 }
840 
842 {
843 }
844 
846 {
847  SvxConfigEntry* pEntryData =
848  reinterpret_cast<SvxConfigEntry*>(m_xControl->get_id(nRow).toInt64());
849 
850  if (pEntryData->IsBinding())
851  {
852  pEntryData->SetVisible(m_xControl->get_toggle(nRow, 0) == TRISTATE_TRUE);
853 
855 
856  ToolbarSaveInData* pToolbarSaveInData = static_cast<ToolbarSaveInData*>(
857  m_pPage->GetSaveInData() );
858 
859  pToolbarSaveInData->ApplyToolbar( pToolbar );
860  }
861 }
862 
863 IMPL_LINK(SvxToolbarEntriesListBox, CheckButtonHdl, const row_col&, rRowCol, void)
864 {
865  ChangedVisibility(rRowCol.first);
866 }
867 
868 IMPL_LINK(SvxToolbarEntriesListBox, KeyInputHdl, const KeyEvent&, rKeyEvent, bool)
869 {
870  // space key will change visibility of toolbar items
871  if ( rKeyEvent.GetKeyCode() == KEY_SPACE )
872  {
873  int nRow = m_xControl->get_selected_index();
874  SvxConfigEntry* pEntryData = reinterpret_cast<SvxConfigEntry*>(m_xControl->get_id(nRow).toInt64());
875  if (pEntryData->IsBinding() && !pEntryData->IsSeparator())
876  {
877  m_xControl->set_toggle(nRow, m_xControl->get_toggle(nRow, 0) == TRISTATE_TRUE ? TRISTATE_FALSE : TRISTATE_TRUE, 0);
878  ChangedVisibility(nRow);
879  }
880  return true;
881  }
882  return SvxMenuEntriesListBox::KeyInputHdl(rKeyEvent);
883 }
884 
885 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
void RemoveToolbar(SvxConfigEntry *pToolbar)
Definition: cfg.cxx:2448
std::unique_ptr< CuiConfigFunctionListBox > m_xFunctions
Definition: cfg.hxx:392
SvxEntries * GetEntries() const
Definition: cfg.hxx:289
std::unique_ptr< weld::Button > m_xResetBtn
Definition: cfg.hxx:419
void AddFunction(int nTarget=-1)
void set_title(const OUString &rTitle)
const OUString & GetName() const
Definition: cfg.hxx:277
static OUString generateCustomURL(SvxEntries *entries)
Generates a custom resource URL for a new toolbar.
std::unique_ptr< weld::MenuButton > m_xModifyBtn
Definition: cfg.hxx:417
bool IsVisible() const
Definition: cfg.hxx:306
std::unique_ptr< CommandCategoryListBox > m_xCommandCategoryListBox
Definition: cfg.hxx:391
OUString m_aURLToSelect
the ResourceURL to select when opening the dialog
Definition: cfg.hxx:384
virtual ~SvxToolbarConfigPage() override
static OUString stripHotKey(const OUString &str)
std::unique_ptr< ContentProperties > pData
std::string GetValue
Reference< XControl > m_xControl
void SetModified(bool bValue=true)
Definition: cfg.hxx:298
std::unique_ptr< SvxConfigPageFunctionDropTarget > m_xDropTargetHelper
Definition: cfg.hxx:409
OUString GetSystemUIName(const OUString &rResourceURL)
Definition: cfg.cxx:2031
css::uno::Reference< css::frame::XFrame > m_xFrame
Definition: cfg.hxx:386
SvxConfigEntry * GetTopLevelSelection()
Definition: cfg.hxx:498
static sal_Int16 GetImageType()
std::unique_ptr< weld::Button > m_xRemoveCommandButton
Definition: cfg.hxx:423
css::uno::Reference< css::lang::XComponent > m_xFrame
void SetBackupGraphic(css::uno::Reference< css::graphic::XGraphic > const &graphic)
Definition: cfg.hxx:308
virtual void MoveEntry(bool bMoveUp)
Definition: cfg.cxx:1619
constexpr sal_uInt16 KEY_SPACE
OUString GetName() const
Definition: dlgname.hxx:40
std::unique_ptr< SvxMenuEntriesListBox > m_xContentsListBox
Definition: cfg.hxx:408
TRISTATE_TRUE
void ReloadTopLevelListBox(SvxConfigEntry const *pSelection=nullptr)
Definition: cfg.cxx:1319
Dialog for editing a name.
Definition: dlgname.hxx:25
static css::uno::Reference< css::graphic::XGraphic > GetGraphic(const css::uno::Reference< css::ui::XImageManager > &xImageManager, const OUString &rCommandURL)
#define HID_SVX_CONFIG_TOOLBAR_CONTENTS
Definition: helpids.h:28
std::vector< SvxConfigEntry * > SvxEntries
Definition: cfg.hxx:61
std::unique_ptr< weld::ComboBox > m_xTopLevelListBox
Definition: cfg.hxx:405
bool IsRenamable() const
Definition: cfg.cxx:1877
const OUString & GetCommand() const
Definition: cfg.hxx:275
void DeleteSelectedContent() override
#define HID_SVX_CONFIG_RENAME_TOOLBAR
Definition: helpids.h:35
void connect_changed(const Link< TreeView &, void > &rLink)
Reference< XNameAccess > m_xContainer
RET_YES
virtual void show()=0
bool IsBinding() const
Definition: cfg.hxx:286
OUString GetName() const
Definition: cfg.hxx:610
std::unique_ptr< weld::TreeView > m_xControl
Definition: cfg.hxx:321
int nCount
static void RemoveEntry(SvxEntries *pEntries, SvxConfigEntry const *pChildEntry)
virtual void set_column_fixed_widths(const std::vector< int > &rWidths)=0
void SetName(const OUString &rStr)
Definition: cfg.hxx:278
void SetMain()
Definition: cfg.hxx:292
virtual void set_help_id(const OString &rName)=0
virtual void set_vexpand(bool bExpand)=0
SaveInData * CreateSaveInData(const css::uno::Reference< css::ui::XUIConfigurationManager > &, const css::uno::Reference< css::ui::XUIConfigurationManager > &, const OUString &aModuleId, bool docConfig) override
static OUString generateCustomName(const OUString &prefix, SvxEntries *entries, sal_Int32 suffix=1)
static OUString replaceSaveInName(const OUString &rMessage, const OUString &rSaveInName)
virtual void SelectElement() override
IMPL_LINK(SvxToolbarConfigPage, MoveHdl, weld::Button &, rButton, void)
const css::uno::Reference< css::graphic::XGraphic > & GetBackupGraphic() const
Definition: cfg.hxx:311
#define TOOLS_WARN_EXCEPTION(area, stream)
void SetSystemStyle(const OUString &rResourceURL, sal_Int32 nStyle)
Definition: cfg.cxx:1992
void SetUserDefined(bool bOn=true)
Definition: cfg.hxx:283
#define HID_SVX_CONFIG_RENAME_TOOLBAR_ITEM
Definition: helpids.h:36
#define HID_SVX_TOPLEVELLISTBOX
Definition: helpids.h:40
int i
virtual void ListModified() override
TRISTATE_FALSE
std::unique_ptr< weld::ComboBox > m_xSaveInListBox
Definition: cfg.hxx:605
void SetVisible(bool b)
Definition: cfg.hxx:305
void SetStyle(sal_Int32 style)
Definition: cfg.hxx:315
virtual void set_hexpand(bool bExpand)=0
static const char ITEM_TOOLBAR_URL[]
Definition: cfg.hxx:54
void set_help_id(const OString &rHelpId)
SfxItemPool * GetPool() const
#define HID_SVX_CONFIG_TOOLBAR
Definition: helpids.h:27
OUString CuiResId(const char *pKey)
Definition: cuiresmgr.cxx:23
std::unique_ptr< weld::MenuButton > m_xInsertBtn
Definition: cfg.hxx:416
int get_checkbox_column_width() const
sal_Int32 GetStyle() const
Definition: cfg.hxx:314
void RestoreToolbar(SvxConfigEntry *pToolbar)
Definition: cfg.cxx:2471
weld::Window * GetFrameWeld() const
void UpdateButtonStates() override
sal_uInt16 GetWhich(sal_uInt16 nSlot, bool bDeep=true) const
void SetModified(bool bValue=true)
Definition: cfg.hxx:125
int AddFunction(int nTarget, bool bAllowDuplicates)
Definition: cfg.cxx:1394
RET_OK
bool IsDeletable() const
Definition: cfg.cxx:1872
IMPL_LINK_NOARG(SvxToolbarConfigPage, SelectToolbarEntry, weld::TreeView &, void)
SvxToolbarConfigPage(weld::Container *pPage, weld::DialogController *pController, const SfxItemSet &rItemSet)
virtual short run()
Reference< XComponentContext > getProcessComponentContext()
void CreateToolbar(SvxConfigEntry *pToolbar)
Definition: cfg.cxx:2421
#define HID_SVX_SAVE_IN
Definition: helpids.h:39
virtual ~SvxToolbarEntriesListBox() override
void InsertEntryIntoUI(SvxConfigEntry *pNewEntryData, weld::TreeView &rTreeView, int nPos, int nStartCol)
Definition: cfg.cxx:1536
static weld::MessageDialog * CreateMessageDialog(weld::Widget *pParent, VclMessageType eMessageType, VclButtonsType eButtonType, const OUString &rPrimaryMessage)
std::unique_ptr< weld::ComboBox > m_xSaveInListBox
Definition: cfg.hxx:414
void ApplyToolbar(css::uno::Reference< css::container::XIndexContainer > const &rNewToolbarBar, css::uno::Reference< css::lang::XSingleComponentFactory > &rFactory, SvxConfigEntry const *pToolbar)
SvxConfigPage * m_pPage
Definition: cfg.hxx:323
def text(shape, st)
OUString sId
std::unique_ptr< weld::TextView > m_xDescriptionField
Definition: cfg.hxx:396
std::unique_ptr< weld::Button > m_xMoveDownButton
Definition: cfg.hxx:412
#define SAL_WARN(area, stream)
#define HID_SVX_DOWN_TOOLBAR_ITEM
Definition: helpids.h:38
css::uno::Reference< css::graphic::XGraphic > GetSelectedIcon()
Definition: cfg.cxx:2791
void DeleteSelectedTopLevel() override
bool IsSeparator() const
Definition: cfg.hxx:287
std::unique_ptr< weld::Button > m_xMoveUpButton
Definition: cfg.hxx:411
def label(st)
OUString m_aModuleId
Definition: cfg.hxx:387
#define HID_SVX_DESCFIELD
Definition: helpids.h:41
std::unique_ptr< weld::MenuButton > m_xGearBtn
Definition: cfg.hxx:407
virtual void set_size_request(int nWidth, int nHeight)=0
const SfxPoolItem * GetItem(sal_uInt16 nWhich, bool bSearchInParent=true) const
void MoveEntry(bool bMoveUp) override
weld::Window * GetFrameWeld(const SfxFrame *pFrame)
SvxToolbarEntriesListBox(std::unique_ptr< weld::TreeView > xControl, SvxToolbarConfigPage *pPg)
SaveInData * GetSaveInData()
Definition: cfg.hxx:479
sal_uInt16 nPos
#define HID_SVX_UP_TOOLBAR_ITEM
Definition: helpids.h:37
std::unique_ptr< weld::Button > m_xAddCommandButton
Definition: cfg.hxx:422