LibreOffice Module vcl (master)  1
builder.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 
10 #include <config_feature_desktop.h>
11 #include <config_options.h>
12 
13 #include <memory>
14 #include <string_view>
15 #include <unordered_map>
16 #include <com/sun/star/accessibility/AccessibleRole.hpp>
17 
18 #include <comphelper/lok.hxx>
19 #include <i18nutil/unicode.hxx>
20 #include <jsdialog/enabled.hxx>
21 #include <o3tl/string_view.hxx>
22 #include <officecfg/Office/Common.hxx>
23 #include <osl/module.hxx>
24 #include <sal/log.hxx>
26 #include <unotools/resmgr.hxx>
27 #include <vcl/builder.hxx>
28 #include <vcl/dialoghelper.hxx>
29 #include <vcl/menu.hxx>
30 #include <vcl/toolkit/button.hxx>
31 #include <vcl/toolkit/dialog.hxx>
32 #include <vcl/toolkit/edit.hxx>
33 #include <vcl/toolkit/field.hxx>
34 #include <vcl/fieldvalues.hxx>
35 #include <vcl/toolkit/fmtfield.hxx>
36 #include <vcl/toolkit/fixed.hxx>
38 #include <vcl/headbar.hxx>
40 #include <vcl/toolkit/ivctrl.hxx>
41 #include <vcl/layout.hxx>
42 #include <vcl/toolkit/lstbox.hxx>
43 #include <vcl/toolkit/menubtn.hxx>
44 #include <vcl/mnemonic.hxx>
45 #include <vcl/toolkit/prgsbar.hxx>
46 #include <vcl/scrbar.hxx>
47 #include <vcl/split.hxx>
48 #include <vcl/svapp.hxx>
49 #include <vcl/toolkit/svtabbx.hxx>
50 #include <vcl/tabctrl.hxx>
51 #include <vcl/tabpage.hxx>
52 #include <vcl/toolkit/throbber.hxx>
53 #include <vcl/toolbox.hxx>
55 #include <vcl/toolkit/vclmedit.hxx>
56 #include <vcl/settings.hxx>
57 #include <slider.hxx>
58 #include <vcl/weld.hxx>
59 #include <vcl/weldutils.hxx>
61 #include <iconview.hxx>
62 #include <svdata.hxx>
63 #include <bitmaps.hlst>
64 #include <managedmenubutton.hxx>
65 #include <messagedialog.hxx>
66 #include <ContextVBox.hxx>
67 #include <DropdownBox.hxx>
68 #include <IPrioritable.hxx>
69 #include <OptionalBox.hxx>
70 #include <PriorityMergedHBox.hxx>
71 #include <PriorityHBox.hxx>
72 #include <window.h>
73 #include <xmlreader/xmlreader.hxx>
74 #include <desktop/crashreport.hxx>
75 #include <calendar.hxx>
76 #include <menutogglebutton.hxx>
77 #include <salinst.hxx>
78 #include <strings.hrc>
79 #include <treeglue.hxx>
80 #include <tools/diagnose_ex.h>
81 #include <verticaltabctrl.hxx>
82 #include <wizdlg.hxx>
83 #include <tools/svlibrary.h>
85 
86 #if defined(DISABLE_DYNLOADING) || defined(LINUX)
87 #include <dlfcn.h>
88 #endif
89 
90 static bool toBool(std::string_view rValue)
91 {
92  return (!rValue.empty() && (rValue[0] == 't' || rValue[0] == 'T' || rValue[0] == '1'));
93 }
94 
95 namespace
96 {
97  OUString mapStockToImageResource(std::u16string_view sType)
98  {
99  if (sType == u"view-refresh")
100  return SV_RESID_BITMAP_REFRESH;
101  else if (sType == u"dialog-error")
102  return IMG_ERROR;
103  else if (sType == u"list-add")
104  return IMG_ADD;
105  else if (sType == u"list-remove")
106  return IMG_REMOVE;
107  else if (sType == u"edit-copy")
108  return IMG_COPY;
109  else if (sType == u"edit-paste")
110  return IMG_PASTE;
111  else if (sType == u"document-open")
112  return IMG_OPEN;
113  else if (sType == u"open-menu-symbolic")
114  return IMG_MENU;
115  else if (sType == u"window-close-symbolic")
116  return SV_RESID_BITMAP_CLOSEDOC;
117  else if (sType == u"x-office-calendar")
118  return IMG_CALENDAR;
119  return OUString();
120  }
121 
122 }
123 
124 SymbolType VclBuilder::mapStockToSymbol(std::u16string_view sType)
125 {
127  if (sType == u"media-skip-forward")
128  eRet = SymbolType::NEXT;
129  else if (sType == u"media-skip-backward")
130  eRet = SymbolType::PREV;
131  else if (sType == u"media-playback-start")
132  eRet = SymbolType::PLAY;
133  else if (sType == u"media-playback-stop")
134  eRet = SymbolType::STOP;
135  else if (sType == u"go-first")
136  eRet = SymbolType::FIRST;
137  else if (sType == u"go-last")
138  eRet = SymbolType::LAST;
139  else if (sType == u"go-previous")
140  eRet = SymbolType::ARROW_LEFT;
141  else if (sType == u"go-next")
143  else if (sType == u"go-up")
144  eRet = SymbolType::ARROW_UP;
145  else if (sType == u"go-down")
146  eRet = SymbolType::ARROW_DOWN;
147  else if (sType == u"missing-image")
148  eRet = SymbolType::IMAGE;
149  else if (sType == u"help-browser" || sType == u"help-browser-symbolic")
150  eRet = SymbolType::HELP;
151  else if (sType == u"window-close")
152  eRet = SymbolType::CLOSE;
153  else if (sType == u"document-new")
154  eRet = SymbolType::PLUS;
155  else if (sType == u"pan-down-symbolic")
156  eRet = SymbolType::SPIN_DOWN;
157  else if (sType == u"pan-up-symbolic")
158  eRet = SymbolType::SPIN_UP;
159  else if (!mapStockToImageResource(sType).isEmpty())
160  eRet = SymbolType::IMAGE;
161  return eRet;
162 }
163 
164 namespace
165 {
166  void setupFromActionName(Button *pButton, VclBuilder::stringmap &rMap, const css::uno::Reference<css::frame::XFrame>& rFrame);
167 
168 #if defined SAL_LOG_WARN
169  bool isButtonType(WindowType nType)
170  {
171  return nType == WindowType::PUSHBUTTON ||
172  nType == WindowType::OKBUTTON ||
173  nType == WindowType::CANCELBUTTON ||
174  nType == WindowType::HELPBUTTON ||
175  nType == WindowType::IMAGEBUTTON ||
176  nType == WindowType::MENUBUTTON ||
177  nType == WindowType::MOREBUTTON ||
178  nType == WindowType::SPINBUTTON;
179  }
180 #endif
181 
182 }
183 
184 std::unique_ptr<weld::Builder> Application::CreateBuilder(weld::Widget* pParent, const OUString &rUIFile, bool bMobile, sal_uInt64 nLOKWindowId)
185 {
187  {
189  return JSInstanceBuilder::CreateSidebarBuilder(pParent, AllSettings::GetUIRootDir(), rUIFile, nLOKWindowId);
190  else if (jsdialog::isBuilderEnabledForPopup(rUIFile))
192  else if (jsdialog::isBuilderEnabled(rUIFile, bMobile))
194  }
195 
196  return ImplGetSVData()->mpDefInst->CreateBuilder(pParent, AllSettings::GetUIRootDir(), rUIFile);
197 }
198 
199 std::unique_ptr<weld::Builder> Application::CreateInterimBuilder(vcl::Window* pParent, const OUString &rUIFile, bool bAllowCycleFocusOut, sal_uInt64 nLOKWindowId)
200 {
202  {
203  // Notebookbar sub controls
205  return JSInstanceBuilder::CreateNotebookbarBuilder(pParent, AllSettings::GetUIRootDir(), rUIFile, css::uno::Reference<css::frame::XFrame>(), nLOKWindowId);
206  else if (rUIFile == u"modules/scalc/ui/inputbar.ui")
207  return JSInstanceBuilder::CreateFormulabarBuilder(pParent, AllSettings::GetUIRootDir(), rUIFile, nLOKWindowId);
208  }
209 
210  return ImplGetSVData()->mpDefInst->CreateInterimBuilder(pParent, AllSettings::GetUIRootDir(), rUIFile, bAllowCycleFocusOut, nLOKWindowId);
211 }
212 
214  VclButtonsType eButtonType, const OUString& rPrimaryMessage,
215  bool /*bMobile*/)
216 {
218  return JSInstanceBuilder::CreateMessageDialog(pParent, eMessageType, eButtonType, rPrimaryMessage);
219  else
220  return ImplGetSVData()->mpDefInst->CreateMessageDialog(pParent, eMessageType, eButtonType, rPrimaryMessage);
221 }
222 
223 weld::Window* Application::GetFrameWeld(const css::uno::Reference<css::awt::XWindow>& rWindow)
224 {
225  return ImplGetSVData()->mpDefInst->GetFrameWeld(rWindow);
226 }
227 
228 namespace weld
229 {
231  {
232  const FieldUnitStringList& rList = ImplGetFieldUnits();
233  // return unit's default string (ie, the first one )
234  auto it = std::find_if(
235  rList.begin(), rList.end(),
236  [&rUnit](const std::pair<OUString, FieldUnit>& rItem) { return rItem.second == rUnit; });
237  if (it != rList.end())
238  return it->first;
239 
240  return OUString();
241  }
242 
243  IMPL_LINK_NOARG(MetricSpinButton, spin_button_value_changed, SpinButton&, void)
244  {
245  signal_value_changed();
246  }
247 
248  IMPL_LINK(MetricSpinButton, spin_button_output, SpinButton&, rSpinButton, void)
249  {
250  OUString sNewText(format_number(rSpinButton.get_value()));
251  if (sNewText != rSpinButton.get_text())
252  rSpinButton.set_text(sNewText);
253  }
254 
256  {
257  sal_Int64 min, max;
258  m_xSpinButton->get_range(min, max);
259  auto width = std::max(m_xSpinButton->get_pixel_size(format_number(min)).Width(),
260  m_xSpinButton->get_pixel_size(format_number(max)).Width());
261  int chars = ceil(width / m_xSpinButton->get_approximate_digit_width());
262  m_xSpinButton->set_width_chars(chars);
263  }
264 
265  unsigned int SpinButton::Power10(unsigned int n)
266  {
267  unsigned int nValue = 1;
268  for (unsigned int i = 0; i < n; ++i)
269  nValue *= 10;
270  return nValue;
271  }
272 
273  sal_Int64 SpinButton::denormalize(sal_Int64 nValue) const
274  {
275  const int nFactor = Power10(get_digits());
276 
277  if ((nValue < (std::numeric_limits<sal_Int64>::min() + nFactor)) ||
278  (nValue > (std::numeric_limits<sal_Int64>::max() - nFactor)))
279  {
280  return nValue / nFactor;
281  }
282 
283  const int nHalf = nFactor / 2;
284 
285  if (nValue < 0)
286  return (nValue - nHalf) / nFactor;
287  return (nValue + nHalf) / nFactor;
288  }
289 
290  OUString MetricSpinButton::format_number(sal_Int64 nValue) const
291  {
292  OUString aStr;
293 
295 
296  unsigned int nDecimalDigits = m_xSpinButton->get_digits();
297  //pawn percent off to icu to decide whether percent is separated from its number for this locale
298  if (m_eSrcUnit == FieldUnit::PERCENT)
299  {
300  double fValue = nValue;
301  fValue /= SpinButton::Power10(nDecimalDigits);
302  aStr = unicode::formatPercent(fValue, rLocaleData.getLanguageTag());
303  }
304  else
305  {
306  aStr = rLocaleData.getNum(nValue, nDecimalDigits, true, true);
307  OUString aSuffix = MetricToString(m_eSrcUnit);
308  if (m_eSrcUnit != FieldUnit::NONE && m_eSrcUnit != FieldUnit::DEGREE && m_eSrcUnit != FieldUnit::INCH && m_eSrcUnit != FieldUnit::FOOT)
309  aStr += " ";
310  if (m_eSrcUnit == FieldUnit::INCH)
311  {
312  OUString sDoublePrime = u"\u2033";
313  if (aSuffix != "\"" && aSuffix != sDoublePrime)
314  aStr += " ";
315  else
316  aSuffix = sDoublePrime;
317  }
318  else if (m_eSrcUnit == FieldUnit::FOOT)
319  {
320  OUString sPrime = u"\u2032";
321  if (aSuffix != "'" && aSuffix != sPrime)
322  aStr += " ";
323  else
324  aSuffix = sPrime;
325  }
326 
327  assert(m_eSrcUnit != FieldUnit::PERCENT);
328  aStr += aSuffix;
329  }
330 
331  return aStr;
332  }
333 
334  void MetricSpinButton::set_digits(unsigned int digits)
335  {
336  int step, page;
337  get_increments(step, page, m_eSrcUnit);
338  sal_Int64 value = get_value(m_eSrcUnit);
339  m_xSpinButton->set_digits(digits);
340  set_increments(step, page, m_eSrcUnit);
341  set_value(value, m_eSrcUnit);
343  }
344 
346  {
347  if (eUnit != m_eSrcUnit)
348  {
349  int step, page;
350  get_increments(step, page, m_eSrcUnit);
351  sal_Int64 value = get_value(m_eSrcUnit);
352  m_eSrcUnit = eUnit;
353  set_increments(step, page, m_eSrcUnit);
354  set_value(value, m_eSrcUnit);
355  spin_button_output(*m_xSpinButton);
357  }
358  }
359 
360  sal_Int64 MetricSpinButton::ConvertValue(sal_Int64 nValue, FieldUnit eInUnit, FieldUnit eOutUnit) const
361  {
362  return vcl::ConvertValue(nValue, 0, m_xSpinButton->get_digits(), eInUnit, eOutUnit);
363  }
364 
365  IMPL_LINK(MetricSpinButton, spin_button_input, int*, result, bool)
366  {
368  double fResult(0.0);
369  bool bRet = vcl::TextToValue(get_text(), fResult, 0, m_xSpinButton->get_digits(), rLocaleData, m_eSrcUnit);
370  if (bRet)
371  {
372  if (fResult > SAL_MAX_INT32)
373  fResult = SAL_MAX_INT32;
374  else if (fResult < SAL_MIN_INT32)
375  fResult = SAL_MIN_INT32;
376  *result = fResult;
377  }
378  return bRet;
379  }
380 
381  EntryTreeView::EntryTreeView(std::unique_ptr<Entry> xEntry, std::unique_ptr<TreeView> xTreeView)
382  : m_xEntry(std::move(xEntry))
383  , m_xTreeView(std::move(xTreeView))
384  {
385  m_xTreeView->connect_changed(LINK(this, EntryTreeView, ClickHdl));
386  m_xEntry->connect_changed(LINK(this, EntryTreeView, ModifyHdl));
387  }
388 
389  IMPL_LINK(EntryTreeView, ClickHdl, weld::TreeView&, rView, void)
390  {
391  m_xEntry->set_text(rView.get_selected_text());
392  m_aChangeHdl.Call(*this);
393  }
394 
396  {
397  m_aChangeHdl.Call(*this);
398  }
399 
401  {
402  int nHeight = nRows == -1 ? -1 : m_xTreeView->get_height_rows(nRows);
403  m_xTreeView->set_size_request(m_xTreeView->get_size_request().Width(), nHeight);
404  }
405 
406  size_t GetAbsPos(const weld::TreeView& rTreeView, const weld::TreeIter& rIter)
407  {
408  size_t nAbsPos = 0;
409 
410  std::unique_ptr<weld::TreeIter> xEntry(rTreeView.make_iterator(&rIter));
411  if (!rTreeView.get_iter_first(*xEntry))
412  xEntry.reset();
413 
414  while (xEntry && rTreeView.iter_compare(*xEntry, rIter) != 0)
415  {
416  if (!rTreeView.iter_next(*xEntry))
417  xEntry.reset();
418  nAbsPos++;
419  }
420 
421  return nAbsPos;
422  }
423 
424  bool IsEntryVisible(const weld::TreeView& rTreeView, const weld::TreeIter& rIter)
425  {
426  // short circuit for the common case
427  if (rTreeView.get_iter_depth(rIter) == 0)
428  return true;
429 
430  std::unique_ptr<weld::TreeIter> xEntry(rTreeView.make_iterator(&rIter));
431  bool bRetVal = false;
432  do
433  {
434  if (rTreeView.get_iter_depth(*xEntry) == 0)
435  {
436  bRetVal = true;
437  break;
438  }
439  } while (rTreeView.iter_parent(*xEntry) && rTreeView.get_row_expanded(*xEntry));
440  return bRetVal;
441  }
442 }
443 
444 VclBuilder::VclBuilder(vcl::Window* pParent, const OUString& sUIDir, const OUString& sUIFile,
445  const OString& sID, const css::uno::Reference<css::frame::XFrame>& rFrame,
446  bool bLegacy, const NotebookBarAddonsItem* pNotebookBarAddonsItem)
447  : m_pNotebookBarAddonsItem(pNotebookBarAddonsItem
448  ? new NotebookBarAddonsItem(*pNotebookBarAddonsItem)
449  : new NotebookBarAddonsItem{})
450  , m_sID(sID)
451  , m_sHelpRoot(OUStringToOString(sUIFile, RTL_TEXTENCODING_UTF8))
452  , m_pStringReplace(Translate::GetReadStringHook())
453  , m_pParent(pParent)
454  , m_bToplevelParentFound(false)
455  , m_bLegacy(bLegacy)
456  , m_pParserState(new ParserState)
457  , m_xFrame(rFrame)
458 {
459  m_bToplevelHasDeferredInit = pParent &&
460  ((pParent->IsSystemWindow() && static_cast<SystemWindow*>(pParent)->isDeferredInit()) ||
461  (pParent->IsDockingWindow() && static_cast<DockingWindow*>(pParent)->isDeferredInit()));
462  m_bToplevelHasDeferredProperties = m_bToplevelHasDeferredInit;
463 
464  sal_Int32 nIdx = m_sHelpRoot.lastIndexOf('.');
465  if (nIdx != -1)
466  m_sHelpRoot = m_sHelpRoot.copy(0, nIdx);
467  m_sHelpRoot += "/";
468 
469  OUString sUri = sUIDir + sUIFile;
470 
471  try
472  {
473  xmlreader::XmlReader reader(sUri);
474 
475  handleChild(pParent, nullptr, reader);
476  }
477  catch (const css::uno::Exception &rExcept)
478  {
479  DBG_UNHANDLED_EXCEPTION("vcl.builder", "Unable to read .ui file");
480  CrashReporter::addKeyValue("VclBuilderException", "Unable to read .ui file: " + rExcept.Message, CrashReporter::Write);
481  throw;
482  }
483 
484  //Set Mnemonic widgets when everything has been imported
485  for (auto const& mnemonicWidget : m_pParserState->m_aMnemonicWidgetMaps)
486  {
487  FixedText *pOne = get<FixedText>(mnemonicWidget.m_sID);
488  vcl::Window *pOther = get(mnemonicWidget.m_sValue.toUtf8());
489  SAL_WARN_IF(!pOne || !pOther, "vcl", "missing either source " << mnemonicWidget.m_sID
490  << " or target " << mnemonicWidget.m_sValue << " member of Mnemonic Widget Mapping");
491  if (pOne && pOther)
492  pOne->set_mnemonic_widget(pOther);
493  }
494 
495  //Set a11y relations and role when everything has been imported
496  for (auto const& elemAtk : m_pParserState->m_aAtkInfo)
497  {
498  vcl::Window *pSource = elemAtk.first;
499  const stringmap &rMap = elemAtk.second;
500 
501  for (auto const& elemMap : rMap)
502  {
503  const OString &rType = elemMap.first;
504  const OUString &rParam = elemMap.second;
505  if (rType == "role")
506  {
507  sal_Int16 role = BuilderUtils::getRoleFromName(rParam.toUtf8());
508  if (role != com::sun::star::accessibility::AccessibleRole::UNKNOWN)
509  pSource->SetAccessibleRole(role);
510  }
511  else
512  {
513  vcl::Window *pTarget = get(rParam.toUtf8());
514  SAL_WARN_IF(!pTarget, "vcl", "missing parameter of a11y relation: " << rParam);
515  if (!pTarget)
516  continue;
517  if (rType == "labelled-by")
518  pSource->SetAccessibleRelationLabeledBy(pTarget);
519  else if (rType == "label-for")
520  pSource->SetAccessibleRelationLabelFor(pTarget);
521  else
522  {
523  SAL_WARN("vcl.builder", "unhandled a11y relation :" << rType);
524  }
525  }
526  }
527  }
528 
529  //Set radiobutton groups when everything has been imported
530  for (auto const& elem : m_pParserState->m_aGroupMaps)
531  {
532  RadioButton *pOne = get<RadioButton>(elem.m_sID);
533  RadioButton *pOther = get<RadioButton>(elem.m_sValue);
534  SAL_WARN_IF(!pOne || !pOther, "vcl", "missing member of radiobutton group");
535  if (pOne && pOther)
536  {
537  if (m_bLegacy)
538  pOne->group(*pOther);
539  else
540  {
541  pOther->group(*pOne);
542  std::stable_sort(pOther->m_xGroup->begin(), pOther->m_xGroup->end(), sortIntoBestTabTraversalOrder(this));
543  }
544  }
545  }
546 
547 #ifndef NDEBUG
549 #endif
550  //Set ComboBox models when everything has been imported
551  for (auto const& elem : m_pParserState->m_aModelMaps)
552  {
553  assert(models.insert(elem.m_sValue).second && "a liststore or treestore is used in duplicate widgets");
554  vcl::Window* pTarget = get(elem.m_sID);
555  ListBox *pListBoxTarget = dynamic_cast<ListBox*>(pTarget);
556  ComboBox *pComboBoxTarget = dynamic_cast<ComboBox*>(pTarget);
557  SvTabListBox *pTreeBoxTarget = dynamic_cast<SvTabListBox*>(pTarget);
558  // pStore may be empty
559  const ListStore *pStore = get_model_by_name(elem.m_sValue.toUtf8());
560  SAL_WARN_IF(!pListBoxTarget && !pComboBoxTarget && !pTreeBoxTarget && !dynamic_cast<IconView*>(pTarget), "vcl", "missing elements of combobox");
561  if (pListBoxTarget && pStore)
562  mungeModel(*pListBoxTarget, *pStore, elem.m_nActiveId);
563  else if (pComboBoxTarget && pStore)
564  mungeModel(*pComboBoxTarget, *pStore, elem.m_nActiveId);
565  else if (pTreeBoxTarget && pStore)
566  mungeModel(*pTreeBoxTarget, *pStore, elem.m_nActiveId);
567  }
568 
569  //Set TextView buffers when everything has been imported
570  for (auto const& elem : m_pParserState->m_aTextBufferMaps)
571  {
572  VclMultiLineEdit *pTarget = get<VclMultiLineEdit>(elem.m_sID);
573  const TextBuffer *pBuffer = get_buffer_by_name(elem.m_sValue.toUtf8());
574  SAL_WARN_IF(!pTarget || !pBuffer, "vcl", "missing elements of textview/textbuffer");
575  if (pTarget && pBuffer)
576  mungeTextBuffer(*pTarget, *pBuffer);
577  }
578 
579  //Set SpinButton adjustments when everything has been imported
580  for (auto const& elem : m_pParserState->m_aNumericFormatterAdjustmentMaps)
581  {
582  NumericFormatter *pTarget = dynamic_cast<NumericFormatter*>(get(elem.m_sID));
583  const Adjustment *pAdjustment = get_adjustment_by_name(elem.m_sValue.toUtf8());
584  SAL_WARN_IF(!pTarget, "vcl", "missing NumericFormatter element of spinbutton/adjustment");
585  SAL_WARN_IF(!pAdjustment, "vcl", "missing Adjustment element of spinbutton/adjustment");
586  if (pTarget && pAdjustment)
587  mungeAdjustment(*pTarget, *pAdjustment);
588  }
589 
590  for (auto const& elem : m_pParserState->m_aFormattedFormatterAdjustmentMaps)
591  {
592  FormattedField *pTarget = dynamic_cast<FormattedField*>(get(elem.m_sID));
593  const Adjustment *pAdjustment = get_adjustment_by_name(elem.m_sValue.toUtf8());
594  SAL_WARN_IF(!pTarget, "vcl", "missing FormattedField element of spinbutton/adjustment");
595  SAL_WARN_IF(!pAdjustment, "vcl", "missing Adjustment element of spinbutton/adjustment");
596  if (pTarget && pAdjustment)
597  mungeAdjustment(*pTarget, *pAdjustment);
598  }
599 
600  //Set ScrollBar adjustments when everything has been imported
601  for (auto const& elem : m_pParserState->m_aScrollAdjustmentMaps)
602  {
603  ScrollBar *pTarget = get<ScrollBar>(elem.m_sID);
604  const Adjustment *pAdjustment = get_adjustment_by_name(elem.m_sValue.toUtf8());
605  SAL_WARN_IF(!pTarget || !pAdjustment, "vcl", "missing elements of scrollbar/adjustment");
606  if (pTarget && pAdjustment)
607  mungeAdjustment(*pTarget, *pAdjustment);
608  }
609 
610  //Set Scale(Slider) adjustments
611  for (auto const& elem : m_pParserState->m_aSliderAdjustmentMaps)
612  {
613  Slider* pTarget = dynamic_cast<Slider*>(get(elem.m_sID));
614  const Adjustment* pAdjustment = get_adjustment_by_name(elem.m_sValue.toUtf8());
615  SAL_WARN_IF(!pTarget || !pAdjustment, "vcl", "missing elements of scale(slider)/adjustment");
616  if (pTarget && pAdjustment)
617  {
618  mungeAdjustment(*pTarget, *pAdjustment);
619  }
620  }
621 
622  //Set size-groups when all widgets have been imported
623  for (auto const& sizeGroup : m_pParserState->m_aSizeGroups)
624  {
625  std::shared_ptr<VclSizeGroup> xGroup(std::make_shared<VclSizeGroup>());
626 
627  for (auto const& elem : sizeGroup.m_aProperties)
628  {
629  const OString &rKey = elem.first;
630  const OUString &rValue = elem.second;
631  xGroup->set_property(rKey, rValue);
632  }
633 
634  for (auto const& elem : sizeGroup.m_aWidgets)
635  {
636  vcl::Window* pWindow = get(elem.getStr());
637  pWindow->add_to_size_group(xGroup);
638  }
639  }
640 
641  //Set button images when everything has been imported
642  std::set<OUString> aImagesToBeRemoved;
643  for (auto const& elem : m_pParserState->m_aButtonImageWidgetMaps)
644  {
645  PushButton *pTargetButton = nullptr;
646  RadioButton *pTargetRadio = nullptr;
647  Button *pTarget = nullptr;
648 
649  if (!elem.m_bRadio)
650  {
651  pTargetButton = get<PushButton>(elem.m_sID);
652  pTarget = pTargetButton;
653  }
654  else
655  {
656  pTargetRadio = get<RadioButton>(elem.m_sID);
657  pTarget = pTargetRadio;
658  }
659 
660  FixedImage *pImage = get<FixedImage>(elem.m_sValue.toUtf8());
661  SAL_WARN_IF(!pTarget || !pImage,
662  "vcl", "missing elements of button/image/stock");
663  if (!pTarget || !pImage)
664  continue;
665  aImagesToBeRemoved.insert(elem.m_sValue);
666 
667  if (!elem.m_bRadio)
668  {
669  const Image& rImage = pImage->GetImage();
670  SymbolType eSymbol = mapStockToSymbol(rImage.GetStock());
671  if (eSymbol != SymbolType::IMAGE && eSymbol != SymbolType::DONTKNOW)
672  {
673  pTargetButton->SetSymbol(eSymbol);
674  //fdo#76457 keep symbol images small e.g. tools->customize->menu
675  //but images the right size. Really the PushButton::CalcMinimumSize
676  //and PushButton::ImplDrawPushButton are the better place to handle
677  //this, but its such a train-wreck
678  pTargetButton->SetStyle(pTargetButton->GetStyle() | WB_SMALLSTYLE);
679  }
680  else
681  {
682  pTargetButton->SetModeImage(rImage);
683  if (pImage->GetStyle() & WB_SMALLSTYLE)
684  {
685  Size aSz(rImage.GetSizePixel());
686  aSz.AdjustWidth(6);
687  aSz.AdjustHeight(6);
688  if (pTargetButton->get_width_request() == -1)
689  pTargetButton->set_width_request(aSz.Width());
690  if (pTargetButton->get_height_request() == -1)
691  pTargetButton->set_height_request(aSz.Height());
692  }
693  }
694  }
695  else
696  pTargetRadio->SetModeRadioImage(pImage->GetImage());
697 
698  auto aFind = m_pParserState->m_aImageSizeMap.find(elem.m_sValue.toUtf8());
699  if (aFind != m_pParserState->m_aImageSizeMap.end())
700  {
701  switch (aFind->second)
702  {
703  case 1:
704  pTarget->SetSmallSymbol();
705  break;
706  case 2:
707  assert(pImage->GetStyle() & WB_SMALLSTYLE);
708  pTarget->SetStyle(pTarget->GetStyle() | WB_SMALLSTYLE);
709  break;
710  case 3:
711  pTarget->SetStyle(pTarget->GetStyle() | WB_SMALLSTYLE);
712  // large toolbar, make bigger than normal (4)
713  pTarget->set_width_request(pTarget->GetOptimalSize().Width() * 1.5);
714  pTarget->set_height_request(pTarget->GetOptimalSize().Height() * 1.5);
715  break;
716  case 4:
717  break;
718  default:
719  SAL_WARN("vcl.builder", "unsupported image size " << aFind->second);
720  break;
721  }
722  m_pParserState->m_aImageSizeMap.erase(aFind);
723  }
724  }
725 
726  //There may be duplicate use of an Image, so we used a set to collect and
727  //now we can remove them from the tree after their final munge
728  for (auto const& elem : aImagesToBeRemoved)
729  {
730  delete_by_name(elem.toUtf8());
731  }
732 
733  //Set button menus when everything has been imported
734  for (auto const& elem : m_pParserState->m_aButtonMenuMaps)
735  {
736  MenuButton *pTarget = get<MenuButton>(elem.m_sID);
737  PopupMenu *pMenu = get_menu(elem.m_sValue.toUtf8());
738  SAL_WARN_IF(!pTarget || !pMenu,
739  "vcl", "missing elements of button/menu");
740  if (!pTarget || !pMenu)
741  continue;
742  pTarget->SetPopupMenu(pMenu);
743  }
744 
745  //Remove ScrollWindow parent widgets whose children in vcl implement scrolling
746  //internally.
747  for (auto const& elem : m_pParserState->m_aRedundantParentWidgets)
748  {
749  delete_by_window(elem.first);
750  }
751 
752  //fdo#67378 merge the label into the disclosure button
753  for (auto const& elem : m_pParserState->m_aExpanderWidgets)
754  {
755  vcl::Window *pChild = elem->get_child();
757  if (pLabel && pLabel != pChild && pLabel->GetType() == WindowType::FIXEDTEXT)
758  {
759  FixedText *pLabelWidget = static_cast<FixedText*>(pLabel);
760  elem->set_label(pLabelWidget->GetText());
761  if (pLabelWidget->IsControlFont())
762  elem->get_label_widget()->SetControlFont(pLabelWidget->GetControlFont());
763  delete_by_window(pLabel);
764  }
765  }
766 
767  // create message dialog message area now
768  for (auto const& elem : m_pParserState->m_aMessageDialogs)
769  elem->create_message_area();
770 
771  //drop maps, etc. that we don't need again
772  m_pParserState.reset();
773 
774  SAL_WARN_IF(!m_sID.isEmpty() && (!m_bToplevelParentFound && !get_by_name(m_sID)), "vcl.builder",
775  "Requested top level widget \"" << m_sID << "\" not found in " << sUIFile);
776 
777 #if defined SAL_LOG_WARN
778  if (m_bToplevelParentFound && m_pParent->IsDialog())
779  {
780  int nButtons = 0;
781  bool bHasDefButton = false;
782  for (auto const& child : m_aChildren)
783  {
784  if (isButtonType(child.m_pWindow->GetType()))
785  {
786  ++nButtons;
787  if (child.m_pWindow->GetStyle() & WB_DEFBUTTON)
788  {
789  bHasDefButton = true;
790  break;
791  }
792  }
793  }
794  SAL_WARN_IF(nButtons && !bHasDefButton, "vcl.builder", "No default button defined in " << sUIFile);
795  }
796 #endif
797 
798  const bool bHideHelp = comphelper::LibreOfficeKit::isActive() &&
799  officecfg::Office::Common::Help::HelpRootURL::get().isEmpty();
800  if (bHideHelp)
801  {
802  if (vcl::Window *pHelpButton = get("help"))
803  pHelpButton->Hide();
804  }
805 }
806 
808 {
809  disposeBuilder();
810 }
811 
813 {
814  for (std::vector<WinAndId>::reverse_iterator aI = m_aChildren.rbegin(),
815  aEnd = m_aChildren.rend(); aI != aEnd; ++aI)
816  {
817  aI->m_pWindow.disposeAndClear();
818  }
819  m_aChildren.clear();
820 
821  for (std::vector<MenuAndId>::reverse_iterator aI = m_aMenus.rbegin(),
822  aEnd = m_aMenus.rend(); aI != aEnd; ++aI)
823  {
824  aI->m_pMenu.disposeAndClear();
825  }
826  m_aMenus.clear();
827  m_pParent.clear();
828 }
829 
830 namespace
831 {
832  bool extractHasFrame(VclBuilder::stringmap& rMap)
833  {
834  bool bHasFrame = true;
835  VclBuilder::stringmap::iterator aFind = rMap.find("has-frame");
836  if (aFind != rMap.end())
837  {
838  bHasFrame = toBool(aFind->second);
839  rMap.erase(aFind);
840  }
841  return bHasFrame;
842  }
843 
844  bool extractDrawValue(VclBuilder::stringmap& rMap)
845  {
846  bool bDrawValue = true;
847  VclBuilder::stringmap::iterator aFind = rMap.find("draw-value");
848  if (aFind != rMap.end())
849  {
850  bDrawValue = toBool(aFind->second);
851  rMap.erase(aFind);
852  }
853  return bDrawValue;
854  }
855 
856  OUString extractPopupMenu(VclBuilder::stringmap& rMap)
857  {
858  OUString sRet;
859  VclBuilder::stringmap::iterator aFind = rMap.find("popup");
860  if (aFind != rMap.end())
861  {
862  sRet = aFind->second;
863  rMap.erase(aFind);
864  }
865  return sRet;
866  }
867 
868  OUString extractWidgetName(VclBuilder::stringmap& rMap)
869  {
870  OUString sRet;
871  VclBuilder::stringmap::iterator aFind = rMap.find("name");
872  if (aFind != rMap.end())
873  {
874  sRet = aFind->second;
875  rMap.erase(aFind);
876  }
877  return sRet;
878  }
879 
880  OUString extractValuePos(VclBuilder::stringmap& rMap)
881  {
882  OUString sRet("top");
883  VclBuilder::stringmap::iterator aFind = rMap.find("value-pos");
884  if (aFind != rMap.end())
885  {
886  sRet = aFind->second;
887  rMap.erase(aFind);
888  }
889  return sRet;
890  }
891 
892  OUString extractTypeHint(VclBuilder::stringmap &rMap)
893  {
894  OUString sRet("normal");
895  VclBuilder::stringmap::iterator aFind = rMap.find("type-hint");
896  if (aFind != rMap.end())
897  {
898  sRet = aFind->second;
899  rMap.erase(aFind);
900  }
901  return sRet;
902  }
903 
904  bool extractResizable(VclBuilder::stringmap &rMap)
905  {
906  bool bResizable = true;
907  VclBuilder::stringmap::iterator aFind = rMap.find("resizable");
908  if (aFind != rMap.end())
909  {
910  bResizable = toBool(aFind->second);
911  rMap.erase(aFind);
912  }
913  return bResizable;
914  }
915 
916 #if HAVE_FEATURE_DESKTOP
917  bool extractModal(VclBuilder::stringmap &rMap)
918  {
919  bool bModal = false;
920  VclBuilder::stringmap::iterator aFind = rMap.find("modal");
921  if (aFind != rMap.end())
922  {
923  bModal = toBool(aFind->second);
924  rMap.erase(aFind);
925  }
926  return bModal;
927  }
928 #endif
929 
930  bool extractDecorated(VclBuilder::stringmap &rMap)
931  {
932  bool bDecorated = true;
933  VclBuilder::stringmap::iterator aFind = rMap.find("decorated");
934  if (aFind != rMap.end())
935  {
936  bDecorated = toBool(aFind->second);
937  rMap.erase(aFind);
938  }
939  return bDecorated;
940  }
941 
942  bool extractCloseable(VclBuilder::stringmap &rMap)
943  {
944  bool bCloseable = true;
945  VclBuilder::stringmap::iterator aFind = rMap.find("deletable");
946  if (aFind != rMap.end())
947  {
948  bCloseable = toBool(aFind->second);
949  rMap.erase(aFind);
950  }
951  return bCloseable;
952  }
953 
954  bool extractEntry(VclBuilder::stringmap &rMap)
955  {
956  bool bHasEntry = false;
957  VclBuilder::stringmap::iterator aFind = rMap.find("has-entry");
958  if (aFind != rMap.end())
959  {
960  bHasEntry = toBool(aFind->second);
961  rMap.erase(aFind);
962  }
963  return bHasEntry;
964  }
965 
966  bool extractOrientation(VclBuilder::stringmap &rMap)
967  {
968  bool bVertical = false;
969  VclBuilder::stringmap::iterator aFind = rMap.find("orientation");
970  if (aFind != rMap.end())
971  {
972  bVertical = aFind->second.equalsIgnoreAsciiCase("vertical");
973  rMap.erase(aFind);
974  }
975  return bVertical;
976  }
977 
978  bool extractVerticalTabPos(VclBuilder::stringmap &rMap)
979  {
980  bool bVertical = false;
981  VclBuilder::stringmap::iterator aFind = rMap.find("tab-pos");
982  if (aFind != rMap.end())
983  {
984  bVertical = aFind->second.equalsIgnoreAsciiCase("left") ||
985  aFind->second.equalsIgnoreAsciiCase("right");
986  rMap.erase(aFind);
987  }
988  return bVertical;
989  }
990 
991  bool extractInconsistent(VclBuilder::stringmap &rMap)
992  {
993  bool bInconsistent = false;
994  VclBuilder::stringmap::iterator aFind = rMap.find("inconsistent");
995  if (aFind != rMap.end())
996  {
997  bInconsistent = toBool(aFind->second);
998  rMap.erase(aFind);
999  }
1000  return bInconsistent;
1001  }
1002 
1003  OUString extractIconName(VclBuilder::stringmap &rMap)
1004  {
1005  OUString sIconName;
1006  // allow pixbuf, but prefer icon-name
1007  {
1008  VclBuilder::stringmap::iterator aFind = rMap.find(OString("pixbuf"));
1009  if (aFind != rMap.end())
1010  {
1011  sIconName = aFind->second;
1012  rMap.erase(aFind);
1013  }
1014  }
1015  {
1016  VclBuilder::stringmap::iterator aFind = rMap.find(OString("icon-name"));
1017  if (aFind != rMap.end())
1018  {
1019  sIconName = aFind->second;
1020  rMap.erase(aFind);
1021  }
1022  }
1023  if (sIconName == "missing-image")
1024  return OUString();
1025  OUString sReplace = mapStockToImageResource(sIconName);
1026  return !sReplace.isEmpty() ? sReplace : sIconName;
1027  }
1028 
1029  WinBits extractRelief(VclBuilder::stringmap &rMap)
1030  {
1031  WinBits nBits = WB_3DLOOK;
1032  VclBuilder::stringmap::iterator aFind = rMap.find(OString("relief"));
1033  if (aFind != rMap.end())
1034  {
1035  if (aFind->second == "half")
1036  nBits = WB_FLATBUTTON | WB_BEVELBUTTON;
1037  else if (aFind->second == "none")
1038  nBits = WB_FLATBUTTON;
1039  rMap.erase(aFind);
1040  }
1041  return nBits;
1042  }
1043 
1044  OUString extractLabel(VclBuilder::stringmap &rMap)
1045  {
1046  OUString sType;
1047  VclBuilder::stringmap::iterator aFind = rMap.find(OString("label"));
1048  if (aFind != rMap.end())
1049  {
1050  sType = aFind->second;
1051  rMap.erase(aFind);
1052  }
1053  return sType;
1054  }
1055 
1056  OUString extractActionName(VclBuilder::stringmap &rMap)
1057  {
1058  OUString sActionName;
1059  VclBuilder::stringmap::iterator aFind = rMap.find(OString("action-name"));
1060  if (aFind != rMap.end())
1061  {
1062  sActionName = aFind->second;
1063  rMap.erase(aFind);
1064  }
1065  return sActionName;
1066  }
1067 
1068  bool extractVisible(VclBuilder::stringmap &rMap)
1069  {
1070  bool bRet = false;
1071  VclBuilder::stringmap::iterator aFind = rMap.find(OString("visible"));
1072  if (aFind != rMap.end())
1073  {
1074  bRet = toBool(aFind->second);
1075  rMap.erase(aFind);
1076  }
1077  return bRet;
1078  }
1079 
1080  Size extractSizeRequest(VclBuilder::stringmap &rMap)
1081  {
1082  OUString sWidthRequest("0");
1083  OUString sHeightRequest("0");
1084  VclBuilder::stringmap::iterator aFind = rMap.find(OString("width-request"));
1085  if (aFind != rMap.end())
1086  {
1087  sWidthRequest = aFind->second;
1088  rMap.erase(aFind);
1089  }
1090  aFind = rMap.find("height-request");
1091  if (aFind != rMap.end())
1092  {
1093  sHeightRequest = aFind->second;
1094  rMap.erase(aFind);
1095  }
1096  return Size(sWidthRequest.toInt32(), sHeightRequest.toInt32());
1097  }
1098 
1099  OUString extractTooltipText(VclBuilder::stringmap &rMap)
1100  {
1101  OUString sTooltipText;
1102  VclBuilder::stringmap::iterator aFind = rMap.find(OString("tooltip-text"));
1103  if (aFind == rMap.end())
1104  aFind = rMap.find(OString("tooltip-markup"));
1105  if (aFind != rMap.end())
1106  {
1107  sTooltipText = aFind->second;
1108  rMap.erase(aFind);
1109  }
1110  return sTooltipText;
1111  }
1112 
1113  float extractAlignment(VclBuilder::stringmap &rMap)
1114  {
1115  float f = 0.0;
1116  VclBuilder::stringmap::iterator aFind = rMap.find(OString("alignment"));
1117  if (aFind != rMap.end())
1118  {
1119  f = aFind->second.toFloat();
1120  rMap.erase(aFind);
1121  }
1122  return f;
1123  }
1124 
1125  OUString extractTitle(VclBuilder::stringmap &rMap)
1126  {
1127  OUString sTitle;
1128  VclBuilder::stringmap::iterator aFind = rMap.find(OString("title"));
1129  if (aFind != rMap.end())
1130  {
1131  sTitle = aFind->second;
1132  rMap.erase(aFind);
1133  }
1134  return sTitle;
1135  }
1136 
1137  bool extractHeadersVisible(VclBuilder::stringmap &rMap)
1138  {
1139  bool bHeadersVisible = true;
1140  VclBuilder::stringmap::iterator aFind = rMap.find(OString("headers-visible"));
1141  if (aFind != rMap.end())
1142  {
1143  bHeadersVisible = toBool(aFind->second);
1144  rMap.erase(aFind);
1145  }
1146  return bHeadersVisible;
1147  }
1148 
1149  bool extractSortIndicator(VclBuilder::stringmap &rMap)
1150  {
1151  bool bSortIndicator = false;
1152  VclBuilder::stringmap::iterator aFind = rMap.find(OString("sort-indicator"));
1153  if (aFind != rMap.end())
1154  {
1155  bSortIndicator = toBool(aFind->second);
1156  rMap.erase(aFind);
1157  }
1158  return bSortIndicator;
1159  }
1160 
1161  bool extractClickable(VclBuilder::stringmap &rMap)
1162  {
1163  bool bClickable = false;
1164  VclBuilder::stringmap::iterator aFind = rMap.find(OString("clickable"));
1165  if (aFind != rMap.end())
1166  {
1167  bClickable = toBool(aFind->second);
1168  rMap.erase(aFind);
1169  }
1170  return bClickable;
1171  }
1172 
1173  void setupFromActionName(Button *pButton, VclBuilder::stringmap &rMap, const css::uno::Reference<css::frame::XFrame>& rFrame)
1174  {
1175  if (!rFrame.is())
1176  return;
1177 
1178  OUString aCommand(extractActionName(rMap));
1179  if (aCommand.isEmpty())
1180  return;
1181 
1182  OUString aModuleName(vcl::CommandInfoProvider::GetModuleIdentifier(rFrame));
1183  auto aProperties = vcl::CommandInfoProvider::GetCommandProperties(aCommand, aModuleName);
1185  if (!aLabel.isEmpty())
1186  pButton->SetText(aLabel);
1187 
1188  OUString aTooltip(vcl::CommandInfoProvider::GetTooltipForCommand(aCommand, aProperties, rFrame));
1189  if (!aTooltip.isEmpty())
1190  pButton->SetQuickHelpText(aTooltip);
1191 
1192  Image aImage(vcl::CommandInfoProvider::GetImageForCommand(aCommand, rFrame));
1193  pButton->SetModeImage(aImage);
1194 
1195  pButton->SetCommandHandler(aCommand);
1196  }
1197 
1198  VclPtr<Button> extractStockAndBuildPushButton(vcl::Window *pParent, VclBuilder::stringmap &rMap, bool bToggle)
1199  {
1201  if (bToggle)
1202  nBits |= WB_TOGGLE;
1203 
1204  nBits |= extractRelief(rMap);
1205 
1206  VclPtr<Button> xWindow = VclPtr<PushButton>::Create(pParent, nBits);
1207  return xWindow;
1208  }
1209 
1210  VclPtr<MenuButton> extractStockAndBuildMenuButton(vcl::Window *pParent, VclBuilder::stringmap &rMap)
1211  {
1213 
1214  nBits |= extractRelief(rMap);
1215 
1216  VclPtr<MenuButton> xWindow = VclPtr<MenuButton>::Create(pParent, nBits);
1217  return xWindow;
1218  }
1219 
1220  VclPtr<MenuButton> extractStockAndBuildMenuToggleButton(vcl::Window *pParent, VclBuilder::stringmap &rMap)
1221  {
1223 
1224  nBits |= extractRelief(rMap);
1225 
1226  VclPtr<MenuButton> xWindow = VclPtr<MenuToggleButton>::Create(pParent, nBits);
1227  return xWindow;
1228  }
1229 
1230  WinBits extractDeferredBits(VclBuilder::stringmap &rMap)
1231  {
1232  WinBits nBits = WB_3DLOOK|WB_HIDE;
1233  if (extractResizable(rMap))
1234  nBits |= WB_SIZEABLE;
1235  if (extractCloseable(rMap))
1236  nBits |= WB_CLOSEABLE;
1237  if (!extractDecorated(rMap))
1238  nBits |= WB_OWNERDRAWDECORATION;
1239  OUString sType(extractTypeHint(rMap));
1240  if (sType == "utility")
1242  else if (sType == "popup-menu")
1244  else if (sType == "dock")
1245  nBits |= WB_DOCKABLE | WB_MOVEABLE;
1246  else
1247  nBits |= WB_MOVEABLE;
1248  return nBits;
1249  }
1250 }
1251 
1252 void VclBuilder::extractGroup(const OString &id, stringmap &rMap)
1253 {
1254  VclBuilder::stringmap::iterator aFind = rMap.find(OString("group"));
1255  if (aFind != rMap.end())
1256  {
1257  OUString sID = aFind->second;
1258  sal_Int32 nDelim = sID.indexOf(':');
1259  if (nDelim != -1)
1260  sID = sID.copy(0, nDelim);
1261  m_pParserState->m_aGroupMaps.emplace_back(id, sID.toUtf8());
1262  rMap.erase(aFind);
1263  }
1264 }
1265 
1266 void VclBuilder::connectNumericFormatterAdjustment(const OString &id, const OUString &rAdjustment)
1267 {
1268  if (!rAdjustment.isEmpty())
1269  m_pParserState->m_aNumericFormatterAdjustmentMaps.emplace_back(id, rAdjustment);
1270 }
1271 
1272 void VclBuilder::connectFormattedFormatterAdjustment(const OString &id, const OUString &rAdjustment)
1273 {
1274  if (!rAdjustment.isEmpty())
1275  m_pParserState->m_aFormattedFormatterAdjustmentMaps.emplace_back(id, rAdjustment);
1276 }
1277 
1278 bool VclBuilder::extractAdjustmentToMap(const OString& id, VclBuilder::stringmap& rMap, std::vector<WidgetAdjustmentMap>& rAdjustmentMap)
1279 {
1280  VclBuilder::stringmap::iterator aFind = rMap.find(OString("adjustment"));
1281  if (aFind != rMap.end())
1282  {
1283  rAdjustmentMap.emplace_back(id, aFind->second);
1284  rMap.erase(aFind);
1285  return true;
1286  }
1287  return false;
1288 }
1289 
1290 namespace
1291 {
1292  sal_Int32 extractActive(VclBuilder::stringmap &rMap)
1293  {
1294  sal_Int32 nActiveId = 0;
1295  VclBuilder::stringmap::iterator aFind = rMap.find(OString("active"));
1296  if (aFind != rMap.end())
1297  {
1298  nActiveId = aFind->second.toInt32();
1299  rMap.erase(aFind);
1300  }
1301  return nActiveId;
1302  }
1303 
1304  bool extractSelectable(VclBuilder::stringmap &rMap)
1305  {
1306  bool bSelectable = false;
1307  VclBuilder::stringmap::iterator aFind = rMap.find(OString("selectable"));
1308  if (aFind != rMap.end())
1309  {
1310  bSelectable = toBool(aFind->second);
1311  rMap.erase(aFind);
1312  }
1313  return bSelectable;
1314  }
1315 
1316  OUString extractAdjustment(VclBuilder::stringmap &rMap)
1317  {
1318  OUString sAdjustment;
1319  VclBuilder::stringmap::iterator aFind = rMap.find(OString("adjustment"));
1320  if (aFind != rMap.end())
1321  {
1322  sAdjustment= aFind->second;
1323  rMap.erase(aFind);
1324  return sAdjustment;
1325  }
1326  return sAdjustment;
1327  }
1328 
1329  bool extractDrawIndicator(VclBuilder::stringmap &rMap)
1330  {
1331  bool bDrawIndicator = false;
1332  VclBuilder::stringmap::iterator aFind = rMap.find(OString("draw-indicator"));
1333  if (aFind != rMap.end())
1334  {
1335  bDrawIndicator = toBool(aFind->second);
1336  rMap.erase(aFind);
1337  }
1338  return bDrawIndicator;
1339  }
1340 }
1341 
1342 void VclBuilder::extractModel(const OString &id, stringmap &rMap)
1343 {
1344  VclBuilder::stringmap::iterator aFind = rMap.find(OString("model"));
1345  if (aFind != rMap.end())
1346  {
1347  m_pParserState->m_aModelMaps.emplace_back(id, aFind->second,
1348  extractActive(rMap));
1349  rMap.erase(aFind);
1350  }
1351 }
1352 
1353 void VclBuilder::extractBuffer(const OString &id, stringmap &rMap)
1354 {
1355  VclBuilder::stringmap::iterator aFind = rMap.find(OString("buffer"));
1356  if (aFind != rMap.end())
1357  {
1358  m_pParserState->m_aTextBufferMaps.emplace_back(id, aFind->second);
1359  rMap.erase(aFind);
1360  }
1361 }
1362 
1364 {
1365  int nSize = 4;
1366  auto aFind = rMap.find(OString("icon-size"));
1367  if (aFind != rMap.end())
1368  nSize = aFind->second.toInt32();
1369  return nSize;
1370 }
1371 
1372 void VclBuilder::extractButtonImage(const OString &id, stringmap &rMap, bool bRadio)
1373 {
1374  VclBuilder::stringmap::iterator aFind = rMap.find(OString("image"));
1375  if (aFind != rMap.end())
1376  {
1377  m_pParserState->m_aButtonImageWidgetMaps.emplace_back(id, aFind->second, bRadio);
1378  rMap.erase(aFind);
1379  }
1380 }
1381 
1382 void VclBuilder::extractMnemonicWidget(const OString &rLabelID, stringmap &rMap)
1383 {
1384  VclBuilder::stringmap::iterator aFind = rMap.find(OString("mnemonic-widget"));
1385  if (aFind != rMap.end())
1386  {
1387  OUString sID = aFind->second;
1388  sal_Int32 nDelim = sID.indexOf(':');
1389  if (nDelim != -1)
1390  sID = sID.copy(0, nDelim);
1391  m_pParserState->m_aMnemonicWidgetMaps.emplace_back(rLabelID, sID);
1392  rMap.erase(aFind);
1393  }
1394 }
1395 
1397 {
1398  //For Widgets that manage their own scrolling, if one appears as a child of
1399  //a scrolling window shoehorn that scrolling settings to this widget and
1400  //return the real parent to use
1401  if (pParent && pParent->GetType() == WindowType::SCROLLWINDOW)
1402  {
1403  WinBits nScrollBits = pParent->GetStyle();
1405  rWinStyle |= nScrollBits;
1406  if (static_cast<VclScrolledWindow*>(pParent)->HasVisibleBorder())
1407  rWinStyle |= WB_BORDER;
1408  pParent = pParent->GetParent();
1409  }
1410 
1411  return pParent;
1412 }
1413 
1415 {
1416  //remove the redundant scrolling parent
1417  sal_Int32 nWidthReq = pScrollParent->get_width_request();
1418  rMap[OString("width-request")] = OUString::number(nWidthReq);
1419  sal_Int32 nHeightReq = pScrollParent->get_height_request();
1420  rMap[OString("height-request")] = OUString::number(nHeightReq);
1421 
1422  m_pParserState->m_aRedundantParentWidgets[pScrollParent] = pWindow;
1423 }
1424 
1425 #ifndef DISABLE_DYNLOADING
1426 
1427 extern "C" { static void thisModule() {} }
1428 
1429 namespace {
1430 
1431 // Don't unload the module on destruction
1432 class NoAutoUnloadModule : public osl::Module
1433 {
1434 public:
1435  ~NoAutoUnloadModule() { release(); }
1436 };
1437 
1438 }
1439 
1440 typedef std::map<OUString, std::shared_ptr<NoAutoUnloadModule>> ModuleMap;
1441 static ModuleMap g_aModuleMap;
1442 
1443 #if ENABLE_MERGELIBS
1444 static std::shared_ptr<NoAutoUnloadModule> g_pMergedLib = std::make_shared<NoAutoUnloadModule>();
1445 #endif
1446 
1447 #ifndef SAL_DLLPREFIX
1448 # define SAL_DLLPREFIX ""
1449 #endif
1450 
1451 #endif
1452 
1453 namespace vcl {
1454 
1456 {
1457 #ifndef DISABLE_DYNLOADING
1458 
1459 #if ENABLE_MERGELIBS
1460  g_pMergedLib->loadRelative(&thisModule, SVLIBRARY("merged"));
1461 #else
1462 // find -name '*ui*' | xargs grep 'class=".*lo-' |
1463 // sed 's/.*class="//' | sed 's/-.*$//' | sort | uniq
1464  static const char *aWidgetLibs[] = {
1465  "sfxlo", "svtlo"
1466  };
1467  for (const auto & lib : aWidgetLibs)
1468  {
1469  std::unique_ptr<NoAutoUnloadModule> pModule(new NoAutoUnloadModule);
1470  OUString sModule = SAL_DLLPREFIX + OUString::createFromAscii(lib) + SAL_DLLEXTENSION;
1471  if (pModule->loadRelative(&thisModule, sModule))
1472  g_aModuleMap.insert(std::make_pair(sModule, std::move(pModule)));
1473  }
1474 #endif // ENABLE_MERGELIBS
1475 #endif // DISABLE_DYNLOADING
1476 }
1477 
1478 }
1479 
1480 #if defined DISABLE_DYNLOADING && !HAVE_FEATURE_DESKTOP
1481 extern "C" VclBuilder::customMakeWidget lo_get_custom_widget_func(const char* name);
1482 #endif
1483 
1484 namespace
1485 {
1486 // Takes a string like "sfxlo-NotebookbarToolBox"
1487 VclBuilder::customMakeWidget GetCustomMakeWidget(const OString& rName)
1488 {
1489  const OString name = rName == "sfxlo-SidebarToolBox" ? "sfxlo-NotebookbarToolBox" : rName;
1490  VclBuilder::customMakeWidget pFunction = nullptr;
1491  if (sal_Int32 nDelim = name.indexOf('-'); nDelim != -1)
1492  {
1493  const OString aFunction(OString::Concat("make") + name.subView(nDelim + 1));
1494  const OUString sFunction(OStringToOUString(aFunction, RTL_TEXTENCODING_UTF8));
1495 
1496 #ifndef DISABLE_DYNLOADING
1497  const OUString sModule = SAL_DLLPREFIX
1498  + OStringToOUString(name.subView(0, nDelim), RTL_TEXTENCODING_UTF8)
1499  + SAL_DLLEXTENSION;
1500  ModuleMap::iterator aI = g_aModuleMap.find(sModule);
1501  if (aI == g_aModuleMap.end())
1502  {
1503  std::shared_ptr<NoAutoUnloadModule> pModule;
1504 #if ENABLE_MERGELIBS
1505  if (!g_pMergedLib->is())
1506  g_pMergedLib->loadRelative(&thisModule, SVLIBRARY("merged"));
1507  if ((pFunction = reinterpret_cast<VclBuilder::customMakeWidget>(
1508  g_pMergedLib->getFunctionSymbol(sFunction))))
1509  pModule = g_pMergedLib;
1510 #endif
1511  if (!pFunction)
1512  {
1513  pModule = std::make_shared<NoAutoUnloadModule>();
1514  bool ok = pModule->loadRelative(&thisModule, sModule);
1515  if (!ok)
1516  {
1517 #ifdef LINUX
1518  // in the case of preloading, we don't have eg. the
1519  // libcuilo.so, but still need to dlsym the symbols -
1520  // which are already in-process
1522  {
1523  pFunction = reinterpret_cast<VclBuilder::customMakeWidget>(dlsym(RTLD_DEFAULT, aFunction.getStr()));
1524  ok = !!pFunction;
1525  assert(ok && "couldn't even directly dlsym the sFunction (available via preload)");
1526  }
1527 #endif
1528  assert(ok && "bad module name in .ui");
1529  }
1530  else
1531  {
1532  pFunction = reinterpret_cast<VclBuilder::customMakeWidget>(
1533  pModule->getFunctionSymbol(sFunction));
1534  }
1535  }
1536  g_aModuleMap.insert(std::make_pair(sModule, pModule));
1537  }
1538  else
1539  pFunction = reinterpret_cast<VclBuilder::customMakeWidget>(
1540  aI->second->getFunctionSymbol(sFunction));
1541 #elif !HAVE_FEATURE_DESKTOP
1542  pFunction = lo_get_custom_widget_func(sFunction.toUtf8().getStr());
1543  SAL_WARN_IF(!pFunction, "vcl.builder", "Could not find " << sFunction);
1544  assert(pFunction);
1545 #else
1546  pFunction = reinterpret_cast<VclBuilder::customMakeWidget>(
1547  osl_getFunctionSymbol((oslModule)RTLD_DEFAULT, sFunction.pData));
1548 #endif
1549  }
1550  return pFunction;
1551 }
1552 }
1553 
1554 VclPtr<vcl::Window> VclBuilder::makeObject(vcl::Window *pParent, const OString &name, const OString &id,
1555  stringmap &rMap)
1556 {
1557  bool bIsPlaceHolder = name.isEmpty();
1558  bool bVertical = false;
1559 
1560  if (pParent && (pParent->GetType() == WindowType::TABCONTROL ||
1561  pParent->GetType() == WindowType::VERTICALTABCONTROL))
1562  {
1563  bool bTopLevel(name == "GtkDialog" || name == "GtkMessageDialog" ||
1564  name == "GtkWindow" || name == "GtkPopover" || name == "GtkAssistant");
1565  if (!bTopLevel)
1566  {
1567  if (pParent->GetType() == WindowType::TABCONTROL)
1568  {
1569  //We have to add a page
1570  //make default pageid == position
1571  TabControl *pTabControl = static_cast<TabControl*>(pParent);
1572  sal_uInt16 nNewPageCount = pTabControl->GetPageCount()+1;
1573  sal_uInt16 nNewPageId = nNewPageCount;
1574  pTabControl->InsertPage(nNewPageId, OUString());
1575  pTabControl->SetCurPageId(nNewPageId);
1576  SAL_WARN_IF(bIsPlaceHolder, "vcl.builder", "we should have no placeholders for tabpages");
1577  if (!bIsPlaceHolder)
1578  {
1579  VclPtrInstance<TabPage> pPage(pTabControl);
1580  pPage->Show();
1581 
1582  //Make up a name for it
1583  OString sTabPageId = get_by_window(pParent) +
1584  "-page" +
1585  OString::number(nNewPageCount);
1586  m_aChildren.emplace_back(sTabPageId, pPage, false);
1587  pPage->SetHelpId(m_sHelpRoot + sTabPageId);
1588 
1589  pParent = pPage;
1590 
1591  pTabControl->SetTabPage(nNewPageId, pPage);
1592  }
1593  }
1594  else
1595  {
1596  VerticalTabControl *pTabControl = static_cast<VerticalTabControl*>(pParent);
1597  SAL_WARN_IF(bIsPlaceHolder, "vcl.builder", "we should have no placeholders for tabpages");
1598  if (!bIsPlaceHolder)
1599  pParent = pTabControl->GetPageParent();
1600  }
1601  }
1602  }
1603 
1604  if (bIsPlaceHolder || name == "GtkTreeSelection")
1605  return nullptr;
1606 
1607  ToolBox *pToolBox = (pParent && pParent->GetType() == WindowType::TOOLBOX) ? static_cast<ToolBox*>(pParent) : nullptr;
1608 
1609  extractButtonImage(id, rMap, name == "GtkRadioButton");
1610 
1611  VclPtr<vcl::Window> xWindow;
1612  if (name == "GtkDialog" || name == "GtkAssistant")
1613  {
1614  // WB_ALLOWMENUBAR because we don't know in advance if we will encounter
1615  // a menubar, and menubars need a BorderWindow in the toplevel, and
1616  // such border windows need to be in created during the dialog ctor
1618  if (extractResizable(rMap))
1619  nBits |= WB_SIZEABLE;
1620  if (extractCloseable(rMap))
1621  nBits |= WB_CLOSEABLE;
1623  if (name == "GtkAssistant")
1624  xWindow = VclPtr<vcl::RoadmapWizard>::Create(pParent, nBits, eInit);
1625  else
1626  xWindow = VclPtr<Dialog>::Create(pParent, nBits, eInit);
1627 #if HAVE_FEATURE_DESKTOP
1628  if (!extractModal(rMap))
1629  xWindow->SetType(WindowType::MODELESSDIALOG);
1630 #endif
1631  }
1632  else if (name == "GtkMessageDialog")
1633  {
1635  if (extractResizable(rMap))
1636  nBits |= WB_SIZEABLE;
1637  VclPtr<MessageDialog> xDialog(VclPtr<MessageDialog>::Create(pParent, nBits));
1638  m_pParserState->m_aMessageDialogs.push_back(xDialog);
1639  xWindow = xDialog;
1640 #if defined _WIN32
1641  xWindow->set_border_width(3);
1642 #else
1643  xWindow->set_border_width(12);
1644 #endif
1645  }
1646  else if (name == "GtkBox" || name == "GtkStatusbar")
1647  {
1648  bVertical = extractOrientation(rMap);
1649  if (bVertical)
1650  xWindow = VclPtr<VclVBox>::Create(pParent);
1651  else
1652  xWindow = VclPtr<VclHBox>::Create(pParent);
1653  }
1654  else if (name == "GtkPaned")
1655  {
1656  bVertical = extractOrientation(rMap);
1657  if (bVertical)
1658  xWindow = VclPtr<VclVPaned>::Create(pParent);
1659  else
1660  xWindow = VclPtr<VclHPaned>::Create(pParent);
1661  }
1662  else if (name == "GtkHBox")
1663  xWindow = VclPtr<VclHBox>::Create(pParent);
1664  else if (name == "GtkVBox")
1665  xWindow = VclPtr<VclVBox>::Create(pParent);
1666  else if (name == "GtkButtonBox")
1667  {
1668  bVertical = extractOrientation(rMap);
1669  if (bVertical)
1670  xWindow = VclPtr<VclVButtonBox>::Create(pParent);
1671  else
1672  xWindow = VclPtr<VclHButtonBox>::Create(pParent);
1673  }
1674  else if (name == "GtkHButtonBox")
1675  xWindow = VclPtr<VclHButtonBox>::Create(pParent);
1676  else if (name == "GtkVButtonBox")
1677  xWindow = VclPtr<VclVButtonBox>::Create(pParent);
1678  else if (name == "GtkGrid")
1679  xWindow = VclPtr<VclGrid>::Create(pParent);
1680  else if (name == "GtkFrame")
1681  xWindow = VclPtr<VclFrame>::Create(pParent);
1682  else if (name == "GtkExpander")
1683  {
1684  VclPtrInstance<VclExpander> pExpander(pParent);
1685  m_pParserState->m_aExpanderWidgets.push_back(pExpander);
1686  xWindow = pExpander;
1687  }
1688  else if (name == "GtkButton" || (!m_bLegacy && name == "GtkToggleButton"))
1689  {
1690  VclPtr<Button> xButton;
1691  OUString sMenu = BuilderUtils::extractCustomProperty(rMap);
1692  if (sMenu.isEmpty())
1693  xButton = extractStockAndBuildPushButton(pParent, rMap, name == "GtkToggleButton");
1694  else
1695  {
1696  assert(m_bLegacy && "use GtkMenuButton");
1697  xButton = extractStockAndBuildMenuButton(pParent, rMap);
1698  m_pParserState->m_aButtonMenuMaps.emplace_back(id, sMenu);
1699  }
1700  xButton->SetImageAlign(ImageAlign::Left); //default to left
1701  setupFromActionName(xButton, rMap, m_xFrame);
1702  xWindow = xButton;
1703  }
1704  else if (name == "GtkMenuButton")
1705  {
1706  VclPtr<MenuButton> xButton;
1707 
1708  OUString sMenu = extractPopupMenu(rMap);
1709  if (!sMenu.isEmpty())
1710  m_pParserState->m_aButtonMenuMaps.emplace_back(id, sMenu);
1711 
1712  OUString sType = extractWidgetName(rMap);
1713  if (sType.isEmpty())
1714  {
1715  xButton = extractStockAndBuildMenuButton(pParent, rMap);
1716  xButton->SetAccessibleRole(css::accessibility::AccessibleRole::BUTTON_MENU);
1717  }
1718  else
1719  {
1720  xButton = extractStockAndBuildMenuToggleButton(pParent, rMap);
1721  }
1722 
1723  xButton->SetImageAlign(ImageAlign::Left); //default to left
1724 
1725  if (!extractDrawIndicator(rMap))
1727 
1728  setupFromActionName(xButton, rMap, m_xFrame);
1729  xWindow = xButton;
1730  }
1731  else if (name == "GtkToggleButton" && m_bLegacy)
1732  {
1733  VclPtr<Button> xButton;
1734  OUString sMenu = BuilderUtils::extractCustomProperty(rMap);
1735  assert(sMenu.getLength() && "not implemented yet");
1736  xButton = extractStockAndBuildMenuToggleButton(pParent, rMap);
1737  m_pParserState->m_aButtonMenuMaps.emplace_back(id, sMenu);
1738  xButton->SetImageAlign(ImageAlign::Left); //default to left
1739  setupFromActionName(xButton, rMap, m_xFrame);
1740  xWindow = xButton;
1741  }
1742  else if (name == "GtkRadioButton")
1743  {
1744  extractGroup(id, rMap);
1746  VclPtr<RadioButton> xButton = VclPtr<RadioButton>::Create(pParent, true, nBits);
1747  xButton->SetImageAlign(ImageAlign::Left); //default to left
1748  xWindow = xButton;
1749  }
1750  else if (name == "GtkCheckButton")
1751  {
1753  bool bIsTriState = extractInconsistent(rMap);
1754  VclPtr<CheckBox> xCheckBox = VclPtr<CheckBox>::Create(pParent, nBits);
1755  if (bIsTriState)
1756  {
1757  xCheckBox->EnableTriState(true);
1758  xCheckBox->SetState(TRISTATE_INDET);
1759  }
1760  xCheckBox->SetImageAlign(ImageAlign::Left); //default to left
1761 
1762  xWindow = xCheckBox;
1763  }
1764  else if (name == "GtkSpinButton")
1765  {
1766  OUString sAdjustment = extractAdjustment(rMap);
1767 
1769  if (extractHasFrame(rMap))
1770  nBits |= WB_BORDER;
1771 
1772  connectFormattedFormatterAdjustment(id, sAdjustment);
1773  VclPtrInstance<FormattedField> xField(pParent, nBits);
1774  xField->GetFormatter().SetMinValue(0);
1775  xWindow = xField;
1776  }
1777  else if (name == "GtkLinkButton")
1779  else if (name == "GtkComboBox" || name == "GtkComboBoxText")
1780  {
1781  extractModel(id, rMap);
1782 
1784 
1785  bool bDropdown = BuilderUtils::extractDropdown(rMap);
1786 
1787  if (bDropdown)
1788  nBits |= WB_DROPDOWN;
1789 
1790  if (extractEntry(rMap))
1791  {
1792  VclPtrInstance<ComboBox> xComboBox(pParent, nBits);
1793  xComboBox->EnableAutoSize(true);
1794  xWindow = xComboBox;
1795  }
1796  else
1797  {
1798  VclPtrInstance<ListBox> xListBox(pParent, nBits|WB_SIMPLEMODE);
1799  xListBox->EnableAutoSize(true);
1800  xWindow = xListBox;
1801  }
1802  }
1803  else if (name == "VclOptionalBox" || name == "sfxlo-OptionalBox")
1804  {
1805  // tdf#135495 fallback sfxlo-OptionalBox to VclOptionalBox as a stopgap
1806  xWindow = VclPtr<OptionalBox>::Create(pParent);
1807  }
1808  else if (name == "svtlo-ManagedMenuButton")
1809  {
1810  // like tdf#135495 keep the name svtlo-ManagedMenuButton even though it's a misnomer
1811  // and is not dlsymed from the svt library
1813  OUString sMenu = BuilderUtils::extractCustomProperty(rMap);
1814  if (!sMenu.isEmpty())
1815  m_pParserState->m_aButtonMenuMaps.emplace_back(id, sMenu);
1816  setupFromActionName(static_cast<Button*>(xWindow.get()), rMap, m_xFrame);
1817  }
1818  else if (name == "sfxlo-PriorityMergedHBox")
1819  {
1820  // like tdf#135495 above, keep the sfxlo-PriorityMergedHBox even though its not in sfx anymore
1821  xWindow = VclPtr<PriorityMergedHBox>::Create(pParent);
1822  }
1823  else if (name == "sfxlo-PriorityHBox")
1824  {
1825  // like tdf#135495 above, keep the sfxlo-PriorityMergedHBox even though its not in sfx anymore
1826  xWindow = VclPtr<PriorityHBox>::Create(pParent);
1827  }
1828  else if (name == "sfxlo-DropdownBox")
1829  {
1830  // like tdf#135495 above, keep the sfxlo-PriorityMergedHBox even though its not in sfx anymore
1831  xWindow = VclPtr<DropdownBox>::Create(pParent);
1832  }
1833  else if (name == "sfxlo-ContextVBox")
1834  {
1835  // like tdf#135495 above, keep the sfxlo-PriorityMergedHBox even though its not in sfx anymore
1836  xWindow = VclPtr<ContextVBox>::Create(pParent);
1837  }
1838  else if (name == "GtkIconView")
1839  {
1840  assert(rMap.find(OString("model")) != rMap.end() && "GtkIconView must have a model");
1841 
1842  //window we want to apply the packing props for this GtkIconView to
1843  VclPtr<vcl::Window> xWindowForPackingProps;
1844  extractModel(id, rMap);
1846  //IconView manages its own scrolling,
1847  vcl::Window *pRealParent = prepareWidgetOwnScrolling(pParent, nWinStyle);
1848 
1849  VclPtr<IconView> xBox = VclPtr<IconView>::Create(pRealParent, nWinStyle);
1850  xWindowForPackingProps = xBox;
1851 
1852  xWindow = xBox;
1853  xBox->SetNoAutoCurEntry(true);
1854  xBox->SetQuickSearch(true);
1855 
1856  if (pRealParent != pParent)
1857  cleanupWidgetOwnScrolling(pParent, xWindowForPackingProps, rMap);
1858  }
1859  else if (name == "GtkTreeView")
1860  {
1861  if (!m_bLegacy)
1862  {
1863  assert(rMap.find(OString("model")) != rMap.end() && "GtkTreeView must have a model");
1864  }
1865 
1866  //window we want to apply the packing props for this GtkTreeView to
1867  VclPtr<vcl::Window> xWindowForPackingProps;
1868  //To-Do
1869  //a) make SvHeaderTabListBox/SvTabListBox the default target for GtkTreeView
1870  //b) remove the non-drop down mode of ListBox and convert
1871  // everything over to SvHeaderTabListBox/SvTabListBox
1872  extractModel(id, rMap);
1874  if (m_bLegacy)
1875  {
1877  if (!sBorder.isEmpty())
1878  nWinStyle |= WB_BORDER;
1879  }
1880  else
1881  {
1882  nWinStyle |= WB_HASBUTTONS | WB_HASBUTTONSATROOT;
1883  }
1884  //ListBox/SvHeaderTabListBox manages its own scrolling,
1885  vcl::Window *pRealParent = prepareWidgetOwnScrolling(pParent, nWinStyle);
1886  if (m_bLegacy)
1887  {
1888  xWindow = VclPtr<ListBox>::Create(pRealParent, nWinStyle | WB_SIMPLEMODE);
1889  xWindowForPackingProps = xWindow;
1890  }
1891  else
1892  {
1893  VclPtr<SvTabListBox> xBox;
1894  bool bHeadersVisible = extractHeadersVisible(rMap);
1895  if (bHeadersVisible)
1896  {
1897  VclPtr<VclVBox> xContainer = VclPtr<VclVBox>::Create(pRealParent);
1898  OString containerid(id + "-container");
1899  xContainer->SetHelpId(m_sHelpRoot + containerid);
1900  m_aChildren.emplace_back(containerid, xContainer, true);
1901 
1903  xHeader->set_width_request(0); // let the headerbar width not affect the size request
1904  OString headerid(id + "-header");
1905  xHeader->SetHelpId(m_sHelpRoot + headerid);
1906  m_aChildren.emplace_back(headerid, xHeader, true);
1907 
1908  VclPtr<LclHeaderTabListBox> xHeaderBox = VclPtr<LclHeaderTabListBox>::Create(xContainer, nWinStyle);
1909  xHeaderBox->InitHeaderBar(xHeader);
1910  xContainer->set_expand(true);
1911  xHeader->Show();
1912  xContainer->Show();
1913  xBox = xHeaderBox;
1914  xWindowForPackingProps = xContainer;
1915  }
1916  else
1917  {
1918  xBox = VclPtr<LclTabListBox>::Create(pRealParent, nWinStyle);
1919  xWindowForPackingProps = xBox;
1920  }
1921  xWindow = xBox;
1922  xBox->SetNoAutoCurEntry(true);
1923  xBox->SetQuickSearch(true);
1924  xBox->SetSpaceBetweenEntries(3);
1925  xBox->SetEntryHeight(16);
1926  xBox->SetHighlightRange(); // select over the whole width
1927  }
1928  if (pRealParent != pParent)
1929  cleanupWidgetOwnScrolling(pParent, xWindowForPackingProps, rMap);
1930  }
1931  else if (name == "GtkTreeViewColumn")
1932  {
1933  if (!m_bLegacy)
1934  {
1935  SvHeaderTabListBox* pTreeView = dynamic_cast<SvHeaderTabListBox*>(pParent);
1936  if (HeaderBar* pHeaderBar = pTreeView ? pTreeView->GetHeaderBar() : nullptr)
1937  {
1939  if (extractClickable(rMap))
1941  if (extractSortIndicator(rMap))
1943  float fAlign = extractAlignment(rMap);
1944  if (fAlign == 0.0)
1945  nBits |= HeaderBarItemBits::LEFT;
1946  else if (fAlign == 1.0)
1947  nBits |= HeaderBarItemBits::RIGHT;
1948  else if (fAlign == 0.5)
1949  nBits |= HeaderBarItemBits::CENTER;
1950  auto nItemId = pHeaderBar->GetItemCount() + 1;
1951  OUString sTitle(extractTitle(rMap));
1952  pHeaderBar->InsertItem(nItemId, sTitle, 100, nBits);
1953  }
1954  }
1955  }
1956  else if (name == "GtkLabel")
1957  {
1958  WinBits nWinStyle = WB_CENTER|WB_VCENTER|WB_3DLOOK;
1959  extractMnemonicWidget(id, rMap);
1960  if (extractSelectable(rMap))
1961  xWindow = VclPtr<SelectableFixedText>::Create(pParent, nWinStyle);
1962  else
1963  xWindow = VclPtr<FixedText>::Create(pParent, nWinStyle);
1964  }
1965  else if (name == "GtkImage")
1966  {
1968  OUString sIconName = extractIconName(rMap);
1969  if (!sIconName.isEmpty())
1970  xFixedImage->SetImage(FixedImage::loadThemeImage(sIconName));
1971  m_pParserState->m_aImageSizeMap[id] = getImageSize(rMap);
1972  xWindow = xFixedImage;
1973  //such parentless GtkImages are temps used to set icons on buttons
1974  //default them to hidden to stop e.g. insert->index entry flicking temp
1975  //full screen windows
1976  if (!pParent)
1977  {
1978  rMap["visible"] = "false";
1979  }
1980  }
1981  else if (name == "GtkSeparator")
1982  {
1983  bVertical = extractOrientation(rMap);
1984  xWindow = VclPtr<FixedLine>::Create(pParent, bVertical ? WB_VERT : WB_HORZ);
1985  }
1986  else if (name == "GtkScrollbar")
1987  {
1988  extractAdjustmentToMap(id, rMap, m_pParserState->m_aScrollAdjustmentMaps);
1989  bVertical = extractOrientation(rMap);
1990  xWindow = VclPtr<ScrollBar>::Create(pParent, bVertical ? WB_VERT : WB_HORZ);
1991  }
1992  else if (name == "GtkProgressBar")
1993  {
1994  extractAdjustmentToMap(id, rMap, m_pParserState->m_aScrollAdjustmentMaps);
1995  bVertical = extractOrientation(rMap);
1996  xWindow = VclPtr<ProgressBar>::Create(pParent, bVertical ? WB_VERT : WB_HORZ);
1997  }
1998  else if (name == "GtkScrolledWindow")
1999  {
2000  xWindow = VclPtr<VclScrolledWindow>::Create(pParent);
2001  }
2002  else if (name == "GtkViewport")
2003  {
2004  xWindow = VclPtr<VclViewport>::Create(pParent);
2005  }
2006  else if (name == "GtkEventBox")
2007  {
2008  xWindow = VclPtr<VclEventBox>::Create(pParent);
2009  }
2010  else if (name == "GtkEntry")
2011  {
2012  WinBits nWinStyle = WB_LEFT|WB_VCENTER|WB_3DLOOK;
2013  if (extractHasFrame(rMap))
2014  nWinStyle |= WB_BORDER;
2015  xWindow = VclPtr<Edit>::Create(pParent, nWinStyle);
2017  }
2018  else if (name == "GtkNotebook")
2019  {
2020  if (!extractVerticalTabPos(rMap))
2022  else
2023  xWindow = VclPtr<VerticalTabControl>::Create(pParent);
2024  }
2025  else if (name == "GtkDrawingArea")
2026  {
2027  xWindow = VclPtr<VclDrawingArea>::Create(pParent, WB_TABSTOP);
2028  }
2029  else if (name == "GtkTextView")
2030  {
2031  extractBuffer(id, rMap);
2032 
2033  WinBits nWinStyle = WB_CLIPCHILDREN|WB_LEFT;
2034  //VclMultiLineEdit manages its own scrolling,
2035  vcl::Window *pRealParent = prepareWidgetOwnScrolling(pParent, nWinStyle);
2036  xWindow = VclPtr<VclMultiLineEdit>::Create(pRealParent, nWinStyle);
2037  if (pRealParent != pParent)
2038  cleanupWidgetOwnScrolling(pParent, xWindow, rMap);
2039  }
2040  else if (name == "GtkSpinner")
2041  {
2042  xWindow = VclPtr<Throbber>::Create(pParent, WB_3DLOOK);
2043  }
2044  else if (name == "GtkScale")
2045  {
2046  extractAdjustmentToMap(id, rMap, m_pParserState->m_aSliderAdjustmentMaps);
2047  bool bDrawValue = extractDrawValue(rMap);
2048  if (bDrawValue)
2049  {
2050  OUString sValuePos = extractValuePos(rMap);
2051  (void)sValuePos;
2052  }
2053  bVertical = extractOrientation(rMap);
2054 
2055  WinBits nWinStyle = bVertical ? WB_VERT : WB_HORZ;
2056 
2057  xWindow = VclPtr<Slider>::Create(pParent, nWinStyle);
2058  }
2059  else if (name == "GtkToolbar")
2060  {
2061  xWindow = VclPtr<ToolBox>::Create(pParent, WB_3DLOOK | WB_TABSTOP);
2062  }
2063  else if(name == "NotebookBarAddonsToolMergePoint")
2064  {
2065  customMakeWidget pFunction = GetCustomMakeWidget("sfxlo-NotebookbarToolBox");
2066  if(pFunction != nullptr)
2068  return nullptr;
2069  }
2070  else if (name == "GtkToolButton" || name == "GtkMenuToolButton" ||
2071  name == "GtkToggleToolButton" || name == "GtkRadioToolButton" || name == "GtkToolItem")
2072  {
2073  if (pToolBox)
2074  {
2075  OUString aCommand(extractActionName(rMap));
2076 
2077  ToolBoxItemId nItemId(0);
2079  if (name == "GtkMenuToolButton")
2080  nBits |= ToolBoxItemBits::DROPDOWN;
2081  else if (name == "GtkToggleToolButton")
2083  else if (name == "GtkRadioToolButton")
2085 
2086  if (!aCommand.isEmpty() && m_xFrame.is())
2087  {
2088  pToolBox->InsertItem(aCommand, m_xFrame, nBits, extractSizeRequest(rMap));
2089  nItemId = pToolBox->GetItemId(aCommand);
2090  }
2091  else
2092  {
2093  nItemId = ToolBoxItemId(pToolBox->GetItemCount() + 1);
2094  //TODO: ImplToolItems::size_type -> sal_uInt16!
2095  pToolBox->InsertItem(nItemId, extractLabel(rMap), nBits);
2096  if (aCommand.isEmpty() && !m_bLegacy)
2097  aCommand = OUString::fromUtf8(id);
2098  pToolBox->SetItemCommand(nItemId, aCommand);
2099  }
2100 
2101  pToolBox->SetHelpId(nItemId, m_sHelpRoot + id);
2102  OUString sTooltip(extractTooltipText(rMap));
2103  if (!sTooltip.isEmpty())
2104  pToolBox->SetQuickHelpText(nItemId, sTooltip);
2105 
2106  OUString sIconName(extractIconName(rMap));
2107  if (!sIconName.isEmpty())
2108  pToolBox->SetItemImage(nItemId, FixedImage::loadThemeImage(sIconName));
2109 
2110  if (!extractVisible(rMap))
2111  pToolBox->HideItem(nItemId);
2112 
2113  m_pParserState->m_nLastToolbarId = nItemId;
2114 
2115  return nullptr; // no widget to be created
2116  }
2117  }
2118  else if (name == "GtkSeparatorToolItem")
2119  {
2120  if (pToolBox)
2121  {
2122  pToolBox->InsertSeparator();
2123  return nullptr; // no widget to be created
2124  }
2125  }
2126  else if (name == "GtkWindow")
2127  {
2128  WinBits nBits = extractDeferredBits(rMap);
2129  if (nBits & WB_DOCKABLE)
2130  xWindow = VclPtr<DockingWindow>::Create(pParent, nBits|WB_MOVEABLE);
2131  else
2132  xWindow = VclPtr<FloatingWindow>::Create(pParent, nBits|WB_MOVEABLE);
2133  }
2134  else if (name == "GtkPopover")
2135  {
2136  WinBits nBits = extractDeferredBits(rMap);
2137  xWindow = VclPtr<DockingWindow>::Create(pParent, nBits|WB_DOCKABLE|WB_MOVEABLE);
2138  }
2139  else if (name == "GtkCalendar")
2140  {
2141  WinBits nBits = extractDeferredBits(rMap);
2142  xWindow = VclPtr<Calendar>::Create(pParent, nBits);
2143  }
2144  else
2145  {
2146  if (customMakeWidget pFunction = GetCustomMakeWidget(name))
2147  {
2148  pFunction(xWindow, pParent, rMap);
2149  if (xWindow->GetType() == WindowType::PUSHBUTTON)
2150  setupFromActionName(static_cast<Button*>(xWindow.get()), rMap, m_xFrame);
2151  else if (xWindow->GetType() == WindowType::MENUBUTTON)
2152  {
2153  OUString sMenu = BuilderUtils::extractCustomProperty(rMap);
2154  if (!sMenu.isEmpty())
2155  m_pParserState->m_aButtonMenuMaps.emplace_back(id, sMenu);
2156  setupFromActionName(static_cast<Button*>(xWindow.get()), rMap, m_xFrame);
2157  }
2158  }
2159  }
2160 
2161  SAL_INFO_IF(!xWindow, "vcl.builder", "probably need to implement " << name << " or add a make" << name << " function");
2162  if (xWindow)
2163  {
2164  // child windows of disabled windows are made disabled by vcl by default, we don't want that
2165  WindowImpl *pWindowImpl = xWindow->ImplGetWindowImpl();
2166  pWindowImpl->mbDisabled = false;
2167 
2168  xWindow->SetHelpId(m_sHelpRoot + id);
2169  SAL_INFO("vcl.builder", "for name '" << name << "' and id '" << id <<
2170  "', created " << xWindow.get() << " child of " <<
2171  pParent << "(" << xWindow->ImplGetWindowImpl()->mpParent.get() << "/" <<
2172  xWindow->ImplGetWindowImpl()->mpRealParent.get() << "/" <<
2173  xWindow->ImplGetWindowImpl()->mpBorderWindow.get() << ") with helpid " <<
2174  xWindow->GetHelpId());
2175  m_aChildren.emplace_back(id, xWindow, bVertical);
2176 
2177  // if the parent was a toolbox set it as an itemwindow for the latest itemid
2178  if (pToolBox)
2179  {
2180  Size aSize(xWindow->GetSizePixel());
2181  aSize.setHeight(xWindow->get_preferred_size().Height());
2182  xWindow->SetSizePixel(aSize);
2183  pToolBox->SetItemWindow(m_pParserState->m_nLastToolbarId, xWindow);
2184  pToolBox->SetItemExpand(m_pParserState->m_nLastToolbarId, true);
2185  }
2186  }
2187  return xWindow;
2188 }
2189 
2190 namespace
2191 {
2192  //return true for window types which exist in vcl but are not themselves
2193  //represented in the .ui format, i.e. only their children exist.
2194  bool isConsideredGtkPseudo(vcl::Window const *pWindow)
2195  {
2196  return pWindow->GetType() == WindowType::TABPAGE;
2197  }
2198 }
2199 
2200 //Any properties from .ui load we couldn't set because of potential virtual methods
2201 //during ctor are applied here
2203 {
2205  return;
2206  stringmap aDeferredProperties;
2207  aDeferredProperties.swap(m_aDeferredProperties);
2209  BuilderUtils::set_properties(m_pParent, aDeferredProperties);
2210 }
2211 
2212 namespace BuilderUtils
2213 {
2214  void set_properties(vcl::Window *pWindow, const VclBuilder::stringmap &rProps)
2215  {
2216  for (auto const& prop : rProps)
2217  {
2218  const OString &rKey = prop.first;
2219  const OUString &rValue = prop.second;
2220  pWindow->set_property(rKey, rValue);
2221  }
2222  }
2223 
2224  OUString convertMnemonicMarkup(std::u16string_view rIn)
2225  {
2226  OUStringBuffer aRet(rIn);
2227  for (sal_Int32 nI = 0; nI < aRet.getLength(); ++nI)
2228  {
2229  if (aRet[nI] == '_' && nI+1 < aRet.getLength())
2230  {
2231  if (aRet[nI+1] != '_')
2232  aRet[nI] = MNEMONIC_CHAR;
2233  else
2234  aRet.remove(nI, 1);
2235  ++nI;
2236  }
2237  }
2238  return aRet.makeStringAndClear();
2239  }
2240 
2242  {
2243  OUString sCustomProperty;
2244  VclBuilder::stringmap::iterator aFind = rMap.find(OString("customproperty"));
2245  if (aFind != rMap.end())
2246  {
2247  sCustomProperty = aFind->second;
2248  rMap.erase(aFind);
2249  }
2250  return sCustomProperty;
2251  }
2252 
2254  {
2255  OString sWidthChars("width-chars");
2256  VclBuilder::stringmap::iterator aFind = rMap.find(sWidthChars);
2257  if (aFind == rMap.end())
2258  rMap[sWidthChars] = "20";
2259  }
2260 
2262  {
2263  bool bDropdown = true;
2264  VclBuilder::stringmap::iterator aFind = rMap.find(OString("dropdown"));
2265  if (aFind != rMap.end())
2266  {
2267  bDropdown = toBool(aFind->second);
2268  rMap.erase(aFind);
2269  }
2270  return bDropdown;
2271  }
2272 
2273  void reorderWithinParent(vcl::Window &rWindow, sal_uInt16 nNewPosition)
2274  {
2275  WindowImpl *pWindowImpl = rWindow.ImplGetWindowImpl();
2276  if (pWindowImpl->mpParent != pWindowImpl->mpRealParent)
2277  {
2278  assert(pWindowImpl->mpBorderWindow == pWindowImpl->mpParent);
2279  assert(pWindowImpl->mpBorderWindow->ImplGetWindowImpl()->mpParent == pWindowImpl->mpRealParent);
2280  reorderWithinParent(*pWindowImpl->mpBorderWindow, nNewPosition);
2281  return;
2282  }
2283  rWindow.reorderWithinParent(nNewPosition);
2284  }
2285 
2286  void reorderWithinParent(std::vector<vcl::Window*>& rChilds, bool bIsButtonBox)
2287  {
2288  for (size_t i = 0; i < rChilds.size(); ++i)
2289  {
2290  reorderWithinParent(*rChilds[i], i);
2291 
2292  if (!bIsButtonBox)
2293  continue;
2294 
2295  //The first member of the group for legacy code needs WB_GROUP set and the
2296  //others not
2297  WinBits nBits = rChilds[i]->GetStyle();
2298  nBits &= ~WB_GROUP;
2299  if (i == 0)
2300  nBits |= WB_GROUP;
2301  rChilds[i]->SetStyle(nBits);
2302  }
2303  }
2304 
2305  sal_Int16 getRoleFromName(const OString& roleName)
2306  {
2307  using namespace com::sun::star::accessibility;
2308 
2309  static const std::unordered_map<OString, sal_Int16> aAtkRoleToAccessibleRole = {
2310  /* This is in atkobject.h's AtkRole order */
2311  { "invalid", AccessibleRole::UNKNOWN },
2312  { "accelerator label", AccessibleRole::UNKNOWN },
2313  { "alert", AccessibleRole::ALERT },
2314  { "animation", AccessibleRole::UNKNOWN },
2315  { "arrow", AccessibleRole::UNKNOWN },
2316  { "calendar", AccessibleRole::UNKNOWN },
2317  { "canvas", AccessibleRole::CANVAS },
2318  { "check box", AccessibleRole::CHECK_BOX },
2319  { "check menu item", AccessibleRole::CHECK_MENU_ITEM },
2320  { "color chooser", AccessibleRole::COLOR_CHOOSER },
2321  { "column header", AccessibleRole::COLUMN_HEADER },
2322  { "combo box", AccessibleRole::COMBO_BOX },
2323  { "date editor", AccessibleRole::DATE_EDITOR },
2324  { "desktop icon", AccessibleRole::DESKTOP_ICON },
2325  { "desktop frame", AccessibleRole::DESKTOP_PANE }, // ?
2326  { "dial", AccessibleRole::UNKNOWN },
2327  { "dialog", AccessibleRole::DIALOG },
2328  { "directory pane", AccessibleRole::DIRECTORY_PANE },
2329  { "drawing area", AccessibleRole::UNKNOWN },
2330  { "file chooser", AccessibleRole::FILE_CHOOSER },
2331  { "filler", AccessibleRole::FILLER },
2332  { "font chooser", AccessibleRole::FONT_CHOOSER },
2333  { "frame", AccessibleRole::FRAME },
2334  { "glass pane", AccessibleRole::GLASS_PANE },
2335  { "html container", AccessibleRole::UNKNOWN },
2336  { "icon", AccessibleRole::ICON },
2337  { "image", AccessibleRole::GRAPHIC },
2338  { "internal frame", AccessibleRole::INTERNAL_FRAME },
2339  { "label", AccessibleRole::LABEL },
2340  { "layered pane", AccessibleRole::LAYERED_PANE },
2341  { "list", AccessibleRole::LIST },
2342  { "list item", AccessibleRole::LIST_ITEM },
2343  { "menu", AccessibleRole::MENU },
2344  { "menu bar", AccessibleRole::MENU_BAR },
2345  { "menu item", AccessibleRole::MENU_ITEM },
2346  { "option pane", AccessibleRole::OPTION_PANE },
2347  { "page tab", AccessibleRole::PAGE_TAB },
2348  { "page tab list", AccessibleRole::PAGE_TAB_LIST },
2349  { "panel", AccessibleRole::PANEL }, // or SHAPE or TEXT_FRAME ?
2350  { "password text", AccessibleRole::PASSWORD_TEXT },
2351  { "popup menu", AccessibleRole::POPUP_MENU },
2352  { "progress bar", AccessibleRole::PROGRESS_BAR },
2353  { "push button", AccessibleRole::PUSH_BUTTON }, // or BUTTON_DROPDOWN or BUTTON_MENU
2354  { "radio button", AccessibleRole::RADIO_BUTTON },
2355  { "radio menu item", AccessibleRole::RADIO_MENU_ITEM },
2356  { "root pane", AccessibleRole::ROOT_PANE },
2357  { "row header", AccessibleRole::ROW_HEADER },
2358  { "scroll bar", AccessibleRole::SCROLL_BAR },
2359  { "scroll pane", AccessibleRole::SCROLL_PANE },
2360  { "separator", AccessibleRole::SEPARATOR },
2361  { "slider", AccessibleRole::SLIDER },
2362  { "split pane", AccessibleRole::SPLIT_PANE },
2363  { "spin button", AccessibleRole::SPIN_BOX }, // ?
2364  { "statusbar", AccessibleRole::STATUS_BAR },
2365  { "table", AccessibleRole::TABLE },
2366  { "table cell", AccessibleRole::TABLE_CELL },
2367  { "table column header", AccessibleRole::COLUMN_HEADER }, // approximate
2368  { "table row header", AccessibleRole::ROW_HEADER }, // approximate
2369  { "tear off menu item", AccessibleRole::UNKNOWN },
2370  { "terminal", AccessibleRole::UNKNOWN },
2371  { "text", AccessibleRole::TEXT },
2372  { "toggle button", AccessibleRole::TOGGLE_BUTTON },
2373  { "tool bar", AccessibleRole::TOOL_BAR },
2374  { "tool tip", AccessibleRole::TOOL_TIP },
2375  { "tree", AccessibleRole::TREE },
2376  { "tree table", AccessibleRole::TREE_TABLE },
2377  { "unknown", AccessibleRole::UNKNOWN },
2378  { "viewport", AccessibleRole::VIEW_PORT },
2379  { "window", AccessibleRole::WINDOW },
2380  { "header", AccessibleRole::HEADER },
2381  { "footer", AccessibleRole::FOOTER },
2382  { "paragraph", AccessibleRole::PARAGRAPH },
2383  { "ruler", AccessibleRole::RULER },
2384  { "application", AccessibleRole::UNKNOWN },
2385  { "autocomplete", AccessibleRole::UNKNOWN },
2386  { "edit bar", AccessibleRole::EDIT_BAR },
2387  { "embedded", AccessibleRole::EMBEDDED_OBJECT },
2388  { "entry", AccessibleRole::UNKNOWN },
2389  { "chart", AccessibleRole::CHART },
2390  { "caption", AccessibleRole::CAPTION },
2391  { "document frame", AccessibleRole::DOCUMENT },
2392  { "heading", AccessibleRole::HEADING },
2393  { "page", AccessibleRole::PAGE },
2394  { "section", AccessibleRole::SECTION },
2395  { "redundant object", AccessibleRole::UNKNOWN },
2396  { "form", AccessibleRole::FORM },
2397  { "link", AccessibleRole::HYPER_LINK },
2398  { "input method window", AccessibleRole::UNKNOWN },
2399  { "table row", AccessibleRole::UNKNOWN },
2400  { "tree item", AccessibleRole::TREE_ITEM },
2401  { "document spreadsheet", AccessibleRole::DOCUMENT_SPREADSHEET },
2402  { "document presentation", AccessibleRole::DOCUMENT_PRESENTATION },
2403  { "document text", AccessibleRole::DOCUMENT_TEXT },
2404  { "document web", AccessibleRole::DOCUMENT }, // approximate
2405  { "document email", AccessibleRole::DOCUMENT }, // approximate
2406  { "comment", AccessibleRole::COMMENT }, // or NOTE or END_NOTE or FOOTNOTE or SCROLL_PANE
2407  { "list box", AccessibleRole::UNKNOWN },
2408  { "grouping", AccessibleRole::GROUP_BOX },
2409  { "image map", AccessibleRole::IMAGE_MAP },
2410  { "notification", AccessibleRole::UNKNOWN },
2411  { "info bar", AccessibleRole::UNKNOWN },
2412  { "level bar", AccessibleRole::UNKNOWN },
2413  { "title bar", AccessibleRole::UNKNOWN },
2414  { "block quote", AccessibleRole::UNKNOWN },
2415  { "audio", AccessibleRole::UNKNOWN },
2416  { "video", AccessibleRole::UNKNOWN },
2417  { "definition", AccessibleRole::UNKNOWN },
2418  { "article", AccessibleRole::UNKNOWN },
2419  { "landmark", AccessibleRole::UNKNOWN },
2420  { "log", AccessibleRole::UNKNOWN },
2421  { "marquee", AccessibleRole::UNKNOWN },
2422  { "math", AccessibleRole::UNKNOWN },
2423  { "rating", AccessibleRole::UNKNOWN },
2424  { "timer", AccessibleRole::UNKNOWN },
2425  { "description list", AccessibleRole::UNKNOWN },
2426  { "description term", AccessibleRole::UNKNOWN },
2427  { "description value", AccessibleRole::UNKNOWN },
2428  { "static", AccessibleRole::STATIC },
2429  { "math fraction", AccessibleRole::UNKNOWN },
2430  { "math root", AccessibleRole::UNKNOWN },
2431  { "subscript", AccessibleRole::UNKNOWN },
2432  { "superscript", AccessibleRole::UNKNOWN },
2433  { "footnote", AccessibleRole::FOOTNOTE },
2434  };
2435 
2436  auto it = aAtkRoleToAccessibleRole.find(roleName);
2437  if (it == aAtkRoleToAccessibleRole.end())
2438  return AccessibleRole::UNKNOWN;
2439  return it->second;
2440  }
2441 }
2442 
2444  const OString &rID, stringmap &rProps, stringmap &rPango, stringmap &rAtk)
2445 {
2446  VclPtr<vcl::Window> pCurrentChild;
2447 
2448  if (m_pParent && !isConsideredGtkPseudo(m_pParent) && !m_sID.isEmpty() && rID == m_sID)
2449  {
2450  pCurrentChild = m_pParent;
2451 
2452  //toplevels default to resizable and apparently you can't change them
2453  //afterwards, so we need to wait until now before we can truly
2454  //initialize the dialog.
2455  if (pParent && pParent->IsSystemWindow())
2456  {
2457  SystemWindow *pSysWin = static_cast<SystemWindow*>(pCurrentChild.get());
2458  pSysWin->doDeferredInit(extractDeferredBits(rProps));
2459  m_bToplevelHasDeferredInit = false;
2460  }
2461  else if (pParent && pParent->IsDockingWindow())
2462  {
2463  DockingWindow *pDockWin = static_cast<DockingWindow*>(pCurrentChild.get());
2464  pDockWin->doDeferredInit(extractDeferredBits(rProps));
2465  m_bToplevelHasDeferredInit = false;
2466  }
2467 
2468  if (pCurrentChild->GetHelpId().isEmpty())
2469  {
2470  pCurrentChild->SetHelpId(m_sHelpRoot + m_sID);
2471  SAL_INFO("vcl.builder", "for toplevel dialog " << this << " " <<
2472  rID << ", set helpid " << pCurrentChild->GetHelpId());
2473  }
2474  m_bToplevelParentFound = true;
2475  }
2476  else
2477  {
2478  //if we're being inserting under a toplevel dialog whose init is
2479  //deferred due to waiting to encounter it in this .ui, and it hasn't
2480  //been seen yet, then make unattached widgets parent-less toplevels
2481  if (pParent == m_pParent.get() && m_bToplevelHasDeferredInit)
2482  pParent = nullptr;
2483  pCurrentChild = makeObject(pParent, rClass, rID, rProps);
2484  }
2485 
2486  if (pCurrentChild)
2487  {
2488  pCurrentChild->set_id(OStringToOUString(rID, RTL_TEXTENCODING_UTF8));
2489  if (pCurrentChild == m_pParent.get() && m_bToplevelHasDeferredProperties)
2490  m_aDeferredProperties = rProps;
2491  else
2492  BuilderUtils::set_properties(pCurrentChild, rProps);
2493 
2494  // tdf#119827 handle size before scale so we can trivially
2495  // scale on the current font size whether size is present
2496  // or not.
2497  VclBuilder::stringmap::iterator aSize = rPango.find(OString("size"));
2498  if (aSize != rPango.end())
2499  {
2500  pCurrentChild->set_font_attribute(aSize->first, aSize->second);
2501  rPango.erase(aSize);
2502  }
2503  for (auto const& elem : rPango)
2504  {
2505  const OString &rKey = elem.first;
2506  const OUString &rValue = elem.second;
2507  pCurrentChild->set_font_attribute(rKey, rValue);
2508  }
2509 
2510  m_pParserState->m_aAtkInfo[pCurrentChild] = rAtk;
2511  }
2512 
2513  rProps.clear();
2514  rPango.clear();
2515  rAtk.clear();
2516 
2517  if (!pCurrentChild)
2518  {
2519  bool bToolbarParent = (pParent && pParent->GetType() == WindowType::TOOLBOX);
2520  pCurrentChild = (m_aChildren.empty() || bToolbarParent) ? pParent : m_aChildren.back().m_pWindow.get();
2521  }
2522  return pCurrentChild;
2523 }
2524 
2526 {
2527  TabControl *pTabControl = pParent && pParent->GetType() == WindowType::TABCONTROL ?
2528  static_cast<TabControl*>(pParent) : nullptr;
2529 
2530  std::vector<OString> sIDs;
2531 
2532  int nLevel = 1;
2534  stringmap aAtkProperties;
2535  std::vector<vcl::EnumContext::Context> context;
2536 
2537  while(true)
2538  {
2539  xmlreader::Span name;
2540  int nsId;
2541 
2543  xmlreader::XmlReader::Text::NONE, &name, &nsId);
2544 
2546  {
2547  ++nLevel;
2548  if (name == "object")
2549  {
2550  while (reader.nextAttribute(&nsId, &name))
2551  {
2552  if (name == "id")
2553  {
2554  name = reader.getAttributeValue(false);
2555  OString sID(name.begin, name.length);
2556  sal_Int32 nDelim = sID.indexOf(':');
2557  if (nDelim != -1)
2558  {
2559  OString sPattern = sID.copy(nDelim+1);
2560  aProperties[OString("customproperty")] = OUString::fromUtf8(sPattern);
2561  sID = sID.copy(0, nDelim);
2562  }
2563  sIDs.push_back(sID);
2564  }
2565  }
2566  }
2567  else if (name == "style")
2568  {
2569  int nPriority = 0;
2570  context = handleStyle(reader, nPriority);
2571  --nLevel;
2572  }
2573  else if (name == "property")
2574  collectProperty(reader, aProperties);
2575  else if (pTabControl && name == "child")
2576  {
2577  // just to collect the atk properties (if any) for the label
2578  handleChild(nullptr, &aAtkProperties, reader);
2579  --nLevel;
2580  }
2581  }
2582 
2584  --nLevel;
2585 
2586  if (!nLevel)
2587  break;
2588 
2590  break;
2591  }
2592 
2593  if (!pParent)
2594  return;
2595 
2596  VerticalTabControl *pVerticalTabControl = pParent->GetType() == WindowType::VERTICALTABCONTROL ?
2597  static_cast<VerticalTabControl*>(pParent) : nullptr;
2598  assert(pTabControl || pVerticalTabControl);
2599  VclBuilder::stringmap::iterator aFind = aProperties.find(OString("label"));
2600  if (aFind != aProperties.end())
2601  {
2602  OUString sTooltip(extractTooltipText(aProperties));
2603  if (pTabControl)
2604  {
2605  sal_uInt16 nPageId = pTabControl->GetCurPageId();
2606  pTabControl->SetPageText(nPageId, aFind->second);
2607  pTabControl->SetPageName(nPageId, sIDs.back());
2608  pTabControl->SetHelpText(nPageId, sTooltip);
2609  if (!context.empty())
2610  {
2611  TabPage* pPage = pTabControl->GetTabPage(nPageId);
2612  pPage->SetContext(std::move(context));
2613  }
2614 
2615  for (auto const& prop : aAtkProperties)
2616  {
2617  const OString &rKey = prop.first;
2618  const OUString &rValue = prop.second;
2619 
2620  if (rKey == "AtkObject::accessible-name")
2621  pTabControl->SetAccessibleName(nPageId, rValue);
2622  else if (rKey == "AtkObject::accessible-description")
2623  pTabControl->SetAccessibleDescription(nPageId, rValue);
2624  else
2625  SAL_INFO("vcl.builder", "unhandled atk property: " << rKey);
2626  }
2627 
2628  }
2629  else
2630  {
2631  OUString sLabel(BuilderUtils::convertMnemonicMarkup(aFind->second));
2632  OUString sIconName(extractIconName(aProperties));
2633  pVerticalTabControl->InsertPage(sIDs.front(), sLabel, FixedImage::loadThemeImage(sIconName), sTooltip,
2634  pVerticalTabControl->GetPageParent()->GetWindow(GetWindowType::LastChild));
2635  }
2636  }
2637  else
2638  {
2639  if (pTabControl)
2640  pTabControl->RemovePage(pTabControl->GetCurPageId());
2641  }
2642 }
2643 
2644 //so that tabbing between controls goes in a visually sensible sequence
2645 //we sort these into a best-tab-order sequence
2647 {
2648  //sort child order within parent list by grid position
2649  sal_Int32 nTopA = pA->get_grid_top_attach();
2650  sal_Int32 nTopB = pB->get_grid_top_attach();
2651  if (nTopA < nTopB)
2652  return true;
2653  if (nTopA > nTopB)
2654  return false;
2655  sal_Int32 nLeftA = pA->get_grid_left_attach();
2656  sal_Int32 nLeftB = pB->get_grid_left_attach();
2657  if (nLeftA < nLeftB)
2658  return true;
2659  if (nLeftA > nLeftB)
2660  return false;
2661  //sort into two groups of pack start and pack end
2662  VclPackType ePackA = pA->get_pack_type();
2663  VclPackType ePackB = pB->get_pack_type();
2664  if (ePackA < ePackB)
2665  return true;
2666  if (ePackA > ePackB)
2667  return false;
2668  bool bVerticalContainer = m_pBuilder->get_window_packing_data(pA->GetParent()).m_bVerticalOrient;
2669  bool bPackA = pA->get_secondary();
2670  bool bPackB = pB->get_secondary();
2671  if (!bVerticalContainer)
2672  {
2673  //for horizontal boxes group secondaries before primaries
2674  if (bPackA > bPackB)
2675  return true;
2676  if (bPackA < bPackB)
2677  return false;
2678  }
2679  else
2680  {
2681  //for vertical boxes group secondaries after primaries
2682  if (bPackA < bPackB)
2683  return true;
2684  if (bPackA > bPackB)
2685  return false;
2686  }
2687  //honour relative box positions with pack group, (numerical order is reversed
2688  //for VclPackType::End, they are packed from the end back, but here we need
2689  //them in visual layout order so that tabbing works as expected)
2690  sal_Int32 nPackA = m_pBuilder->get_window_packing_data(pA).m_nPosition;
2691  sal_Int32 nPackB = m_pBuilder->get_window_packing_data(pB).m_nPosition;
2692  if (nPackA < nPackB)
2693  return ePackA == VclPackType::Start;
2694  if (nPackA > nPackB)
2695  return ePackA != VclPackType::Start;
2696  //sort labels of Frames before body
2697  if (pA->GetParent() == pB->GetParent())
2698  {
2699  const VclFrame *pFrameParent = dynamic_cast<const VclFrame*>(pA->GetParent());
2700  if (pFrameParent)
2701  {
2702  const vcl::Window *pLabel = pFrameParent->get_label_widget();
2703  int nFramePosA = (pA == pLabel) ? 0 : 1;
2704  int nFramePosB = (pB == pLabel) ? 0 : 1;
2705  return nFramePosA < nFramePosB;
2706  }
2707  }
2708  return false;
2709 }
2710 
2712 {
2713  vcl::Window *pCurrentChild = nullptr;
2714 
2715  xmlreader::Span name;
2716  int nsId;
2717  OString sType, sInternalChild;
2718 
2719  while (reader.nextAttribute(&nsId, &name))
2720  {
2721  if (name == "type")
2722  {
2723  name = reader.getAttributeValue(false);
2724  sType = OString(name.begin, name.length);
2725  }
2726  else if (name == "internal-child")
2727  {
2728  name = reader.getAttributeValue(false);
2729  sInternalChild = OString(name.begin, name.length);
2730  }
2731  }
2732 
2733  if (sType == "tab")
2734  {
2735  handleTabChild(pParent, reader);
2736  return;
2737  }
2738 
2739  int nLevel = 1;
2740  while(true)
2741  {
2743  xmlreader::XmlReader::Text::NONE, &name, &nsId);
2744 
2746  {
2747  if (name == "object" || name == "placeholder")
2748  {
2749  pCurrentChild = handleObject(pParent, pAtkProps, reader).get();
2750 
2751  bool bObjectInserted = pCurrentChild && pParent != pCurrentChild;
2752 
2753  if (bObjectInserted)
2754  {
2755  //Internal-children default in glade to not having their visible bits set
2756  //even though they are visible (generally anyway)
2757  if (!sInternalChild.isEmpty())
2758  pCurrentChild->Show();
2759 
2760  //Select the first page if it's a notebook
2761  if (pCurrentChild->GetType() == WindowType::TABCONTROL)
2762  {
2763  TabControl *pTabControl = static_cast<TabControl*>(pCurrentChild);
2764  pTabControl->SetCurPageId(pTabControl->GetPageId(0));
2765 
2766  //To-Do add reorder capability to the TabControl
2767  }
2768  else
2769  {
2770  // We want to sort labels before contents of frames
2771  // for keyboard traversal, especially if there
2772  // are multiple widgets using the same mnemonic
2773  if (sType == "label")
2774  {
2775  if (VclFrame *pFrameParent = dynamic_cast<VclFrame*>(pParent))
2776  pFrameParent->designate_label(pCurrentChild);
2777  }
2778  if (sInternalChild.startsWith("vbox") || sInternalChild.startsWith("messagedialog-vbox"))
2779  {
2780  if (Dialog *pBoxParent = dynamic_cast<Dialog*>(pParent))
2781  pBoxParent->set_content_area(static_cast<VclBox*>(pCurrentChild)); // FIXME-VCLPTR
2782  }
2783  else if (sInternalChild.startsWith("action_area") || sInternalChild.startsWith("messagedialog-action_area"))
2784  {
2785  vcl::Window *pContentArea = pCurrentChild->GetParent();
2786  if (Dialog *pBoxParent = dynamic_cast<Dialog*>(pContentArea ? pContentArea->GetParent() : nullptr))
2787  {
2788  pBoxParent->set_action_area(static_cast<VclButtonBox*>(pCurrentChild)); // FIXME-VCLPTR
2789  }
2790  }
2791 
2792  bool bIsButtonBox = dynamic_cast<VclButtonBox*>(pCurrentChild) != nullptr;
2793 
2794  //To-Do make reorder a virtual in Window, move this foo
2795  //there and see above
2796  std::vector<vcl::Window*> aChilds;
2797  for (vcl::Window* pChild = pCurrentChild->GetWindow(GetWindowType::FirstChild); pChild;
2798  pChild = pChild->GetWindow(GetWindowType::Next))
2799  {
2800  if (bIsButtonBox)
2801  {
2802  if (PushButton* pPushButton = dynamic_cast<PushButton*>(pChild))
2803  pPushButton->setAction(true);
2804  }
2805 
2806  aChilds.push_back(pChild);
2807  }
2808 
2809  //sort child order within parent so that tabbing
2810  //between controls goes in a visually sensible sequence
2811  std::stable_sort(aChilds.begin(), aChilds.end(), sortIntoBestTabTraversalOrder(this));
2812  BuilderUtils::reorderWithinParent(aChilds, bIsButtonBox);
2813  }
2814  }
2815  }
2816  else if (name == "packing")
2817  {
2818  handlePacking(pCurrentChild, pParent, reader);
2819  }
2820  else if (name == "interface")
2821  {
2822  while (reader.nextAttribute(&nsId, &name))
2823  {
2824  if (name == "domain")
2825  {
2826  name = reader.getAttributeValue(false);
2827  sType = OString(name.begin, name.length);
2828  m_pParserState->m_aResLocale = Translate::Create(sType);
2829  }
2830  }
2831  ++nLevel;
2832  }
2833  else
2834  ++nLevel;
2835  }
2836 
2838  --nLevel;
2839 
2840  if (!nLevel)
2841  break;
2842 
2844  break;
2845  }
2846 }
2847 
2849 {
2850  xmlreader::Span span;
2851  int nsId;
2852 
2853  OString sProperty;
2854  OString sValue;
2855 
2856  while (reader.nextAttribute(&nsId, &span))
2857  {
2858  if (span == "name")
2859  {
2860  span = reader.getAttributeValue(false);
2861  sProperty = OString(span.begin, span.length);
2862  }
2863  else if (span == "value")
2864  {
2865  span = reader.getAttributeValue(false);
2866  sValue = OString(span.begin, span.length);
2867  }
2868  }
2869 
2870  if (!sProperty.isEmpty())
2871  rMap[sProperty] = OUString::fromUtf8(sValue);
2872 }
2873 
2875 {
2876  xmlreader::Span span;
2877  int nsId;
2878 
2879  OString sProperty;
2880  OString sValue;
2881 
2882  while (reader.nextAttribute(&nsId, &span))
2883  {
2884  if (span == "type")
2885  {
2886  span = reader.getAttributeValue(false);
2887  sProperty = OString(span.begin, span.length);
2888  }
2889  else if (span == "target")
2890  {
2891  span = reader.getAttributeValue(false);
2892  sValue = OString(span.begin, span.length);
2893  sal_Int32 nDelim = sValue.indexOf(':');
2894  if (nDelim != -1)
2895  sValue = sValue.copy(0, nDelim);
2896  }
2897  }
2898 
2899  if (!sProperty.isEmpty())
2900  rMap[sProperty] = OUString::fromUtf8(sValue);
2901 }
2902 
2904 {
2905  xmlreader::Span span;
2906  int nsId;
2907 
2908  OString sProperty;
2909 
2910  while (reader.nextAttribute(&nsId, &span))
2911  {
2912  if (span == "type")
2913  {
2914  span = reader.getAttributeValue(false);
2915  sProperty = OString(span.begin, span.length);
2916  }
2917  }
2918 
2919  if (!sProperty.isEmpty())
2920  rMap["role"] = OUString::fromUtf8(sProperty);
2921 }
2922 
2923 void VclBuilder::handleRow(xmlreader::XmlReader &reader, const OString &rID)
2924 {
2925  int nLevel = 1;
2926 
2927  ListStore::row aRow;
2928 
2929  while(true)
2930  {
2931  xmlreader::Span name;
2932  int nsId;
2933 
2935  xmlreader::XmlReader::Text::NONE, &name, &nsId);
2936 
2938  break;
2939 
2941  {
2942  ++nLevel;
2943  if (name == "col")
2944  {
2945  bool bTranslated = false;
2946  sal_uInt32 nId = 0;
2947  OString sContext;
2948 
2949  while (reader.nextAttribute(&nsId, &name))
2950  {
2951  if (name == "id")
2952  {
2953  name = reader.getAttributeValue(false);
2954  nId = OString(name.begin, name.length).toUInt32();
2955  }
2956  else if (nId == 0 && name == "translatable" && reader.getAttributeValue(false) == "yes")
2957  {
2958  bTranslated = true;
2959  }
2960  else if (name == "context")
2961  {
2962  name = reader.getAttributeValue(false);
2963  sContext = OString(name.begin, name.length);
2964  }
2965  }
2966 
2967  (void)reader.nextItem(
2968  xmlreader::XmlReader::Text::Raw, &name, &nsId);
2969 
2970  OString sValue(name.begin, name.length);
2971  OUString sFinalValue;
2972  if (bTranslated)
2973  {
2974  sFinalValue = Translate::get(TranslateId{sContext.getStr(), sValue.getStr()}, m_pParserState->m_aResLocale);
2975  }
2976  else
2977  sFinalValue = OUString::fromUtf8(sValue);
2978 
2979 
2980  if (aRow.size() < nId+1)
2981  aRow.resize(nId+1);
2982  aRow[nId] = sFinalValue;
2983  }
2984  }
2985 
2987  {
2988  --nLevel;
2989  }
2990 
2991  if (!nLevel)
2992  break;
2993  }
2994 
2995  m_pParserState->m_aModels[rID].m_aEntries.push_back(aRow);
2996 }
2997 
2998 void VclBuilder::handleListStore(xmlreader::XmlReader &reader, const OString &rID, std::string_view rClass)
2999 {
3000  int nLevel = 1;
3001 
3002  while(true)
3003  {
3004  xmlreader::Span name;
3005  int nsId;
3006 
3008  xmlreader::XmlReader::Text::NONE, &name, &nsId);
3009 
3011  break;
3012 
3014  {
3015  if (name == "row")
3016  {
3017  bool bNotTreeStore = rClass != "GtkTreeStore";
3018  if (bNotTreeStore)
3019  handleRow(reader, rID);
3020  assert(bNotTreeStore && "gtk, as the time of writing, doesn't support data in GtkTreeStore serialization");
3021  }
3022  else
3023  ++nLevel;
3024  }
3025 
3027  {
3028  --nLevel;
3029  }
3030 
3031  if (!nLevel)
3032  break;
3033  }
3034 }
3035 
3037 {
3038  int nLevel = 1;
3039 
3041 
3042  while (true)
3043  {
3044  xmlreader::Span name;
3045  int nsId;
3046 
3048  xmlreader::XmlReader::Text::NONE, &name, &nsId);
3049 
3051  break;
3052 
3054  {
3055  ++nLevel;
3056  if (name == "property")
3057  collectProperty(reader, aProperties);
3058  }
3059 
3061  {
3062  --nLevel;
3063  }
3064 
3065  if (!nLevel)
3066  break;
3067  }
3068 
3069  return aProperties;
3070 }
3071 
3072 void VclBuilder::applyAtkProperties(vcl::Window *pWindow, const stringmap& rProperties)
3073 {
3074  assert(pWindow);
3075  for (auto const& prop : rProperties)
3076  {
3077  const OString &rKey = prop.first;
3078  const OUString &rValue = prop.second;
3079 
3080  if (pWindow && rKey.match("AtkObject::"))
3081  pWindow->set_property(rKey.copy(RTL_CONSTASCII_LENGTH("AtkObject::")), rValue);
3082  else
3083  SAL_WARN("vcl.builder", "unhandled atk prop: " << rKey);
3084  }
3085 }
3086 
3087 std::vector<ComboBoxTextItem> VclBuilder::handleItems(xmlreader::XmlReader &reader) const
3088 {
3089  int nLevel = 1;
3090 
3091  std::vector<ComboBoxTextItem> aItems;
3092 
3093  while(true)
3094  {
3095  xmlreader::Span name;
3096  int nsId;
3097 
3099  xmlreader::XmlReader::Text::NONE, &name, &nsId);
3100 
3102  break;
3103 
3105  {
3106  ++nLevel;
3107  if (name == "item")
3108  {
3109  bool bTranslated = false;
3110  OString sContext, sId;
3111 
3112  while (reader.nextAttribute(&nsId, &name))
3113  {
3114  if (name == "translatable" && reader.getAttributeValue(false) == "yes")
3115  {
3116  bTranslated = true;
3117  }
3118  else if (name == "context")
3119  {
3120  name = reader.getAttributeValue(false);
3121  sContext = OString(name.begin, name.length);
3122  }
3123  else if (name == "id")
3124  {
3125  name = reader.getAttributeValue(false);
3126  sId = OString(name.begin, name.length);
3127  }
3128  }
3129 
3130  (void)reader.nextItem(
3131  xmlreader::XmlReader::Text::Raw, &name, &nsId);
3132 
3133  OString sValue(name.begin, name.length);
3134  OUString sFinalValue;
3135  if (bTranslated)
3136  {
3137  sFinalValue = Translate::get(TranslateId{sContext.getStr(), sValue.getStr()}, m_pParserState->m_aResLocale);
3138  }
3139  else
3140  sFinalValue = OUString::fromUtf8(sValue);
3141 
3142  if (m_pStringReplace)
3143  sFinalValue = (*m_pStringReplace)(sFinalValue);
3144 
3145  aItems.emplace_back(sFinalValue, sId);
3146  }
3147  }
3148 
3150  {
3151  --nLevel;
3152  }
3153 
3154  if (!nLevel)
3155  break;
3156  }
3157 
3158  return aItems;
3159 }
3160 
3161 VclPtr<Menu> VclBuilder::handleMenu(xmlreader::XmlReader &reader, const OString &rID, bool bMenuBar)
3162 {
3163  VclPtr<Menu> pCurrentMenu;
3164  if (bMenuBar)
3165  pCurrentMenu = VclPtr<MenuBar>::Create();
3166  else
3167  pCurrentMenu = VclPtr<PopupMenu>::Create();
3168 
3169  pCurrentMenu->set_id(OStringToOUString(rID, RTL_TEXTENCODING_UTF8));
3170 
3171  int nLevel = 1;
3172 
3174 
3175  while(true)
3176  {
3177  xmlreader::Span name;
3178  int nsId;
3179 
3181  xmlreader::XmlReader::Text::NONE, &name, &nsId);
3182 
3184  break;
3185 
3187  {
3188  if (name == "child")
3189  {
3190  handleMenuChild(pCurrentMenu, reader);
3191  }
3192  else
3193  {
3194  ++nLevel;
3195  if (name == "property")
3196  collectProperty(reader, aProperties);
3197  }
3198  }
3199 
3201  {
3202  --nLevel;
3203  }
3204 
3205  if (!nLevel)
3206  break;
3207  }
3208 
3209  m_aMenus.emplace_back(rID, pCurrentMenu);
3210 
3211  return pCurrentMenu;
3212 }
3213 
3215 {
3216  xmlreader::Span name;
3217  int nsId;
3218 
3219  int nLevel = 1;
3220  while(true)
3221  {
3223  xmlreader::XmlReader::Text::NONE, &name, &nsId);
3224 
3226  {
3227  if (name == "object" || name == "placeholder")
3228  {
3229  handleMenuObject(pParent, reader);
3230  }
3231  else
3232  ++nLevel;
3233  }
3234 
3236  --nLevel;
3237 
3238  if (!nLevel)
3239  break;
3240 
3242  break;
3243  }
3244 }
3245 
3247 {
3248  OString sClass;
3249  OString sID;
3250  OUString sCustomProperty;
3251  PopupMenu *pSubMenu = nullptr;
3252 
3253  xmlreader::Span name;
3254  int nsId;
3255 
3256  while (reader.nextAttribute(&nsId, &name))
3257  {
3258  if (name == "class")
3259  {
3260  name = reader.getAttributeValue(false);
3261  sClass = OString(name.begin, name.length);
3262  }
3263  else if (name == "id")
3264  {
3265  name = reader.getAttributeValue(false);
3266  sID = OString(name.begin, name.length);
3267  if (m_bLegacy)
3268  {
3269  sal_Int32 nDelim = sID.indexOf(':');
3270  if (nDelim != -1)
3271  {
3272  sCustomProperty = OUString::fromUtf8(sID.subView(nDelim+1));
3273  sID = sID.copy(0, nDelim);
3274  }
3275  }
3276  }
3277  }
3278 
3279  int nLevel = 1;
3280 
3282  stringmap aAtkProperties;
3283  accelmap aAccelerators;
3284 
3285  if (!sCustomProperty.isEmpty())
3286  aProperties[OString("customproperty")] = sCustomProperty;
3287 
3288  while(true)
3289  {
3291  xmlreader::XmlReader::Text::NONE, &name, &nsId);
3292 
3294  break;
3295 
3297  {
3298  if (name == "child")
3299  {
3300  size_t nChildMenuIdx = m_aMenus.size();
3301  handleChild(nullptr, &aAtkProperties, reader);
3302  bool bSubMenuInserted = m_aMenus.size() > nChildMenuIdx;
3303  if (bSubMenuInserted)
3304  pSubMenu = dynamic_cast<PopupMenu*>(m_aMenus[nChildMenuIdx].m_pMenu.get());
3305  }
3306  else
3307  {
3308  ++nLevel;
3309  if (name == "property")
3310  collectProperty(reader, aProperties);
3311  else if (name == "accelerator")
3312  collectAccelerator(reader, aAccelerators);
3313  }
3314  }
3315 
3317  {
3318  --nLevel;
3319  }
3320 
3321  if (!nLevel)
3322  break;
3323  }
3324 
3325  insertMenuObject(pParent, pSubMenu, sClass, sID, aProperties, aAtkProperties, aAccelerators);
3326 }
3327 
3329 {
3330  m_pParserState->m_aSizeGroups.emplace_back();
3331  SizeGroup &rSizeGroup = m_pParserState->m_aSizeGroups.back();
3332 
3333  int nLevel = 1;
3334 
3335  while(true)
3336  {
3337  xmlreader::Span name;
3338  int nsId;
3339 
3341  xmlreader::XmlReader::Text::NONE, &name, &nsId);
3342 
3344  break;
3345 
3347  {
3348  ++nLevel;
3349  if (name == "widget")
3350  {
3351  while (reader.nextAttribute(&nsId, &name))
3352  {
3353  if (name == "name")
3354  {
3355  name = reader.getAttributeValue(false);
3356  OString sWidget(name.begin, name.length);
3357  sal_Int32 nDelim = sWidget.indexOf(':');
3358  if (nDelim != -1)
3359  sWidget = sWidget.copy(0, nDelim);
3360  rSizeGroup.m_aWidgets.push_back(sWidget);
3361  }
3362  }
3363  }
3364  else
3365  {
3366  if (name == "property")
3367  collectProperty(reader, rSizeGroup.m_aProperties);
3368  }
3369  }
3370 
3372  {
3373  --nLevel;
3374  }
3375 
3376  if (!nLevel)
3377  break;
3378  }
3379 }
3380 
3381 namespace
3382 {
3383  vcl::KeyCode makeKeyCode(const std::pair<OString,OString> &rKey)
3384  {
3385  bool bShift = rKey.second.indexOf("GDK_SHIFT_MASK") != -1;
3386  bool bMod1 = rKey.second.indexOf("GDK_CONTROL_MASK") != -1;
3387  bool bMod2 = rKey.second.indexOf("GDK_ALT_MASK") != -1;
3388  bool bMod3 = rKey.second.indexOf("GDK_MOD2_MASK") != -1;
3389 
3390  if (rKey.first == "Insert")
3391  return vcl::KeyCode(KEY_INSERT, bShift, bMod1, bMod2, bMod3);
3392  else if (rKey.first == "Delete")
3393  return vcl::KeyCode(KEY_DELETE, bShift, bMod1, bMod2, bMod3);
3394  else if (rKey.first == "Return")
3395  return vcl::KeyCode(KEY_RETURN, bShift, bMod1, bMod2, bMod3);
3396  else if (rKey.first == "Up")
3397  return vcl::KeyCode(KEY_UP, bShift, bMod1, bMod2, bMod3);
3398  else if (rKey.first == "Down")
3399  return vcl::KeyCode(KEY_DOWN, bShift, bMod1, bMod2, bMod3);
3400  else if (rKey.first == "Left")
3401  return vcl::KeyCode(KEY_LEFT, bShift, bMod1, bMod2, bMod3);
3402  else if (rKey.first == "Right")
3403  return vcl::KeyCode(KEY_RIGHT, bShift, bMod1, bMod2, bMod3);
3404  else if (rKey.first == "asterisk")
3405  return vcl::KeyCode(KEY_MULTIPLY, bShift, bMod1, bMod2, bMod3);
3406  else if (rKey.first.getLength() > 1 && rKey.first[0] == 'F')
3407  {
3408  sal_uInt32 nIndex = o3tl::toUInt32(rKey.first.subView(1));
3409  assert(nIndex >= 1 && nIndex <= 26);
3410  return vcl::KeyCode(KEY_F1 + nIndex - 1, bShift, bMod1, bMod2, bMod3);
3411  }
3412 
3413  assert (rKey.first.getLength() == 1);
3414  char cChar = rKey.first.toChar();
3415 
3416  if (cChar >= 'a' && cChar <= 'z')
3417  return vcl::KeyCode(KEY_A + (cChar - 'a'), bShift, bMod1, bMod2, bMod3);
3418  else if (cChar >= 'A' && cChar <= 'Z')
3419  return vcl::KeyCode(KEY_A + (cChar - 'A'), bShift, bMod1, bMod2, bMod3);
3420  else if (cChar >= '0' && cChar <= '9')
3421  return vcl::KeyCode(KEY_0 + (cChar - 'A'), bShift, bMod1, bMod2, bMod3);
3422 
3423  return vcl::KeyCode(cChar, bShift, bMod1, bMod2, bMod3);
3424  }
3425 }
3426 
3427 void VclBuilder::insertMenuObject(Menu *pParent, PopupMenu *pSubMenu, const OString &rClass, const OString &rID,
3428  stringmap &rProps, stringmap &rAtkProps, accelmap &rAccels)
3429 {
3430  sal_uInt16 nOldCount = pParent->GetItemCount();
3431  sal_uInt16 nNewId = ++m_pParserState->m_nLastMenuItemId;
3432 
3433  if(rClass == "NotebookBarAddonsMenuMergePoint")
3434  {
3435  NotebookBarAddonsMerger::MergeNotebookBarMenuAddons(pParent, nNewId, rID, *m_pNotebookBarAddonsItem);
3436  m_pParserState->m_nLastMenuItemId = pParent->GetItemCount();
3437  }
3438  else if (rClass == "GtkMenuItem")
3439  {
3440  OUString sLabel(BuilderUtils::convertMnemonicMarkup(extractLabel(rProps)));
3441  OUString aCommand(extractActionName(rProps));
3442  pParent->InsertItem(nNewId, sLabel, MenuItemBits::NONE , rID);
3443  pParent->SetItemCommand(nNewId, aCommand);
3444  if (pSubMenu)
3445  pParent->SetPopupMenu(nNewId, pSubMenu);
3446  }
3447  else if (rClass == "GtkCheckMenuItem")
3448  {
3449  OUString sLabel(BuilderUtils::convertMnemonicMarkup(extractLabel(rProps)));
3450  OUString aCommand(extractActionName(rProps));
3451  pParent->InsertItem(nNewId, sLabel, MenuItemBits::CHECKABLE, rID);
3452  pParent->SetItemCommand(nNewId, aCommand);
3453  }
3454  else if (rClass == "GtkRadioMenuItem")
3455  {
3456  OUString sLabel(BuilderUtils::convertMnemonicMarkup(extractLabel(rProps)));
3457  OUString aCommand(extractActionName(rProps));
3458  pParent->InsertItem(nNewId, sLabel, MenuItemBits::AUTOCHECK | MenuItemBits::RADIOCHECK, rID);
3459  pParent->SetItemCommand(nNewId, aCommand);
3460  }
3461  else if (rClass == "GtkSeparatorMenuItem")
3462  {
3463  pParent->InsertSeparator(rID);
3464  }
3465 
3466  SAL_WARN_IF(nOldCount == pParent->GetItemCount(), "vcl.builder", "probably need to implement " << rClass);
3467 
3468  if (nOldCount != pParent->GetItemCount())
3469  {
3470  pParent->SetHelpId(nNewId, m_sHelpRoot + rID);
3471  if (!extractVisible(rProps))
3472  pParent->HideItem(nNewId);
3473 
3474  for (auto const& prop : rProps)
3475  {
3476  const OString &rKey = prop.first;
3477  const OUString &rValue = prop.second;
3478 
3479  if (rKey == "tooltip-markup")
3480  pParent->SetTipHelpText(nNewId, rValue);
3481  else if (rKey == "tooltip-text")
3482  pParent->SetTipHelpText(nNewId, rValue);
3483  else
3484  SAL_INFO("vcl.builder", "unhandled property: " << rKey);
3485  }
3486 
3487  for (auto const& prop : rAtkProps)
3488  {
3489  const OString &rKey = prop.first;
3490  const OUString &rValue = prop.second;
3491 
3492  if (rKey == "AtkObject::accessible-name")
3493  pParent->SetAccessibleName(nNewId, rValue);
3494  else if (rKey == "AtkObject::accessible-description")
3495  pParent->SetAccessibleDescription(nNewId, rValue);
3496  else
3497  SAL_INFO("vcl.builder", "unhandled atk property: " << rKey);
3498  }
3499 
3500  for (auto const& accel : rAccels)
3501  {
3502  const OString &rSignal = accel.first;
3503  const auto &rValue = accel.second;
3504 
3505  if (rSignal == "activate")
3506  pParent->SetAccelKey(nNewId, makeKeyCode(rValue));
3507  else
3508  SAL_INFO("vcl.builder", "unhandled accelerator for: " << rSignal);
3509  }
3510  }
3511 
3512  rProps.clear();
3513 }
3514 
3517 template<typename T> static bool insertItems(vcl::Window *pWindow, VclBuilder::stringmap &rMap,
3518  std::vector<std::unique_ptr<OUString>>& rUserData,
3519  const std::vector<ComboBoxTextItem> &rItems)
3520 {
3521  T *pContainer = dynamic_cast<T*>(pWindow);
3522  if (!pContainer)
3523  return false;
3524 
3525  sal_uInt16 nActiveId = extractActive(rMap);
3526  for (auto const& item : rItems)
3527  {
3528  sal_Int32 nPos = pContainer->InsertEntry(item.m_sItem);
3529  if (!item.m_sId.isEmpty())
3530  {
3531  rUserData.emplace_back(std::make_unique<OUString>(OUString::fromUtf8(item.m_sId)));
3532  pContainer->SetEntryData(nPos, rUserData.back().get());
3533  }
3534  }
3535  if (nActiveId < rItems.size())
3536  pContainer->SelectEntryPos(nActiveId);
3537 
3538  return true;
3539 }
3540 
3542 {
3543  OString sClass;
3544  OString sID;
3545  OUString sCustomProperty;
3546 
3547  xmlreader::Span name;
3548  int nsId;
3549 
3550  while (reader.nextAttribute(&nsId, &name))
3551  {
3552  if (name == "class")
3553  {
3554  name = reader.getAttributeValue(false);
3555  sClass = OString(name.begin, name.length);
3556  }
3557  else if (name == "id")
3558  {
3559  name = reader.getAttributeValue(false);
3560  sID = OString(name.begin, name.length);
3561  if (m_bLegacy)
3562  {
3563  sal_Int32 nDelim = sID.indexOf(':');
3564  if (nDelim != -1)
3565  {
3566  sCustomProperty = OUString::fromUtf8(sID.subView(nDelim+1));
3567  sID = sID.copy(0, nDelim);
3568  }
3569  }
3570  }
3571  }
3572 
3573  if (sClass == "GtkListStore" || sClass == "GtkTreeStore")
3574  {
3575  handleListStore(reader, sID, sClass);
3576  return nullptr;
3577  }
3578  else if (sClass == "GtkMenu")
3579  {
3580  handleMenu(reader, sID, false);
3581  return nullptr;
3582  }
3583  else if (sClass == "GtkMenuBar")
3584  {
3585  VclPtr<Menu> xMenu = handleMenu(reader, sID, true);
3586  if (SystemWindow* pTopLevel = pParent ? pParent->GetSystemWindow() : nullptr)
3587  pTopLevel->SetMenuBar(dynamic_cast<MenuBar*>(xMenu.get()));
3588  return nullptr;
3589  }
3590  else if (sClass == "GtkSizeGroup")
3591  {
3592  handleSizeGroup(reader);
3593  return nullptr;
3594  }
3595  else if (sClass == "AtkObject")
3596  {
3597  assert((pParent || pAtkProps) && "must have one set");
3598  assert(!(pParent && pAtkProps) && "must not have both");
3599  auto aAtkProperties = handleAtkObject(reader);
3600  if (pParent)
3601  applyAtkProperties(pParent, aAtkProperties);
3602  if (pAtkProps)
3603  *pAtkProps = aAtkProperties;
3604  return nullptr;
3605  }
3606 
3607  int nLevel = 1;
3608 
3609  stringmap aProperties, aPangoAttributes;
3610  stringmap aAtkAttributes;
3611  std::vector<ComboBoxTextItem> aItems;
3612 
3613  if (!sCustomProperty.isEmpty())
3614  aProperties[OString("customproperty")] = sCustomProperty;
3615 
3616  VclPtr<vcl::Window> pCurrentChild;
3617  while(true)
3618  {
3620  xmlreader::XmlReader::Text::NONE, &name, &nsId);
3621 
3623  break;
3624 
3626  {
3627  if (name == "child")
3628  {
3629  if (!pCurrentChild)
3630  {
3631  pCurrentChild = insertObject(pParent, sClass, sID,
3632  aProperties, aPangoAttributes, aAtkAttributes);
3633  }
3634  handleChild(pCurrentChild, nullptr, reader);
3635  }
3636  else if (name == "items")
3637  aItems = handleItems(reader);
3638  else if (name == "style")
3639  {
3640  int nPriority = 0;
3641  std::vector<vcl::EnumContext::Context> aContext = handleStyle(reader, nPriority);
3642  if (nPriority != 0)
3643  {
3644  vcl::IPrioritable* pPrioritable = dynamic_cast<vcl::IPrioritable*>(pCurrentChild.get());
3645  SAL_WARN_IF(!pPrioritable, "vcl", "priority set for not supported item");
3646  if (pPrioritable)
3647  pPrioritable->SetPriority(nPriority);
3648  }
3649  if (!aContext.empty())
3650  {
3651  vcl::IContext* pContextControl = dynamic_cast<vcl::IContext*>(pCurrentChild.get());
3652  SAL_WARN_IF(!pContextControl, "vcl", "context set for not supported item");
3653  if (pContextControl)
3654  pContextControl->SetContext(std::move(aContext));
3655  }
3656  }
3657  else
3658  {
3659  ++nLevel;
3660  if (name == "property")
3661  collectProperty(reader, aProperties);
3662  else if (name == "attribute")
3663  collectPangoAttribute(reader, aPangoAttributes);
3664  else if (name == "relation")
3665  collectAtkRelationAttribute(reader, aAtkAttributes);
3666  else if (name == "role")
3667  collectAtkRoleAttribute(reader, aAtkAttributes);
3668  else if (name == "action-widget")
3669  handleActionWidget(reader);
3670  }
3671  }
3672 
3674  {
3675  --nLevel;
3676  }
3677 
3678  if (!nLevel)
3679  break;
3680  }
3681 
3682  if (sClass == "GtkAdjustment")
3683  {
3684  m_pParserState->m_aAdjustments[sID] = aProperties;
3685  return nullptr;
3686  }
3687  else if (sClass == "GtkTextBuffer")
3688  {
3689  m_pParserState->m_aTextBuffers[sID] = aProperties;
3690  return nullptr;
3691  }
3692 
3693  if (!pCurrentChild)
3694  {
3695  pCurrentChild = insertObject(pParent, sClass, sID, aProperties,
3696  aPangoAttributes, aAtkAttributes);
3697  }
3698 
3699  if (!aItems.empty())
3700  {
3701  // try to fill-in the items
3702  if (!insertItems<ComboBox>(pCurrentChild, aProperties, m_aUserData, aItems))
3703  insertItems<ListBox>(pCurrentChild, aProperties, m_aUserData, aItems);
3704  }
3705 
3706  return pCurrentChild;
3707 }
3708 
3710 {
3711  xmlreader::Span name;
3712  int nsId;
3713 
3714  int nLevel = 1;
3715 
3716  while(true)
3717  {
3719  xmlreader::XmlReader::Text::NONE, &name, &nsId);
3720 
3722  break;
3723 
3725  {
3726  ++nLevel;
3727  if (name == "property")
3728  applyPackingProperty(pCurrent, pParent, reader);
3729  }
3730 
3732  {
3733  --nLevel;
3734  }
3735 
3736  if (!nLevel)
3737  break;
3738  }
3739 }
3740 
3742  vcl::Window *pParent,
3743  xmlreader::XmlReader &reader)
3744 {
3745  if (!pCurrent)
3746  return;
3747 
3748  //ToolBoxItems are not true widgets just elements
3749  //of the ToolBox itself
3750  ToolBox *pToolBoxParent = nullptr;
3751  if (pCurrent == pParent)
3752  pToolBoxParent = dynamic_cast<ToolBox*>(pParent);
3753 
3754  xmlreader::Span name;
3755  int nsId;
3756 
3757  if (pCurrent->GetType() == WindowType::SCROLLWINDOW)
3758  {
3759  auto aFind = m_pParserState->m_aRedundantParentWidgets.find(VclPtr<vcl::Window>(pCurrent));
3760  if (aFind != m_pParserState->m_aRedundantParentWidgets.end())
3761  {
3762  pCurrent = aFind->second;
3763  assert(pCurrent);
3764  }
3765  }
3766 
3767  while (reader.nextAttribute(&nsId, &name))
3768  {
3769  if (name == "name")
3770  {
3771  name = reader.getAttributeValue(false);
3772  OString sKey(name.begin, name.length);
3773  sKey = sKey.replace('_', '-');
3774  (void)reader.nextItem(
3775  xmlreader::XmlReader::Text::Raw, &name, &nsId);
3776  OString sValue(name.begin, name.length);
3777 
3778  if (sKey == "expand" || sKey == "resize")
3779  {
3780  bool bTrue = (!sValue.isEmpty() && (sValue[0] == 't' || sValue[0] == 'T' || sValue[0] == '1'));
3781  if (pToolBoxParent)
3782  pToolBoxParent->SetItemExpand(m_pParserState->m_nLastToolbarId, bTrue);
3783  else
3784  pCurrent->set_expand(bTrue);
3785  continue;
3786  }
3787 
3788  if (pToolBoxParent)
3789  continue;
3790 
3791  if (sKey == "fill")
3792  {
3793  bool bTrue = (!sValue.isEmpty() && (sValue[0] == 't' || sValue[0] == 'T' || sValue[0] == '1'));
3794  pCurrent->set_fill(bTrue);
3795  }
3796  else if (sKey == "pack-type")
3797  {
3798  VclPackType ePackType = (!sValue.isEmpty() && (sValue[0] == 'e' || sValue[0] == 'E')) ? VclPackType::End : VclPackType::Start;
3799  pCurrent->set_pack_type(ePackType);
3800  }
3801  else if (sKey == "left-attach")
3802  {
3803  pCurrent->set_grid_left_attach(sValue.toInt32());
3804  }
3805  else if (sKey == "top-attach")
3806  {
3807  pCurrent->set_grid_top_attach(sValue.toInt32());
3808  }
3809  else if (sKey == "width")
3810  {
3811  pCurrent->set_grid_width(sValue.toInt32());
3812  }
3813  else if (sKey == "height")
3814  {
3815  pCurrent->set_grid_height(sValue.toInt32());
3816  }
3817  else if (sKey == "padding")
3818  {
3819  pCurrent->set_padding(sValue.toInt32());
3820  }
3821  else if (sKey == "position")
3822  {
3823  set_window_packing_position(pCurrent, sValue.toInt32());
3824  }
3825  else if (sKey == "secondary")
3826  {
3827  pCurrent->set_secondary(toBool(sValue));
3828  }
3829  else if (sKey == "non-homogeneous")
3830  {
3831  pCurrent->set_non_homogeneous(toBool(sValue));
3832  }
3833  else if (sKey == "homogeneous")
3834  {
3835  pCurrent->set_non_homogeneous(!toBool(sValue));
3836  }
3837  else
3838  {
3839  SAL_WARN_IF(sKey != "shrink", "vcl.builder", "unknown packing: " << sKey);
3840  }
3841  }
3842  }
3843 }
3844 
3845 std::vector<vcl::EnumContext::Context> VclBuilder::handleStyle(xmlreader::XmlReader &reader, int &nPriority)
3846 {
3847  std::vector<vcl::EnumContext::Context> aContext;
3848 
3849  xmlreader::Span name;
3850  int nsId;
3851 
3852  int nLevel = 1;
3853 
3854  while(true)
3855  {
3857  xmlreader::XmlReader::Text::NONE, &name, &nsId);
3858 
3860  break;
3861 
3863  {
3864  ++nLevel;
3865  if (name == "class")
3866  {
3867  OString classStyle = getStyleClass(reader);
3868 
3869  if (classStyle.startsWith("context-"))
3870  {
3871  OString sContext = classStyle.copy(classStyle.indexOf('-') + 1);
3872  OUString sContext2(sContext.getStr(), sContext.getLength(), RTL_TEXTENCODING_UTF8);
3873  aContext.push_back(vcl::EnumContext::GetContextEnum(sContext2));
3874  }
3875  else if (classStyle.startsWith("priority-"))
3876  {
3877  OString aPriority = classStyle.copy(classStyle.indexOf('-') + 1);
3878  OUString aPriority2(aPriority.getStr(), aPriority.getLength(), RTL_TEXTENCODING_UTF8);
3879  nPriority = aPriority2.toInt32();
3880  }
3881  else if (classStyle != "small-button" && classStyle != "destructive-action" && classStyle != "suggested-action")
3882  {
3883  SAL_WARN("vcl.builder", "unknown class: " << classStyle);
3884  }
3885  }
3886  }
3887 
3889  {
3890  --nLevel;
3891  }
3892 
3893  if (!nLevel)
3894  break;
3895  }
3896 
3897  return aContext;
3898 }
3899 
3901 {
3902  xmlreader::Span name;
3903  int nsId;
3904  OString aRet;
3905 
3906  while (reader.nextAttribute(&nsId, &name))
3907  {
3908  if (name == "name")
3909  {
3910  name = reader.getAttributeValue(false);
3911  aRet = OString (name.begin, name.length);
3912  }
3913  }
3914 
3915  return aRet;
3916 }
3917 
3919 {
3920  xmlreader::Span name;
3921  int nsId;
3922 
3923  OString sProperty, sContext;
3924 
3925  bool bTranslated = false;
3926 
3927  while (reader.nextAttribute(&nsId, &name))
3928  {
3929  if (name == "name")
3930  {
3931  name = reader.getAttributeValue(false);
3932  sProperty = OString(name.begin, name.length);
3933  }
3934  else if (name == "context")
3935  {
3936  name = reader.getAttributeValue(false);
3937  sContext = OString(name.begin, name.length);
3938  }
3939  else if (name == "translatable" && reader.getAttributeValue(false) == "yes")
3940  {
3941  bTranslated = true;
3942  }
3943  }
3944 
3945  (void)reader.nextItem(xmlreader::XmlReader::Text::Raw, &name, &nsId);
3946  OString sValue(name.begin, name.length);
3947  OUString sFinalValue;
3948  if (bTranslated)
3949  {
3950  sFinalValue = Translate::get(TranslateId{sContext.getStr(), sValue.getStr()}, m_pParserState->m_aResLocale);
3951  }
3952  else
3953  sFinalValue = OUString::fromUtf8(sValue);
3954 
3955  if (!sProperty.isEmpty())
3956  {
3957  sProperty = sProperty.replace('_', '-');
3958  if (m_pStringReplace)
3959  sFinalValue = (*m_pStringReplace)(sFinalValue);
3960  rMap[sProperty] = sFinalValue;
3961  }
3962 }
3963 
3965 {
3966  xmlreader::Span name;
3967  int nsId;
3968 
3969  OString sResponse;
3970 
3971  while (reader.nextAttribute(&nsId, &name))
3972  {
3973  if (name == "response")
3974  {
3975  name = reader.getAttributeValue(false);
3976  sResponse = OString(name.begin, name.length);
3977  }
3978  }
3979 
3980  (void)reader.nextItem(xmlreader::XmlReader::Text::Raw, &name, &nsId);
3981  OString sID(name.begin, name.length);
3982  sal_Int32 nDelim = sID.indexOf(':');
3983  if (nDelim != -1)
3984  sID = sID.copy(0, nDelim);
3985  set_response(sID, sResponse.toInt32());
3986 }
3987 
3989 {
3990  xmlreader::Span name;
3991  int nsId;
3992 
3993  OString sProperty;
3994  OString sValue;
3995  OString sModifiers;
3996 
3997  while (reader.nextAttribute(&nsId, &name))
3998  {
3999  if (name == "key")
4000  {
4001  name = reader.getAttributeValue(false);
4002  sValue = OString(name.begin, name.length);
4003  }
4004  else if (name == "signal")
4005  {
4006  name = reader.getAttributeValue(false);
4007  sProperty = OString(name.begin, name.length);
4008  }
4009  else if (name == "modifiers")
4010  {
4011  name = reader.getAttributeValue(false);
4012  sModifiers = OString(name.begin, name.length);
4013  }
4014  }
4015 
4016  if (!sProperty.isEmpty() && !sValue.isEmpty())
4017  {
4018  rMap[sProperty] = std::make_pair(sValue, sModifiers);
4019  }
4020 }
4021 
4023 {
4024  return m_aChildren.empty() ? nullptr : m_aChildren[0].m_pWindow.get();
4025 }
4026 
4027 vcl::Window *VclBuilder::get_by_name(std::string_view sID)
4028 {
4029  for (auto const& child : m_aChildren)
4030  {
4031  if (child.m_sID == sID)
4032  return child.m_pWindow;
4033  }
4034 
4035  return nullptr;
4036 }
4037 
4038 PopupMenu *VclBuilder::get_menu(std::string_view sID)
4039 {
4040  for (auto const& menu : m_aMenus)
4041  {
4042  if (menu.m_sID == sID)
4043  return dynamic_cast<PopupMenu*>(menu.m_pMenu.get());
4044  }
4045 
4046  return nullptr;
4047 }
4048 
4049 void VclBuilder::set_response(std::string_view sID, short nResponse)
4050 {
4051  switch (nResponse)
4052  {
4053  case -5:
4054  nResponse = RET_OK;
4055  break;
4056  case -6:
4057  nResponse = RET_CANCEL;
4058  break;
4059  case -7:
4060  nResponse = RET_CLOSE;
4061  break;
4062  case -8:
4063  nResponse = RET_YES;
4064  break;
4065  case -9:
4066  nResponse = RET_NO;
4067  break;
4068  case -11:
4069  nResponse = RET_HELP;
4070  break;
4071  default:
4072  assert(nResponse >= 100 && "keep non-canned responses in range 100+ to avoid collision with vcl RET_*");
4073  break;
4074  }
4075 
4076  for (const auto & child : m_aChildren)
4077  {
4078  if (child.m_sID == sID)
4079  {
4080  PushButton* pPushButton = dynamic_cast<PushButton*>(child.m_pWindow.get());
4081  assert(pPushButton);
4082  Dialog* pDialog = pPushButton->GetParentDialog();
4083  assert(pDialog);
4084  pDialog->add_button(pPushButton, nResponse, false);
4085  return;
4086  }
4087  }
4088 
4089  assert(false);
4090 }
4091 
4092 void VclBuilder::delete_by_name(const OString& sID)
4093 {
4094  auto aI = std::find_if(m_aChildren.begin(), m_aChildren.end(),
4095  [&sID](WinAndId& rItem) { return rItem.m_sID == sID; });
4096  if (aI != m_aChildren.end())
4097  {
4098  aI->m_pWindow.disposeAndClear();
4099  m_aChildren.erase(aI);
4100  }
4101 }
4102 
4104 {
4105  drop_ownership(pWindow);
4106  pWindow->disposeOnce();
4107 }
4108 
4110 {
4111  auto aI = std::find_if(m_aChildren.begin(), m_aChildren.end(),
4112  [&pWindow](WinAndId& rItem) { return rItem.m_pWindow == pWindow; });
4113  if (aI != m_aChildren.end())
4114  m_aChildren.erase(aI);
4115 }
4116 
4117 OString VclBuilder::get_by_window(const vcl::Window *pWindow) const
4118 {
4119  for (auto const& child : m_aChildren)
4120  {
4121  if (child.m_pWindow == pWindow)
4122  return child.m_sID;
4123  }
4124 
4125  return OString();
4126 }
4127 
4129 {
4130  //We've stored the return of new Control, some of these get
4131  //border windows placed around them which are what you get
4132  //from GetChild, so scoot up a level if necessary to get the
4133  //window whose position value we have
4134  const vcl::Window *pPropHolder = pWindow->ImplGetWindow();
4135 
4136  for (auto const& child : m_aChildren)
4137  {
4138  if (child.m_pWindow == pPropHolder)
4139  return child.m_aPackingData;
4140  }
4141 
4142  return PackingData();
4143 }
4144 
4145 void VclBuilder::set_window_packing_position(const vcl::Window *pWindow, sal_Int32 nPosition)
4146 {
4147  for (auto & child : m_aChildren)
4148  {
4149  if (child.m_pWindow == pWindow)
4150  child.m_aPackingData.m_nPosition = nPosition;
4151  }
4152 }
4153 
4155 {
4156  std::map<OString, ListStore>::const_iterator aI = m_pParserState->m_aModels.find(sID);
4157  if (aI != m_pParserState->m_aModels.end())
4158  return &(aI->second);
4159  return nullptr;
4160 }
4161 
4163 {
4164  std::map<OString, TextBuffer>::const_iterator aI = m_pParserState->m_aTextBuffers.find(sID);
4165  if (aI != m_pParserState->m_aTextBuffers.end())
4166  return &(aI->second);
4167  return nullptr;
4168 }
4169 
4171 {
4172  std::map<OString, Adjustment>::const_iterator aI = m_pParserState->m_aAdjustments.find(sID);
4173  if (aI != m_pParserState->m_aAdjustments.end())
4174  return &(aI->second);
4175  return nullptr;
4176 }
4177 
4178 void VclBuilder::mungeModel(ComboBox &rTarget, const ListStore &rStore, sal_uInt16 nActiveId)
4179 {
4180  for (auto const& entry : rStore.m_aEntries)
4181  {
4182  const ListStore::row &rRow = entry;
4183  sal_uInt16 nEntry = rTarget.InsertEntry(rRow[0]);
4184  if (rRow.size() > 1)
4185  {
4186  if (m_bLegacy)
4187  {
4188  sal_Int32 nValue = rRow[1].toInt32();
4189  rTarget.SetEntryData(nEntry, reinterpret_cast<void*>(nValue));
4190  }
4191  else
4192  {
4193  if (!rRow[1].isEmpty())
4194  {
4195  m_aUserData.emplace_back(std::make_unique<OUString>(rRow[1]));
4196  rTarget.SetEntryData(nEntry, m_aUserData.back().get());
4197  }
4198  }
4199  }
4200  }
4201  if (nActiveId < rStore.m_aEntries.size())
4202  rTarget.SelectEntryPos(nActiveId);
4203 }
4204 
4205 void VclBuilder::mungeModel(ListBox &rTarget, const ListStore &rStore, sal_uInt16 nActiveId)
4206 {
4207  for (auto const& entry : rStore.m_aEntries)
4208  {
4209  const ListStore::row &rRow = entry;
4210  sal_uInt16 nEntry = rTarget.InsertEntry(rRow[0]);
4211  if (rRow.size() > 1)
4212  {
4213  if (m_bLegacy)
4214  {
4215  sal_Int32 nValue = rRow[1].toInt32();
4216  rTarget.SetEntryData(nEntry, reinterpret_cast<void*>(nValue));
4217  }
4218  else
4219  {
4220  if (!rRow[1].isEmpty())
4221  {
4222  m_aUserData.emplace_back(std::make_unique<OUString>(rRow[1]));
4223  rTarget.SetEntryData(nEntry, m_aUserData.back().get());
4224  }
4225  }
4226  }
4227  }
4228  if (nActiveId < rStore.m_aEntries.size())
4229  rTarget.SelectEntryPos(nActiveId);
4230 }
4231 
4232 void VclBuilder::mungeModel(SvTabListBox& rTarget, const ListStore &rStore, sal_uInt16 nActiveId)
4233 {
4234  for (auto const& entry : rStore.m_aEntries)
4235  {
4236  const ListStore::row &rRow = entry;
4237  auto pEntry = rTarget.InsertEntry(rRow[0]);
4238  if (rRow.size() > 1)
4239  {
4240  if (m_bLegacy)
4241  {
4242  sal_Int32 nValue = rRow[1].toInt32();
4243  pEntry->SetUserData(reinterpret_cast<void*>(nValue));
4244  }
4245  else
4246  {
4247  if (!rRow[1].isEmpty())
4248  {
4249  m_aUserData.emplace_back(std::make_unique<OUString>(rRow[1]));
4250  pEntry->SetUserData(m_aUserData.back().get());
4251  }
4252  }
4253  }
4254  }
4255  if (nActiveId < rStore.m_aEntries.size())
4256  {
4257  SvTreeListEntry* pEntry = rTarget.GetEntry(nullptr, nActiveId);
4258  rTarget.Select(pEntry);
4259  }
4260 }
4261 
4262 void VclBuilder::mungeAdjustment(NumericFormatter &rTarget, const Adjustment &rAdjustment)
4263 {
4264  int nMul = rtl_math_pow10Exp(1, rTarget.GetDecimalDigits());
4265 
4266  for (auto const& elem : rAdjustment)
4267  {
4268  const OString &rKey = elem.first;
4269  const OUString &rValue = elem.second;
4270 
4271  if (rKey == "upper")
4272  {
4273  sal_Int64 nUpper = rValue.toDouble() * nMul;
4274  rTarget.SetMax(nUpper);
4275  rTarget.SetLast(nUpper);
4276  }
4277  else if (rKey == "lower")
4278  {
4279  sal_Int64 nLower = rValue.toDouble() * nMul;
4280  rTarget.SetMin(nLower);
4281  rTarget.SetFirst(nLower);
4282  }
4283  else if (rKey == "value")
4284  {
4285  sal_Int64 nValue = rValue.toDouble() * nMul;
4286  rTarget.SetValue(nValue);
4287  }
4288  else if (rKey == "step-increment")
4289  {
4290  sal_Int64 nSpinSize = rValue.toDouble() * nMul;
4291  rTarget.SetSpinSize(nSpinSize);
4292  }
4293  else
4294  {
4295  SAL_INFO("vcl.builder", "unhandled property :" << rKey);
4296  }
4297  }
4298 }
4299 
4300 void VclBuilder::mungeAdjustment(FormattedField &rTarget, const Adjustment &rAdjustment)
4301 {
4302  double nMaxValue = 0, nMinValue = 0, nValue = 0, nSpinSize = 0;
4303 
4304  for (auto const& elem : rAdjustment)
4305  {
4306  const OString &rKey = elem.first;
4307  const OUString &rValue = elem.second;
4308 
4309  if (rKey == "upper")
4310  nMaxValue = rValue.toDouble();
4311  else if (rKey == "lower")
4312  nMinValue = rValue.toDouble();
4313  else if (rKey == "value")
4314  nValue = rValue.toDouble();
4315  else if (rKey == "step-increment")
4316  nSpinSize = rValue.toDouble();
4317  else
4318  SAL_INFO("vcl.builder", "unhandled property :" << rKey);
4319  }
4320 
4321  Formatter& rFormatter = rTarget.GetFormatter();
4322  rFormatter.SetMinValue(nMinValue);
4323  rFormatter.SetMaxValue(nMaxValue);
4324  rFormatter.SetValue(nValue);
4325  rFormatter.SetSpinSize(nSpinSize);
4326 }
4327 
4328 void VclBuilder::mungeAdjustment(ScrollBar &rTarget, const Adjustment &rAdjustment)
4329 {
4330  for (auto const& elem : rAdjustment)
4331  {
4332  const OString &rKey = elem.first;
4333  const OUString &rValue = elem.second;
4334 
4335  if (rKey == "upper")
4336  rTarget.SetRangeMax(rValue.toInt32());
4337  else if (rKey == "lower")
4338  rTarget.SetRangeMin(rValue.toInt32());
4339  else if (rKey == "value")
4340  rTarget.SetThumbPos(rValue.toInt32());
4341  else if (rKey == "step-increment")
4342  rTarget.SetLineSize(rValue.toInt32());
4343  else if (rKey == "page-increment")
4344  rTarget.SetPageSize(rValue.toInt32());
4345  else
4346  {
4347  SAL_INFO("vcl.builder", "unhandled property :" << rKey);
4348  }
4349  }
4350 }
4351 
4352 void VclBuilder::mungeAdjustment(Slider& rTarget, const Adjustment& rAdjustment)
4353 {
4354  for (auto const& elem : rAdjustment)
4355  {
4356  const OString &rKey = elem.first;
4357  const OUString &rValue = elem.second;
4358 
4359  if (rKey == "upper")
4360  rTarget.SetRangeMax(rValue.toInt32());
4361  else if (rKey == "lower")
4362  rTarget.SetRangeMin(rValue.toInt32());
4363  else if (rKey == "value")
4364  rTarget.SetThumbPos(rValue.toInt32());
4365  else if (rKey == "step-increment")
4366  rTarget.SetLineSize(rValue.toInt32());
4367  else if (rKey == "page-increment")
4368  rTarget.SetPageSize(rValue.toInt32());
4369  else
4370  {
4371  SAL_INFO("vcl.builder", "unhandled property :" << rKey);
4372  }
4373  }
4374 }
4375 
4376 void VclBuilder::mungeTextBuffer(VclMultiLineEdit &rTarget, const TextBuffer &rTextBuffer)
4377 {
4378  for (auto const& elem : rTextBuffer)
4379  {
4380  const OString &rKey = elem.first;
4381  const OUString &rValue = elem.second;
4382 
4383  if (rKey == "text")
4384  rTarget.SetText(rValue);
4385  else
4386  {
4387  SAL_INFO("vcl.builder", "unhandled property :" << rKey);
4388  }
4389  }
4390 }
4391 
4393  : m_nLastToolbarId(0)
4394  , m_nLastMenuItemId(0)
4395 {}
4396 
4397 VclBuilder::MenuAndId::MenuAndId(const OString &rId, Menu *pMenu)
4398  : m_sID(rId)
4399  , m_pMenu(pMenu)
4400 {}
4401 
4402 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
void SetHelpId(ToolBoxItemId nItemId, const OString &rHelpId)
Definition: toolbox2.cxx:1376
static bool toBool(std::string_view rValue)
Definition: builder.cxx:90
void SetRangeMin(tools::Long nNewRange)
Definition: scrbar.cxx:1327
SwNodeOffset min(const SwNodeOffset &a, const SwNodeOffset &b)
Size GetSizePixel() const
Definition: Image.cxx:86
void delete_by_window(vcl::Window *pWindow)
Definition: builder.cxx:4103
void set_mnemonic_widget(vcl::Window *pWindow)
Definition: fixed.cxx:406
WinBits const WB_DOCKABLE
vcl::Window * ImplGetWindow() const
if this is a proxy return the client, otherwise itself
Definition: window2.cxx:853
void SetEntryHeight(short nHeight)
void handleMenuObject(Menu *pParent, xmlreader::XmlReader &reader)
Definition: builder.cxx:3246
FieldUnit
MenuAndId(const OString &rId, Menu *pMenu)
Definition: builder.cxx:4397
const LocaleDataWrapper & GetLocaleDataWrapper() const
void HideItem(ToolBoxItemId nItemId)
Convenience method to hide items (via ShowItem).
Definition: toolbox.hxx:401
sal_Int32 nIndex
void SetRangeMax(tools::Long nNewRange)
Definition: slider.cxx:844
void set_height_request_by_rows(int nRows)
Definition: builder.cxx:400
static Image loadThemeImage(const OUString &rFileName)
Definition: fixed.cxx:956
static void thisModule()
Definition: builder.cxx:1427
WinBits const WB_TOGGLE
void extractBuffer(const OString &id, stringmap &rVec)
Definition: builder.cxx:1353
bool isBuilderEnabledForPopup(std::u16string_view rUIFile)
WinBits const WB_SYSTEMWINDOW
#define SAL_DLLEXTENSION
SystemWindow * GetSystemWindow() const
Definition: stacking.cxx:806
WinBits const WB_NOLABEL
void set_border_width(sal_Int32 nBorderWidth)
Definition: window2.cxx:1866
PackingData get_window_packing_data(const vcl::Window *pWindow) const
Definition: builder.cxx:4128
void SetNoAutoCurEntry(bool b)
void SetModeRadioImage(const Image &rImage)
Definition: button.cxx:2695
void group(RadioButton &rOther)
Definition: button.cxx:2255
virtual bool iter_parent(TreeIter &rIter) const =0
void set_value(sal_Int64 nValue, FieldUnit eValueUnit)
Definition: weld.hxx:1995
VclButtonsType
Definition: vclenum.hxx:222
VclBuilder(vcl::Window *pParent, const OUString &sUIRootDir, const OUString &sUIFile, const OString &sID=OString(), const css::uno::Reference< css::frame::XFrame > &rFrame=css::uno::Reference< css::frame::XFrame >(), bool bLegacy=true, const NotebookBarAddonsItem *pNotebookBarAddonsItem=nullptr)
Definition: builder.cxx:444
void SetContext(std::vector< vcl::EnumContext::Context > &&aContext)
Definition: IContext.hxx:25
void SetMax(sal_Int64 nNewMax)
Definition: field.cxx:584
sal_Int32 get_grid_top_attach() const
Definition: window2.cxx:1854
void set_grid_width(sal_Int32 nCols)
Definition: window2.cxx:1824
void SetModeImage(const Image &rImage)
Definition: button.cxx:133
size_t GetAbsPos(const weld::TreeView &rTreeView, const weld::TreeIter &rIter)
Definition: builder.cxx:406
void set_grid_left_attach(sal_Int32 nAttach)
Definition: window2.cxx:1836
stringmap m_aProperties
Definition: builder.hxx:246
void SetHelpId(sal_uInt16 nItemId, const OString &rHelpId)
Definition: menu.cxx:1120
bool m_bLegacy
Definition: builder.hxx:301
A widget used to choose from a list of items and which has no entry.
Definition: lstbox.hxx:82
void handleSizeGroup(xmlreader::XmlReader &reader)
Definition: builder.cxx:3328
WinBits const WB_HASBUTTONSATROOT
void set_digits(unsigned int digits)
Definition: builder.cxx:334
static void applyAtkProperties(vcl::Window *pWindow, const stringmap &rProperties)
Definition: builder.cxx:3072
Formatter & GetFormatter()
Definition: fmtfield.cxx:1312
stringmap handleAtkObject(xmlreader::XmlReader &reader) const
Definition: builder.cxx:3036
void SetCommandHandler(const OUString &aCommand)
Setup handler for UNO commands so that commands like .uno:Something are handled automagically by this...
Definition: button.cxx:119
static Context GetContextEnum(const OUString &rsContextName)
void delete_by_name(const OString &sID)
Definition: builder.cxx:4092
#define SAL_INFO_IF(condition, area, stream)
void set_non_homogeneous(bool bNonHomogeneous)
Definition: window2.cxx:1972
const Image & GetImage() const
Definition: fixed.hxx:171
static const AllSettings & GetSettings()
Gets the application's settings.
Definition: svapp.cxx:760
constexpr sal_uInt16 KEY_A
Definition: keycodes.hxx:56
constexpr sal_uInt16 KEY_0
Definition: keycodes.hxx:45
void handleRow(xmlreader::XmlReader &reader, const OString &rID)
Definition: builder.cxx:2923
OUString GetLabelForCommand(const css::uno::Sequence< css::beans::PropertyValue > &rProperties)
Return a label for the given command.
stringmap Adjustment
Definition: builder.hxx:233
void connectFormattedFormatterAdjustment(const OString &id, const OUString &rAdjustment)
Definition: builder.cxx:1272
css::uno::Reference< css::lang::XComponent > m_xFrame
virtual std::unique_ptr< weld::Builder > CreateInterimBuilder(vcl::Window *pParent, const OUString &rUIRoot, const OUString &rUIFile, bool bAllowCycleFocusOut, sal_uInt64 nLOKWindowId=0)
VclPtr< vcl::Window > handleObject(vcl::Window *pParent, stringmap *pAtkProps, xmlreader::XmlReader &reader)
Definition: builder.cxx:3541
virtual Size GetSizePixel() const
Definition: window.cxx:2404
virtual void SetSizePixel(const Size &rNewSize)
Definition: window2.cxx:1285
void SetAccessibleRelationLabelFor(vcl::Window *pLabelFor)
void extractButtonImage(const OString &id, stringmap &rMap, bool bRadio)
Definition: builder.cxx:1372
std::vector< OUString > row
Definition: builder.hxx:219
#define max(a, b)
std::vector< OString > m_aWidgets
Definition: builder.hxx:245
weld::Builder * m_pBuilder
SAL_DLLPRIVATE WindowImpl * ImplGetWindowImpl() const
Definition: window.hxx:527
static void collectPangoAttribute(xmlreader::XmlReader &reader, stringmap &rMap)
Definition: builder.cxx:2848
sal_Int16 nId
TabPage * GetTabPage(sal_uInt16 nPageId) const
Definition: tabctrl.cxx:1914
WinBits const WB_AUTOVSCROLL
void handleListStore(xmlreader::XmlReader &reader, const OString &rID, std::string_view rClass)
Definition: builder.cxx:2998
bool set_font_attribute(const OString &rKey, std::u16string_view rValue)
Definition: window2.cxx:1409
void set_height_request(sal_Int32 nHeightRequest)
Definition: window2.cxx:1641
std::map< OString, std::pair< OString, OString > > accelmap
Definition: builder.hxx:71
WinBits const WB_VSCROLL
void VclBuilderPreload()
Pre-loads all modules containing UI information.
Definition: builder.cxx:1455
void SetHelpId(const OString &)
Definition: window2.cxx:841
char const * begin
stringmap m_aDeferredProperties
Definition: builder.hxx:125
void set_pack_type(VclPackType ePackType)
Definition: window2.cxx:1788
bool IsControlFont() const
Definition: window2.cxx:1090
void SetState(TriState eState)
Definition: button.cxx:3576
static weld::MessageDialog * CreateMessageDialog(weld::Widget *pParent, VclMessageType eMessageType, VclButtonsType eButtonType, const OUString &rPrimaryMessage)
void SetRangeMax(tools::Long nNewRange)
Definition: scrbar.cxx:1332
void SetType(WindowType nType)
Definition: window2.cxx:991
void SetTipHelpText(sal_uInt16 nItemId, const OUString &rString)
Definition: menu.cxx:1102
static std::unique_ptr< JSInstanceBuilder > CreateNotebookbarBuilder(vcl::Window *pParent, const OUString &rUIRoot, const OUString &rUIFile, const css::uno::Reference< css::frame::XFrame > &rFrame, sal_uInt64 nWindowId=0)
ResHookProc GetReadStringHook()
void SetQuickHelpText(const OUString &rHelpText)
Definition: window2.cxx:1249
static OUString MetricToString(FieldUnit rUnit)
Definition: builder.cxx:230
virtual void SetMinValue(double dMin)
Definition: fmtfield.cxx:703
std::vector< row > m_aEntries
Definition: builder.hxx:220
OString m_sHelpRoot
Definition: builder.hxx:295
void HideItem(sal_uInt16 nItemId)
Definition: menu.hxx:288
Dialog * GetParentDialog() const
Definition: window2.cxx:1005
static void mungeAdjustment(NumericFormatter &rTarget, const Adjustment &rAdjustment)
Definition: builder.cxx:4262
constexpr sal_uInt16 KEY_UP
Definition: keycodes.hxx:111
#define SAL_DLLPREFIX
Definition: builder.cxx:1448
void SetDropDown(PushButtonDropdownStyle nStyle)
Definition: button.cxx:1625
virtual std::unique_ptr< TreeIter > make_iterator(const TreeIter *pOrig=nullptr) const =0
virtual unsigned int get_digits() const =0
void SetSpinSize(sal_Int64 nNewSize)
Definition: field.hxx:111
void SetMin(sal_Int64 nNewMin)
Definition: field.cxx:577
void set_properties(vcl::Window *pWindow, const VclBuilder::stringmap &rProps)
Definition: builder.cxx:2214
constexpr sal_uInt16 KEY_F1
Definition: keycodes.hxx:83
void SetEntryData(sal_Int32 nPos, void *pNewData)
Definition: combobox.cxx:1314
void set_window_packing_position(const vcl::Window *pWindow, sal_Int32 nPosition)
Definition: builder.cxx:4145
static OString getStyleClass(xmlreader::XmlReader &reader)
Definition: builder.cxx:3900
constexpr tools::Long Width() const
o3tl::strong_int< sal_uInt16, struct ToolBoxItemIdTag > ToolBoxItemId
Definition: toolboxid.hxx:14
static int getImageSize(const stringmap &rMap)
Definition: builder.cxx:1363
WinBits const WB_SCALE
void SetAccessibleName(sal_uInt16 nItemId, const OUString &rStr)
Definition: tabctrl.cxx:1970
static bool insertItems(vcl::Window *pWindow, VclBuilder::stringmap &rMap, std::vector< std::unique_ptr< OUString >> &rUserData, const std::vector< ComboBoxTextItem > &rItems)
Insert items to a ComboBox or a ListBox.
Definition: builder.cxx:3517
void MergeNotebookBarMenuAddons(Menu *pPopupMenu, sal_Int16 nItemId, const OString &sItemIdName, NotebookBarAddonsItem &aNotebookBarAddonsItem)
WinBits const WB_OWNERDRAWDECORATION
sal_Int64 WinBits
void insertMenuObject(Menu *pParent, PopupMenu *pSubMenu, const OString &rClass, const OString &rID, stringmap &rProps, stringmap &rAtkProps, accelmap &rAccels)
Definition: builder.cxx:3427
virtual weld::Window * GetFrameWeld(const css::uno::Reference< css::awt::XWindow > &rWindow)
void SetControlFont()
Definition: window2.cxx:432
sal_uInt16 nPageId
void EnableAutoSize(bool bAuto)
Definition: listbox.cxx:496
PropertiesInfo aProperties
void get_increments(int &step, int &page, FieldUnit eDestUnit) const
Definition: weld.hxx:2060
void SetPageSize(tools::Long nNewSize)
Definition: scrbar.hxx:125
void SetSymbol(SymbolType eSymbol)
Definition: button.cxx:1611
WinBits const WB_DEFBUTTON
SymbolType
Definition: vclenum.hxx:73
static void mungeTextBuffer(VclMultiLineEdit &rTarget, const TextBuffer &rTextBuffer)
Definition: builder.cxx:4376
WinBits const WB_VERT
bool isInterimBuilderEnabledForNotebookbar(std::u16string_view rUIFile)
IMPL_LINK(CustomWeld, DoResize, const Size &, rSize, void)
Definition: customweld.cxx:46
WinBits const WB_HSCROLL
sal_uInt16 GetDecimalDigits() const
Definition: field.hxx:115
void reorderWithinParent(vcl::Window &rWindow, sal_uInt16 nNewPosition)
Definition: builder.cxx:2273
void SetItemCommand(sal_uInt16 nItemId, const OUString &rCommand)
Definition: menu.cxx:1029
void SetThumbPos(tools::Long nThumbPos)
Definition: slider.cxx:873
std::unique_ptr< weld::SpinButton > m_xSpinButton
Definition: weld.hxx:1953
void set_unit(FieldUnit eUnit)
Definition: builder.cxx:345
VclPtr< vcl::Window > makeObject(vcl::Window *pParent, const OString &rClass, const OString &rID, stringmap &rVec)
Definition: builder.cxx:1554
void mungeModel(ListBox &rTarget, const ListStore &rStore, sal_uInt16 nActiveId)
Definition: builder.cxx:4205
void SetImageAlign(ImageAlign eAlign)
Definition: button.cxx:153
virtual SvTreeListEntry * InsertEntry(const OUString &rText, SvTreeListEntry *pParent=nullptr, bool bChildrenOnDemand=false, sal_uInt32 nPos=TREELIST_APPEND, void *pUserData=nullptr) override
Definition: svtabbx.cxx:217
void set_width_request(sal_Int32 nWidthRequest)
Definition: window2.cxx:1655
virtual OUString GetText() const
Definition: window.cxx:3060
VclMessageType
Definition: vclenum.hxx:232
void InsertSeparator(const OString &rIdent=OString(), sal_uInt16 nPos=MENU_APPEND)
Definition: menu.cxx:472
void SetCurPageId(sal_uInt16 nPageId)
Definition: tabctrl.cxx:1824
OString OUStringToOString(std::u16string_view str, ConnectionSettings const *settings)
std::unique_ptr< TreeView > m_xTreeView
Definition: weld.hxx:1864
virtual void InsertItem(const OUString &rCommand, const css::uno::Reference< css::frame::XFrame > &rFrame, ToolBoxItemBits nBits, const Size &rRequestedSize, ImplToolItems::size_type nPos=APPEND)
Insert a command (like '.uno:Save').
Definition: toolbox2.cxx:437
void SetItemWindow(ToolBoxItemId nItemId, vcl::Window *pNewWindow)
Definition: toolbox2.cxx:1082
void MergeNotebookBarAddons(vcl::Window *pParent, const VclBuilder::customMakeWidget &pFunction, const css::uno::Reference< css::frame::XFrame > &m_xFrame, const NotebookBarAddonsItem &aNotebookBarAddonsItem, VclBuilder::stringmap &rMap)
void SetThumbPos(tools::Long nThumbPos)
Definition: scrbar.cxx:1361
WinBits const WB_BEVELBUTTON
bool get_secondary() const
Definition: window2.cxx:1954
TRISTATE_INDET
WinBits const WB_HIDE
sal_uInt16 GetPageCount() const
Definition: tabctrl.cxx:1782
void SetLineSize(tools::Long nNewSize)
Definition: scrbar.hxx:123
static ModuleMap g_aModuleMap
Definition: builder.cxx:1441
static std::unique_ptr< JSInstanceBuilder > CreateSidebarBuilder(weld::Widget *pParent, const OUString &rUIRoot, const OUString &rUIFile, sal_uInt64 nLOKWindowId=0)
void SetPopupMenu(sal_uInt16 nItemId, PopupMenu *pMenu)
Definition: menu.cxx:713
void SetItemExpand(ToolBoxItemId nItemId, bool bExpand)
Definition: toolbox2.cxx:911
void drop_ownership(const vcl::Window *pWindow)
Definition: builder.cxx:4109
void extractGroup(const OString &id, stringmap &rVec)
Definition: builder.cxx:1252
bool IsDockingWindow() const
Definition: window2.cxx:929
std::locale Create(std::string_view aPrefixName, const LanguageTag &rLocale)
void set_fill(bool bFill)
Definition: window2.cxx:1812
OUString GetStock() const
Definition: Image.cxx:79
bool mbDisabled
Definition: window.h:317
constexpr sal_uInt16 KEY_DOWN
Definition: keycodes.hxx:110
void SetHighlightRange(sal_uInt16 nFirstTab=0, sal_uInt16 nLastTab=0xffff)
OUString extractCustomProperty(VclBuilder::stringmap &rMap)
Definition: builder.cxx:2241
static OUString GetUIRootDir()
Definition: dialog.cxx:556
Image GetImageForCommand(const OUString &rsCommandName, const Reference< frame::XFrame > &rxFrame, vcl::ImageType eImageType)
WinBits const WB_DIALOGCONTROL
ImplSVData * ImplGetSVData()
Definition: svdata.cxx:76
Use given parent or get a default one using GetDefaultParent(...)
std::map< OUString, std::shared_ptr< NoAutoUnloadModule > > ModuleMap
Definition: builder.cxx:1440
#define DBG_UNHANDLED_EXCEPTION(...)
const OString & GetHelpId() const
Definition: window2.cxx:846
void collectProperty(xmlreader::XmlReader &reader, stringmap &rVec) const
Definition: builder.cxx:3918
ToolBoxItemBits
Definition: vclenum.hxx:50
void clear()
Definition: vclptr.hxx:190
void(* customMakeWidget)(VclPtr< vcl::Window > &rRet, const VclPtr< vcl::Window > &pParent, stringmap &rVec)
These functions create a new widget with parent pParent and return it in rRet.
Definition: builder.hxx:73
void SetAccessibleDescription(sal_uInt16 nItemId, const OUString &rStr)
Definition: tabctrl.cxx:1986
virtual void doDeferredInit(WinBits nBits)
Definition: syswin.cxx:1103
void SetAccessibleDescription(sal_uInt16 nItemId, const OUString &rStr)
Definition: menu.cxx:2295
static vcl::Window * prepareWidgetOwnScrolling(vcl::Window *pParent, WinBits &rWinStyle)
Definition: builder.cxx:1396
#define SAL_MAX_INT32
OUString convertMnemonicMarkup(std::u16string_view rIn)
Definition: builder.cxx:2224
OUString GetModuleIdentifier(const Reference< frame::XFrame > &rxFrame)
VclPackType
Definition: vclenum.hxx:200
OString get_by_window(const vcl::Window *pWindow) const
Definition: builder.cxx:4117
int i
HeaderBar * GetHeaderBar()
Definition: svtabbx.cxx:493
virtual std::unique_ptr< weld::Builder > CreateBuilder(weld::Widget *pParent, const OUString &rUIRoot, const OUString &rUIFile)
bool IsSystemWindow() const
Definition: window2.cxx:1020
void SetQuickHelpText(ToolBoxItemId nItemId, const OUString &rText)
Definition: toolbox2.cxx:1345
void SetPageText(sal_uInt16 nPageId, const OUString &rText)
Definition: tabctrl.cxx:1924
A toolbar: contains all those icons, typically below the menu bar.
Definition: toolbox.hxx:75
void set_secondary(bool bSecondary)
Definition: window2.cxx:1960
void SetValue(double dVal)
Definition: fmtfield.cxx:856
#define WB_BUTTONSTYLE
Definition: headbar.hxx:177
void SetItemImage(ToolBoxItemId nItemId, const Image &rImage)
Definition: toolbox2.cxx:945
void SetAccessibleRelationLabeledBy(vcl::Window *pLabeledBy)
void SelectEntryPos(sal_Int32 nPos, bool bSelect=true)
Definition: listbox.cxx:1026
WinBits const WB_SIMPLEMODE
virtual void SetText(const OUString &rStr) override
Definition: ctrl.cxx:95
void handleMenuChild(Menu *pParent, xmlreader::XmlReader &reader)
Definition: builder.cxx:3214
bool m_bToplevelHasDeferredProperties
Definition: builder.hxx:299
WinBits const WB_VCENTER
PopupMenu * get_menu(std::string_view sID)
Definition: builder.cxx:4038
static weld::Window * GetFrameWeld(const css::uno::Reference< css::awt::XWindow > &rWindow)
Definition: builder.cxx:223
void EnableTriState(bool bTriState=true)
Definition: button.cxx:3598
#define SAL_MIN_INT32
static void collectAtkRelationAttribute(xmlreader::XmlReader &reader, stringmap &rMap)
Definition: builder.cxx:2874
virtual bool iter_next(TreeIter &rIter) const =0
std::map< OString, OUString > stringmap
Definition: builder.hxx:70
vcl::Window * get_widget_root()
Definition: builder.cxx:4022
float u
void add_button(PushButton *pButton, int nResponse, bool bTransferOwnership)
Definition: dialog.cxx:1431
WinBits const WB_SMALLSTYLE
OUString get(TranslateId sContextAndId, const std::locale &loc)
Size get_preferred_size() const
Definition: window2.cxx:1691
sal_Int32 InsertEntry(const OUString &rStr, sal_Int32 nPos=LISTBOX_APPEND)
Definition: listbox.cxx:936
VclPtr< vcl::Window > m_pParent
Definition: builder.hxx:297
void InitHeaderBar(HeaderBar *pHeaderBar)
Definition: svtabbx.cxx:484
WinBits const WB_DROPDOWN
stringmap TextBuffer
Definition: builder.hxx:228
void SetImage(const Image &rImage)
Definition: fixed.cxx:946
sal_Int64 denormalize(sal_Int64 nValue) const
Definition: builder.cxx:273
virtual bool set_property(const OString &rKey, const OUString &rValue)
Definition: window2.cxx:1475
void reorderWithinParent(sal_uInt16 nNewPosition)
Definition: stacking.cxx:162
VclPackType get_pack_type() const
Definition: window2.cxx:1782
virtual void SetMaxValue(double dMax)
Definition: fmtfield.cxx:713
void cleanupWidgetOwnScrolling(vcl::Window *pScrollParent, vcl::Window *pWindow, stringmap &rMap)
Definition: builder.cxx:1414
vcl::Window * GetParent() const
Definition: window2.cxx:1120
bool isBuilderEnabledForSidebar(std::u16string_view rUIFile)
WinBits const WB_LEFT
VclPtr< vcl::Window > mpBorderWindow
Definition: window.h:233
void InsertPage(const OString &rPageId, const OUString &rLabel, const Image &rImage, const OUString &rTooltip, VclPtr< vcl::Window > xPage, int nPos=-1)
Definition: ivctrl.cxx:554
void SetStyle(WinBits nStyle)
Definition: window.cxx:1964
sal_Int64 get_value(FieldUnit eDestUnit) const
Definition: weld.hxx:2000
WinBits const WB_REPEAT
constexpr sal_uInt16 KEY_RETURN
Definition: keycodes.hxx:119
bool TextToValue(const OUString &rStr, double &rValue, sal_Int64 nBaseValue, sal_uInt16 nDecDigits, const LocaleDataWrapper &rLocaleDataWrapper, FieldUnit eUnit)
Definition: field.cxx:1201
void set_increments(int step, int page, FieldUnit eValueUnit)
Definition: weld.hxx:2053
vcl::Window * GetWindow(GetWindowType nType) const
Definition: stacking.cxx:1035
constexpr sal_uInt16 KEY_RIGHT
Definition: keycodes.hxx:113
InitFlag
Definition: dialog.hxx:43
void handleChild(vcl::Window *pParent, stringmap *pAtkProps, xmlreader::XmlReader &reader)
Definition: builder.cxx:2711
void SetSpaceBetweenEntries(short nSpace)
void applyPackingProperty(vcl::Window *pCurrent, vcl::Window *pParent, xmlreader::XmlReader &reader)
Definition: builder.cxx:3741
void set_grid_top_attach(sal_Int32 nAttach)
Definition: window2.cxx:1860
void set_grid_height(sal_Int32 nRows)
Definition: window2.cxx:1848
bool isBuilderEnabled(std::u16string_view rUIFile, bool bMobile)
WinBits const WB_3DLOOK
WinBits const WB_SIZEABLE
void setDeferredProperties()
Definition: builder.cxx:2202
Sequence< beans::PropertyValue > GetCommandProperties(const OUString &rsCommandName, const OUString &rsModuleName)
Return a label for the given command.
virtual Size GetOptimalSize() const override
Definition: ctrl.cxx:369
void set_id(const OUString &rID)
Sets an ID.
Definition: window.cxx:3929
void extractModel(const OString &id, stringmap &rVec)
Definition: builder.cxx:1342
A construction helper for a temporary VclPtr.
Definition: vclptr.hxx:275
void extractMnemonicWidget(const OString &id, stringmap &rMap)
Definition: builder.cxx:1382
const Adjustment * get_adjustment_by_name(const OString &sID) const
Definition: builder.cxx:4170
void SetPageName(sal_uInt16 nPageId, const OString &rName) const
Definition: tabctrl.cxx:2002
void InsertItem(sal_uInt16 nItemId, const OUString &rStr, MenuItemBits nItemBits=MenuItemBits::NONE, const OString &rIdent=OString(), sal_uInt16 nPos=MENU_APPEND)
Definition: menu.cxx:432
static void collectAtkRoleAttribute(xmlreader::XmlReader &reader, stringmap &rMap)
Definition: builder.cxx:2903
std::unique_ptr< ParserState > m_pParserState
Definition: builder.hxx:302
void SetSmallSymbol()
Definition: button.cxx:533
Definition: menu.hxx:115
static OUString formatPercent(double dNumber, const LanguageTag &rLangTag)
sal_Int32 get_height_request() const
Definition: window2.cxx:1942
const LanguageTag & getLanguageTag() const
void disposeBuilder()
releases references and disposes all children.
Definition: builder.cxx:812
IMPL_LINK_NOARG(HexColorControl, OnAsyncModifyHdl, void *, void)
sal_Int32 length
void connectNumericFormatterAdjustment(const OString &id, const OUString &rAdjustment)
Definition: builder.cxx:1266
void handleActionWidget(xmlreader::XmlReader &reader)
Definition: builder.cxx:3964
WindowType
sal_Int32 get_grid_left_attach() const
Definition: window2.cxx:1830
void handlePacking(vcl::Window *pCurrent, vcl::Window *pParent, xmlreader::XmlReader &reader)
Definition: builder.cxx:3709
void set_id(const OUString &rID)
Sets an ID.
Definition: menu.hxx:393
#define SAL_WARN_IF(condition, area, stream)
void SetAccessibleName(sal_uInt16 nItemId, const OUString &rStr)
Definition: menu.cxx:2273
constexpr tools::Long Height() const
WinBits const WB_BORDER
void SetFirst(sal_Int64 nNewFirst)
Definition: field.hxx:107
Span getAttributeValue(bool fullyNormalize)
void SetRangeMin(tools::Long nNewRange)
Definition: slider.cxx:839
static std::vector< vcl::EnumContext::Context > handleStyle(xmlreader::XmlReader &reader, int &nPriority)
Definition: builder.cxx:3845
css::uno::Reference< css::frame::XFrame > m_xFrame
XFrame to be able to extract labels and other properties of the UNO commands (like of ...
Definition: builder.hxx:320
SvTreeListEntry * GetEntry(SvTreeListEntry *pParent, sal_uInt32 nPos) const
vcl::Window * get_label_widget()
Definition: layout.cxx:1510
void handleTabChild(vcl::Window *pParent, xmlreader::XmlReader &reader)
Definition: builder.cxx:2525
#define SAL_INFO(area, stream)
sal_Int32 get_width_request() const
Definition: window2.cxx:1948
OString m_sID
Definition: builder.hxx:294
const char sBorder[]
virtual void doDeferredInit(WinBits nBits)
Definition: dockwin.cxx:363
#define MNEMONIC_CHAR
Definition: mnemonic.hxx:48
sal_uInt16 GetPageId(sal_uInt16 nPos) const
Definition: tabctrl.cxx:1787
void SetPopupMenu(PopupMenu *pNewMenu)
Definition: menubtn.cxx:241
sal_uInt16 GetItemCount() const
Definition: menu.cxx:577
tools::Long AdjustWidth(tools::Long n)
Definition: image.hxx:39
vcl::Window * get_by_name(std::string_view sID)
Definition: builder.cxx:4027
static VclPtr< reference_type > Create(Arg &&...arg)
A construction helper for VclPtr.
Definition: vclptr.hxx:127
sal_uInt32 toUInt32(std::u16string_view str, sal_Int16 radix=10)
VclPtr< vcl::Window > mpParent
Definition: window.h:235
std::unique_ptr< NotebookBarAddonsItem > m_pNotebookBarAddonsItem
Definition: builder.hxx:127
virtual bool get_iter_first(TreeIter &rIter) const =0
std::vector< MenuAndId > m_aMenus
Definition: builder.hxx:160
void InsertSeparator(ImplToolItems::size_type nPos=APPEND, sal_uInt16 nPixSize=0)
Definition: toolbox2.cxx:500
void SetItemCommand(ToolBoxItemId nItemId, const OUString &rCommand)
Definition: toolbox2.cxx:1327
OUString aLabel
void SetAccelKey(sal_uInt16 nItemId, const vcl::KeyCode &rKeyCode)
Definition: menu.cxx:760
const char * name
const TextBuffer * get_buffer_by_name(const OString &sID) const
Definition: builder.cxx:4162
std::vector< std::pair< OUString, FieldUnit > > FieldUnitStringList
Definition: svdata.hxx:274
void RemovePage(sal_uInt16 nPageId)
Definition: tabctrl.cxx:1690
VclPtr< vcl::Window > insertObject(vcl::Window *pParent, const OString &rClass, const OString &rID, stringmap &rProps, stringmap &rPangoAttributes, stringmap &rAtkProps)
Definition: builder.cxx:2443
sal_Int64 ConvertValue(sal_Int64 nValue, FieldUnit eInUnit, FieldUnit eOutUnit) const
Definition: builder.cxx:360
Any value
const ListStore * get_model_by_name(const OString &sID) const
Definition: builder.cxx:4154
WinBits const WB_AUTOHSCROLL
bool extractDropdown(VclBuilder::stringmap &rMap)
Definition: builder.cxx:2261
#define SVLIBRARY(Base)
WinBits const WB_TABSTOP
sal_Int16 getRoleFromName(const OString &roleName)
Definition: builder.cxx:2305
void setHeight(tools::Long nHeight)
sal_Int64 ConvertValue(sal_Int64 nValue, sal_Int64 mnBaseValue, sal_uInt16 nDecDigits, FieldUnit eInUnit, FieldUnit eOutUnit)
Definition: field.cxx:1030
A widget used to choose from a list of items and which has an entry.
Definition: combobox.hxx:38
WindowType GetType() const
Definition: window2.cxx:997
WinBits const WB_HASBUTTONS
constexpr sal_uInt16 KEY_MULTIPLY
Definition: keycodes.hxx:129
static std::unique_ptr< JSInstanceBuilder > CreatePopupBuilder(weld::Widget *pParent, const OUString &rUIRoot, const OUString &rUIFile)
void SetTabPage(sal_uInt16 nPageId, TabPage *pPage)
Definition: tabctrl.cxx:1888
VclPtr< Menu > handleMenu(xmlreader::XmlReader &reader, const OString &rID, bool bMenuBar)
Definition: builder.cxx:3161
WinBits const WB_CENTER
static std::unique_ptr< JSInstanceBuilder > CreateDialogBuilder(weld::Widget *pParent, const OUString &rUIRoot, const OUString &rUIFile)
void add_to_size_group(const std::shared_ptr< VclSizeGroup > &xGroup)
Definition: window2.cxx:1978
reference_type * get() const
Get the body.
Definition: vclptr.hxx:143
bool nextAttribute(int *nsId, Span *localName)
static bool extractAdjustmentToMap(const OString &id, stringmap &rVec, std::vector< WidgetAdjustmentMap > &rAdjustmentMap)
Definition: builder.cxx:1278
Any result
#define SAL_WARN(area, stream)
VclPtr< vcl::Window > mpRealParent
Definition: window.h:236
void SetPriority(int nPriority)
void ensureDefaultWidthChars(VclBuilder::stringmap &rMap)
Definition: builder.cxx:2253
OUString aCommand
WinBits GetStyle() const
Definition: window2.cxx:976
std::vector< ComboBoxTextItem > handleItems(xmlreader::XmlReader &reader) const
Definition: builder.cxx:3087
void(* f)(TrueTypeTable *)
Definition: ttcr.cxx:482
FieldUnit m_eSrcUnit
Definition: weld.hxx:1952
virtual bool get_row_expanded(const TreeIter &rIter) const =0
OUString getNum(sal_Int64 nNumber, sal_uInt16 nDecimals, bool bUseThousandSep=true, bool bTrailingZeros=true) const
constexpr sal_uInt16 KEY_DELETE
Definition: keycodes.hxx:125
constexpr sal_uInt16 KEY_LEFT
Definition: keycodes.hxx:112
bool Select(SvTreeListEntry *pEntry, bool bSelect=true)
Result nextItem(Text reportText, Span *data, int *nsId)
virtual weld::MessageDialog * CreateMessageDialog(weld::Widget *pParent, VclMessageType eMessageType, VclButtonsType eButtonType, const OUString &rPrimaryMessage)
WinBits const WB_GROUP
void SelectEntryPos(sal_Int32 nPos, bool bSelect=true)
Definition: combobox.cxx:1377
WinBits const WB_CLOSEABLE
sal_Int32 InsertEntry(const OUString &rStr, sal_Int32 nPos=COMBOBOX_APPEND)
Definition: combobox.cxx:882
const FieldUnitStringList & ImplGetFieldUnits()
Definition: svdata.cxx:265
WinBits const WB_MOVEABLE
static void collectAccelerator(xmlreader::XmlReader &reader, accelmap &rMap)
Definition: builder.cxx:3988
void SetLast(sal_Int64 nNewLast)
Definition: field.hxx:109
void SetPageSize(tools::Long nNewSize)
Definition: slider.hxx:93
void SetEntryData(sal_Int32 nPos, void *pNewData)
Definition: listbox.cxx:1075
void SetAccessibleRole(sal_uInt16 nRole)
WinBits const WB_FLATBUTTON
constexpr sal_uInt16 KEY_INSERT
Definition: keycodes.hxx:124
std::pair< const_iterator, bool > insert(Value &&x)
ToolBoxItemId GetItemId(ImplToolItems::size_type nPos) const
Definition: toolbox2.cxx:743
vcl::Font GetControlFont() const
Definition: window2.cxx:461
void InsertPage(sal_uInt16 nPageId, const OUString &rText, sal_uInt16 nPos=TAB_APPEND)
Definition: tabctrl.cxx:1640
static std::unique_ptr< weld::Builder > CreateInterimBuilder(vcl::Window *pParent, const OUString &rUIFile, bool bAllowCycleFocusOut, sal_uInt64 nLOKWindowId=0)
Definition: builder.cxx:199
WinBits const WB_STDTABCONTROL
static unsigned int Power10(unsigned int n)
Definition: builder.cxx:265
WinBits const WB_HORZ
EntryTreeView(std::unique_ptr< Entry > xEntry, std::unique_ptr< TreeView > xTreeView)
Definition: builder.cxx:381
WinBits const WB_SPIN
WinBits const WB_POPUP
static SymbolType mapStockToSymbol(std::u16string_view icon_name)
Definition: builder.cxx:124
bool operator()(const vcl::Window *pA, const vcl::Window *pB) const
Definition: builder.cxx:2646
OUString GetTooltipForCommand(const OUString &rsCommandName, const css::uno::Sequence< css::beans::PropertyValue > &rProperties, const Reference< frame::XFrame > &rxFrame)
WinBits const WB_CLIPCHILDREN
OUString format_number(sal_Int64 nValue) const
Definition: builder.cxx:290
void SetLineSize(tools::Long nNewSize)
Definition: slider.hxx:91
aStr
void EnableAutoSize(bool bAuto)
Definition: combobox.cxx:516
static std::unique_ptr< JSInstanceBuilder > CreateFormulabarBuilder(vcl::Window *pParent, const OUString &rUIRoot, const OUString &rUIFile, sal_uInt64 nLOKWindowId)
std::unique_ptr< Entry > m_xEntry
Definition: weld.hxx:1863
ImplToolItems::size_type GetItemCount() const
Definition: toolbox2.cxx:709
bool IsEntryVisible(const weld::TreeView &rTreeView, const weld::TreeIter &rIter)
Definition: builder.cxx:424
void SetHelpText(sal_uInt16 nPageId, const OUString &rText)
Definition: tabctrl.cxx:1954
static weld::MessageDialog * CreateMessageDialog(weld::Widget *pParent, VclMessageType eMessageType, VclButtonsType eButtonType, const OUString &rPrimaryMessage, bool bMobile=false)
Definition: builder.cxx:213
virtual void SetText(const OUString &rStr) override
Definition: vclmedit.cxx:1103
SalInstance * mpDefInst
Definition: svdata.hxx:390
void SetQuickSearch(bool bEnable)
HeaderBarItemBits
Definition: headbar.hxx:180
virtual void SetValue(sal_Int64 nNewValue)
Definition: field.cxx:603
void set_padding(sal_Int32 nPadding)
Definition: window2.cxx:1800
vcl::Window * GetPageParent()
WinBits const WB_ALLOWMENUBAR
void set_response(std::string_view sID, short nResponse)
Definition: builder.cxx:4049
sal_uInt16 nPos
static void addKeyValue(SAL_UNUSED_PARAMETER const OUString &, SAL_UNUSED_PARAMETER const OUString &, SAL_UNUSED_PARAMETER tAddKeyHandling)
static std::unique_ptr< weld::Builder > CreateBuilder(weld::Widget *pParent, const OUString &rUIFile, bool bMobile=false, sal_uInt64 nLOKWindowId=0)
Definition: builder.cxx:184
sal_uInt16 GetCurPageId() const
Definition: tabctrl.cxx:1858
void set_expand(bool bExpand)
Definition: window2.cxx:1776
virtual void SetSpinSize(double dStep)
Definition: formatter.hxx:226
sal_Int16 nValue
virtual int iter_compare(const TreeIter &a, const TreeIter &b) const =0
virtual int get_iter_depth(const TreeIter &rIter) const =0
void Show(bool bVisible=true, ShowFlags nFlags=ShowFlags::NONE)
Definition: window.cxx:2189
OUString sId
typedef void(CALLTYPE *GetFuncDataPtr)(sal_uInt16 &nNo