Use COMReference to handle COM pointers in CreateShortcut
[LibreOffice.git] / starmath / source / dialog.cxx
blob498c3070f0beaae6e1c731811ade43bd6bfa6481
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3 * This file is part of the LibreOffice project.
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 * This file incorporates work covered by the following license notice:
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
20 #include <sal/config.h>
21 #include <sal/log.hxx>
23 #include <comphelper/string.hxx>
24 #include <o3tl/temporary.hxx>
25 #include <svl/eitem.hxx>
26 #include <svl/intitem.hxx>
27 #include <svl/stritem.hxx>
28 #include <vcl/event.hxx>
29 #include <vcl/svapp.hxx>
30 #include <vcl/virdev.hxx>
31 #include <vcl/weld.hxx>
32 #include <svtools/ctrltool.hxx>
33 #include <vcl/settings.hxx>
34 #include <vcl/wall.hxx>
35 #include <vcl/fontcharmap.hxx>
36 #include <sfx2/dispatch.hxx>
37 #include <svx/charmap.hxx>
38 #include <svx/ucsubset.hxx>
40 #include <dialog.hxx>
41 #include <starmath.hrc>
42 #include <strings.hrc>
43 #include <helpids.h>
44 #include <cfgitem.hxx>
45 #include <officecfg/Office/Math.hxx>
46 #include <smmod.hxx>
47 #include <symbol.hxx>
48 #include <view.hxx>
50 #include <algorithm>
52 namespace
55 void lclGetSettingColors(Color& rBackgroundColor, Color& rTextColor)
57 const StyleSettings& rStyleSettings = Application::GetSettings().GetStyleSettings();
58 if (rStyleSettings.GetHighContrastMode())
60 rBackgroundColor = rStyleSettings.GetFieldColor();
61 rTextColor = rStyleSettings.GetFieldTextColor();
63 else
65 rBackgroundColor = rStyleSettings.GetFaceColor();
66 rTextColor = rStyleSettings.GetLabelTextColor();
70 // Since it's better to set/query the FontStyle via its attributes rather
71 // than via the StyleName we create a way to translate
72 // Attribute <-> StyleName
74 class SmFontStyles
76 OUString aNormal;
77 OUString aBold;
78 OUString aItalic;
79 OUString aBoldItalic;
81 public:
82 SmFontStyles();
84 static sal_uInt16 GetCount() { return 4; }
85 const OUString& GetStyleName(const vcl::Font& rFont) const;
86 const OUString& GetStyleName(sal_uInt16 nIdx) const;
89 vcl::Font lclGetSymbolFont(const SmViewShell& rViewShell, const SmSym &rSymbol)
91 const SmDocShell* pDoc = rViewShell.GetDoc();
92 if (pDoc)
94 // If we have a document, we want to render the symbol using the font and style used in
95 // the document, so we do that by creating a node and preparing it, then get the resolved
96 // font and style from it.
97 SmToken token(TSPECIAL, '\0', "%" + rSymbol.GetUiName());
98 SmSpecialNode aNode(token);
99 aNode.Prepare(pDoc->GetFormat(), *pDoc, 1);
100 aNode.PrepareAttributes();
101 return aNode.GetFont();
104 return rSymbol.GetFace();
107 } // end anonymous namespace
109 SmFontStyles::SmFontStyles()
110 : aNormal(SmResId(RID_FONTREGULAR))
111 , aBold(SmResId(RID_FONTBOLD))
112 , aItalic(SmResId(RID_FONTITALIC))
114 aBoldItalic = aBold;
115 aBoldItalic += ", ";
116 aBoldItalic += aItalic;
119 const OUString& SmFontStyles::GetStyleName(const vcl::Font& rFont) const
121 //! compare also SmSpecialNode::Prepare
122 bool bBold = IsBold( rFont ),
123 bItalic = IsItalic( rFont );
125 if (bBold && bItalic)
126 return aBoldItalic;
127 else if (bItalic)
128 return aItalic;
129 else if (bBold)
130 return aBold;
131 return aNormal;
134 const OUString& SmFontStyles::GetStyleName( sal_uInt16 nIdx ) const
136 // 0 = "normal", 1 = "italic",
137 // 2 = "bold", 3 = "bold italic"
139 assert( nIdx < GetCount() );
140 switch (nIdx)
142 case 0 : return aNormal;
143 case 1 : return aItalic;
144 case 2 : return aBold;
145 default: /*case 3:*/ return aBoldItalic;
149 static const SmFontStyles & GetFontStyles()
151 static const SmFontStyles aImpl;
152 return aImpl;
155 void SetFontStyle(std::u16string_view rStyleName, vcl::Font &rFont)
157 // Find index related to StyleName. For an empty StyleName it's assumed to be
158 // 0 (neither bold nor italic).
159 sal_uInt16 nIndex = 0;
160 if (!rStyleName.empty())
162 sal_uInt16 i;
163 const SmFontStyles &rStyles = GetFontStyles();
164 for (i = 0; i < SmFontStyles::GetCount(); ++i)
165 if (rStyleName == rStyles.GetStyleName(i))
166 break;
167 assert(i < SmFontStyles::GetCount() && "style-name unknown");
168 nIndex = i;
171 rFont.SetItalic((nIndex & 0x1) ? ITALIC_NORMAL : ITALIC_NONE);
172 rFont.SetWeight((nIndex & 0x2) ? WEIGHT_BOLD : WEIGHT_NORMAL);
175 IMPL_LINK_NOARG(SmPrintOptionsTabPage, SizeButtonClickHdl, weld::Toggleable&, void)
177 m_xZoom->set_sensitive(m_xSizeZoomed->get_active());
180 SmPrintOptionsTabPage::SmPrintOptionsTabPage(weld::Container* pPage, weld::DialogController* pController, const SfxItemSet& rOptions)
181 : SfxTabPage(pPage, pController, u"modules/smath/ui/smathsettings.ui"_ustr, u"SmathSettings"_ustr, &rOptions)
182 , m_xTitle(m_xBuilder->weld_check_button(u"title"_ustr))
183 , m_xTitleImg(m_xBuilder->weld_widget(u"locktitle"_ustr))
184 , m_xText(m_xBuilder->weld_check_button(u"text"_ustr))
185 , m_xTextImg(m_xBuilder->weld_widget(u"locktext"_ustr))
186 , m_xFrame(m_xBuilder->weld_check_button(u"frame"_ustr))
187 , m_xFrameImg(m_xBuilder->weld_widget(u"lockframe"_ustr))
188 , m_xSizeNormal(m_xBuilder->weld_radio_button(u"sizenormal"_ustr))
189 , m_xSizeScaled(m_xBuilder->weld_radio_button(u"sizescaled"_ustr))
190 , m_xSizeZoomed(m_xBuilder->weld_radio_button(u"sizezoomed"_ustr))
191 , m_xLockPrintImg(m_xBuilder->weld_widget(u"lockprintformat"_ustr))
192 , m_xZoom(m_xBuilder->weld_metric_spin_button(u"zoom"_ustr, FieldUnit::PERCENT))
193 , m_xEnableInlineEdit(m_xBuilder->weld_check_button(u"enableinlineedit"_ustr))
194 , m_xEnableInlineEditImg(m_xBuilder->weld_widget(u"lockenableinlineedit"_ustr))
195 , m_xNoRightSpaces(m_xBuilder->weld_check_button(u"norightspaces"_ustr))
196 , m_xNoRightSpacesImg(m_xBuilder->weld_widget(u"locknorightspaces"_ustr))
197 , m_xSaveOnlyUsedSymbols(m_xBuilder->weld_check_button(u"saveonlyusedsymbols"_ustr))
198 , m_xSaveOnlyUsedSymbolsImg(m_xBuilder->weld_widget(u"locksaveonlyusedsymbols"_ustr))
199 , m_xAutoCloseBrackets(m_xBuilder->weld_check_button(u"autoclosebrackets"_ustr))
200 , m_xAutoCloseBracketsImg(m_xBuilder->weld_widget(u"lockautoclosebrackets"_ustr))
201 , m_xSmZoom(m_xBuilder->weld_metric_spin_button(u"smzoom"_ustr, FieldUnit::PERCENT))
202 , m_xSmZoomImg(m_xBuilder->weld_widget(u"locksmzoom"_ustr))
204 m_xSizeNormal->connect_toggled(LINK(this, SmPrintOptionsTabPage, SizeButtonClickHdl));
205 m_xSizeScaled->connect_toggled(LINK(this, SmPrintOptionsTabPage, SizeButtonClickHdl));
206 m_xSizeZoomed->connect_toggled(LINK(this, SmPrintOptionsTabPage, SizeButtonClickHdl));
208 Reset(&rOptions);
211 SmPrintOptionsTabPage::~SmPrintOptionsTabPage()
213 if (SmViewShell *pViewSh = SmGetActiveView())
214 if (SmEditWindow* pEdit = pViewSh->GetEditWindow())
215 pEdit->UpdateStatus();
218 OUString SmPrintOptionsTabPage::GetAllStrings()
220 OUString sAllStrings;
221 OUString labels[] = { u"label4"_ustr, u"label5"_ustr, u"label1"_ustr, u"label6"_ustr };
223 for (const auto& label : labels)
225 if (const auto pString = m_xBuilder->weld_label(label))
226 sAllStrings += pString->get_label() + " ";
229 OUString checkButton[]
230 = { u"title"_ustr, u"text"_ustr, u"frame"_ustr, u"norightspaces"_ustr, u"saveonlyusedsymbols"_ustr, u"autoclosebrackets"_ustr };
232 for (const auto& check : checkButton)
234 if (const auto pString = m_xBuilder->weld_check_button(check))
235 sAllStrings += pString->get_label() + " ";
238 OUString radioButton[] = { u"sizenormal"_ustr, u"sizescaled"_ustr, u"sizezoomed"_ustr };
240 for (const auto& radio : radioButton)
242 if (const auto pString = m_xBuilder->weld_radio_button(radio))
243 sAllStrings += pString->get_label() + " ";
246 return sAllStrings.replaceAll("_", "");
249 bool SmPrintOptionsTabPage::FillItemSet(SfxItemSet* rSet)
251 sal_uInt16 nPrintSize;
252 if (m_xSizeNormal->get_active())
253 nPrintSize = PRINT_SIZE_NORMAL;
254 else if (m_xSizeScaled->get_active())
255 nPrintSize = PRINT_SIZE_SCALED;
256 else
257 nPrintSize = PRINT_SIZE_ZOOMED;
259 rSet->Put(SfxUInt16Item(SID_PRINTSIZE, nPrintSize));
260 rSet->Put(SfxUInt16Item(SID_PRINTZOOM, sal::static_int_cast<sal_uInt16>(m_xZoom->get_value(FieldUnit::PERCENT))));
261 rSet->Put(SfxBoolItem(SID_PRINTTITLE, m_xTitle->get_active()));
262 rSet->Put(SfxBoolItem(SID_PRINTTEXT, m_xText->get_active()));
263 rSet->Put(SfxBoolItem(SID_PRINTFRAME, m_xFrame->get_active()));
264 rSet->Put(SfxBoolItem(SID_INLINE_EDIT_ENABLE, m_xEnableInlineEdit->get_active()));
265 rSet->Put(SfxBoolItem(SID_NO_RIGHT_SPACES, m_xNoRightSpaces->get_active()));
266 rSet->Put(SfxBoolItem(SID_SAVE_ONLY_USED_SYMBOLS, m_xSaveOnlyUsedSymbols->get_active()));
267 rSet->Put(SfxBoolItem(SID_AUTO_CLOSE_BRACKETS, m_xAutoCloseBrackets->get_active()));
268 rSet->Put(SfxUInt16Item(SID_SMEDITWINDOWZOOM, sal::static_int_cast<sal_uInt16>(m_xSmZoom->get_value(FieldUnit::PERCENT))));
270 if (SmViewShell *pViewSh = SmGetActiveView())
271 if (SmEditWindow* pEdit = pViewSh->GetEditWindow())
272 pEdit->UpdateStatus();
274 return true;
277 void SmPrintOptionsTabPage::Reset(const SfxItemSet* rSet)
279 SmPrintSize ePrintSize = static_cast<SmPrintSize>(rSet->Get(SID_PRINTSIZE).GetValue());
281 m_xSizeNormal->set_active(ePrintSize == PRINT_SIZE_NORMAL);
282 m_xSizeScaled->set_active(ePrintSize == PRINT_SIZE_SCALED);
283 m_xSizeZoomed->set_active(ePrintSize == PRINT_SIZE_ZOOMED);
284 bool bReadOnly = officecfg::Office::Math::Print::Size::isReadOnly();
285 if (bReadOnly)
287 m_xSizeNormal->set_sensitive(false);
288 m_xSizeScaled->set_sensitive(false);
289 m_xSizeZoomed->set_sensitive(false);
290 m_xLockPrintImg->set_visible(true);
293 bReadOnly = officecfg::Office::Math::Print::ZoomFactor::isReadOnly();
294 m_xZoom->set_value(rSet->Get(SID_PRINTZOOM).GetValue(), FieldUnit::PERCENT);
295 m_xZoom->set_sensitive(m_xSizeZoomed->get_active() && !bReadOnly);
297 bReadOnly = officecfg::Office::Math::Misc::SmEditWindowZoomFactor::isReadOnly();
298 m_xSmZoom->set_value(rSet->Get(SID_SMEDITWINDOWZOOM).GetValue(), FieldUnit::PERCENT);
299 m_xSmZoom->set_sensitive(!bReadOnly);
300 m_xSmZoomImg->set_visible(bReadOnly);
302 bReadOnly = officecfg::Office::Math::Print::Title::isReadOnly();
303 m_xTitle->set_active(rSet->Get(SID_PRINTTITLE).GetValue());
304 m_xTitle->set_sensitive(!bReadOnly);
305 m_xTitleImg->set_visible(bReadOnly);
307 bReadOnly = officecfg::Office::Math::Print::FormulaText::isReadOnly();
308 m_xText->set_active(rSet->Get(GetWhich(SID_PRINTTEXT)).GetValue());
309 m_xText->set_sensitive(!bReadOnly);
310 m_xTextImg->set_visible(bReadOnly);
312 bReadOnly = officecfg::Office::Math::Print::Frame::isReadOnly();
313 m_xFrame->set_active(rSet->Get(GetWhich(SID_PRINTFRAME)).GetValue());
314 m_xFrame->set_sensitive(!bReadOnly);
315 m_xFrameImg->set_visible(bReadOnly);
317 bReadOnly = officecfg::Office::Math::Misc::InlineEditEnable::isReadOnly();
318 m_xEnableInlineEdit->set_active(rSet->Get(SID_INLINE_EDIT_ENABLE).GetValue());
319 m_xEnableInlineEdit->set_sensitive(!bReadOnly);
320 m_xEnableInlineEditImg->set_visible(bReadOnly);
322 bReadOnly = officecfg::Office::Math::Misc::IgnoreSpacesRight::isReadOnly();
323 m_xNoRightSpaces->set_active(rSet->Get(SID_NO_RIGHT_SPACES).GetValue());
324 m_xNoRightSpaces->set_sensitive(!bReadOnly);
325 m_xNoRightSpacesImg->set_visible(bReadOnly);
327 bReadOnly = officecfg::Office::Math::LoadSave::IsSaveOnlyUsedSymbols::isReadOnly();
328 m_xSaveOnlyUsedSymbols->set_active(rSet->Get(SID_SAVE_ONLY_USED_SYMBOLS).GetValue());
329 m_xSaveOnlyUsedSymbols->set_sensitive(!bReadOnly);
330 m_xSaveOnlyUsedSymbolsImg->set_visible(bReadOnly);
332 bReadOnly = officecfg::Office::Math::Misc::AutoCloseBrackets::isReadOnly();
333 m_xAutoCloseBrackets->set_active(rSet->Get(SID_AUTO_CLOSE_BRACKETS).GetValue());
334 m_xAutoCloseBrackets->set_sensitive(!bReadOnly);
335 m_xAutoCloseBracketsImg->set_visible(bReadOnly);
338 std::unique_ptr<SfxTabPage> SmPrintOptionsTabPage::Create(weld::Container* pPage, weld::DialogController* pController, const SfxItemSet& rSet)
340 return std::make_unique<SmPrintOptionsTabPage>(pPage, pController, rSet);
343 void SmShowFont::Paint(vcl::RenderContext& rRenderContext, const tools::Rectangle& /*rRect*/)
345 Color aBackColor;
346 Color aTextColor;
347 lclGetSettingColors(aBackColor, aTextColor);
349 rRenderContext.SetBackground(Wallpaper(aBackColor));
351 vcl::Font aFont(maFont);
352 aFont.SetFontSize(Size(0, 24 * rRenderContext.GetDPIScaleFactor()));
353 aFont.SetAlignment(ALIGN_TOP);
354 rRenderContext.SetFont(aFont);
355 rRenderContext.SetTextColor(aTextColor);
357 OUString sText(rRenderContext.GetFont().GetFamilyName());
358 Size aTextSize(rRenderContext.GetTextWidth(sText), rRenderContext.GetTextHeight());
360 rRenderContext.DrawText(Point((rRenderContext.GetOutputSize().Width() - aTextSize.Width()) / 2,
361 (rRenderContext.GetOutputSize().Height() - aTextSize.Height()) / 2), sText);
364 void SmShowFont::SetDrawingArea(weld::DrawingArea* pDrawingArea)
366 CustomWidgetController::SetDrawingArea(pDrawingArea);
367 Size aSize(pDrawingArea->get_ref_device().LogicToPixel(Size(111 , 31), MapMode(MapUnit::MapAppFont)));
368 pDrawingArea->set_size_request(aSize.Width(), aSize.Height());
371 void SmShowFont::SetFont(const vcl::Font& rFont)
373 maFont = rFont;
374 Invalidate();
377 IMPL_LINK( SmFontDialog, FontSelectHdl, weld::ComboBox&, rComboBox, void )
379 maFont.SetFamilyName(rComboBox.get_active_text());
380 m_aShowFont.SetFont(maFont);
383 IMPL_LINK_NOARG(SmFontDialog, AttrChangeHdl, weld::Toggleable&, void)
385 if (m_xBoldCheckBox->get_active())
386 maFont.SetWeight(WEIGHT_BOLD);
387 else
388 maFont.SetWeight(WEIGHT_NORMAL);
390 if (m_xItalicCheckBox->get_active())
391 maFont.SetItalic(ITALIC_NORMAL);
392 else
393 maFont.SetItalic(ITALIC_NONE);
395 m_aShowFont.SetFont(maFont);
398 void SmFontDialog::SetFont(const vcl::Font &rFont)
400 maFont = rFont;
402 m_xFontBox->set_active_text(maFont.GetFamilyName());
403 m_xBoldCheckBox->set_active(IsBold(maFont));
404 m_xItalicCheckBox->set_active(IsItalic(maFont));
405 m_aShowFont.SetFont(maFont);
408 SmFontDialog::SmFontDialog(weld::Window * pParent, OutputDevice *pFntListDevice, bool bHideCheckboxes)
409 : GenericDialogController(pParent, u"modules/smath/ui/fontdialog.ui"_ustr, u"FontDialog"_ustr)
410 , m_xFontBox(m_xBuilder->weld_entry_tree_view(u"fontgrid"_ustr, u"font"_ustr, u"fonts"_ustr))
411 , m_xAttrFrame(m_xBuilder->weld_widget(u"attrframe"_ustr))
412 , m_xBoldCheckBox(m_xBuilder->weld_check_button(u"bold"_ustr))
413 , m_xItalicCheckBox(m_xBuilder->weld_check_button(u"italic"_ustr))
414 , m_xShowFont(new weld::CustomWeld(*m_xBuilder, u"preview"_ustr, m_aShowFont))
416 m_xFontBox->set_height_request_by_rows(8);
419 weld::WaitObject aWait(pParent);
421 FontList aFontList( pFntListDevice );
423 sal_uInt16 nCount = aFontList.GetFontNameCount();
424 for (sal_uInt16 i = 0; i < nCount; ++i)
426 m_xFontBox->append_text(aFontList.GetFontName(i).GetFamilyName());
428 maFont.SetFontSize(Size(0, 24));
429 maFont.SetWeight(WEIGHT_NORMAL);
430 maFont.SetItalic(ITALIC_NONE);
431 maFont.SetFamily(FAMILY_DONTKNOW);
432 maFont.SetPitch(PITCH_DONTKNOW);
433 maFont.SetCharSet(RTL_TEXTENCODING_DONTKNOW);
434 maFont.SetTransparent(true);
437 m_xFontBox->connect_changed(LINK(this, SmFontDialog, FontSelectHdl));
438 m_xBoldCheckBox->connect_toggled(LINK(this, SmFontDialog, AttrChangeHdl));
439 m_xItalicCheckBox->connect_toggled(LINK(this, SmFontDialog, AttrChangeHdl));
441 if (bHideCheckboxes)
443 m_xBoldCheckBox->set_active(false);
444 m_xBoldCheckBox->set_sensitive(false);
445 m_xItalicCheckBox->set_active(false);
446 m_xItalicCheckBox->set_sensitive(false);
447 m_xAttrFrame->hide();
451 SmFontDialog::~SmFontDialog()
455 namespace {
457 class SaveDefaultsQuery : public weld::MessageDialogController
459 public:
460 explicit SaveDefaultsQuery(weld::Widget* pParent)
461 : MessageDialogController(pParent, u"modules/smath/ui/savedefaultsdialog.ui"_ustr,
462 u"SaveDefaultsDialog"_ustr)
469 IMPL_LINK_NOARG( SmFontSizeDialog, DefaultButtonClickHdl, weld::Button&, void )
471 SaveDefaultsQuery aQuery(m_xDialog.get());
472 if (aQuery.run() == RET_YES)
474 auto* config = SmModule::get()->GetConfig();
475 SmFormat aFmt(config->GetStandardFormat());
476 WriteTo( aFmt );
477 config->SetStandardFormat(aFmt);
481 SmFontSizeDialog::SmFontSizeDialog(weld::Window* pParent)
482 : GenericDialogController(pParent, u"modules/smath/ui/fontsizedialog.ui"_ustr, u"FontSizeDialog"_ustr)
483 , m_xBaseSize(m_xBuilder->weld_metric_spin_button(u"spinB_baseSize"_ustr, FieldUnit::POINT))
484 , m_xTextSize(m_xBuilder->weld_metric_spin_button(u"spinB_text"_ustr, FieldUnit::PERCENT))
485 , m_xIndexSize(m_xBuilder->weld_metric_spin_button(u"spinB_index"_ustr, FieldUnit::PERCENT))
486 , m_xFunctionSize(m_xBuilder->weld_metric_spin_button(u"spinB_function"_ustr, FieldUnit::PERCENT))
487 , m_xOperatorSize(m_xBuilder->weld_metric_spin_button(u"spinB_operator"_ustr, FieldUnit::PERCENT))
488 , m_xBorderSize(m_xBuilder->weld_metric_spin_button(u"spinB_limit"_ustr, FieldUnit::PERCENT))
489 , m_xDefaultButton(m_xBuilder->weld_button(u"default"_ustr))
491 m_xDefaultButton->connect_clicked(LINK(this, SmFontSizeDialog, DefaultButtonClickHdl));
494 SmFontSizeDialog::~SmFontSizeDialog()
498 void SmFontSizeDialog::ReadFrom(const SmFormat &rFormat)
500 //! watch out: round properly!
501 m_xBaseSize->set_value(
502 o3tl::convert(rFormat.GetBaseSize().Height(), SmO3tlLengthUnit(), o3tl::Length::pt),
503 FieldUnit::NONE);
505 m_xTextSize->set_value( rFormat.GetRelSize(SIZ_TEXT), FieldUnit::NONE );
506 m_xIndexSize->set_value( rFormat.GetRelSize(SIZ_INDEX), FieldUnit::NONE );
507 m_xFunctionSize->set_value( rFormat.GetRelSize(SIZ_FUNCTION), FieldUnit::NONE );
508 m_xOperatorSize->set_value( rFormat.GetRelSize(SIZ_OPERATOR), FieldUnit::NONE );
509 m_xBorderSize->set_value( rFormat.GetRelSize(SIZ_LIMITS), FieldUnit::NONE );
512 void SmFontSizeDialog::WriteTo(SmFormat &rFormat) const
514 rFormat.SetBaseSize( Size(0, o3tl::convert(m_xBaseSize->get_value(FieldUnit::NONE), o3tl::Length::pt, SmO3tlLengthUnit())) );
516 rFormat.SetRelSize(SIZ_TEXT, sal::static_int_cast<sal_uInt16>(m_xTextSize->get_value(FieldUnit::NONE)));
517 rFormat.SetRelSize(SIZ_INDEX, sal::static_int_cast<sal_uInt16>(m_xIndexSize->get_value(FieldUnit::NONE)));
518 rFormat.SetRelSize(SIZ_FUNCTION, sal::static_int_cast<sal_uInt16>(m_xFunctionSize->get_value(FieldUnit::NONE)));
519 rFormat.SetRelSize(SIZ_OPERATOR, sal::static_int_cast<sal_uInt16>(m_xOperatorSize->get_value(FieldUnit::NONE)));
520 rFormat.SetRelSize(SIZ_LIMITS, sal::static_int_cast<sal_uInt16>(m_xBorderSize->get_value(FieldUnit::NONE)));
522 const Size aTmp (rFormat.GetBaseSize());
523 for (sal_uInt16 i = FNT_BEGIN; i <= FNT_END; i++)
524 rFormat.SetFontSize(i, aTmp);
526 rFormat.RequestApplyChanges();
529 IMPL_LINK(SmFontTypeDialog, MenuSelectHdl, const OUString&, rIdent, void)
531 SmFontPickListBox *pActiveListBox;
533 bool bHideCheckboxes = false;
534 if (rIdent == "math")
535 pActiveListBox = m_xMathFont.get();
536 else if (rIdent == "variables")
537 pActiveListBox = m_xVariableFont.get();
538 else if (rIdent == "functions")
539 pActiveListBox = m_xFunctionFont.get();
540 else if (rIdent == "numbers")
541 pActiveListBox = m_xNumberFont.get();
542 else if (rIdent == "text")
543 pActiveListBox = m_xTextFont.get();
544 else if (rIdent == "serif")
546 pActiveListBox = m_xSerifFont.get();
547 bHideCheckboxes = true;
549 else if (rIdent == "sansserif")
551 pActiveListBox = m_xSansFont.get();
552 bHideCheckboxes = true;
554 else if (rIdent == "fixedwidth")
556 pActiveListBox = m_xFixedFont.get();
557 bHideCheckboxes = true;
559 else
560 pActiveListBox = nullptr;
562 if (pActiveListBox)
564 SmFontDialog aFontDialog(m_xDialog.get(), pFontListDev, bHideCheckboxes);
566 pActiveListBox->WriteTo(aFontDialog);
567 if (aFontDialog.run() == RET_OK)
568 pActiveListBox->ReadFrom(aFontDialog);
572 IMPL_LINK_NOARG(SmFontTypeDialog, DefaultButtonClickHdl, weld::Button&, void)
574 SaveDefaultsQuery aQuery(m_xDialog.get());
575 if (aQuery.run() == RET_YES)
577 auto* config = SmModule::get()->GetConfig();
578 SmFormat aFmt(config->GetStandardFormat());
579 WriteTo( aFmt );
580 config->SetStandardFormat(aFmt, true);
584 SmFontTypeDialog::SmFontTypeDialog(weld::Window* pParent, OutputDevice *pFntListDevice)
585 : GenericDialogController(pParent, u"modules/smath/ui/fonttypedialog.ui"_ustr, u"FontsDialog"_ustr)
586 , pFontListDev(pFntListDevice)
587 , m_xMathFont(new SmFontPickListBox(m_xBuilder->weld_combo_box(u"mathCB"_ustr)))
588 , m_xVariableFont(new SmFontPickListBox(m_xBuilder->weld_combo_box(u"variableCB"_ustr)))
589 , m_xFunctionFont(new SmFontPickListBox(m_xBuilder->weld_combo_box(u"functionCB"_ustr)))
590 , m_xNumberFont(new SmFontPickListBox(m_xBuilder->weld_combo_box(u"numberCB"_ustr)))
591 , m_xTextFont(new SmFontPickListBox(m_xBuilder->weld_combo_box(u"textCB"_ustr)))
592 , m_xSerifFont(new SmFontPickListBox(m_xBuilder->weld_combo_box(u"serifCB"_ustr)))
593 , m_xSansFont(new SmFontPickListBox(m_xBuilder->weld_combo_box(u"sansCB"_ustr)))
594 , m_xFixedFont(new SmFontPickListBox(m_xBuilder->weld_combo_box(u"fixedCB"_ustr)))
595 , m_xMenuButton(m_xBuilder->weld_menu_button(u"modify"_ustr))
596 , m_xDefaultButton(m_xBuilder->weld_button(u"default"_ustr))
598 m_xDefaultButton->connect_clicked(LINK(this, SmFontTypeDialog, DefaultButtonClickHdl));
599 m_xMenuButton->connect_selected(LINK(this, SmFontTypeDialog, MenuSelectHdl));
602 SmFontTypeDialog::~SmFontTypeDialog()
606 void SmFontTypeDialog::ReadFrom(const SmFormat &rFormat)
608 auto* config = SmModule::get()->GetConfig();
610 *m_xMathFont = config->GetFontPickList(FNT_MATH);
611 *m_xVariableFont = config->GetFontPickList(FNT_VARIABLE);
612 *m_xFunctionFont = config->GetFontPickList(FNT_FUNCTION);
613 *m_xNumberFont = config->GetFontPickList(FNT_NUMBER);
614 *m_xTextFont = config->GetFontPickList(FNT_TEXT);
615 *m_xSerifFont = config->GetFontPickList(FNT_SERIF);
616 *m_xSansFont = config->GetFontPickList(FNT_SANS);
617 *m_xFixedFont = config->GetFontPickList(FNT_FIXED);
619 m_xMathFont->Insert( rFormat.GetFont(FNT_MATH) );
620 m_xVariableFont->Insert( rFormat.GetFont(FNT_VARIABLE) );
621 m_xFunctionFont->Insert( rFormat.GetFont(FNT_FUNCTION) );
622 m_xNumberFont->Insert( rFormat.GetFont(FNT_NUMBER) );
623 m_xTextFont->Insert( rFormat.GetFont(FNT_TEXT) );
624 m_xSerifFont->Insert( rFormat.GetFont(FNT_SERIF) );
625 m_xSansFont->Insert( rFormat.GetFont(FNT_SANS) );
626 m_xFixedFont->Insert( rFormat.GetFont(FNT_FIXED) );
630 void SmFontTypeDialog::WriteTo(SmFormat &rFormat) const
632 auto* config = SmModule::get()->GetConfig();
634 config->GetFontPickList(FNT_MATH) = *m_xMathFont;
635 config->GetFontPickList(FNT_VARIABLE) = *m_xVariableFont;
636 config->GetFontPickList(FNT_FUNCTION) = *m_xFunctionFont;
637 config->GetFontPickList(FNT_NUMBER) = *m_xNumberFont;
638 config->GetFontPickList(FNT_TEXT) = *m_xTextFont;
639 config->GetFontPickList(FNT_SERIF) = *m_xSerifFont;
640 config->GetFontPickList(FNT_SANS) = *m_xSansFont;
641 config->GetFontPickList(FNT_FIXED) = *m_xFixedFont;
643 rFormat.SetFont( FNT_MATH, SmFace(m_xMathFont->Get()) );
644 rFormat.SetFont( FNT_VARIABLE, SmFace(m_xVariableFont->Get()) );
645 rFormat.SetFont( FNT_FUNCTION, SmFace(m_xFunctionFont->Get()) );
646 rFormat.SetFont( FNT_NUMBER, SmFace(m_xNumberFont->Get()) );
647 rFormat.SetFont( FNT_TEXT, SmFace(m_xTextFont->Get()) );
648 rFormat.SetFont( FNT_SERIF, SmFace(m_xSerifFont->Get()) );
649 rFormat.SetFont( FNT_SANS, SmFace(m_xSansFont->Get()) );
650 rFormat.SetFont( FNT_FIXED, SmFace(m_xFixedFont->Get()) );
652 rFormat.RequestApplyChanges();
655 /**************************************************************************/
657 namespace {
659 struct FieldMinMax
661 sal_uInt16 nMin, nMax;
666 // Data for min and max values of the 4 metric fields
667 // for each of the 10 categories
668 const FieldMinMax pMinMaxData[10][4] =
670 // 0
671 {{ 0, 200 }, { 0, 200 }, { 0, 100 }, { 0, 0 }},
672 // 1
673 {{ 0, 100 }, { 0, 100 }, { 0, 0 }, { 0, 0 }},
674 // 2
675 {{ 0, 100 }, { 0, 100 }, { 0, 0 }, { 0, 0 }},
676 // 3
677 {{ 0, 100 }, { 1, 100 }, { 0, 0 }, { 0, 0 }},
678 // 4
679 {{ 0, 100 }, { 0, 100 }, { 0, 0 }, { 0, 0 }},
680 // 5
681 {{ 0, 100 }, { 0, 100 }, { 0, 0 }, { 0, 100 }},
682 // 6
683 {{ 0, 300 }, { 0, 300 }, { 0, 0 }, { 0, 0 }},
684 // 7
685 {{ 0, 100 }, { 0, 100 }, { 0, 0 }, { 0, 0 }},
686 // 8
687 {{ 0, 100 }, { 0, 100 }, { 0, 0 }, { 0, 0 }},
688 // 9
689 {{ 0, 10000 }, { 0, 10000 }, { 0, 10000 }, { 0, 10000 }}
692 SmCategoryDesc::SmCategoryDesc(weld::Builder& rBuilder, sal_uInt16 nCategoryIdx)
694 ++nCategoryIdx;
695 std::unique_ptr<weld::Label> xTitle(rBuilder.weld_label(OUString::number(nCategoryIdx)+"title"));
696 if (xTitle)
698 Name = xTitle->get_label();
700 for (int i = 0; i < 4; ++i)
702 std::unique_ptr<weld::Label> xLabel(rBuilder.weld_label(OUString::number(nCategoryIdx)+"label"+OUString::number(i+1)));
704 if (xLabel)
706 Strings[i] = xLabel->get_label();
707 Graphics[i] = rBuilder.weld_widget(OUString::number(nCategoryIdx)+"image"+OUString::number(i+1));
709 else
711 Strings[i].clear();
712 Graphics[i].reset();
715 const FieldMinMax& rMinMax = pMinMaxData[ nCategoryIdx-1 ][i];
716 Value[i] = Minimum[i] = rMinMax.nMin;
717 Maximum[i] = rMinMax.nMax;
721 SmCategoryDesc::~SmCategoryDesc()
725 /**************************************************************************/
727 IMPL_LINK( SmDistanceDialog, GetFocusHdl, weld::Widget&, rControl, void )
729 if (!m_xCategories[nActiveCategory])
730 return;
732 sal_uInt16 i;
734 if (&rControl == &m_xMetricField1->get_widget())
735 i = 0;
736 else if (&rControl == &m_xMetricField2->get_widget())
737 i = 1;
738 else if (&rControl == &m_xMetricField3->get_widget())
739 i = 2;
740 else if (&rControl == &m_xMetricField4->get_widget())
741 i = 3;
742 else
743 return;
744 if (m_pCurrentImage)
745 m_pCurrentImage->hide();
746 m_pCurrentImage = m_xCategories[nActiveCategory]->GetGraphic(i);
747 m_pCurrentImage->show();
750 IMPL_LINK(SmDistanceDialog, MenuSelectHdl, const OUString&, rId, void)
752 assert(rId.startsWith("menuitem"));
753 SetCategory(rId.replaceFirst("menuitem", "").toInt32() - 1);
756 IMPL_LINK_NOARG( SmDistanceDialog, DefaultButtonClickHdl, weld::Button&, void )
758 SaveDefaultsQuery aQuery(m_xDialog.get());
759 if (aQuery.run() == RET_YES)
761 auto* config = SmModule::get()->GetConfig();
762 SmFormat aFmt(config->GetStandardFormat());
763 WriteTo( aFmt );
764 config->SetStandardFormat( aFmt );
768 IMPL_LINK( SmDistanceDialog, CheckBoxClickHdl, weld::Toggleable&, rCheckBox, void )
770 if (&rCheckBox == m_xCheckBox1.get())
772 bool bChecked = m_xCheckBox1->get_active();
773 m_xFixedText4->set_sensitive( bChecked );
774 m_xMetricField4->set_sensitive( bChecked );
778 void SmDistanceDialog::SetCategory(sal_uInt16 nCategory)
780 assert(nCategory < NOCATEGORIES && "Sm: wrong category number in SmDistanceDialog");
782 // array to convert category- and metricfield-number in help ids.
783 // 0 is used in case of unused combinations.
784 assert(NOCATEGORIES == 10 && "Sm : array doesn't fit into the number of categories");
785 static constexpr OUString EMPTY(u""_ustr);
786 static constexpr OUString aCatMf2Hid[10][4] =
788 { HID_SMA_DEFAULT_DIST, HID_SMA_LINE_DIST, HID_SMA_ROOT_DIST, EMPTY },
789 { HID_SMA_SUP_DIST, HID_SMA_SUB_DIST , EMPTY, EMPTY },
790 { HID_SMA_NUMERATOR_DIST, HID_SMA_DENOMINATOR_DIST, EMPTY, EMPTY },
791 { HID_SMA_FRACLINE_EXCWIDTH, HID_SMA_FRACLINE_LINEWIDTH, EMPTY, EMPTY },
792 { HID_SMA_UPPERLIMIT_DIST, HID_SMA_LOWERLIMIT_DIST, EMPTY, EMPTY },
793 { HID_SMA_BRACKET_EXCHEIGHT, HID_SMA_BRACKET_DIST, EMPTY, HID_SMA_BRACKET_EXCHEIGHT2 },
794 { HID_SMA_MATRIXROW_DIST, HID_SMA_MATRIXCOL_DIST, EMPTY, EMPTY },
795 { HID_SMA_ATTRIBUT_DIST, HID_SMA_INTERATTRIBUT_DIST, EMPTY, EMPTY },
796 { HID_SMA_OPERATOR_EXCHEIGHT, HID_SMA_OPERATOR_DIST, EMPTY, EMPTY },
797 { HID_SMA_LEFTBORDER_DIST, HID_SMA_RIGHTBORDER_DIST, HID_SMA_UPPERBORDER_DIST, HID_SMA_LOWERBORDER_DIST }
800 // array to help iterate over the controls
801 std::pair<weld::Label*, weld::MetricSpinButton*> const aWin[4] =
803 { m_xFixedText1.get(), m_xMetricField1.get() },
804 { m_xFixedText2.get(), m_xMetricField2.get() },
805 { m_xFixedText3.get(), m_xMetricField3.get() },
806 { m_xFixedText4.get(), m_xMetricField4.get() }
809 SmCategoryDesc *pCat;
811 // remember the (maybe new) settings of the active SmCategoryDesc
812 // before switching to the new one
813 if (nActiveCategory != CATEGORY_NONE)
815 pCat = m_xCategories[nActiveCategory].get();
816 pCat->SetValue(0, sal::static_int_cast<sal_uInt16>(m_xMetricField1->get_value(FieldUnit::NONE)));
817 pCat->SetValue(1, sal::static_int_cast<sal_uInt16>(m_xMetricField2->get_value(FieldUnit::NONE)));
818 pCat->SetValue(2, sal::static_int_cast<sal_uInt16>(m_xMetricField3->get_value(FieldUnit::NONE)));
819 pCat->SetValue(3, sal::static_int_cast<sal_uInt16>(m_xMetricField4->get_value(FieldUnit::NONE)));
821 if (nActiveCategory == 5)
822 bScaleAllBrackets = m_xCheckBox1->get_active();
824 m_xMenuButton->set_item_active("menuitem" + OUString::number(nActiveCategory + 1), false);
827 // activation/deactivation of the associated controls depending on the chosen category
828 bool bActive;
829 for (sal_uInt16 i = 0; i < 4; i++)
831 weld::Label *pFT = aWin[i].first;
832 weld::MetricSpinButton *pMF = aWin[i].second;
834 // To determine which Controls should be active, the existence
835 // of an associated HelpID is checked
836 bActive = !aCatMf2Hid[nCategory][i].isEmpty();
838 pFT->set_visible(bActive);
839 pFT->set_sensitive(bActive);
840 pMF->set_visible(bActive);
841 pMF->set_sensitive(bActive);
843 // set measurement unit and number of decimal places
844 FieldUnit eUnit;
845 sal_uInt16 nDigits;
846 if (nCategory < 9)
848 eUnit = FieldUnit::PERCENT;
849 nDigits = 0;
851 else
853 eUnit = FieldUnit::MM_100TH;
854 nDigits = 2;
856 pMF->set_unit(eUnit); // changes the value
857 pMF->set_digits(nDigits);
859 if (bActive)
861 pCat = m_xCategories[nCategory].get();
862 pFT->set_label(pCat->GetString(i));
864 pMF->set_range(pCat->GetMinimum(i), pCat->GetMaximum(i), FieldUnit::NONE);
865 pMF->set_value(pCat->GetValue(i), FieldUnit::NONE);
867 pMF->set_help_id(aCatMf2Hid[nCategory][i]);
870 // activate the CheckBox and the associated MetricField if we're dealing with the brackets menu
871 bActive = nCategory == 5;
872 m_xCheckBox1->set_visible(bActive);
873 m_xCheckBox1->set_sensitive(bActive);
874 if (bActive)
876 m_xCheckBox1->set_active(bScaleAllBrackets);
878 bool bChecked = m_xCheckBox1->get_active();
879 m_xFixedText4->set_sensitive( bChecked );
880 m_xMetricField4->set_sensitive( bChecked );
883 m_xMenuButton->set_item_active("menuitem" + OUString::number(nCategory + 1), true);
884 m_xFrame->set_label(m_xCategories[nCategory]->GetName());
886 nActiveCategory = nCategory;
888 m_xMetricField1->grab_focus();
891 SmDistanceDialog::SmDistanceDialog(weld::Window *pParent)
892 : GenericDialogController(pParent, u"modules/smath/ui/spacingdialog.ui"_ustr, u"SpacingDialog"_ustr)
893 , m_xFrame(m_xBuilder->weld_frame(u"template"_ustr))
894 , m_xFixedText1(m_xBuilder->weld_label(u"label1"_ustr))
895 , m_xMetricField1(m_xBuilder->weld_metric_spin_button(u"spinbutton1"_ustr, FieldUnit::CM))
896 , m_xFixedText2(m_xBuilder->weld_label(u"label2"_ustr))
897 , m_xMetricField2(m_xBuilder->weld_metric_spin_button(u"spinbutton2"_ustr, FieldUnit::CM))
898 , m_xFixedText3(m_xBuilder->weld_label(u"label3"_ustr))
899 , m_xMetricField3(m_xBuilder->weld_metric_spin_button(u"spinbutton3"_ustr, FieldUnit::CM))
900 , m_xCheckBox1(m_xBuilder->weld_check_button(u"checkbutton"_ustr))
901 , m_xFixedText4(m_xBuilder->weld_label(u"label4"_ustr))
902 , m_xMetricField4(m_xBuilder->weld_metric_spin_button(u"spinbutton4"_ustr, FieldUnit::CM))
903 , m_xMenuButton(m_xBuilder->weld_menu_button(u"category"_ustr))
904 , m_xDefaultButton(m_xBuilder->weld_button(u"default"_ustr))
905 , m_xBitmap(m_xBuilder->weld_widget(u"image"_ustr))
906 , m_pCurrentImage(m_xBitmap.get())
908 for (sal_uInt16 i = 0; i < NOCATEGORIES; ++i)
909 m_xCategories[i].reset( new SmCategoryDesc(*m_xBuilder, i) );
910 nActiveCategory = CATEGORY_NONE;
911 bScaleAllBrackets = false;
913 m_xMetricField1->connect_focus_in(LINK(this, SmDistanceDialog, GetFocusHdl));
914 m_xMetricField2->connect_focus_in(LINK(this, SmDistanceDialog, GetFocusHdl));
915 m_xMetricField3->connect_focus_in(LINK(this, SmDistanceDialog, GetFocusHdl));
916 m_xMetricField4->connect_focus_in(LINK(this, SmDistanceDialog, GetFocusHdl));
917 m_xCheckBox1->connect_toggled(LINK(this, SmDistanceDialog, CheckBoxClickHdl));
918 m_xMenuButton->connect_selected(LINK(this, SmDistanceDialog, MenuSelectHdl));
919 m_xDefaultButton->connect_clicked(LINK(this, SmDistanceDialog, DefaultButtonClickHdl));
921 //set the initial size, with max visible widgets visible, as preferred size
922 m_xDialog->set_size_request(-1, m_xDialog->get_preferred_size().Height());
925 SmDistanceDialog::~SmDistanceDialog()
929 void SmDistanceDialog::ReadFrom(const SmFormat &rFormat)
931 m_xCategories[0]->SetValue(0, rFormat.GetDistance(DIS_HORIZONTAL));
932 m_xCategories[0]->SetValue(1, rFormat.GetDistance(DIS_VERTICAL));
933 m_xCategories[0]->SetValue(2, rFormat.GetDistance(DIS_ROOT));
934 m_xCategories[1]->SetValue(0, rFormat.GetDistance(DIS_SUPERSCRIPT));
935 m_xCategories[1]->SetValue(1, rFormat.GetDistance(DIS_SUBSCRIPT));
936 m_xCategories[2]->SetValue(0, rFormat.GetDistance(DIS_NUMERATOR));
937 m_xCategories[2]->SetValue(1, rFormat.GetDistance(DIS_DENOMINATOR));
938 m_xCategories[3]->SetValue(0, rFormat.GetDistance(DIS_FRACTION));
939 m_xCategories[3]->SetValue(1, rFormat.GetDistance(DIS_STROKEWIDTH));
940 m_xCategories[4]->SetValue(0, rFormat.GetDistance(DIS_UPPERLIMIT));
941 m_xCategories[4]->SetValue(1, rFormat.GetDistance(DIS_LOWERLIMIT));
942 m_xCategories[5]->SetValue(0, rFormat.GetDistance(DIS_BRACKETSIZE));
943 m_xCategories[5]->SetValue(1, rFormat.GetDistance(DIS_BRACKETSPACE));
944 m_xCategories[5]->SetValue(3, rFormat.GetDistance(DIS_NORMALBRACKETSIZE));
945 m_xCategories[6]->SetValue(0, rFormat.GetDistance(DIS_MATRIXROW));
946 m_xCategories[6]->SetValue(1, rFormat.GetDistance(DIS_MATRIXCOL));
947 m_xCategories[7]->SetValue(0, rFormat.GetDistance(DIS_ORNAMENTSIZE));
948 m_xCategories[7]->SetValue(1, rFormat.GetDistance(DIS_ORNAMENTSPACE));
949 m_xCategories[8]->SetValue(0, rFormat.GetDistance(DIS_OPERATORSIZE));
950 m_xCategories[8]->SetValue(1, rFormat.GetDistance(DIS_OPERATORSPACE));
951 m_xCategories[9]->SetValue(0, rFormat.GetDistance(DIS_LEFTSPACE));
952 m_xCategories[9]->SetValue(1, rFormat.GetDistance(DIS_RIGHTSPACE));
953 m_xCategories[9]->SetValue(2, rFormat.GetDistance(DIS_TOPSPACE));
954 m_xCategories[9]->SetValue(3, rFormat.GetDistance(DIS_BOTTOMSPACE));
956 bScaleAllBrackets = rFormat.IsScaleNormalBrackets();
958 // force update (even of category 0) by setting nActiveCategory to a
959 // non-existent category number
960 nActiveCategory = CATEGORY_NONE;
961 SetCategory(0);
965 void SmDistanceDialog::WriteTo(SmFormat &rFormat) /*const*/
967 // TODO can they actually be different?
968 // if that's not the case 'const' could be used above!
969 SetCategory(nActiveCategory);
971 rFormat.SetDistance( DIS_HORIZONTAL, m_xCategories[0]->GetValue(0) );
972 rFormat.SetDistance( DIS_VERTICAL, m_xCategories[0]->GetValue(1) );
973 rFormat.SetDistance( DIS_ROOT, m_xCategories[0]->GetValue(2) );
974 rFormat.SetDistance( DIS_SUPERSCRIPT, m_xCategories[1]->GetValue(0) );
975 rFormat.SetDistance( DIS_SUBSCRIPT, m_xCategories[1]->GetValue(1) );
976 rFormat.SetDistance( DIS_NUMERATOR, m_xCategories[2]->GetValue(0) );
977 rFormat.SetDistance( DIS_DENOMINATOR, m_xCategories[2]->GetValue(1) );
978 rFormat.SetDistance( DIS_FRACTION, m_xCategories[3]->GetValue(0) );
979 rFormat.SetDistance( DIS_STROKEWIDTH, m_xCategories[3]->GetValue(1) );
980 rFormat.SetDistance( DIS_UPPERLIMIT, m_xCategories[4]->GetValue(0) );
981 rFormat.SetDistance( DIS_LOWERLIMIT, m_xCategories[4]->GetValue(1) );
982 rFormat.SetDistance( DIS_BRACKETSIZE, m_xCategories[5]->GetValue(0) );
983 rFormat.SetDistance( DIS_BRACKETSPACE, m_xCategories[5]->GetValue(1) );
984 rFormat.SetDistance( DIS_MATRIXROW, m_xCategories[6]->GetValue(0) );
985 rFormat.SetDistance( DIS_MATRIXCOL, m_xCategories[6]->GetValue(1) );
986 rFormat.SetDistance( DIS_ORNAMENTSIZE, m_xCategories[7]->GetValue(0) );
987 rFormat.SetDistance( DIS_ORNAMENTSPACE, m_xCategories[7]->GetValue(1) );
988 rFormat.SetDistance( DIS_OPERATORSIZE, m_xCategories[8]->GetValue(0) );
989 rFormat.SetDistance( DIS_OPERATORSPACE, m_xCategories[8]->GetValue(1) );
990 rFormat.SetDistance( DIS_LEFTSPACE, m_xCategories[9]->GetValue(0) );
991 rFormat.SetDistance( DIS_RIGHTSPACE, m_xCategories[9]->GetValue(1) );
992 rFormat.SetDistance( DIS_TOPSPACE, m_xCategories[9]->GetValue(2) );
993 rFormat.SetDistance( DIS_BOTTOMSPACE, m_xCategories[9]->GetValue(3) );
994 rFormat.SetDistance( DIS_NORMALBRACKETSIZE, m_xCategories[5]->GetValue(3) );
996 rFormat.SetScaleNormalBrackets( bScaleAllBrackets );
998 rFormat.RequestApplyChanges();
1001 IMPL_LINK_NOARG( SmAlignDialog, DefaultButtonClickHdl, weld::Button&, void )
1003 SaveDefaultsQuery aQuery(m_xDialog.get());
1004 if (aQuery.run() == RET_YES)
1006 auto* config = SmModule::get()->GetConfig();
1007 SmFormat aFmt(config->GetStandardFormat());
1008 WriteTo( aFmt );
1009 config->SetStandardFormat(aFmt);
1013 SmAlignDialog::SmAlignDialog(weld::Window* pParent)
1014 : GenericDialogController(pParent, u"modules/smath/ui/alignmentdialog.ui"_ustr, u"AlignmentDialog"_ustr)
1015 , m_xLeft(m_xBuilder->weld_radio_button(u"left"_ustr))
1016 , m_xCenter(m_xBuilder->weld_radio_button(u"center"_ustr))
1017 , m_xRight(m_xBuilder->weld_radio_button(u"right"_ustr))
1018 , m_xDefaultButton(m_xBuilder->weld_button(u"default"_ustr))
1020 m_xDefaultButton->connect_clicked(LINK(this, SmAlignDialog, DefaultButtonClickHdl));
1023 SmAlignDialog::~SmAlignDialog()
1027 void SmAlignDialog::ReadFrom(const SmFormat &rFormat)
1029 switch (rFormat.GetHorAlign())
1031 case SmHorAlign::Left:
1032 m_xLeft->set_active(true);
1033 break;
1034 case SmHorAlign::Center:
1035 m_xCenter->set_active(true);
1036 break;
1037 case SmHorAlign::Right:
1038 m_xRight->set_active(true);
1039 break;
1043 void SmAlignDialog::WriteTo(SmFormat &rFormat) const
1045 if (m_xLeft->get_active())
1046 rFormat.SetHorAlign(SmHorAlign::Left);
1047 else if (m_xRight->get_active())
1048 rFormat.SetHorAlign(SmHorAlign::Right);
1049 else
1050 rFormat.SetHorAlign(SmHorAlign::Center);
1052 rFormat.RequestApplyChanges();
1055 SmShowSymbolSet::SmShowSymbolSet(std::unique_ptr<weld::ScrolledWindow> pScrolledWindow, SmViewShell &rViewShell)
1056 : m_rViewShell(rViewShell)
1057 , nLen(0)
1058 , nRows(0)
1059 , nColumns(0)
1060 , nXOffset(0)
1061 , nYOffset(0)
1062 , nSelectSymbol(SYMBOL_NONE)
1063 , m_xScrolledWindow(std::move(pScrolledWindow))
1065 m_xScrolledWindow->connect_vadjustment_changed(LINK(this, SmShowSymbolSet, ScrollHdl));
1068 Point SmShowSymbolSet::OffsetPoint(const Point &rPoint) const
1070 return Point(rPoint.X() + nXOffset, rPoint.Y() + nYOffset);
1073 void SmShowSymbolSet::Resize()
1075 CustomWidgetController::Resize();
1076 Size aWinSize(GetOutputSizePixel());
1077 if (aWinSize != m_aOldSize)
1079 calccols(GetDrawingArea()->get_ref_device());
1080 m_aOldSize = aWinSize;
1084 void SmShowSymbolSet::Paint(vcl::RenderContext& rRenderContext, const tools::Rectangle&)
1086 Color aBackgroundColor;
1087 Color aTextColor;
1088 lclGetSettingColors(aBackgroundColor, aTextColor);
1090 rRenderContext.SetBackground(Wallpaper(aBackgroundColor));
1091 rRenderContext.SetTextColor(aTextColor);
1093 rRenderContext.Push(vcl::PushFlags::MAPMODE);
1095 // set MapUnit for which 'nLen' has been calculated
1096 rRenderContext.SetMapMode(MapMode(MapUnit::MapPixel));
1098 sal_uInt16 v = sal::static_int_cast< sal_uInt16 >(m_xScrolledWindow->vadjustment_get_value() * nColumns);
1099 size_t nSymbols = aSymbolSet.size();
1101 Color aTxtColor(rRenderContext.GetTextColor());
1102 for (size_t i = v; i < nSymbols ; i++)
1104 SmSym aSymbol(*aSymbolSet[i]);
1105 vcl::Font aFont(lclGetSymbolFont(m_rViewShell, aSymbol));
1106 aFont.SetAlignment(ALIGN_TOP);
1108 // taking a FontSize which is a bit smaller (compared to nLen) in order to have a buffer
1109 // (hopefully enough for left and right, too)
1110 aFont.SetFontSize(Size(0, nLen - (nLen / 3)));
1111 rRenderContext.SetFont(aFont);
1112 // keep text color
1113 rRenderContext.SetTextColor(aTxtColor);
1115 int nIV = i - v;
1116 sal_UCS4 cChar = aSymbol.GetCharacter();
1117 OUString aText(&cChar, 1);
1118 Size aSize(rRenderContext.GetTextWidth( aText ), rRenderContext.GetTextHeight());
1120 Point aPoint((nIV % nColumns) * nLen + (nLen - aSize.Width()) / 2,
1121 (nIV / nColumns) * nLen + (nLen - aSize.Height()) / 2);
1123 rRenderContext.DrawText(OffsetPoint(aPoint), aText);
1126 if (nSelectSymbol != SYMBOL_NONE)
1128 Point aPoint(((nSelectSymbol - v) % nColumns) * nLen,
1129 ((nSelectSymbol - v) / nColumns) * nLen);
1131 rRenderContext.Invert(tools::Rectangle(OffsetPoint(aPoint), Size(nLen, nLen)));
1135 rRenderContext.Pop();
1138 bool SmShowSymbolSet::MouseButtonDown(const MouseEvent& rMEvt)
1140 GrabFocus();
1142 Size aOutputSize(nColumns * nLen, nRows * nLen);
1143 aOutputSize.AdjustWidth(nXOffset );
1144 aOutputSize.AdjustHeight(nYOffset );
1145 Point aPoint(rMEvt.GetPosPixel());
1146 aPoint.AdjustX( -nXOffset );
1147 aPoint.AdjustY( -nYOffset );
1149 if (rMEvt.IsLeft() && tools::Rectangle(Point(0, 0), aOutputSize).Contains(rMEvt.GetPosPixel()))
1151 tools::Long nPos = (aPoint.Y() / nLen) * nColumns + (aPoint.X() / nLen) +
1152 m_xScrolledWindow->vadjustment_get_value() * nColumns;
1153 SelectSymbol( sal::static_int_cast< sal_uInt16 >(nPos) );
1155 aSelectHdlLink.Call(*this);
1157 if (rMEvt.GetClicks() > 1)
1158 aDblClickHdlLink.Call(*this);
1161 return true;
1164 bool SmShowSymbolSet::KeyInput(const KeyEvent& rKEvt)
1166 sal_uInt16 n = nSelectSymbol;
1168 if (n != SYMBOL_NONE)
1170 switch (rKEvt.GetKeyCode().GetCode())
1172 case KEY_DOWN: n = n + nColumns; break;
1173 case KEY_UP: n = n - nColumns; break;
1174 case KEY_LEFT: n -= 1; break;
1175 case KEY_RIGHT: n += 1; break;
1176 case KEY_HOME: n = 0; break;
1177 case KEY_END: n = static_cast< sal_uInt16 >(aSymbolSet.size() - 1); break;
1178 case KEY_PAGEUP: n -= nColumns * nRows; break;
1179 case KEY_PAGEDOWN: n += nColumns * nRows; break;
1180 default:
1181 return false;
1184 else
1185 n = 0;
1187 if (n >= aSymbolSet.size())
1188 n = nSelectSymbol;
1190 // adjust scrollbar
1191 if ((n < sal::static_int_cast<sal_uInt16>(m_xScrolledWindow->vadjustment_get_value() * nColumns)) ||
1192 (n >= sal::static_int_cast<sal_uInt16>((m_xScrolledWindow->vadjustment_get_value() + nRows) * nColumns)))
1194 m_xScrolledWindow->vadjustment_set_value(n / nColumns);
1195 Invalidate();
1198 SelectSymbol(n);
1199 aSelectHdlLink.Call(*this);
1201 return true;
1204 void SmShowSymbolSet::calccols(const vcl::RenderContext& rRenderContext)
1206 // Height of 16pt in pixels (matching 'aOutputSize')
1207 nLen = rRenderContext.LogicToPixel(Size(0, 16), MapMode(MapUnit::MapPoint)).Height();
1209 Size aOutputSize(GetOutputSizePixel());
1211 nColumns = aOutputSize.Width() / nLen;
1212 nRows = aOutputSize.Height() / nLen;
1213 nColumns = std::max<tools::Long>(1, nColumns);
1214 nRows = std::max<tools::Long>(1, nRows);
1216 nXOffset = (aOutputSize.Width() - (nColumns * nLen)) / 2;
1217 nYOffset = (aOutputSize.Height() - (nRows * nLen)) / 2;
1219 SetScrollBarRange();
1222 void SmShowSymbolSet::SetSymbolSet(const SymbolPtrVec_t & rSymbolSet)
1224 aSymbolSet = rSymbolSet;
1225 SetScrollBarRange();
1226 Invalidate();
1229 void SmShowSymbolSet::SetScrollBarRange()
1231 const int nLastRow = (aSymbolSet.size() - 1 + nColumns) / nColumns;
1232 m_xScrolledWindow->vadjustment_configure(m_xScrolledWindow->vadjustment_get_value(), 0, nLastRow, 1, nRows - 1, nRows);
1233 Invalidate();
1236 void SmShowSymbolSet::SelectSymbol(sal_uInt16 nSymbol)
1238 int v = m_xScrolledWindow->vadjustment_get_value() * nColumns;
1240 if (nSelectSymbol != SYMBOL_NONE && nColumns)
1242 Point aPoint(OffsetPoint(Point(((nSelectSymbol - v) % nColumns) * nLen,
1243 ((nSelectSymbol - v) / nColumns) * nLen)));
1244 Invalidate(tools::Rectangle(aPoint, Size(nLen, nLen)));
1247 if (nSymbol < aSymbolSet.size())
1248 nSelectSymbol = nSymbol;
1250 if (aSymbolSet.empty())
1251 nSelectSymbol = SYMBOL_NONE;
1253 if (nSelectSymbol != SYMBOL_NONE && nColumns)
1255 Point aPoint(OffsetPoint(Point(((nSelectSymbol - v) % nColumns) * nLen,
1256 ((nSelectSymbol - v) / nColumns) * nLen)));
1257 Invalidate(tools::Rectangle(aPoint, Size(nLen, nLen)));
1260 if (!nColumns)
1261 Invalidate();
1264 IMPL_LINK_NOARG(SmShowSymbolSet, ScrollHdl, weld::ScrolledWindow&, void)
1266 Invalidate();
1269 SmShowSymbol::SmShowSymbol(SmViewShell& rViewShell)
1270 : m_rViewShell(rViewShell)
1274 void SmShowSymbol::setFontSize(vcl::Font &rFont) const
1276 Size aSize(GetOutputSizePixel());
1277 rFont.SetFontSize(Size(0, aSize.Height() - aSize.Height() / 3));
1280 void SmShowSymbol::Paint(vcl::RenderContext& rRenderContext, const tools::Rectangle&)
1282 Color aBackgroundColor;
1283 Color aTextColor;
1284 lclGetSettingColors(aBackgroundColor, aTextColor);
1285 rRenderContext.SetBackground(Wallpaper(aBackgroundColor));
1286 rRenderContext.SetTextColor(aTextColor);
1287 rRenderContext.Erase();
1289 vcl::Font aFont(GetFont());
1290 setFontSize(aFont);
1291 rRenderContext.SetFont(aFont);
1293 const OUString &rText = GetText();
1294 Size aTextSize(rRenderContext.GetTextWidth(rText), rRenderContext.GetTextHeight());
1296 rRenderContext.DrawText(Point((rRenderContext.GetOutputSize().Width() - aTextSize.Width()) / 2,
1297 (rRenderContext.GetOutputSize().Height() * 7 / 10)), rText);
1300 bool SmShowSymbol::MouseButtonDown(const MouseEvent& rMEvt)
1302 if (rMEvt.GetClicks() > 1)
1303 aDblClickHdlLink.Call(*this);
1304 return true;
1307 void SmShowSymbol::SetSymbol(const SmSym *pSymbol)
1309 if (pSymbol)
1311 vcl::Font aFont(lclGetSymbolFont(m_rViewShell, *pSymbol));
1312 aFont.SetAlignment(ALIGN_BASELINE);
1313 SetFont(aFont);
1315 sal_UCS4 cChar = pSymbol->GetCharacter();
1316 OUString aText(&cChar, 1);
1317 SetText( aText );
1320 Invalidate();
1323 void SmSymbolDialog::FillSymbolSets()
1324 // populate the entries of possible SymbolsSets in the dialog with
1325 // current values of the SymbolSet manager but selects none of those
1327 m_xSymbolSets->clear();
1328 m_xSymbolSets->set_active(-1);
1330 std::set< OUString > aSymbolSetNames( m_rSymbolMgr.GetSymbolSetNames() );
1331 for (const auto& rSymbolSetName : aSymbolSetNames)
1332 m_xSymbolSets->append_text(rSymbolSetName);
1335 IMPL_LINK_NOARG( SmSymbolDialog, SymbolSetChangeHdl, weld::ComboBox&, void )
1337 SelectSymbolSet(m_xSymbolSets->get_active_text());
1340 IMPL_LINK_NOARG( SmSymbolDialog, SymbolChangeHdl, SmShowSymbolSet&, void )
1342 SelectSymbol(m_xSymbolSetDisplay->GetSelectSymbol());
1345 IMPL_LINK_NOARG(SmSymbolDialog, EditClickHdl, weld::Button&, void)
1347 SmSymDefineDialog aDialog(m_xDialog.get(), m_pFontListDev, m_rSymbolMgr);
1349 // set current symbol and SymbolSet for the new dialog
1350 const OUString aSymSetName (m_xSymbolSets->get_active_text()),
1351 aSymName (m_xSymbolName->get_label());
1352 aDialog.SelectOldSymbolSet(aSymSetName);
1353 aDialog.SelectOldSymbol(aSymName);
1354 aDialog.SelectSymbolSet(aSymSetName);
1355 aDialog.SelectSymbol(aSymName);
1357 // remember old SymbolSet
1358 OUString aOldSymbolSet (m_xSymbolSets->get_active_text());
1360 sal_uInt16 nSymPos = m_xSymbolSetDisplay->GetSelectSymbol();
1362 // adapt dialog to data of the SymbolSet manager, which might have changed
1363 if (aDialog.run() == RET_OK && m_rSymbolMgr.IsModified())
1365 m_rSymbolMgr.Save();
1366 FillSymbolSets();
1369 // if the old SymbolSet doesn't exist anymore, go to the first one SymbolSet (if one exists)
1370 if (!SelectSymbolSet(aOldSymbolSet) && m_xSymbolSets->get_count() > 0)
1371 SelectSymbolSet(m_xSymbolSets->get_text(0));
1372 else
1374 // just update display of current symbol set
1375 assert(m_aSymbolSetName == aSymSetName); //unexpected change in symbol set name
1376 m_aSymbolSet = m_rSymbolMgr.GetSymbolSet( m_aSymbolSetName );
1377 m_xSymbolSetDisplay->SetSymbolSet( m_aSymbolSet );
1380 if (nSymPos >= m_aSymbolSet.size())
1381 nSymPos = static_cast< sal_uInt16 >(m_aSymbolSet.size()) - 1;
1382 SelectSymbol( nSymPos );
1385 IMPL_LINK_NOARG( SmSymbolDialog, SymbolDblClickHdl2, SmShowSymbolSet&, void )
1387 SymbolDblClickHdl();
1390 IMPL_LINK_NOARG( SmSymbolDialog, SymbolDblClickHdl, SmShowSymbol&, void )
1392 SymbolDblClickHdl();
1395 void SmSymbolDialog::SymbolDblClickHdl()
1397 GetClickHdl(*m_xGetBtn);
1398 m_xDialog->response(RET_OK);
1401 IMPL_LINK_NOARG(SmSymbolDialog, GetClickHdl, weld::Button&, void)
1403 const SmSym *pSym = GetSymbol();
1404 if (pSym)
1406 OUString aText = "%" + pSym->GetUiName() + " ";
1408 m_rViewSh.GetViewFrame().GetDispatcher()->ExecuteList(
1409 SID_INSERTSPECIAL, SfxCallMode::RECORD,
1410 { new SfxStringItem(SID_INSERTSPECIAL, aText) });
1414 SmSymbolDialog::SmSymbolDialog(weld::Window *pParent, OutputDevice *pFntListDevice,
1415 SmSymbolManager &rMgr, SmViewShell &rViewShell)
1416 : GenericDialogController(pParent, u"modules/smath/ui/catalogdialog.ui"_ustr, u"CatalogDialog"_ustr)
1417 , m_rViewSh(rViewShell)
1418 , m_rSymbolMgr(rMgr)
1419 , m_pFontListDev(pFntListDevice)
1420 , m_aSymbolDisplay(rViewShell)
1421 , m_xSymbolSets(m_xBuilder->weld_combo_box(u"symbolset"_ustr))
1422 , m_xSymbolSetDisplay(new SmShowSymbolSet(m_xBuilder->weld_scrolled_window(u"scrolledwindow"_ustr, true), rViewShell))
1423 , m_xSymbolSetDisplayArea(new weld::CustomWeld(*m_xBuilder, u"symbolsetdisplay"_ustr, *m_xSymbolSetDisplay))
1424 , m_xSymbolName(m_xBuilder->weld_label(u"symbolname"_ustr))
1425 , m_xSymbolDisplay(new weld::CustomWeld(*m_xBuilder, u"preview"_ustr, m_aSymbolDisplay))
1426 , m_xGetBtn(m_xBuilder->weld_button(u"ok"_ustr))
1427 , m_xEditBtn(m_xBuilder->weld_button(u"edit"_ustr))
1429 m_xSymbolSets->make_sorted();
1431 m_aSymbolSetName.clear();
1432 m_aSymbolSet.clear();
1433 FillSymbolSets();
1434 if (m_xSymbolSets->get_count() > 0)
1435 SelectSymbolSet(m_xSymbolSets->get_text(0));
1437 m_xSymbolSets->connect_changed(LINK(this, SmSymbolDialog, SymbolSetChangeHdl));
1438 m_xSymbolSetDisplay->SetSelectHdl(LINK(this, SmSymbolDialog, SymbolChangeHdl));
1439 m_xSymbolSetDisplay->SetDblClickHdl(LINK(this, SmSymbolDialog, SymbolDblClickHdl2));
1440 m_aSymbolDisplay.SetDblClickHdl(LINK(this, SmSymbolDialog, SymbolDblClickHdl));
1441 m_xEditBtn->connect_clicked(LINK(this, SmSymbolDialog, EditClickHdl));
1442 m_xGetBtn->connect_clicked(LINK(this, SmSymbolDialog, GetClickHdl));
1445 SmSymbolDialog::~SmSymbolDialog()
1449 bool SmSymbolDialog::SelectSymbolSet(const OUString &rSymbolSetName)
1451 bool bRet = false;
1452 sal_Int32 nPos = m_xSymbolSets->find_text(rSymbolSetName);
1454 m_aSymbolSetName.clear();
1455 m_aSymbolSet.clear();
1456 if (nPos != -1)
1458 m_xSymbolSets->set_active(nPos);
1460 m_aSymbolSetName = rSymbolSetName;
1461 m_aSymbolSet = m_rSymbolMgr.GetSymbolSet( m_aSymbolSetName );
1463 // sort symbols by Unicode position (useful for displaying Greek characters alphabetically)
1464 std::sort( m_aSymbolSet.begin(), m_aSymbolSet.end(),
1465 [](const SmSym *pSym1, const SmSym *pSym2)
1467 return pSym1->GetCharacter() < pSym2->GetCharacter();
1468 } );
1470 const bool bEmptySymbolSet = m_aSymbolSet.empty();
1471 m_xSymbolSetDisplay->SetSymbolSet( m_aSymbolSet );
1472 if (!bEmptySymbolSet)
1473 SelectSymbol(0);
1475 bRet = true;
1477 else
1478 m_xSymbolSets->set_active(-1);
1480 return bRet;
1483 void SmSymbolDialog::SelectSymbol(sal_uInt16 nSymbolNo)
1485 const SmSym *pSym = nullptr;
1486 if (!m_aSymbolSetName.isEmpty() && nSymbolNo < static_cast< sal_uInt16 >(m_aSymbolSet.size()))
1487 pSym = m_aSymbolSet[ nSymbolNo ];
1489 m_xSymbolSetDisplay->SelectSymbol(nSymbolNo);
1490 m_aSymbolDisplay.SetSymbol(pSym);
1491 m_xSymbolName->set_label(pSym ? pSym->GetUiName() : OUString());
1494 const SmSym* SmSymbolDialog::GetSymbol() const
1496 sal_uInt16 nSymbolNo = m_xSymbolSetDisplay->GetSelectSymbol();
1497 bool bValid = !m_aSymbolSetName.isEmpty() && nSymbolNo < static_cast< sal_uInt16 >(m_aSymbolSet.size());
1498 return bValid ? m_aSymbolSet[ nSymbolNo ] : nullptr;
1501 void SmShowChar::Resize()
1503 const OUString &rText = GetText();
1504 if (rText.isEmpty())
1505 return;
1506 sal_UCS4 cChar = rText.iterateCodePoints(&o3tl::temporary(sal_Int32(0)));
1507 SetSymbol(cChar, GetFont()); //force recalculation of size
1510 void SmShowChar::Paint(vcl::RenderContext& rRenderContext, const tools::Rectangle&)
1512 Color aTextCol = rRenderContext.GetTextColor();
1513 Color aFillCol = rRenderContext.GetFillColor();
1515 const StyleSettings& rStyleSettings = Application::GetSettings().GetStyleSettings();
1516 const Color aWindowTextColor(rStyleSettings.GetDialogTextColor());
1517 const Color aWindowColor(rStyleSettings.GetWindowColor());
1518 rRenderContext.SetTextColor(aWindowTextColor);
1519 rRenderContext.SetFillColor(aWindowColor);
1521 Size aSize(GetOutputSizePixel());
1522 rRenderContext.DrawRect(tools::Rectangle(Point(0, 0), aSize));
1524 OUString aText(GetText());
1525 if (!aText.isEmpty())
1527 vcl::Font aFont(m_aFont);
1528 aFont.SetAlignment(ALIGN_TOP);
1529 rRenderContext.SetFont(aFont);
1531 Size aTextSize(rRenderContext.GetTextWidth(aText), rRenderContext.GetTextHeight());
1533 rRenderContext.DrawText(Point((aSize.Width() - aTextSize.Width()) / 2,
1534 (aSize.Height() - aTextSize.Height()) / 2), aText);
1537 rRenderContext.SetTextColor(aTextCol);
1538 rRenderContext.SetFillColor(aFillCol);
1541 void SmShowChar::SetSymbol( const SmSym *pSym )
1543 if (pSym)
1544 SetSymbol( pSym->GetCharacter(), pSym->GetFace() );
1548 void SmShowChar::SetSymbol( sal_UCS4 cChar, const vcl::Font &rFont )
1550 vcl::Font aFont( rFont );
1551 Size aSize(GetOutputSizePixel());
1552 aFont.SetFontSize(Size(0, aSize.Height() - aSize.Height() / 3));
1553 aFont.SetAlignment(ALIGN_BASELINE);
1554 SetFont(aFont);
1556 OUString aText(&cChar, 1);
1557 SetText( aText );
1559 Invalidate();
1562 void SmSymDefineDialog::FillSymbols(weld::ComboBox& rComboBox, bool bDeleteText)
1564 assert((&rComboBox == m_xOldSymbols.get() || &rComboBox == m_xSymbols.get()) && "Sm : wrong ComboBox");
1566 rComboBox.clear();
1567 if (bDeleteText)
1568 rComboBox.set_entry_text(OUString());
1570 weld::ComboBox& rBox = &rComboBox == m_xOldSymbols.get() ? *m_xOldSymbolSets : *m_xSymbolSets;
1571 SymbolPtrVec_t aSymSet(m_aSymbolMgrCopy.GetSymbolSet(rBox.get_active_text()));
1572 for (const SmSym* i : aSymSet)
1573 rComboBox.append_text(i->GetUiName());
1576 void SmSymDefineDialog::FillSymbolSets(weld::ComboBox& rComboBox, bool bDeleteText)
1578 assert((&rComboBox == m_xOldSymbolSets.get() || &rComboBox == m_xSymbolSets.get()) && "Sm : wrong ComboBox");
1580 rComboBox.clear();
1581 if (bDeleteText)
1582 rComboBox.set_entry_text(OUString());
1584 const std::set< OUString > aSymbolSetNames( m_aSymbolMgrCopy.GetSymbolSetNames() );
1585 for (const auto& rSymbolSetName : aSymbolSetNames)
1586 rComboBox.append_text(rSymbolSetName);
1589 void SmSymDefineDialog::FillFonts()
1591 m_xFonts->clear();
1592 m_xFonts->set_active(-1);
1594 // Include all fonts of FontList into the font list.
1595 // If there are duplicates, only include one entry of each font since the style will be
1596 // already selected using the FontStyleBox.
1597 if (m_xFontList)
1599 sal_uInt16 nCount = m_xFontList->GetFontNameCount();
1600 for (sal_uInt16 i = 0; i < nCount; ++i)
1601 m_xFonts->append_text(m_xFontList->GetFontName(i).GetFamilyName());
1605 void SmSymDefineDialog::FillStyles()
1607 m_xStyles->clear();
1608 // pStyles->SetText(OUString());
1610 OUString aText(m_xFonts->get_active_text());
1611 if (!aText.isEmpty())
1613 // use own StyleNames
1614 const SmFontStyles &rStyles = GetFontStyles();
1615 for (sal_uInt16 i = 0; i < SmFontStyles::GetCount(); ++i)
1616 m_xStyles->append_text(rStyles.GetStyleName(i));
1618 assert(m_xStyles->get_count() > 0 && "Sm : no styles available");
1619 m_xStyles->set_active(0);
1623 SmSym* SmSymDefineDialog::GetSymbol(const weld::ComboBox& rComboBox)
1625 assert((&rComboBox == m_xOldSymbols.get() || &rComboBox == m_xSymbols.get()) && "Sm : wrong combobox");
1626 return m_aSymbolMgrCopy.GetSymbolByUiName(rComboBox.get_active_text());
1629 IMPL_LINK(SmSymDefineDialog, OldSymbolChangeHdl, weld::ComboBox&, rComboBox, void)
1631 (void) rComboBox;
1632 assert(&rComboBox == m_xOldSymbols.get() && "Sm : wrong argument");
1633 SelectSymbol(*m_xOldSymbols, m_xOldSymbols->get_active_text(), false);
1636 IMPL_LINK( SmSymDefineDialog, OldSymbolSetChangeHdl, weld::ComboBox&, rComboBox, void )
1638 (void) rComboBox;
1639 assert(&rComboBox == m_xOldSymbolSets.get() && "Sm : wrong argument");
1640 SelectSymbolSet(*m_xOldSymbolSets, m_xOldSymbolSets->get_active_text(), false);
1643 IMPL_LINK(SmSymDefineDialog, ModifyHdl, weld::ComboBox&, rComboBox, void)
1645 // remember cursor position for later restoring of it
1646 int nStartPos, nEndPos;
1647 rComboBox.get_entry_selection_bounds(nStartPos, nEndPos);
1649 if (&rComboBox == m_xSymbols.get())
1650 SelectSymbol(*m_xSymbols, m_xSymbols->get_active_text(), false);
1651 else if (&rComboBox == m_xSymbolSets.get())
1652 SelectSymbolSet(*m_xSymbolSets, m_xSymbolSets->get_active_text(), false);
1653 else if (&rComboBox == m_xOldSymbols.get())
1654 // allow only names from the list
1655 SelectSymbol(*m_xOldSymbols, m_xOldSymbols->get_active_text(), true);
1656 else if (&rComboBox == m_xOldSymbolSets.get())
1657 // allow only names from the list
1658 SelectSymbolSet(*m_xOldSymbolSets, m_xOldSymbolSets->get_active_text(), true);
1659 else if (&rComboBox == m_xStyles.get())
1660 // allow only names from the list (that's the case here anyway)
1661 SelectStyle(m_xStyles->get_active_text(), true);
1662 else
1663 SAL_WARN("starmath", "wrong combobox argument");
1665 rComboBox.select_entry_region(nStartPos, nEndPos);
1667 UpdateButtons();
1670 IMPL_LINK(SmSymDefineDialog, FontChangeHdl, weld::ComboBox&, rListBox, void)
1672 (void) rListBox;
1673 assert(&rListBox == m_xFonts.get() && "Sm : wrong argument");
1675 SelectFont(m_xFonts->get_active_text());
1678 IMPL_LINK_NOARG(SmSymDefineDialog, SubsetChangeHdl, weld::ComboBox&, void)
1680 int nPos = m_xFontsSubsetLB->get_active();
1681 if (nPos != -1)
1683 const Subset* pSubset = weld::fromId<const Subset*>(m_xFontsSubsetLB->get_active_id());
1684 if (pSubset)
1686 m_xCharsetDisplay->SelectCharacter( pSubset->GetRangeMin() );
1691 IMPL_LINK( SmSymDefineDialog, StyleChangeHdl, weld::ComboBox&, rComboBox, void )
1693 (void) rComboBox;
1694 assert(&rComboBox == m_xStyles.get() && "Sm : wrong argument");
1696 SelectStyle(m_xStyles->get_active_text());
1699 IMPL_LINK_NOARG(SmSymDefineDialog, CharHighlightHdl, SvxShowCharSet*, void)
1701 sal_UCS4 cChar = m_xCharsetDisplay->GetSelectCharacter();
1703 if (m_xSubsetMap)
1705 const Subset* pSubset = m_xSubsetMap->GetSubsetByUnicode(cChar);
1706 if (pSubset)
1707 m_xFontsSubsetLB->set_active_text(pSubset->GetName());
1708 else
1709 m_xFontsSubsetLB->set_active(-1);
1712 m_aSymbolDisplay.SetSymbol(cChar, m_xCharsetDisplay->GetFont());
1714 UpdateButtons();
1716 // display Unicode position as symbol name while iterating over characters
1717 const OUString aHex(OUString::number(cChar, 16).toAsciiUpperCase());
1718 const OUString aPattern( (aHex.getLength() > 4) ? u"Ux000000"_ustr : u"Ux0000"_ustr );
1719 OUString aUnicodePos = aPattern.subView( 0, aPattern.getLength() - aHex.getLength() ) +
1720 aHex;
1721 m_xSymbols->set_entry_text(aUnicodePos);
1722 m_xSymbolName->set_label(aUnicodePos);
1725 IMPL_LINK( SmSymDefineDialog, AddClickHdl, weld::Button&, rButton, void )
1727 (void) rButton;
1728 assert(&rButton == m_xAddBtn.get() && "Sm : wrong argument");
1729 assert(rButton.get_sensitive() && "Sm : requirements met ??");
1731 // add symbol
1732 const SmSym aNewSymbol(m_xSymbols->get_active_text(), m_xCharsetDisplay->GetFont(),
1733 m_xCharsetDisplay->GetSelectCharacter(), m_xSymbolSets->get_active_text());
1734 //OSL_ENSURE( m_aSymbolMgrCopy.GetSymbolByUiName(aTmpSymbolName) == NULL, "symbol already exists" );
1735 m_aSymbolMgrCopy.AddOrReplaceSymbol( aNewSymbol );
1737 // update display of new symbol
1738 m_aSymbolDisplay.SetSymbol( &aNewSymbol );
1739 m_xSymbolName->set_label(aNewSymbol.GetUiName());
1740 m_xSymbolSetName->set_label(aNewSymbol.GetSymbolSetName());
1742 // update list box entries
1743 FillSymbolSets(*m_xOldSymbolSets, false);
1744 FillSymbolSets(*m_xSymbolSets, false);
1745 FillSymbols(*m_xOldSymbols, false);
1746 FillSymbols(*m_xSymbols, false);
1748 UpdateButtons();
1751 IMPL_LINK( SmSymDefineDialog, ChangeClickHdl, weld::Button&, rButton, void )
1753 (void) rButton;
1754 assert(&rButton == m_xChangeBtn.get() && "Sm : wrong argument");
1755 assert(m_xChangeBtn->get_sensitive() && "Sm : requirements met ??");
1757 // get new Symbol to use
1758 //! get font from symbol-disp lay since charset-display does not keep
1759 //! the bold attribute.
1760 const SmSym aNewSymbol(m_xSymbols->get_active_text(), m_xCharsetDisplay->GetFont(),
1761 m_xCharsetDisplay->GetSelectCharacter(), m_xSymbolSets->get_active_text());
1763 // remove old symbol if the name was changed then add new one
1764 const bool bNameChanged = m_xOldSymbols->get_active_text() != m_xSymbols->get_active_text();
1765 if (bNameChanged)
1766 m_aSymbolMgrCopy.RemoveSymbol(m_xOldSymbols->get_active_text());
1767 m_aSymbolMgrCopy.AddOrReplaceSymbol( aNewSymbol, true );
1769 // clear display for original symbol if necessary
1770 if (bNameChanged)
1771 SetOrigSymbol(nullptr, OUString());
1773 // update display of new symbol
1774 m_aSymbolDisplay.SetSymbol(&aNewSymbol);
1775 m_xSymbolName->set_label(aNewSymbol.GetUiName());
1776 m_xSymbolSetName->set_label(aNewSymbol.GetSymbolSetName());
1778 // update list box entries
1779 FillSymbolSets(*m_xOldSymbolSets, false);
1780 FillSymbolSets(*m_xSymbolSets, false);
1781 FillSymbols(*m_xOldSymbols, false);
1782 FillSymbols(*m_xSymbols, false);
1784 UpdateButtons();
1787 IMPL_LINK(SmSymDefineDialog, DeleteClickHdl, weld::Button&, rButton, void)
1789 (void) rButton;
1790 assert(&rButton == m_xDeleteBtn.get() && "Sm : wrong argument");
1791 assert(m_xDeleteBtn->get_sensitive() && "Sm : requirements met ??");
1793 if (m_xOrigSymbol)
1795 m_aSymbolMgrCopy.RemoveSymbol(m_xOrigSymbol->GetUiName());
1797 // clear display for original symbol
1798 SetOrigSymbol(nullptr, OUString());
1800 // update list box entries
1801 FillSymbolSets(*m_xOldSymbolSets, false);
1802 FillSymbolSets(*m_xSymbolSets, false);
1803 FillSymbols(*m_xOldSymbols ,false);
1804 FillSymbols(*m_xSymbols ,false);
1807 UpdateButtons();
1810 void SmSymDefineDialog::UpdateButtons()
1812 bool bAdd = false,
1813 bChange = false,
1814 bDelete = false;
1815 OUString aTmpSymbolName(m_xSymbols->get_active_text()),
1816 aTmpSymbolSetName(m_xSymbolSets->get_active_text());
1818 if (!aTmpSymbolName.isEmpty() && !aTmpSymbolSetName.isEmpty())
1820 // are all settings equal?
1821 //! (Font-, Style- and SymbolSet name comparison is not case sensitive)
1822 bool bEqual = m_xOrigSymbol
1823 && aTmpSymbolSetName.equalsIgnoreAsciiCase(m_xOldSymbolSetName->get_label())
1824 && aTmpSymbolName == m_xOrigSymbol->GetUiName()
1825 && m_xFonts->get_active_text().equalsIgnoreAsciiCase(
1826 m_xOrigSymbol->GetFace().GetFamilyName())
1827 && m_xStyles->get_active_text().equalsIgnoreAsciiCase(
1828 GetFontStyles().GetStyleName(m_xOrigSymbol->GetFace()))
1829 && m_xCharsetDisplay->GetSelectCharacter() == m_xOrigSymbol->GetCharacter();
1831 // only add it if there isn't already a symbol with the same name
1832 bAdd = m_aSymbolMgrCopy.GetSymbolByUiName(aTmpSymbolName) == nullptr;
1834 // only delete it if all settings are equal
1835 bDelete = bool(m_xOrigSymbol);
1837 // only change it if the old symbol exists and the new one is different
1838 bChange = m_xOrigSymbol && !bEqual;
1841 m_xAddBtn->set_sensitive(bAdd);
1842 m_xChangeBtn->set_sensitive(bChange);
1843 m_xDeleteBtn->set_sensitive(bDelete);
1846 SmSymDefineDialog::SmSymDefineDialog(weld::Window* pParent, OutputDevice *pFntListDevice, SmSymbolManager &rMgr)
1847 : GenericDialogController(pParent, u"modules/smath/ui/symdefinedialog.ui"_ustr, u"EditSymbols"_ustr)
1848 , m_xVirDev(VclPtr<VirtualDevice>::Create())
1849 , m_rSymbolMgr(rMgr)
1850 , m_xFontList(new FontList(pFntListDevice))
1851 , m_xOldSymbols(m_xBuilder->weld_combo_box(u"oldSymbols"_ustr))
1852 , m_xOldSymbolSets(m_xBuilder->weld_combo_box(u"oldSymbolSets"_ustr))
1853 , m_xSymbols(m_xBuilder->weld_combo_box(u"symbols"_ustr))
1854 , m_xSymbolSets(m_xBuilder->weld_combo_box(u"symbolSets"_ustr))
1855 , m_xFonts(m_xBuilder->weld_combo_box(u"fonts"_ustr))
1856 , m_xFontsSubsetLB(m_xBuilder->weld_combo_box(u"fontsSubsetLB"_ustr))
1857 , m_xStyles(m_xBuilder->weld_combo_box(u"styles"_ustr))
1858 , m_xOldSymbolName(m_xBuilder->weld_label(u"oldSymbolName"_ustr))
1859 , m_xOldSymbolSetName(m_xBuilder->weld_label(u"oldSymbolSetName"_ustr))
1860 , m_xSymbolName(m_xBuilder->weld_label(u"symbolName"_ustr))
1861 , m_xSymbolSetName(m_xBuilder->weld_label(u"symbolSetName"_ustr))
1862 , m_xAddBtn(m_xBuilder->weld_button(u"add"_ustr))
1863 , m_xChangeBtn(m_xBuilder->weld_button(u"modify"_ustr))
1864 , m_xDeleteBtn(m_xBuilder->weld_button(u"delete"_ustr))
1865 , m_xOldSymbolDisplay(new weld::CustomWeld(*m_xBuilder, u"oldSymbolDisplay"_ustr, m_aOldSymbolDisplay))
1866 , m_xSymbolDisplay(new weld::CustomWeld(*m_xBuilder, u"symbolDisplay"_ustr, m_aSymbolDisplay))
1867 , m_xCharsetDisplay(new SvxShowCharSet(m_xBuilder->weld_scrolled_window(u"showscroll"_ustr, true), m_xVirDev))
1868 , m_xCharsetDisplayArea(new weld::CustomWeld(*m_xBuilder, u"charsetDisplay"_ustr, *m_xCharsetDisplay))
1870 // auto completion is troublesome since that symbols character also gets automatically selected in the
1871 // display and if the user previously selected a character to define/redefine that one this is bad
1872 m_xOldSymbols->set_entry_completion(false);
1873 m_xSymbols->set_entry_completion(false);
1875 FillFonts();
1876 if (m_xFonts->get_count() > 0)
1877 SelectFont(m_xFonts->get_text(0));
1879 SetSymbolSetManager(m_rSymbolMgr);
1881 m_xOldSymbols->connect_changed(LINK(this, SmSymDefineDialog, OldSymbolChangeHdl));
1882 m_xOldSymbolSets->connect_changed(LINK(this, SmSymDefineDialog, OldSymbolSetChangeHdl));
1883 m_xSymbolSets->connect_changed(LINK(this, SmSymDefineDialog, ModifyHdl));
1884 m_xOldSymbolSets->connect_changed(LINK(this, SmSymDefineDialog, ModifyHdl));
1885 m_xSymbols->connect_changed(LINK(this, SmSymDefineDialog, ModifyHdl));
1886 m_xOldSymbols->connect_changed(LINK(this, SmSymDefineDialog, ModifyHdl));
1887 m_xStyles->connect_changed(LINK(this, SmSymDefineDialog, ModifyHdl));
1888 m_xFonts->connect_changed(LINK(this, SmSymDefineDialog, FontChangeHdl));
1889 m_xFontsSubsetLB->connect_changed(LINK(this, SmSymDefineDialog, SubsetChangeHdl));
1890 m_xStyles->connect_changed(LINK(this, SmSymDefineDialog, StyleChangeHdl));
1891 m_xAddBtn->connect_clicked(LINK(this, SmSymDefineDialog, AddClickHdl));
1892 m_xChangeBtn->connect_clicked(LINK(this, SmSymDefineDialog, ChangeClickHdl));
1893 m_xDeleteBtn->connect_clicked(LINK(this, SmSymDefineDialog, DeleteClickHdl));
1894 m_xCharsetDisplay->SetHighlightHdl( LINK( this, SmSymDefineDialog, CharHighlightHdl ) );
1897 SmSymDefineDialog::~SmSymDefineDialog()
1901 short SmSymDefineDialog::run()
1903 short nResult = GenericDialogController::run();
1905 // apply changes if dialog was closed by clicking OK
1906 if (m_aSymbolMgrCopy.IsModified() && nResult == RET_OK)
1907 m_rSymbolMgr = m_aSymbolMgrCopy;
1909 return nResult;
1912 void SmSymDefineDialog::SetSymbolSetManager(const SmSymbolManager &rMgr)
1914 m_aSymbolMgrCopy = rMgr;
1916 // Set the modified flag of the copy to false so that
1917 // we can check later on if anything has been changed
1918 m_aSymbolMgrCopy.SetModified(false);
1920 FillSymbolSets(*m_xOldSymbolSets);
1921 if (m_xOldSymbolSets->get_count() > 0)
1922 SelectSymbolSet(m_xOldSymbolSets->get_text(0));
1923 FillSymbolSets(*m_xSymbolSets);
1924 if (m_xSymbolSets->get_count() > 0)
1925 SelectSymbolSet(m_xSymbolSets->get_text(0));
1926 FillSymbols(*m_xOldSymbols);
1927 if (m_xOldSymbols->get_count() > 0)
1928 SelectSymbol(m_xOldSymbols->get_text(0));
1929 FillSymbols(*m_xSymbols);
1930 if (m_xSymbols->get_count() > 0)
1931 SelectSymbol(m_xSymbols->get_text(0));
1933 UpdateButtons();
1936 bool SmSymDefineDialog::SelectSymbolSet(weld::ComboBox& rComboBox,
1937 std::u16string_view rSymbolSetName, bool bDeleteText)
1939 assert((&rComboBox == m_xOldSymbolSets.get() || &rComboBox == m_xSymbolSets.get()) && "Sm : wrong ComboBox");
1941 // trim SymbolName (no leading and trailing blanks)
1942 OUString aNormName( comphelper::string::strip(rSymbolSetName, ' ') );
1943 // and remove possible deviations within the input
1944 rComboBox.set_entry_text(aNormName);
1946 bool bRet = false;
1947 int nPos = rComboBox.find_text(aNormName);
1949 if (nPos != -1)
1951 rComboBox.set_active(nPos);
1952 bRet = true;
1954 else if (bDeleteText)
1955 rComboBox.set_entry_text(OUString());
1957 bool bIsOld = &rComboBox == m_xOldSymbolSets.get();
1959 // setting the SymbolSet name at the associated display
1960 weld::Label& rFT = bIsOld ? *m_xOldSymbolSetName : *m_xSymbolSetName;
1961 rFT.set_label(rComboBox.get_active_text());
1963 // set the symbol name which belongs to the SymbolSet at the associated combobox
1964 weld::ComboBox& rCB = bIsOld ? *m_xOldSymbols : *m_xSymbols;
1965 FillSymbols(rCB, false);
1967 // display a valid respectively no symbol when changing the SymbolSets
1968 if (bIsOld)
1970 OUString aTmpOldSymbolName;
1971 if (m_xOldSymbols->get_count() > 0)
1972 aTmpOldSymbolName = m_xOldSymbols->get_text(0);
1973 SelectSymbol(*m_xOldSymbols, aTmpOldSymbolName, true);
1976 UpdateButtons();
1978 return bRet;
1981 void SmSymDefineDialog::SetOrigSymbol(const SmSym *pSymbol,
1982 const OUString &rSymbolSetName)
1984 // clear old symbol
1985 m_xOrigSymbol.reset();
1987 OUString aSymName,
1988 aSymSetName;
1989 if (pSymbol)
1991 // set new symbol
1992 m_xOrigSymbol.reset(new SmSym(*pSymbol));
1994 aSymName = pSymbol->GetUiName();
1995 aSymSetName = rSymbolSetName;
1996 m_aOldSymbolDisplay.SetSymbol( pSymbol );
1998 else
1999 { // delete displayed symbols
2000 m_aOldSymbolDisplay.SetText(OUString());
2001 m_aOldSymbolDisplay.Invalidate();
2003 m_xOldSymbolName->set_label(aSymName);
2004 m_xOldSymbolSetName->set_label(aSymSetName);
2008 bool SmSymDefineDialog::SelectSymbol(weld::ComboBox& rComboBox,
2009 const OUString &rSymbolName, bool bDeleteText)
2011 assert((&rComboBox == m_xOldSymbols.get() || &rComboBox == m_xSymbols.get()) && "Sm : wrong ComboBox");
2013 // trim SymbolName (no blanks)
2014 OUString aNormName = rSymbolName.replaceAll(" ", "");
2015 // and remove possible deviations within the input
2016 rComboBox.set_entry_text(aNormName);
2018 bool bRet = false;
2019 int nPos = rComboBox.find_text(aNormName);
2021 bool bIsOld = &rComboBox == m_xOldSymbols.get();
2023 if (nPos != -1)
2025 rComboBox.set_active(nPos);
2027 if (!bIsOld)
2029 const SmSym *pSymbol = GetSymbol(*m_xSymbols);
2030 if (pSymbol)
2032 // choose font and style accordingly
2033 const vcl::Font &rFont = pSymbol->GetFace();
2034 SelectFont(rFont.GetFamilyName(), false);
2035 SelectStyle(GetFontStyles().GetStyleName(rFont), false);
2037 // Since setting the Font via the Style name of the SymbolFonts doesn't
2038 // work really well (e.g. it can be empty even though the font itself is
2039 // bold or italic) we're manually setting the Font with respect to the Symbol
2040 m_xCharsetDisplay->SetFont(rFont);
2041 m_aSymbolDisplay.SetFont(rFont);
2043 // select associated character
2044 SelectChar(pSymbol->GetCharacter());
2046 // since SelectChar will also set the unicode point as text in the
2047 // symbols box, we have to set the symbol name again to get that one displayed
2048 m_xSymbols->set_entry_text(pSymbol->GetUiName());
2052 bRet = true;
2054 else if (bDeleteText)
2055 rComboBox.set_entry_text(OUString());
2057 if (bIsOld)
2059 // if there's a change of the old symbol, show only the available ones, otherwise show none
2060 const SmSym *pOldSymbol = nullptr;
2061 OUString aTmpOldSymbolSetName;
2062 if (nPos != -1)
2064 pOldSymbol = m_aSymbolMgrCopy.GetSymbolByUiName(aNormName);
2065 aTmpOldSymbolSetName = m_xOldSymbolSets->get_active_text();
2067 SetOrigSymbol(pOldSymbol, aTmpOldSymbolSetName);
2069 else
2070 m_xSymbolName->set_label(rComboBox.get_active_text());
2072 UpdateButtons();
2074 return bRet;
2078 void SmSymDefineDialog::SetFont(const OUString &rFontName, std::u16string_view rStyleName)
2080 // get Font (FontInfo) matching name and style
2081 FontMetric aFontMetric;
2082 if (m_xFontList)
2083 aFontMetric = m_xFontList->Get(rFontName, WEIGHT_NORMAL, ITALIC_NONE);
2084 SetFontStyle(rStyleName, aFontMetric);
2086 m_xCharsetDisplay->SetFont(aFontMetric);
2087 m_aSymbolDisplay.SetFont(aFontMetric);
2089 // update subset listbox for new font's unicode subsets
2090 FontCharMapRef xFontCharMap = m_xCharsetDisplay->GetFontCharMap();
2091 m_xSubsetMap.reset(new SubsetMap( xFontCharMap ));
2093 m_xFontsSubsetLB->clear();
2094 bool bFirst = true;
2095 for (auto & subset : m_xSubsetMap->GetSubsetMap())
2097 m_xFontsSubsetLB->append(weld::toId(&subset), subset.GetName());
2098 // subset must live at least as long as the selected font !!!
2099 if (bFirst)
2100 m_xFontsSubsetLB->set_active(0);
2101 bFirst = false;
2103 if (bFirst)
2104 m_xFontsSubsetLB->set_active(-1);
2105 m_xFontsSubsetLB->set_sensitive(!bFirst);
2108 bool SmSymDefineDialog::SelectFont(const OUString &rFontName, bool bApplyFont)
2110 bool bRet = false;
2111 int nPos = m_xFonts->find_text(rFontName);
2113 if (nPos != -1)
2115 m_xFonts->set_active(nPos);
2116 if (m_xStyles->get_count() > 0)
2117 SelectStyle(m_xStyles->get_text(0));
2118 if (bApplyFont)
2120 SetFont(m_xFonts->get_active_text(), m_xStyles->get_active_text());
2121 m_aSymbolDisplay.SetSymbol(m_xCharsetDisplay->GetSelectCharacter(), m_xCharsetDisplay->GetFont());
2123 bRet = true;
2125 else
2126 m_xFonts->set_active(-1);
2127 FillStyles();
2129 UpdateButtons();
2131 return bRet;
2135 bool SmSymDefineDialog::SelectStyle(const OUString &rStyleName, bool bApplyFont)
2137 bool bRet = false;
2138 int nPos = m_xStyles->find_text(rStyleName);
2140 // if the style is not available take the first available one (if existent)
2141 if (nPos == -1 && m_xStyles->get_count() > 0)
2142 nPos = 0;
2144 if (nPos != -1)
2146 m_xStyles->set_active(nPos);
2147 if (bApplyFont)
2149 SetFont(m_xFonts->get_active_text(), m_xStyles->get_active_text());
2150 m_aSymbolDisplay.SetSymbol(m_xCharsetDisplay->GetSelectCharacter(), m_xCharsetDisplay->GetFont());
2152 bRet = true;
2154 else
2155 m_xStyles->set_entry_text(OUString());
2157 UpdateButtons();
2159 return bRet;
2162 void SmSymDefineDialog::SelectChar(sal_Unicode cChar)
2164 m_xCharsetDisplay->SelectCharacter( cChar );
2165 m_aSymbolDisplay.SetSymbol(cChar, m_xCharsetDisplay->GetFont());
2167 UpdateButtons();
2170 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */