LibreOffice Module chart2 (master) 1
ChartAxisPanel.cxx
Go to the documentation of this file.
1/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2/*
3 * This file is part of the LibreOffice project.
4 *
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 *
9 * This file incorporates work covered by the following license notice:
10 *
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
18 */
19
20#include <com/sun/star/chart/ChartAxisLabelPosition.hpp>
21#include <com/sun/star/chart2/AxisOrientation.hpp>
22
23#include <vcl/svapp.hxx>
24#include <sal/log.hxx>
25
26#include "ChartAxisPanel.hxx"
27#include <ChartController.hxx>
28#include <ChartModel.hxx>
29#include <Axis.hxx>
30
31using namespace css;
32using namespace css::uno;
33
34namespace chart::sidebar {
35
36namespace {
37
38bool isLabelShown(const rtl::Reference<::chart::ChartModel>& xModel,
39 std::u16string_view rCID)
40{
42
43 if (!xAxis.is())
44 return false;
45
46 uno::Any aAny = xAxis->getPropertyValue("DisplayLabels");
47 if (!aAny.hasValue())
48 return false;
49
50 bool bVisible = false;
51 aAny >>= bVisible;
52 return bVisible;
53}
54
55void setLabelShown(const rtl::Reference<::chart::ChartModel>& xModel,
56 std::u16string_view rCID, bool bVisible)
57{
59
60 if (!xAxis.is())
61 return;
62
63 xAxis->setPropertyValue("DisplayLabels", css::uno::Any(bVisible));
64}
65
66struct AxisLabelPosMap
67{
68 sal_Int32 nPos;
69 css::chart::ChartAxisLabelPosition ePos;
70};
71
72AxisLabelPosMap const aLabelPosMap[] = {
73 { 0, css::chart::ChartAxisLabelPosition_NEAR_AXIS },
74 { 1, css::chart::ChartAxisLabelPosition_NEAR_AXIS_OTHER_SIDE },
75 { 2, css::chart::ChartAxisLabelPosition_OUTSIDE_START },
76 { 3, css::chart::ChartAxisLabelPosition_OUTSIDE_END }
77};
78
79sal_Int32 getLabelPosition(const rtl::Reference<::chart::ChartModel>& xModel,
80 std::u16string_view rCID)
81{
83
84 if (!xAxis.is())
85 return 0;
86
87 uno::Any aAny = xAxis->getPropertyValue("LabelPosition");
88 if (!aAny.hasValue())
89 return 0;
90
91 css::chart::ChartAxisLabelPosition ePos;
92 aAny >>= ePos;
93 for (AxisLabelPosMap const & i : aLabelPosMap)
94 {
95 if (i.ePos == ePos)
96 return i.nPos;
97 }
98
99 return 0;
100}
101
102void setLabelPosition(const rtl::Reference<::chart::ChartModel>& xModel,
103 std::u16string_view rCID, sal_Int32 nPos)
104{
106
107 if (!xAxis.is())
108 return;
109
110 css::chart::ChartAxisLabelPosition ePos;
111 for (AxisLabelPosMap const & i : aLabelPosMap)
112 {
113 if (i.nPos == nPos)
114 ePos = i.ePos;
115 }
116
117 xAxis->setPropertyValue("LabelPosition", css::uno::Any(ePos));
118}
119
120bool isReverse(const rtl::Reference<::chart::ChartModel>& xModel,
121 std::u16string_view rCID)
122{
125
126 if (!xAxis.is())
127 return false;
128
129 css::chart2::ScaleData aData = xAxis->getScaleData();
130
131 return aData.Orientation == css::chart2::AxisOrientation_REVERSE;
132}
133
134void setReverse(const rtl::Reference<::chart::ChartModel>& xModel,
135 std::u16string_view rCID, bool bReverse)
136{
139
140 if (!xAxis.is())
141 return;
142
143 css::chart2::ScaleData aData = xAxis->getScaleData();
144 if (bReverse)
145 aData.Orientation = css::chart2::AxisOrientation_REVERSE;
146 else
147 aData.Orientation = css::chart2::AxisOrientation_MATHEMATICAL;
148
149 xAxis->setScaleData(aData);
150}
151
152OUString getCID(const css::uno::Reference<css::frame::XModel>& xModel)
153{
154 css::uno::Reference<css::frame::XController> xController(xModel->getCurrentController());
155 css::uno::Reference<css::view::XSelectionSupplier> xSelectionSupplier(xController, css::uno::UNO_QUERY);
156 if (!xSelectionSupplier.is())
157 return OUString();
158
159 uno::Any aAny = xSelectionSupplier->getSelection();
160 assert(aAny.hasValue());
161 OUString aCID;
162 aAny >>= aCID;
163#if defined DBG_UTIL && !defined NDEBUG
165 if(eType != OBJECTTYPE_AXIS)
166 SAL_WARN("chart2","Selected item is not an axis");
167#endif
168
169 return aCID;
170}
171
172void setAxisRotation(const rtl::Reference<::chart::ChartModel>& xModel,
173 std::u16string_view rCID, double nVal)
174{
177
178 if (!xAxis.is())
179 return;
180
181 xAxis->setPropertyValue("TextRotation", css::uno::Any(nVal));
182}
183
184double getAxisRotation(const rtl::Reference<::chart::ChartModel>& xModel,
185 std::u16string_view rCID)
186{
189
190 if (!xAxis.is())
191 return 0;
192
193 css::uno::Any aAny = xAxis->getPropertyValue("TextRotation");
194 double nVal = 0;
195 aAny >>= nVal;
196 return nVal;
197}
198
199}
200
202 weld::Widget* pParent,
203 ChartController* pController)
204 : PanelLayout(pParent, "ChartAxisPanel", "modules/schart/ui/sidebaraxis.ui")
205 , mxCBShowLabel(m_xBuilder->weld_check_button("checkbutton_show_label"))
206 , mxCBReverse(m_xBuilder->weld_check_button("checkbutton_reverse"))
207 , mxLBLabelPos(m_xBuilder->weld_combo_box("comboboxtext_label_position"))
208 , mxGridLabel(m_xBuilder->weld_widget("label_props"))
209 , mxNFRotation(m_xBuilder->weld_metric_spin_button("spinbutton1", FieldUnit::DEGREE))
210 , mxModel(pController->getChartModel())
211 , mxModifyListener(new ChartSidebarModifyListener(this))
212 , mxSelectionListener(new ChartSidebarSelectionListener(this, OBJECTTYPE_AXIS))
213 , mbModelValid(true)
214{
215 Initialize();
216}
217
219{
220 doUpdateModel(nullptr);
221
222 mxCBShowLabel.reset();
223 mxCBReverse.reset();
224
225 mxLBLabelPos.reset();
226 mxGridLabel.reset();
227
228 mxNFRotation.reset();
229}
230
232{
233 mxModel->addModifyListener(mxModifyListener);
234
235 css::uno::Reference<css::view::XSelectionSupplier> xSelectionSupplier(mxModel->getCurrentController(), css::uno::UNO_QUERY);
236 if (xSelectionSupplier.is())
237 xSelectionSupplier->addSelectionChangeListener(mxSelectionListener);
238
239 updateData();
240
241 Link<weld::Toggleable&,void> aLink = LINK(this, ChartAxisPanel, CheckBoxHdl);
242 mxCBShowLabel->connect_toggled(aLink);
243 mxCBReverse->connect_toggled(aLink);
244
245 Link<weld::MetricSpinButton&, void> aSpinButtonLink = LINK(this, ChartAxisPanel, TextRotationHdl);
246 mxNFRotation->connect_value_changed(aSpinButtonLink);
247
248 mxLBLabelPos->connect_changed(LINK(this, ChartAxisPanel, ListBoxHdl));
249}
250
252{
253 if (!mbModelValid)
254 return;
255
256 OUString aCID = getCID(mxModel);
259 return;
260
261 SolarMutexGuard aGuard;
262
263 mxCBShowLabel->set_active(isLabelShown(mxModel, aCID));
264 mxCBReverse->set_active(isReverse(mxModel, aCID));
265
266 mxLBLabelPos->set_active(getLabelPosition(mxModel, aCID));
267 mxNFRotation->set_value(getAxisRotation(mxModel, aCID), FieldUnit::DEGREE);
268}
269
270std::unique_ptr<PanelLayout> ChartAxisPanel::Create (
271 weld::Widget* pParent,
272 ChartController* pController)
273{
274 if (pParent == nullptr)
275 throw lang::IllegalArgumentException("no parent Window given to ChartAxisPanel::Create", nullptr, 0);
276 return std::make_unique<ChartAxisPanel>(pParent, pController);
277}
278
280{
282 updateData();
283}
284
286 const vcl::EnumContext& )
287{
288 updateData();
289}
290
292 sal_uInt16 /*nSID*/,
293 SfxItemState /*eState*/,
294 const SfxPoolItem* /*pState*/ )
295{
296}
297
299{
300 mbModelValid = false;
301}
302
304{
305 if (mbModelValid)
306 {
307 mxModel->removeModifyListener(mxModifyListener);
308
309 css::uno::Reference<css::view::XSelectionSupplier> oldSelectionSupplier(
310 mxModel->getCurrentController(), css::uno::UNO_QUERY);
311 if (oldSelectionSupplier.is()) {
312 oldSelectionSupplier->removeSelectionChangeListener(mxSelectionListener);
313 }
314 }
315
316 mxModel = xModel;
317 mbModelValid = mxModel.is();
318
319 if (!mbModelValid)
320 return;
321
322 mxModel->addModifyListener(mxModifyListener);
323
324 css::uno::Reference<css::view::XSelectionSupplier> xSelectionSupplier(mxModel->getCurrentController(), css::uno::UNO_QUERY);
325 if (xSelectionSupplier.is())
326 xSelectionSupplier->addSelectionChangeListener(mxSelectionListener);
327}
328
329void ChartAxisPanel::updateModel(css::uno::Reference<css::frame::XModel> xModel)
330{
331 ::chart::ChartModel* pModel = dynamic_cast<::chart::ChartModel*>(xModel.get());
332 assert(!xModel || pModel);
333 doUpdateModel(pModel);
334}
335
336void ChartAxisPanel::selectionChanged(bool bCorrectType)
337{
338 if (bCorrectType)
339 updateData();
340}
341
342IMPL_LINK(ChartAxisPanel, CheckBoxHdl, weld::Toggleable&, rCheckbox, void)
343{
344 OUString aCID = getCID(mxModel);
345 bool bChecked = rCheckbox.get_active();
346
347 if (&rCheckbox == mxCBShowLabel.get())
348 {
349 mxGridLabel->set_sensitive(bChecked);
350 setLabelShown(mxModel, aCID, bChecked);
351 }
352 else if (&rCheckbox == mxCBReverse.get())
353 setReverse(mxModel, aCID, bChecked);
354}
355
357{
358 OUString aCID = getCID(mxModel);
359 sal_Int32 nPos = mxLBLabelPos->get_active();
360
361 setLabelPosition(mxModel, aCID, nPos);
362}
363
364IMPL_LINK(ChartAxisPanel, TextRotationHdl, weld::MetricSpinButton&, rMetricField, void)
365{
366 OUString aCID = getCID(mxModel);
367 double nVal = rMetricField.get_value(FieldUnit::DEGREE);
368 setAxisRotation(mxModel, aCID, nVal);
369}
370
371} // end of namespace ::chart::sidebar
372
373/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
sal_Int32 nPos
css::chart::ChartAxisLabelPosition ePos
css::uno::Reference< css::frame::XModel2 > mxModel
virtual void DataChanged(const DataChangedEvent &rEvent)
static rtl::Reference< ::chart::Axis > getAxisForCID(std::u16string_view rObjectCID, const rtl::Reference<::chart::ChartModel > &xChartModel)
ObjectType getObjectType() const
std::unique_ptr< weld::ComboBox > mxLBLabelPos
std::unique_ptr< weld::MetricSpinButton > mxNFRotation
css::uno::Reference< css::view::XSelectionChangeListener > mxSelectionListener
rtl::Reference<::chart::ChartModel > mxModel
css::uno::Reference< css::util::XModifyListener > mxModifyListener
virtual void selectionChanged(bool bCorrectType) override
virtual void updateModel(css::uno::Reference< css::frame::XModel > xModel) override
virtual void DataChanged(const DataChangedEvent &rEvent) override
ChartAxisPanel(weld::Widget *pParent, ChartController *pController)
void doUpdateModel(rtl::Reference<::chart::ChartModel > xModel)
virtual void updateData() override
virtual ~ChartAxisPanel() override
std::unique_ptr< weld::Widget > mxGridLabel
virtual void HandleContextChange(const vcl::EnumContext &rContext) override
std::unique_ptr< weld::CheckButton > mxCBShowLabel
std::unique_ptr< weld::CheckButton > mxCBReverse
virtual void NotifyItemUpdate(const sal_uInt16 nSId, const SfxItemState eState, const SfxPoolItem *pState) override
static std::unique_ptr< PanelLayout > Create(weld::Widget *pParent, ChartController *pController)
virtual void modelInvalid() override
FieldUnit
DocumentType eType
#define SAL_WARN(area, stream)
constexpr OUStringLiteral aData
IMPL_LINK_NOARG(ChartAxisPanel, ListBoxHdl, weld::ComboBox &, void)
IMPL_LINK(ChartAxisPanel, CheckBoxHdl, weld::Toggleable &, rCheckbox, void)
int i
ObjectType
SfxItemState
bool hasValue()
Reference< XController > xController
Reference< XModel > xModel
bool bVisible