MNE-CPP  0.1.9
A Framework for Electrophysiology
scalecontrol.cpp
Go to the documentation of this file.
1 //=============================================================================================================
35 #include "scalecontrol.h"
36 #include "ui_scalecontrol.h"
37 #include <math.h>
38 
39 #include <QInputDialog>
40 
41 using namespace DISPLIB;
42 
43 const static float m_dDefaultMin(0.0f);
44 const static float m_dDefaultMax(1.0f);
45 const static float m_dDefaultMaxSensitivityPoint((m_dDefaultMin+m_dDefaultMax)/2.0f);
46 const static float m_dDefaultSensitivity(0.3f);
47 const static int m_iDefaultSliderMin(1);
48 const static int m_iDefaultSliderMax(1000);
49 const static int m_iDefaultSliderStep(1);
50 const static int m_iDefaultSliderPageStep(10);
51 
52 //=============================================================================================================
53 
54 ScaleControl::ScaleControl(const char* label)
55 : ScaleControl(label, nullptr, m_dDefaultMin, m_dDefaultMax)
56 { }
57 
58 //=============================================================================================================
59 
60 ScaleControl::ScaleControl(const char* label,
61  QWidget* parent)
62 : ScaleControl(label, parent, m_dDefaultMin, m_dDefaultMax)
63 { }
64 
65 //=============================================================================================================
66 
67 ScaleControl::ScaleControl(const char* label,
68  QWidget* parent,
69  double min,
70  double max)
71 : QWidget(parent)
72 , m_pUi(new Ui::ScaleControlWidget)
73 , m_bManagingSpinBoxChange(false)
74 , m_bManagingSliderChange(false)
75 , m_fSensitivity(m_dDefaultSensitivity)
76 , m_fMaxSensitivityPoint(m_dDefaultMaxSensitivityPoint)
77 , m_fMapYconstant(0.0f)
78 , m_fMapKconstant(0.0f)
79 , m_bSliderInverted(false)
80 {
81  m_pUi->setupUi(this);
82  initLabel(label);
83  initSpinBox();
84  initSlider();
85  initMenu();
86  updateNLMapConstants();
87  setRange(min, max);
88 }
89 
90 //=============================================================================================================
91 
92 void ScaleControl::initLabel(const char* charTextLabel)
93 {
94  m_pUi->label->setText(charTextLabel);
95 }
96 
97 //=============================================================================================================
98 
99 void ScaleControl::initSpinBox()
100 {
101  m_pUi->spinBox->setKeyboardTracking(false);
102  m_pUi->spinBox->setPrefix("+/- ");
103 
104  connect(m_pUi->spinBox,static_cast<void (QDoubleSpinBox::*)(double)>(&QDoubleSpinBox::valueChanged),
105  this,&ScaleControl::spinBoxChanged);
106 }
107 
108 //=============================================================================================================
109 
110 void ScaleControl::initSlider()
111 {
112  m_pUi->slider->setSizePolicy(QSizePolicy(QSizePolicy::Expanding, QSizePolicy::Preferred));
113  m_pUi->slider->setSingleStep(m_iDefaultSliderStep);
114  m_pUi->slider->setPageStep(m_iDefaultSliderPageStep);
115  setSliderRange(m_iDefaultSliderMin, m_iDefaultSliderMax);
116 
117  connect(m_pUi->slider,static_cast<void (QSlider::*)(int)>(&QSlider::valueChanged),
118  this,&ScaleControl::sliderChanged);
119 }
120 
121 //=============================================================================================================
122 
123 Ui::ScaleControlWidget* ScaleControl::getUI()
124 {
125  return m_pUi;
126 }
127 
128 //=============================================================================================================
129 
130 void ScaleControl::setValue(double dScale)
131 {
132  m_pUi->spinBox->setValue(dScale);
133 }
134 
135 //=============================================================================================================
136 
138 {
139  if(m_pUi->spinBox->minimum() < s && s < m_pUi->spinBox->maximum())
140  {
141  m_fMaxSensitivityPoint = s;
142  updateNLMapConstants();
143  }
144 }
145 
146 //=============================================================================================================
147 
149 {
150  if(0.0 < s && s < 1.0)
151  {
152  m_fSensitivity = s;
153  updateNLMapConstants();
154  }
155 }
156 
157 //=============================================================================================================
158 
159 void ScaleControl::setRange(double min,
160  double max)
161 {
162  m_pUi->spinBox->setRange(min, max);
163  if(m_fMaxSensitivityPoint < m_pUi->spinBox->minimum() || m_pUi->spinBox->maximum() < m_fMaxSensitivityPoint)
164  {
165  m_fMaxSensitivityPoint = (m_pUi->spinBox->minimum() + m_pUi->spinBox->maximum())/2;
166  }
167  updateNLMapConstants();
168 }
169 
170 //=============================================================================================================
171 
172 void ScaleControl::invertSlider(bool inverted)
173 {
174  m_bSliderInverted = inverted;
175 }
176 
177 //=============================================================================================================
178 
179 void ScaleControl::setSliderRange(int min,
180  int max)
181 {
182  if( (0 < min) && (min < max) )
183  {
184  m_pUi->slider->setRange(min, max);
185  updateNLMapConstants();
186  }
187 }
188 
189 //=============================================================================================================
190 
192 {
193  m_pUi->spinBox->setDecimals(d);
194 }
195 
196 //=============================================================================================================
197 
198 void ScaleControl::spinBoxChanged(double dScale)
199 {
200  m_bManagingSpinBoxChange = true;
201  if(!m_bManagingSliderChange)
202  {
203  m_pUi->slider->setValue(mapSpinBoxToSlider(dScale));
204  }
205  m_bManagingSpinBoxChange = false;
206  emit valueChanged(dScale);
207 }
208 
209 //=============================================================================================================
210 
211 void ScaleControl::sliderChanged(int dScale)
212 {
213  m_bManagingSliderChange = true;
214  if(!m_bManagingSpinBoxChange)
215  {
216  m_pUi->spinBox->setValue(mapSliderToSpinBox(dScale));
217  }
218  m_bManagingSliderChange = false;
219 }
220 
221 //=============================================================================================================
222 
223 inline float ScaleControl::weightedSensitivity(float s)
224 {
225  return s * s * s * 100 / m_pUi->spinBox->maximum();
226 }
227 
228 //=============================================================================================================
229 
230 void ScaleControl::updateNLMapConstants()
231 {
232  m_fMapYconstant = atanf(weightedSensitivity(m_fSensitivity) * (m_pUi->spinBox->minimum() - m_fMaxSensitivityPoint));
233  m_fMapKconstant = (m_pUi->slider->maximum() - m_pUi->slider->minimum()) / (atanf(weightedSensitivity(m_fSensitivity) * (m_pUi->spinBox->maximum() - m_fMaxSensitivityPoint)) - m_fMapYconstant);
234 }
235 
236 //=============================================================================================================
237 
238 int ScaleControl::mapSpinBoxToSlider(double dScale)
239 {
240  float map = m_fMapKconstant * (atanf(weightedSensitivity(m_fSensitivity) * (static_cast<float>(dScale) - m_fMaxSensitivityPoint)) - m_fMapYconstant);
241  int out;
242  if(m_bSliderInverted)
243  {
244  out = m_pUi->slider->maximum() - static_cast<int>(roundf(map));
245  } else {
246  out = static_cast<int> (roundf(map));
247  }
248  return out;
249 }
250 
251 //=============================================================================================================
252 
253 double ScaleControl::mapSliderToSpinBox(int dScale)
254 {
255  int valueCorrected = m_bSliderInverted? m_pUi->slider->maximum() - dScale : dScale;
256  float map = (1/weightedSensitivity(m_fSensitivity)) * tanf((static_cast<float>(valueCorrected) / m_fMapKconstant) + m_fMapYconstant) + m_fMaxSensitivityPoint;
257  return static_cast<double>(map);
258 }
259 
260 //=============================================================================================================
261 
262 double ScaleControl::value() const
263 {
264  return m_pUi->spinBox->value();
265 }
266 
267 //=============================================================================================================
268 
269 void ScaleControl::initMenu()
270 {
271  m_pSettingsMenu = new QMenu(this); //Scale Control takes ownership of this QMenu and will trigger its deletion.
272 
273  QAction* minVal = new QAction("Edit minimum value");
274  connect(minVal, &QAction::triggered,
275  this, &ScaleControl::promptMinValueChange,
276  Qt::UniqueConnection);
277  m_pSettingsMenu->addAction(minVal);//takes ownership
278 
279  QAction* maxVal = new QAction("Edit maximum value");
280  connect(maxVal, &QAction::triggered,
281  this, &ScaleControl::promptMaxValueChange,
282  Qt::UniqueConnection);
283  m_pSettingsMenu->addAction(maxVal);//takes ownership
284 
285  m_pUi->toolButton->setMenu(m_pSettingsMenu);
286  m_pUi->toolButton->setPopupMode(QToolButton::InstantPopup);
287  m_pUi->toolButton->setArrowType(Qt::ArrowType::NoArrow);
288 }
289 
290 //=============================================================================================================
291 
292 void ScaleControl::promptMinValueChange()
293 {
294  bool ok;
295  double min = QInputDialog::getDouble(this, tr("Minimum Value"),
296  tr("Please input a new minumum value:"),
297  m_pUi->spinBox->minimum(), 0.01, 100000,
298  2, &ok, Qt::WindowFlags(), 1);
299  if(ok && min <= m_pUi->spinBox->maximum()){
300  setRange(min, m_pUi->spinBox->maximum());
301  }
302 }
303 
304 //=============================================================================================================
305 
306 void ScaleControl::promptMaxValueChange()
307 {
308  bool ok;
309  double max = QInputDialog::getDouble(this, tr("Maximum Value"),
310  tr("Please input a new maximum value:"),
311  m_pUi->spinBox->maximum(), 0.01, 100000,
312  2, &ok, Qt::WindowFlags(), 1);
313  if(ok && max >= m_pUi->spinBox->minimum()){
314  setRange(m_pUi->spinBox->minimum(), max);
315  }
316 }
scalecontrol.h
Declaration of the ScaleControl Class.
DISPLIB::ScaleControl::setDecimals
void setDecimals(int d)
Definition: scalecontrol.cpp:191
DISPLIB::ScaleControl::ScaleControl
ScaleControl(const char *label)
Definition: scalecontrol.cpp:54
DISPLIB::ScaleControl::invertSlider
void invertSlider(bool inverted)
Definition: scalecontrol.cpp:172
DISPLIB::ScaleControl::setValue
void setValue(double dScale)
Definition: scalecontrol.cpp:130
DISPLIB::ScaleControl::setSensitivity
void setSensitivity(double s)
Definition: scalecontrol.cpp:148
DISPLIB::ScaleControl::value
double value() const
Definition: scalecontrol.cpp:262
DISPLIB::ScaleControl::setMaxSensitivityPoint
void setMaxSensitivityPoint(double s)
Definition: scalecontrol.cpp:137
DISPLIB::ScaleControl::setRange
void setRange(double min, double max)
Definition: scalecontrol.cpp:159
DISPLIB::ScaleControl::valueChanged
void valueChanged(double dScale)
DISPLIB::ScaleControl
The ScaleControl class packs together a QLabel, a DoubleSpinbox and a Slider with the necessary facil...
Definition: scalecontrol.h:75
DISPLIB::ScaleControl::getUI
Ui::ScaleControlWidget * getUI()
Definition: scalecontrol.cpp:123