KSeExpr 6.0.0.0
ExprControl.cpp
Go to the documentation of this file.
1// SPDX-FileCopyrightText: 2011-2019 Disney Enterprises, Inc.
2// SPDX-License-Identifier: LicenseRef-Apache-2.0
3// SPDX-FileCopyrightText: 2020 L. E. Segovia <amy@amyspark.me>
4// SPDX-License-Identifier: GPL-3.0-or-later
5/*
6 * @file ExprControl.cpp
7 * @brief UI control widgets for expressions.
8 * @author aselle
9 */
10
11#include "ExprControl.h"
12#include "Debug.h"
13#include "Editable.h"
14#include "ExprColorCurve.h"
15#include "ExprColorSwatch.h"
16#include "ExprFileDialog.h"
17
18
19/* XPM */
20static constexpr std::array<const char *, 24> directoryXPM = {"20 20 3 1",
21 ". c None",
22 "# c #000000",
23 "a c #d8c59e",
24 "....................",
25 "....................",
26 "....................",
27 "....................",
28 "...........#######..",
29 "...........#aaaaa#..",
30 "..##########aaaaa#..",
31 "..#aaaaaaaaaaaaaa#..",
32 "..#aaaaaaaaaaaaaa#..",
33 "..#aaaaaaaaaaaaaa#..",
34 "..#aaaaaaaaaaaaaa#..",
35 "..#aaaaaaaaaaaaaa#..",
36 "..#aaaaa##a##a##a#..",
37 "..#aaaaa##a##a##a#..",
38 "..#aaaaaaaaaaaaaa#..",
39 "..################..",
40 "....................",
41 "....................",
42 "....................",
43 "...................."};
44
45/* XPM */
46static constexpr std::array<const char *, 26> fileXPM = {"20 20 5 1",
47 ". c None",
48 "# c #000000",
49 "c c #303030",
50 "b c #a79b80",
51 "a c #ddcdaa",
52 "....................",
53 "....................",
54 "....#########.......",
55 "....#aaaaaaa##......",
56 "....#aaaaaaa#b#.....",
57 "....#aaaaaaa#bb#....",
58 "....#aaaaaaa####....",
59 "....#aaaaaaaaaa#....",
60 "....#aaaaaaaaaa#....",
61 "....#aaaaaaaaaa#....",
62 "....#aaaaaaaaaa#....",
63 "....#aaaaaaaaaa#....",
64 "....#aaaaaaaaaa#....",
65 "....#aaaaaaaaaa#....",
66 "....#aaaaaaaaaa#....",
67 "....#accaccacca#....",
68 "....#accaccacca#....",
69 "....#aaaaaaaaaa#....",
70 "....############....",
71 "...................."};
72
73void ExprSlider::mousePressEvent(QMouseEvent *e)
74{
76}
77
78void ExprSlider::mouseMoveEvent(QMouseEvent *e)
79{
80 auto r = maximum() - minimum();
81 auto v = ((double)(e->x() - 2) * r / (width() - 5)) + minimum() + .5F;
82 int iv = std::min(std::max((int)v, minimum()), maximum());
83 setValue(iv);
84}
85
86void ExprSlider::paintEvent(QPaintEvent *)
87{
88 QPainter p(this);
89
90 double v = value();
91 double r = maximum() - minimum();
92 int linepos = (int)((v - minimum()) / r * (width() - 5) + 2);
93
94 QColor qcol = palette().color(QPalette::Dark);
95 QColor bcol = palette().color(QPalette::Midlight);
96 QColor dcol = bcol.lighter(140);
97 QColor bgcol = palette().color(QPalette::Base);
98
99 if (underMouse()) {
100 bcol = bcol.lighter(110);
101 bgcol = bgcol.lighter(110);
102 int mx = mapFromGlobal(QCursor::pos()).x();
103 if (abs(linepos - mx) < 4)
104 dcol = dcol.lighter(200);
105 }
106
107 p.fillRect(1, 1, width() - 1, height() - 2, bgcol);
108 p.fillRect(1, 1, linepos - 1, height() - 2, bcol);
109
110 QPen pen = p.pen();
111
112 pen.setColor(dcol);
113 p.setPen(pen);
114 pen.setWidth(3);
115 p.setPen(pen);
116 p.drawLine(linepos, 2, linepos, height() - 2);
117 pen.setWidth(1);
118 pen.setColor(qcol);
119 p.setPen(pen);
120 p.drawLine(linepos - 2, 1, linepos - 2, height() - 1);
121 p.drawLine(linepos + 2, 1, linepos + 2, height() - 1);
122
123 pen.setWidth(1);
124 pen.setColor(qcol);
125 p.setPen(pen);
126 p.drawRect(0, 0, width() - 1, height() - 1);
127}
128
130 : QWidget(parent)
131 , _id(id)
132 , _value(0)
133{
134}
135
137{
138 if (_value < 0 || _value > 1)
139 return;
140 int x = int(_value * (width() - 3) + 0.5);
141 QPainter p(this);
142 p.fillRect(contentsRect(), _col);
143 p.fillRect(x, 0, 3, height(), QColor(64, 64, 64));
144}
145
147{
149}
150
152{
153 setValue(clamp(float(e->x() - 1) / (width() - 3), 0, 1));
154}
155
157{
158 if (value == _value)
159 return;
160 _value = value;
161 emit valueChanged(_id, value);
162 update();
163}
164
165ExprControl::ExprControl(int id, Editable *editable, bool showColorLink)
166 : _id(id)
167 , _updating(false)
168 , _editable(editable)
169{
170 hbox = new QHBoxLayout(this);
171
172 _colorLinkCB = new QCheckBox(this);
173 _colorLinkCB->setFocusPolicy(Qt::NoFocus);
174 connect(_colorLinkCB, SIGNAL(stateChanged(int)), this, SLOT(linkStateChange(int)));
175 hbox->addWidget(_colorLinkCB);
176
177 // see parser's specRegisterEditable
178 // This is the variable name
179 QString editableLabel = QString::fromStdString(_editable->name);
180 _label = new QLabel();
181 QFontMetrics _labelSize(_label->font());
182 // Fix label appearance and word wrap, just in case -- amyspark
183 // 45px gives us some breathing space
184 _label->setMinimumWidth(60);
185 _label->setText(tr("<b>%1</b>").arg(_labelSize.elidedText(editableLabel, Qt::TextElideMode::ElideRight, qMax(0, _label->width() - 15))));
186 _label->setAutoFillBackground(true);
187 hbox->addWidget(_label, 1);
188
189 if (!showColorLink) {
190 _colorLinkCB->setDisabled(true);
191 } else {
192 _colorLinkCB->setDisabled(false);
193 }
194}
195
196void ExprControl::resizeEvent(QResizeEvent *)
197{
198 QString editableLabel = QString::fromStdString(_editable->name);
199 QFontMetrics _labelSize(_label->font());
200 _label->setText(tr("<b>%1</b>").arg(_labelSize.elidedText(editableLabel, Qt::TextElideMode::ElideRight, qMax(0, _label->width() - 15))));
201}
202
204{
205 if (_updating)
206 return;
207
208 if (state == Qt::Checked) {
209 emit linkColorLink(_id);
211 } else {
212 emit linkColorLink(-1);
213 }
214}
215
217{
218 if (newId != _id) {
219 _updating = true;
220 _colorLinkCB->setChecked(false);
221 _updating = false;
222 }
223}
224
226 : ExprControl(id, editable, false)
227 , _numberEditable(editable)
228{
229 auto *slider = new QHBoxLayout();
230 // slider
231 auto smin = editable->min;
232 auto smax = editable->max;
233 if (!_numberEditable->isInt) {
234 smin *= 1e5;
235 smax *= 1e5;
236 }
237 auto srange = smax - smin;
238 _slider = new ExprSlider(Qt::Horizontal, this);
239 _slider->setRange(int(smin), int(smax));
240 _slider->setTickInterval(std::max(1, int(srange / 10)));
241 _slider->setSingleStep(std::max(1, int(srange / 50)));
242 _slider->setPageStep(std::max(1, int(srange / 10)));
243 _slider->setFocusPolicy(Qt::ClickFocus);
244 slider->addWidget(_slider, 3);
245 // edit box
246 _edit = new ExprLineEdit(0, this);
247 slider->addWidget(_edit);
248 hbox->addLayout(slider, 4);
249 connect(_edit, SIGNAL(textChanged(int, const QString &)), SLOT(editChanged(int, const QString &)));
250 connect(_slider, SIGNAL(valueChanged(int)), SLOT(sliderChanged(int)));
251 // show current values
253}
254
256{
257 if (_updating)
258 return;
259 setValue(_numberEditable->isInt ? value : value * 1e-5);
260}
261
262void NumberControl::editChanged(int, const QString &text)
263{
264 if (_updating)
265 return;
266 bool ok = false;
267 float val = text.toFloat(&ok);
268 if (!ok)
269 return;
270 setValue(val);
271}
272
274{
275 _updating = true;
276 int sliderval = int(_numberEditable->isInt ? _numberEditable->v : _numberEditable->v * 1e5);
277 if (sliderval != _slider->value())
278 _slider->setValue(sliderval);
279 _edit->setText(QString(tr("%1")).arg(_numberEditable->v, 0, 'f', _numberEditable->isInt ? 0 : 3));
280 _updating = false;
281}
282
283void NumberControl::setValue(double value)
284{
285 // dbgSeExpr<<"In setValue "<<_id<<value;
286 if (fabs(_numberEditable->v - value) < 1e-5)
287 return;
288 _numberEditable->v = value;
290 emit controlChanged(_id);
291}
292
294 : ExprControl(id, editable, true)
295 , _numberEditable(editable)
296{
297 auto *control = new QHBoxLayout();
299 // CSwatchFrame has size 0 here! see below
300 _swatch = new ExprCSwatchFrame(editable->v);
301 connect(_swatch, SIGNAL(swatchChanged(QColor)), this, SLOT(swatchChanged(QColor)));
302 control->addWidget(_swatch);
303 }
304 for (int i = 0; i < 3; i++) {
305 auto *vbl = new QVBoxLayout();
306 control->addLayout(vbl);
307 vbl->setContentsMargins({});
308 vbl->setSpacing(0);
309
310 auto *edit = new ExprLineEdit(i, this);
311 vbl->addWidget(edit);
312 _edits[i] = edit;
313
315 // piggy-back on the ExprLineEdit height to set the CSwatchFrame - amyspark
316 auto width(edit->minimumSizeHint().width());
317 auto height(edit->minimumSizeHint().height() + 6);
318 _swatch->setMinimumWidth(width);
319 _swatch->setMinimumHeight(height);
320 _swatch->setSizePolicy(QSizePolicy::MinimumExpanding, QSizePolicy::Fixed);
321 }
322
323 auto *slider = new ExprChannelSlider(i, this);
324 vbl->addWidget(slider);
325 _sliders[i] = slider;
326 // keep these, as channelSlider doesn't have a default height - amyspark
327 slider->setFixedHeight(6);
328 // set color
329 static const std::array<QColor, 3> rgb = {QColor(128, 64, 64), QColor(64, 128, 64), QColor(64, 64, 128)};
331 slider->setDisplayColor(rgb[i]);
332
333 connect(edit, SIGNAL(textChanged(int, const QString &)), SLOT(editChanged(int, const QString &)));
334 connect(slider, SIGNAL(valueChanged(int, double)), SLOT(sliderChanged(int, double)));
335 }
336 hbox->addLayout(control, 4);
337 // update controls
339}
340
342{
344 setValue(0, color[0]);
345 setValue(1, color[1]);
346 setValue(2, color[2]);
347}
348
350{
351 return QColor::fromRgbF(clamp(_numberEditable->v[0], 0, 1), clamp(_numberEditable->v[1], 0, 1), clamp(_numberEditable->v[2], 0, 1));
352}
353
354void VectorControl::setColor(QColor color)
355{
356 setValue(0, color.redF());
357 setValue(1, color.greenF());
358 setValue(2, color.blueF());
359}
360
361void VectorControl::sliderChanged(int id, double value)
362{
363 if (_updating)
364 return;
368}
369
370void VectorControl::editChanged(int id, const QString &text)
371{
372 if (_updating)
373 return;
374 bool ok = false;
375 float val = text.toFloat(&ok);
376 if (!ok)
377 return;
378 setValue(id, val);
379}
380
382{
383 // //dbgSeExpr<<"In update control "<<_id;
384 _updating = true;
385 for (auto i = 0; i < 3; i++) {
386 _edits[i]->setText(QString(tr("%1")).arg(_numberEditable->v[i], 0, 'f', 3));
387 }
388 auto min = _numberEditable->min;
389 auto max = _numberEditable->max;
390 for (auto i = 0; i < 3; i++) {
391 _sliders[i]->setValue((_numberEditable->v[i] - min) / (max - min));
392 }
394 // dbgSeExpr<<"trying to set color";
396 auto r = clamp(val[0], 0, 1);
397 auto g = clamp(val[1], 0, 1);
398 auto b = clamp(val[2], 0, 1);
399 auto lum = r * .2 + g * .7 + b * .1;
400 // dbgSeExpr<<" rgb "<<r<<" "<<g<<" "<<b;
401 QPalette pal = palette();
402 pal.setColor(QPalette::Window, QColor(int(r * 255), int(g * 255), int(b * 255)));
403 pal.setColor(QPalette::WindowText, (lum < 0.5) ? QColor(255, 255, 255) : QColor(0, 0, 0));
404 _label->setPalette(pal);
405 }
406 _updating = false;
407}
408
409void VectorControl::setValue(int n, double value)
410{
411 if (n < 0 || n >= 3)
412 return;
413 if (fabs(_numberEditable->v[n] - value) < 1e-5)
414 return;
415 _numberEditable->v[n] = value;
416 if (_swatch)
419 emit controlChanged(_id);
420}
421
423 : ExprControl(id, editable, false)
424 , _stringEditable(editable)
425{
426 // make line edit
427 _edit = new QLineEdit();
428 _edit->setFixedHeight(20);
429 connect(_edit, SIGNAL(textChanged(const QString &)), SLOT(textChanged(const QString &)));
430 // make a button if we are a file or directory
431 if (_stringEditable->type == "file" || _stringEditable->type == "directory") {
432 auto *button = new QPushButton();
433 button->setFixedSize(20, 20);
434
435 hbox->addWidget(_edit, 3);
436 hbox->addWidget(button, 1);
437 if (_stringEditable->type == "directory") {
438 connect(button, SIGNAL(clicked()), SLOT(directoryBrowse()));
439 button->setIcon(QIcon(QPixmap(directoryXPM.data())));
440 } else if (_stringEditable->type == "file") {
441 connect(button, SIGNAL(clicked()), SLOT(fileBrowse()));
442 button->setIcon(QIcon(QPixmap(fileXPM.data())));
443 }
444
445 } else {
446 hbox->addWidget(_edit, 3);
447 }
448 // update controls
450}
451
453{
454 ExprFileDialog dialog(this);
455 dialog.setPreview();
456 QString newFilename = dialog.getOpenFileName(tr("Please choose a file"), _edit->text(), tr("Images (*.tif *.tx *.jpg *.ptx *.png)"));
457 if (!newFilename.isEmpty())
458 _edit->setText(newFilename);
459}
460
462{
463 ExprFileDialog dialog(this);
464 dialog.setPreview();
465 QString newFilename = dialog.getExistingDirectory(tr("Please choose a file"), _edit->text());
466 if (!newFilename.isEmpty())
467 _edit->setText(newFilename);
468}
469
471{
472 QString newText = QString::fromStdString(_stringEditable->v);
473 _edit->setText(newText);
474}
475
476void StringControl::textChanged(const QString &newText)
477{
478 if (_updating)
479 return;
480 _stringEditable->v = newText.toStdString();
481 emit controlChanged(_id);
482}
483
485 : ExprControl(id, editable, false)
486 , _curveEditable(editable)
487{
488 _curve = new ExprCurve(this, tr("Pos:"), tr("Val:"), tr("Interp:"));
489
490 const int numVal = _curveEditable->cvs.size();
491 for (int i = 0; i < numVal; i++) {
493 _curve->addPoint(cv._pos, cv._val, cv._interp);
494 }
495 hbox->addWidget(_curve, 4);
496 connect(_curve->_scene, SIGNAL(curveChanged()), SLOT(curveChanged()));
497 // unneded? updateControl();
498}
499
501{
502 if (_curve && _curveEditable) {
504 emit controlChanged(_id);
505 }
506}
507
509 : ExprControl(id, editable, true)
510 , _curveEditable(editable)
511{
512 _curve = new ExprColorCurve(this, tr("Pos:"), tr("Val:"), tr("Interp:"));
513
514 const int numVal = _curveEditable->cvs.size();
515 for (int i = 0; i < numVal; i++) {
517 _curve->addPoint(cv._pos, cv._val, cv._interp);
518 }
519 hbox->addWidget(_curve, 4);
520 connect(_curve->_scene, SIGNAL(curveChanged()), SLOT(curveChanged()));
521 // unneeded? updateControl();
522}
523
525{
526 if (_curve && _curveEditable) {
528 emit controlChanged(_id);
529 }
530}
531
533{
534 return _curve->getSwatchColor();
535}
536
537void CCurveControl::setColor(QColor color)
538{
539 _curve->setSwatchColor(color);
540}
541
542class ExprGraphPreview : public QWidget
543{
544 Q_OBJECT
545public:
546 std::vector<float> x, y;
547 std::vector<float> cpx, cpy;
548 qreal xmin {}, xmax {}, ymin {}, ymax {}, dx {}, dy {};
549
550 qreal win_xmin {}, win_xmax {}, win_ymin {}, win_ymax {}, win_dx {}, win_dy {};
551
552 ExprGraphPreview(QWidget *parent = nullptr)
553 : QWidget(parent)
554 {
555 win_xmin = -1.;
556 win_xmax = 2.;
557 win_ymin = -1;
558 win_ymax = 2.;
559 }
560
561 QPointF toScreen(qreal x, qreal y)
562 {
563 return {(x - win_xmin) * win_dx, height() - (y - win_ymin) * win_dy};
564 }
565
566 void paintEvent(QPaintEvent *event) override
567 {
568 QWidget::paintEvent(event);
569 QPainter painter(this);
570 painter.setRenderHint(QPainter::Antialiasing, true);
571 painter.setPen(QColor(255, 255, 255));
572 win_xmin = xmin;
573 win_xmax = xmax;
574 win_ymin = ymin;
575 win_ymax = ymax;
576 auto percentXpad = .1 * (win_xmax - win_xmin);
577 auto percentYpad = .1 * (win_ymax - win_ymin);
578 win_xmin -= percentXpad;
579 win_xmax += percentXpad;
580 win_ymin -= percentYpad;
581 win_ymax += percentYpad;
582
583 // make space for text
584 int x_pad_in_pixels = 25;
585 int y_pad_in_pixels = 15;
586 auto xpad = x_pad_in_pixels * (win_xmax - win_xmin) / (width() - x_pad_in_pixels);
587 auto ypad = y_pad_in_pixels * (win_ymax - win_ymin) / (height() - y_pad_in_pixels);
588 win_ymin -= ypad;
589 win_xmax += xpad;
590
591 win_dx = width() / (win_xmax - win_xmin);
592 win_dy = height() / (win_ymax - win_ymin);
593
594 // int h=height();
595 QPainterPath path;
596 QRectF fullarea(toScreen(win_xmin, win_ymax), toScreen(win_xmax, win_ymin));
597 QBrush darkbrush(QColor(100, 100, 100), Qt::SolidPattern);
598 QRectF area(toScreen(xmin, ymax), toScreen(xmax, ymin));
599 QBrush brush(QColor(150, 150, 150), Qt::SolidPattern);
600 // painter.fillRect(fullarea,darkbrush);
601 // painter.setBrush(darkbrush);
602 // painter.drawRoundedRect(fullarea,3,3);
603 // painter.setBrush(QBrush());
604 painter.fillRect(area, brush);
605 if (!x.empty()) {
606 path.moveTo(toScreen(x[0], y[0]));
607 for (int i = 1; i < (int)x.size(); i++)
608 path.lineTo(toScreen(x[i], y[i]));
609 }
610 QRectF right(toScreen(xmax, ymax), toScreen(win_xmax, ymin));
611 QRectF bottom(toScreen(xmin, ymin), toScreen(xmax, win_ymin));
612
613 painter.setPen(QColor(75, 50, 50));
614 painter.drawPath(path);
615
616 painter.setPen(QPen());
617 painter.drawText(right, Qt::AlignTop | Qt::AlignLeft, QString(tr("%1")).arg(ymax, 0, 'f', 1));
618 painter.drawText(right, Qt::AlignBottom | Qt::AlignLeft, QString(tr("%1")).arg(ymin, 0, 'f', 1));
619 painter.drawText(bottom, Qt::AlignTop | Qt::AlignLeft, QString(tr("%1")).arg(xmin, 0, 'f', 1));
620 painter.drawText(bottom, Qt::AlignTop | Qt::AlignRight, QString(tr("%1")).arg(xmax, 0, 'f', 1));
621
622 painter.setBrush(QBrush(QColor(0, 0, 0), Qt::SolidPattern));
623 for (size_t i = 0; i < cpx.size(); i++) {
624 painter.drawEllipse(toScreen(cpx[i], cpy[i]), 2, 2);
625 }
626 }
627};
628
629// Editing widget for color swatch
631 : ExprControl(id, editable, false)
632 , _swatchEditable(editable)
633 , _indexLabel(false)
634{
635 // include index labels if user specifies 'indices' as labelType
636 if (_swatchEditable->labelType == "indices")
637 _indexLabel = true;
639}
640
642{
643 if (_updating)
644 return;
645 if (index >= 0 && index < int(_swatchEditable->colors.size()))
646 _swatchEditable->change(index, value);
647 emit controlChanged(_id);
648}
649
651{
652 if (_updating)
653 return;
654 if (index >= 0 && index <= int(_swatchEditable->colors.size()))
655 _swatchEditable->add(value); // add to end; TODO insert
656 emit controlChanged(_id);
657}
658
660{
661 if (_updating)
662 return;
663 if (index >= 0 && index < int(_swatchEditable->colors.size())) {
664 _swatchEditable->remove(index);
665 _swatch->deleteLater();
666 _swatch = nullptr;
668 }
669 emit controlChanged(_id);
670}
671
673{
675 connect(_swatch, SIGNAL(swatchChanged(int, KSeExpr::Vec3d)), this, SLOT(colorChanged(int, KSeExpr::Vec3d)));
676 connect(_swatch, SIGNAL(swatchAdded(int, KSeExpr::Vec3d)), this, SLOT(colorAdded(int, KSeExpr::Vec3d)));
677 connect(_swatch, SIGNAL(swatchRemoved(int)), this, SLOT(colorRemoved(int)));
678
679 _updating = true;
680 for (size_t i = 0; i < _swatchEditable->colors.size(); i++) {
682 _swatch->addSwatch(val, i);
683 }
684 _updating = false;
685 hbox->addWidget(_swatch, 4);
686}
static constexpr std::array< const char *, 24 > directoryXPM
static constexpr std::array< const char *, 26 > fileXPM
T clamp(const T val, const T2 minval, const T3 maxval)
clamp val to the specified range [minval,maxval]
Definition ExprControl.h:70
static constexpr std::array< int, 514 > p
Definition NoiseTables.h:10
CCurveControl(int id, ColorCurveEditable *stringEditable)
QColor getColor() override
Interface for getting the color (used for linked color picking)
void setColor(QColor color) override
Interface for setting the color (used for linked color picking)
ColorCurveEditable * _curveEditable
color curve model
ExprColorCurve * _curve
color curve widget
std::vector< T_CURVE::CV > _cvs
void colorChanged(int index, KSeExpr::Vec3d value)
void colorAdded(int index, KSeExpr::Vec3d value)
void colorRemoved(int index)
ColorSwatchEditable * _swatchEditable
model for the color swatches control
ExprColorSwatchWidget * _swatch
Edit box for the color swatches.
ColorSwatchControl(int id, ColorSwatchEditable *swatchEditable)
void remove(int index)
Definition Editable.cpp:222
void change(int index, const KSeExpr::Vec3d &value)
Definition Editable.cpp:217
void add(const KSeExpr::Vec3d &value)
Definition Editable.cpp:212
std::string labelType
Definition Editable.h:149
std::vector< KSeExpr::Vec3d > colors
Definition Editable.h:148
void curveChanged()
CurveControl(int id, CurveEditable *stringEditable)
ExprCurve * _curve
curve edit widget
CurveEditable * _curveEditable
curve model
std::vector< T_CURVE::CV > _cvs
Definition ExprCurve.h:78
std::string name
Definition Editable.h:33
KSeExpr::Vec3d getValue() const
void setValue(const KSeExpr::Vec3d &value)
Channel Slider (i.e. for colors)
void mouseMoveEvent(QMouseEvent *e) override
void setValue(double value)
double value() const
void valueChanged(int id, double value)
ExprChannelSlider(int id, QWidget *parent)
void paintEvent(QPaintEvent *e) override
void mousePressEvent(QMouseEvent *e) override
void addPoint(double x, KSeExpr::Vec3d y, T_INTERP interp, bool select=false)
void setSwatchColor(QColor color)
CCurveScene * _scene
void addSwatch(KSeExpr::Vec3d &val, int index=-1)
Base class for all controls for Expressions.
Definition ExprControl.h:25
QCheckBox * _colorLinkCB
Definition ExprControl.h:32
std::atomic< bool > _updating
Definition ExprControl.h:30
Editable * _editable
Definition ExprControl.h:35
QHBoxLayout * hbox
Definition ExprControl.h:31
virtual QColor getColor()
Interface for getting the color (used for linked color picking)
Definition ExprControl.h:42
void resizeEvent(QResizeEvent *event) override
void linkStateChange(int state)
void linkDisconnect(int newId)
QLabel * _label
Definition ExprControl.h:33
void controlChanged(int id)
void linkColorLink(int id)
void linkColorEdited(int id, QColor color)
ExprControl(int id, Editable *editable, bool showColorLink)
void addPoint(double x, double y, T_INTERP interp, bool select=false)
Definition ExprCurve.h:121
CurveScene * _scene
Definition ExprCurve.h:126
QString getExistingDirectory(const QString &caption=QString(), const QString &startWith=QString(), const QString &filter=QString())
QString getOpenFileName(const QString &caption=QString(), const QString &startWith=QString(), const QString &filter=QString())
ExprGraphPreview(QWidget *parent=nullptr)
std::vector< float > cpy
std::vector< float > cpx
void paintEvent(QPaintEvent *event) override
std::vector< float > x
std::vector< float > y
QPointF toScreen(qreal x, qreal y)
Line Editor Widget(used for numbers)
Definition ExprControl.h:83
virtual void setText(const QString &t)
Definition ExprControl.h:87
Generic Slider (used for int and float sliders)
void paintEvent(QPaintEvent *e) override
void mouseMoveEvent(QMouseEvent *e) override
void mousePressEvent(QMouseEvent *e) override
NumberEditable * _numberEditable
Pointer to the number control model.
void editChanged(int id, const QString &text)
void updateControl()
Update values in slider and textbox given what the model contains.
ExprLineEdit * _edit
Text box for the number.
void sliderChanged(int val)
ExprSlider * _slider
Slider for the number.
NumberControl(int id, NumberEditable *editable)
void setValue(double value)
Update the model with the value and notify the collection.
void directoryBrowse()
StringEditable * _stringEditable
model for the string control
void textChanged(const QString &newText)
StringControl(int id, StringEditable *stringEditable)
QLineEdit * _edit
Edit box for the string.
std::string v
Definition Editable.h:84
std::string type
Definition Editable.h:85
void setValue(int n, double value)
set the value in the model (in response to editing from controls)
VectorControl(int id, VectorEditable *editable)
void updateControl()
update the individual slider and eidt box controls
std::array< ExprLineEdit *, 3 > _edits
All three line edit widgets (for each component)
void editChanged(int id, const QString &text)
std::array< ExprChannelSlider *, 3 > _sliders
All three channel sliders (for each component)
void swatchChanged(QColor color)
VectorEditable * _numberEditable
Number model.
void sliderChanged(int id, double val)
QColor getColor() override
Interface for getting the color (used for linked color picking)
void setColor(QColor color) override
Interface for setting the color (used for linked color picking)
ExprCSwatchFrame * _swatch
KSeExpr::Vec3d v
Definition Editable.h:70
std::vector< CV > cvs
Definition Editable.h:99
InterpType _interp
Definition Curve.h:43