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