LibreOffice Module sc (master)  1
FourierAnalysisDialog.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 
11 #include <sfx2/dispatch.hxx>
12 #include <svl/zforlist.hxx>
13 #include <svl/undo.hxx>
14 
15 #include <formulacell.hxx>
16 #include <rangelst.hxx>
17 #include <scitems.hxx>
18 #include <docsh.hxx>
19 #include <document.hxx>
20 #include <uiitems.hxx>
21 #include <reffact.hxx>
22 #include <docfunc.hxx>
25 #include <scresid.hxx>
26 #include <strings.hrc>
27 
29  SfxChildWindow* pChildWindow,
30  weld::Window* pParent, ScViewData* pViewData)
31  : ScStatisticsInputOutputDialog(pSfxBindings, pChildWindow, pParent, pViewData,
32  "modules/scalc/ui/fourieranalysisdialog.ui",
33  "FourierAnalysisDialog")
34  , maLabelAddr(ScAddress::INITIALIZE_INVALID)
35  , maActualInputRange(ScAddress::INITIALIZE_INVALID)
36  , mnLen(0)
37  , mfMinMag(0.0)
38  , mbUse3DAddresses(false)
39  , mbGroupedByColumn(true)
40  , mbWithLabels(false)
41  , mbInverse(false)
42  , mbPolar(false)
43  , mxWithLabelsCheckBox(m_xBuilder->weld_check_button("withlabels-check"))
44  , mxInverseCheckBox(m_xBuilder->weld_check_button("inverse-check"))
45  , mxPolarCheckBox(m_xBuilder->weld_check_button("polar-check"))
46  , mxMinMagnitudeField(m_xBuilder->weld_spin_button("minmagnitude-spin"))
47  , mxErrorMessage(m_xBuilder->weld_label("error-message"))
48 {
49  m_xDialog->set_title(ScResId(STR_FOURIER_ANALYSIS));
50 
51  mxWithLabelsCheckBox->connect_toggled(LINK(this, ScFourierAnalysisDialog, CheckBoxHdl));
52 }
53 
55 
57 {
59 }
60 
61 const char* ScFourierAnalysisDialog::GetUndoNameId() { return STR_FOURIER_ANALYSIS; }
62 
64 {
65  getOptions();
66  AddressWalkerWriter aOutput(mOutputAddress, pDocShell, &mDocument,
69  FormulaTemplate aTemplate(&mDocument);
71 
72  aOutput.writeBoldString(mbInverse ? ScResId(STR_INVERSE_FOURIER_TRANSFORM)
73  : ScResId(STR_FOURIER_TRANSFORM));
74  aOutput.newLine();
75  OUString aLabel;
76  getDataLabel(aLabel);
77  if (aLabel.startsWith("="))
78  aOutput.writeFormula(aLabel);
79  else
80  aOutput.writeString(aLabel);
81 
82  aOutput.newLine();
83  // Components header
84  if (!mbPolar)
85  {
86  aOutput.writeString(ScResId(STR_REAL_PART));
87  aOutput.nextColumn();
88  aOutput.writeString(ScResId(STR_IMAGINARY_PART));
89  }
90  else
91  {
92  aOutput.writeString(ScResId(STR_MAGNITUDE_PART));
93  aOutput.nextColumn();
94  aOutput.writeString(ScResId(STR_PHASE_PART));
95  }
96 
97  aOutput.newLine();
98  aTemplate.autoReplaceRange("%INPUTRANGE%", maActualInputRange);
99 
100  OUString aFormula;
101  genFormula(aFormula);
102 
103  aTemplate.setTemplate(aFormula);
104  aOutput.writeMatrixFormula(aTemplate.getTemplate(), 2, mnLen);
105 
106  return ScRange(aOutput.mMinimumAddress, aOutput.mMaximumAddress);
107 }
108 
110 {
111  if (!mInputRange.IsValid())
112  {
113  mxErrorMessage->set_label(ScResId(STR_MESSAGE_INVALID_INPUT_RANGE));
114  return false;
115  }
116 
117  if (!mOutputAddress.IsValid())
118  {
119  mxErrorMessage->set_label(ScResId(STR_MESSAGE_INVALID_OUTPUT_ADDR));
120  return false;
121  }
122 
124 
126  mbWithLabels = mxWithLabelsCheckBox->get_active();
127 
129 
130  SCSIZE nRows = mInputRange.aEnd.Row() - mInputRange.aStart.Row() + 1;
131  SCSIZE nCols = mInputRange.aEnd.Col() - mInputRange.aStart.Col() + 1;
132 
133  SCSIZE nLen = mbGroupedByColumn ? nRows : nCols;
134  SCSIZE nComponents = mbGroupedByColumn ? nCols : nRows;
135 
136  if (nComponents > 2)
137  {
138  OUString aMsg = mbGroupedByColumn ? ScResId(STR_MESSAGE_INVALID_NUMCOLS)
139  : ScResId(STR_MESSAGE_INVALID_NUMROWS);
140  mxErrorMessage->set_label(aMsg);
141  return false;
142  }
143 
144  if (mbWithLabels && nLen < 2)
145  {
146  mxErrorMessage->set_label(ScResId(STR_MESSAGE_NODATA_IN_RANGE));
147  return false;
148  }
149 
150  // Include space for writing the title, label and Real/Imaginary/Magnitude/Phase heading.
151  SCSIZE nLastOutputRow = mOutputAddress.Row() + nLen + 2;
152  if (mbWithLabels)
153  --nLastOutputRow;
154 
155  if (nLastOutputRow > MAXROW)
156  {
157  mxErrorMessage->set_label(ScResId(STR_MESSAGE_OUTPUT_TOO_LONG));
158  return false;
159  }
160 
161  ScAddress aActualStart(mInputRange.aStart);
162 
163  if (mbWithLabels)
164  {
165  if (mbGroupedByColumn)
166  aActualStart.IncRow();
167  else
168  aActualStart.IncCol();
169 
170  if (nComponents == 1)
172  else
173  mbWithLabels = false;
174 
175  mnLen = nLen - 1;
176  }
177  else
178  {
179  mnLen = nLen;
180  }
181 
182  maActualInputRange = ScRange(aActualStart, mInputRange.aEnd);
183  mxErrorMessage->set_label("");
184 
185  return true;
186 }
187 
189 {
190  mbInverse = mxInverseCheckBox->get_active();
191  mbPolar = mxPolarCheckBox->get_active();
192 
193  sal_Int32 nDeciBels = static_cast<sal_Int32>(mxMinMagnitudeField->get_value());
194  if (nDeciBels <= -150)
195  mfMinMag = 0.0;
196  else
197  mfMinMag = pow(10.0, static_cast<double>(nDeciBels) / 10.0);
198 }
199 
201 {
202  if (mbWithLabels)
203  {
204  rLabel = "="
208 
209  return;
210  }
211 
212  OUString aDataSrc(mInputRange.Format(
214  mAddressDetails));
215 
216  rLabel = ScResId(STR_INPUT_DATA_RANGE) + " : " + aDataSrc;
217  return;
218 }
219 
220 void ScFourierAnalysisDialog::genFormula(OUString& rFormula)
221 {
222  static const OUString aSep(";");
223 
224  if (!mbPolar)
225  {
226  rFormula = "FOURIER(%INPUTRANGE%;" + OUString::boolean(mbGroupedByColumn) + aSep
227  + OUString::boolean(mbInverse) + ")";
228  return;
229  }
230 
231  rFormula = "FOURIER(%INPUTRANGE%;" + OUString::boolean(mbGroupedByColumn) + aSep
232  + OUString::boolean(mbInverse) + ";true;" + OUString::number(mfMinMag) + ")";
233 }
234 
236 {
237  ValidateDialogInput();
238 }
239 
240 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
SC_DLLPUBLIC void Format(OStringBuffer &r, ScRefFlags nFlags, const ScDocument *pDocument=nullptr, const Details &rDetails=detailsOOOa1) const
Definition: address.cxx:2111
ScAddress aStart
Definition: address.hxx:500
std::unique_ptr< weld::Label > mxErrorMessage
void writeFormula(const OUString &aFormula)
SCROW Row() const
Definition: address.hxx:262
void writeString(const OUString &aString)
std::unique_ptr< weld::CheckButton > mxInverseCheckBox
void getDataLabel(OUString &rLabel)
ScAddress aEnd
Definition: address.hxx:501
std::unique_ptr< weld::CheckButton > mxPolarCheckBox
std::unique_ptr< weld::CheckButton > mxWithLabelsCheckBox
formula::FormulaGrammar::AddressConvention eConv
Definition: address.hxx:213
size_t SCSIZE
size_t typedef to be able to find places where code was changed from USHORT to size_t and is used to ...
Definition: address.hxx:45
void writeBoldString(const OUString &aString)
void writeMatrixFormula(const OUString &aFormula, SCCOL nCols=1, SCROW nRows=1)
const SCROW MAXROW
Definition: address.hxx:69
static Grammar mergeToGrammar(const Grammar eGrammar, const AddressConvention eConv)
SCTAB Tab() const
Definition: address.hxx:271
bool IsValid() const
Definition: address.hxx:293
virtual ScRange ApplyOutput(ScDocShell *pDocShell) override
void genFormula(OUString &rFormula)
void IncCol(SCCOL nDelta=1)
Definition: address.hxx:304
virtual void Close() override
SC_DLLPUBLIC OUString Format(const ScDocument &rDocument, ScRefFlags nFlags=ScRefFlags::ZERO, const ScAddress::Details &rDetails=ScAddress::detailsOOOa1, bool bFullAddressNotation=false) const
Returns string with formatted cell range from aStart to aEnd, according to provided address conventio...
Definition: address.cxx:2207
void IncRow(SCROW nDelta=1)
Definition: address.hxx:300
OUString ScResId(const char *pId)
Definition: scdll.cxx:95
ScFourierAnalysisDialog(SfxBindings *pB, SfxChildWindow *pCW, weld::Window *pParent, ScViewData *pViewData)
void autoReplaceRange(const OUString &aVariable, const ScRange &rRange)
bool IsValid() const
Definition: address.hxx:547
SCCOL Col() const
Definition: address.hxx:267
SC_DLLPUBLIC void PutInOrder()
Definition: address.cxx:1577
virtual const char * GetUndoNameId() override
std::unique_ptr< weld::SpinButton > mxMinMagnitudeField
Reference< XExecutableDialog > m_xDialog
OUString aLabel
IMPL_LINK_NOARG(ScFourierAnalysisDialog, CheckBoxHdl, weld::ToggleButton &, void)
void setTemplate(const OUString &aTemplate)
bool DoClose(sal_uInt16 nId)
Definition: anyrefdg.cxx:694
virtual ~ScFourierAnalysisDialog() override
virtual bool InputRangesValid() override