ATLAS Offline Software
Loading...
Searching...
No Matches
VP1MaterialButton.cxx
Go to the documentation of this file.
1/*
2 Copyright (C) 2002-2024 CERN for the benefit of the ATLAS collaboration
3*/
4
5
7// //
8// Implementation of class VP1MaterialButton //
9// //
10// Author: Thomas Kittelmann <Thomas.Kittelmann@cern.ch> //
11// //
12// Initial version: September 2007 //
13// //
15
16//Todo:
17// ~32 colours directly in simple gui + more button launching colour browser.
18// mode switching closes all open colour dialogs!
19
22#include "VP1Base/VP1QtUtils.h"
24#include "ui_vp1materialbuttonform.h"
27
28#include "Inventor/nodes/SoSwitch.h"
29#include "Inventor/nodes/SoCube.h"
30#include "Inventor/nodes/SoCone.h"
31#include "Inventor/nodes/SoComplexity.h"
32#include "Inventor/nodes/SoDrawStyle.h"
33#include "Inventor/nodes/SoMaterial.h"
34#include <Inventor/nodes/SoSeparator.h>
35
36#include <QTimer>
37#include <QByteArray>
38#include <QBuffer>
39#include <QDataStream>
40#include <QMouseEvent>
41#include <QDragEnterEvent>
42#include <QDropEvent>
43#include <QShortcut>
44#include <QMimeData>
45#include <QDrag>
46
47//____________________________________________________________________
49public:
51
53
55
56 int dim;
57
58 QString materialtext;
59 QWidget * editwindow;
60 SoMaterial * preview_material;
61 Ui::VP1MaterialButtonForm editwindow_ui;
62 void initEditWindow();
63
64 SoQtRenderArea * renderarea;
65 SoSwitch * previewswitch;
66
67 void applyValuesToMaterial(SoMaterial*, bool preview = false);
68 QList<SoMaterial*> handledmaterials;
69
70 static SbColor qcol2sbcol(const QColor&);
71 static QColor sbcol2qcol(const SbColor&);
72 static double distSq(const QColor& a, const QColor& b);
73 static bool equal(const QColor& a, const QColor& b, const double& tol = 1.0e-6);
74
75 //Settings returned from the gui, with correct dependency on simplemode:
76 QColor guiAmbientColour() const;
77 QColor guiDiffuseColour() const;
78 QColor guiSpecularColour() const;
79 QColor guiEmissiveColour() const;
80 int guiTransparency() const;
81 int guiShininess() const;
82
83 //Last applied settings:
90 int lastapplied_brightness;//redundant but we use it to give exact
91 //reset functionality to simple mode.
92
93 QString printFloat(const double& d) {
94 if (d==0)
95 return "0";
96 QString s = QString::number(d,'f',5);
97 while (s.right(1)=="0"&&s.contains("."))
98 s = s.left(s.count()-1);
99 if (s=="0.") return "0";
100 if (s=="1.") return "1";
101 return s;
102 }
103 QString toSbColTxt(const QColor& c) { return "SbColor("+printFloat(c.redF())+","
104 +printFloat(c.greenF())+","+printFloat(c.blueF())+")";}
106 bool previewEqualToLastApplied() const;
108 void adaptGuiForMode();
111
112 QColor emissiveColourFromSimpleParameters(const QColor& simpleColour, const double& brightness) const;
113 double brightnessEstimateFromDetailedParameters( const QColor& diffuseColour, const QColor& emissiveColour ) const;
114
116 void blockGuiSignals(bool);
117
118 static QColor simpleAmbient() { return QColor::fromRgbF(0.2,0.2,0.2); }
119 static QColor simpleSpecular() { return Qt::black; }
120 static int simpleShininess() { return 0; }
121};
122
123//____________________________________________________________________
125 : VP1MaterialButtonBase(parent,0,"VP1MaterialButton"), m_d(new Imp)
126{
127 m_d->simplemode = false;
128 m_d->dim = dim;
129 m_d->theclass = this;
130 m_d->editwindow = 0;
131 m_d->preview_material = 0;
132 m_d->renderarea = 0;
133 m_d->previewswitch = 0;
134 m_d->blockcount = 0;
135 connect(this,SIGNAL(clicked()),this,SLOT(showEditMaterialDialog()));
136
137 m_d->lastapplied_ambient = QColor::fromRgbF(0.2,0.2,0.2);
138 m_d->lastapplied_diffuse = QColor::fromRgbF(0.8,0.8,0.8);
139 m_d->lastapplied_specular = Qt::black;
140 m_d->lastapplied_emissive = Qt::black;
141 m_d->lastapplied_shininess = 20;
142 m_d->lastapplied_transparency = 0;
143 m_d->lastapplied_brightness = 0;
144 setMaterialText("");
145 setAcceptDrops(true);
146 QTimer::singleShot(0, this, SLOT(updateButton()));
147}
148
149//____________________________________________________________________
151{
153 setUpdatesEnabled(false);
154 if (m_d->renderarea) {
155 m_d->renderarea->setAutoRedraw(false);
156 SoNode * root = m_d->renderarea->getSceneGraph();
157 root->ref();
158 m_d->renderarea->setSceneGraph(0);
159 delete m_d->renderarea;
160 root->unref();
161 }
162 delete m_d->editwindow;
163 delete m_d;
164}
165
166//____________________________________________________________________
167QColor VP1MaterialButton::lastAppliedDiffuseColour() const { return m_d->lastapplied_diffuse; }
168QColor VP1MaterialButton::lastAppliedAmbientColour() const { return m_d->lastapplied_ambient; }
169QColor VP1MaterialButton::lastAppliedSpecularColour() const { return m_d->lastapplied_specular; }
170QColor VP1MaterialButton::lastAppliedEmissiveColour() const { return m_d->lastapplied_emissive; }
171double VP1MaterialButton::lastAppliedTransparency() const { return std::max<double>(0.0,std::min<double>(1.0,m_d->lastapplied_transparency/100.0)); }
172double VP1MaterialButton::lastAppliedShininess() const { return std::max<double>(0.0,std::min<double>(1.0,m_d->lastapplied_shininess/100.0)); }
173double VP1MaterialButton::lastAppliedBrightness() const { return std::max<double>(0.0,std::min<double>(1.0,m_d->lastapplied_brightness/100.0)); }
174
176 if (!m_d->editwindow)
177 m_d->initEditWindow();
178 return *(m_d->editwindow);
179}
180
181//____________________________________________________________________
183{
184 if (editWindow().isHidden())
185 editWindow().show();
186 else
187 editWindow().hide();
188}
189
190//____________________________________________________________________
192{
193 m_d->materialtext = ( t.isEmpty() ? "Edit Material" : "Edit Material "+t );
194 if (m_d->editwindow)
195 m_d->editwindow->setWindowTitle(m_d->materialtext);
196 setToolTip(m_d->materialtext);
197}
198
199//____________________________________________________________________
201{
203
204 if (VP1Msg::verbose()) {
205 theclass->messageVerbose("Copied values from material: "
206 "diffuse="+str(lastapplied_diffuse)
207 +", ambient="+str(lastapplied_ambient)
208 +", specular="+str(lastapplied_specular)
209 +", emissive="+str(lastapplied_emissive)
210 +", shininess="+str(lastapplied_shininess)
211 +", transparency="+str(lastapplied_transparency)
212 );
213 }
214
215 if (editwindow) {
216 if (VP1Msg::verbose()){
217 theclass->messageVerbose(" => and updating preview.");
218 }
219 blockGuiSignals(true);
220 editwindow_ui.colbutton_ambient->setColor(lastapplied_ambient);
221 editwindow_ui.colbutton_diffuse->setColor(lastapplied_diffuse);
222 editwindow_ui.colbutton_specular->setColor(lastapplied_specular);
223 editwindow_ui.colbutton_emissive->setColor(lastapplied_emissive);
224 editwindow_ui.slider_shininess->setValue(lastapplied_shininess);
225 editwindow_ui.label_num_shininess->setNum(lastapplied_shininess);
226 editwindow_ui.colbutton_simple_colour->setColor(lastapplied_diffuse);
227 editwindow_ui.slider_simple_transparency->setValue(lastapplied_transparency);
228 if (lastapplied_brightness!=-1) {
229 editwindow_ui.slider_simple_brightness->setValue(lastapplied_brightness);
230 editwindow_ui.label_num_simple_brightness->setNum(lastapplied_brightness);
231 }
232 editwindow_ui.slider_transparency->setValue(lastapplied_transparency);
233 editwindow_ui.label_num_transparency->setNum(lastapplied_transparency);
234 editwindow_ui.label_num_simple_transparency->setNum(lastapplied_transparency);
235 blockGuiSignals(false);
236 theclass->updatePreview();
237 }
238 theclass->apply();
240}
241
242//____________________________________________________________________
244{
245 if (!m) {
246 message("VP1MaterialButton::copyValuesFromMaterial Error: Passed material is null!!");
247 return;
248 }
249 m->ref();
250 if (m->ambientColor.getNum()!=1
251 ||m->diffuseColor.getNum()!=1
252 ||m->specularColor.getNum()!=1
253 ||m->emissiveColor.getNum()!=1
254 ||m->transparency.getNum()!=1
255 ||m->shininess.getNum()!=1) {
256 message("VP1MaterialButton::copyValuesFromMaterial Error: Passed material must have exactly one value in each of the 6 fields!!");
257 m->unrefNoDelete();
258 return;
259 }
260
261 int new_shininess = std::min(std::max(0,static_cast<int>(m->shininess[0]*100.0f+0.5f)),100);
262 int new_transparency = std::min(std::max(0,static_cast<int>(m->transparency[0]*100.0f+0.5f)),100);
263
264 m_d->lastapplied_ambient = m_d->sbcol2qcol(m->ambientColor[0]);
265 m_d->lastapplied_diffuse = m_d->sbcol2qcol(m->diffuseColor[0]);
266 m_d->lastapplied_specular = m_d->sbcol2qcol(m->specularColor[0]);
267 m_d->lastapplied_emissive = m_d->sbcol2qcol(m->emissiveColor[0]);
268 m_d->lastapplied_shininess = new_shininess;
269 m_d->lastapplied_transparency = new_transparency;
270 m_d->lastapplied_brightness = std::max<int>(0,std::min<int>(100,static_cast<int>(100*m_d->brightnessEstimateFromDetailedParameters(m_d->lastapplied_diffuse,m_d->lastapplied_emissive)+0.5)));
271
272 m->unrefNoDelete();
273
274 m_d->adaptGuiAndMaterialsToLastApplied();
275
276 emit lastAppliedChanged();
277}
278
279//____________________________________________________________________
281{
282 if (b)
283 ++blockcount;
284 else
285 --blockcount;
286 if ( (b&&blockcount==1) || (!b&&blockcount==0) ) {
287 editwindow_ui.colbutton_ambient->blockSignals(b);
288 editwindow_ui.colbutton_diffuse->blockSignals(b);
289 editwindow_ui.colbutton_specular->blockSignals(b);
290 editwindow_ui.colbutton_emissive->blockSignals(b);
291 editwindow_ui.slider_shininess->blockSignals(b);
292 editwindow_ui.colbutton_simple_colour->blockSignals(b);
293 editwindow_ui.slider_simple_brightness->blockSignals(b);
294 editwindow_ui.slider_simple_transparency->blockSignals(b);
295 editwindow_ui.slider_transparency->blockSignals(b);
296 editwindow_ui.radioButton_cone->blockSignals(b);
297 editwindow_ui.radioButton_lines->blockSignals(b);
298 editwindow_ui.radioButton_box->blockSignals(b);
299 editwindow_ui.pushButton_apply->blockSignals(b);
300 editwindow_ui.pushButton_reset->blockSignals(b);
301 editwindow_ui.pushButton_switch_mode->blockSignals(b);
302 }
303}
304
305
306//____________________________________________________________________
308{
309 if (editwindow)
310 return;
311 if(VP1Msg::verbose()){
312 theclass->messageVerbose("Initialising material editor dialog");
313 }
314 editwindow = new QWidget(0,Qt::WindowStaysOnTopHint);
315 editwindow_ui.setupUi(editwindow);
316 editwindow_ui.colbutton_ambient->setColor(lastapplied_ambient);
317 editwindow_ui.colbutton_diffuse->setColor(lastapplied_diffuse);
318 editwindow_ui.colbutton_specular->setColor(lastapplied_specular);
319 editwindow_ui.colbutton_emissive->setColor(lastapplied_emissive);
320 editwindow_ui.slider_shininess->setValue(lastapplied_shininess);
321 editwindow_ui.label_num_shininess->setNum(lastapplied_shininess);
322 editwindow_ui.slider_transparency->setValue(lastapplied_transparency);
323 editwindow_ui.slider_simple_transparency->setValue(lastapplied_transparency);
324 editwindow_ui.label_num_transparency->setNum(lastapplied_transparency);
325 editwindow_ui.label_num_simple_transparency->setNum(lastapplied_transparency);
326 editwindow_ui.slider_simple_brightness->setValue(lastapplied_brightness);
327 editwindow_ui.label_num_simple_brightness->setNum(lastapplied_brightness);
328 editwindow_ui.colbutton_simple_colour->setColor(lastapplied_diffuse);
329
330 #if defined BUILDVP1LIGHT
331 bool checkDisallowMultipleChannels = VP1QtUtils::expertSettingIsOn("general","ExpertSettings/VP1_DISALLOW_MULTIPLE_CHANNELS");
332 #else
333 bool checkDisallowMultipleChannels = VP1QtUtils::environmentVariableIsOn("VP1_DISALLOW_MULTIPLE_CHANNELS");
334 #endif
335
336 if (!checkDisallowMultipleChannels) {
337 SoSeparator * userroot = new SoSeparator;
338 SoComplexity * complexity = new SoComplexity;
339 complexity->value = 1.0;
340 userroot->addChild(complexity);
341 preview_material = new SoMaterial;
342 userroot->addChild(preview_material);
343 previewswitch = new SoSwitch;
344 previewswitch->addChild(new SoCube);
345 previewswitch->addChild(new SoCone);
346 SoSeparator * linesep = new SoSeparator;
347 SoDrawStyle * linedrawstyle = new SoDrawStyle;
348 linedrawstyle->style = SoDrawStyleElement::LINES;
349 linedrawstyle->lineWidth = 2;
350 linesep->addChild(linedrawstyle);
351 linesep->addChild(new SoCube);
352 previewswitch->addChild(linesep);
353 previewswitch->whichChild = 0;
354 userroot->addChild(previewswitch);
355 VP1ExaminerViewer * viewer = new VP1ExaminerViewer(editwindow_ui.widget_3dpreview,false);
356 viewer->setDecoration(false);
358 viewer->setTransparencyType( SoGLRenderAction::DELAYED_BLEND );
359 viewer->viewAll();
360 renderarea=viewer;
361 renderarea->setAntialiasing(true,4);
362 renderarea->setSceneGraph(userroot);
363 renderarea->setBackgroundColor(SbColor(0.0f, 0.0f, 0.0f));
364 } else {
365 //Put some sort of warning in that 'preview disabled by VP1_DISALLOW_MULTIPLE_CHANNELS env. var.'
366 //int editwindow_ui.widget_3dpreview. Fixme.
367 }
368
369 connect(editwindow_ui.colbutton_ambient,SIGNAL(colorChanged(const QColor&)),theclass,SLOT(updatePreview()));
370 connect(editwindow_ui.colbutton_diffuse,SIGNAL(colorChanged(const QColor&)),theclass,SLOT(updatePreview()));
371 connect(editwindow_ui.colbutton_specular,SIGNAL(colorChanged(const QColor&)),theclass,SLOT(updatePreview()));
372 connect(editwindow_ui.colbutton_emissive,SIGNAL(colorChanged(const QColor&)),theclass,SLOT(updatePreview()));
373 connect(editwindow_ui.slider_shininess,SIGNAL(valueChanged(int)),theclass,SLOT(updatePreview()));
374 connect(editwindow_ui.colbutton_simple_colour,SIGNAL(colorChanged(const QColor&)),theclass,SLOT(updatePreview()));
375 connect(editwindow_ui.slider_simple_brightness,SIGNAL(valueChanged(int)),theclass,SLOT(updatePreview()));
376 //Transparency sliders needs to be coordinated:
377 connect(editwindow_ui.slider_simple_transparency,SIGNAL(valueChanged(int)),theclass,SLOT(transparencyChanged()));
378 connect(editwindow_ui.slider_transparency,SIGNAL(valueChanged(int)),theclass,SLOT(transparencyChanged()));
379
380 editwindow_ui.radioButton_cone->setChecked(true);
381
383
384 theclass->updatePreviewSceneAndBgd();
385
386 connect(editwindow_ui.radioButton_cone,SIGNAL(toggled(bool)),theclass,SLOT(updatePreviewSceneAndBgd()));
387 connect(editwindow_ui.radioButton_box,SIGNAL(toggled(bool)),theclass,SLOT(updatePreviewSceneAndBgd()));
388
389 theclass->updatePreview();
391
392 connect(editwindow_ui.pushButton_apply,SIGNAL(clicked()),theclass,SLOT(apply()));
393 connect(editwindow_ui.pushButton_reset,SIGNAL(clicked()),theclass,SLOT(reset()));
394 connect(editwindow_ui.pushButton_switch_mode,SIGNAL(clicked()),theclass,SLOT(switchMode()));
395
397
398 connect(new QShortcut(QKeySequence(Qt::Key_Escape), editwindow),
399 SIGNAL(activated()),editwindow,SLOT(hide()));
400
401}
402
403
404//____________________________________________________________________
405void VP1MaterialButton::Imp::applyValuesToMaterial(SoMaterial* m, bool preview)
406{
407 if (!m)
408 return;
409 bool save = m->enableNotify(false);
410 if (preview) {
411 //Take value directly from gui:
412 if (!editwindow)
414 m->ambientColor.setValue(qcol2sbcol(guiAmbientColour()));
415 m->diffuseColor.setValue(qcol2sbcol(guiDiffuseColour()));
416 m->specularColor.setValue(qcol2sbcol(guiSpecularColour()));
417 m->emissiveColor.setValue(qcol2sbcol(guiEmissiveColour()));
418 m->shininess.setValue(std::max(0.0f,std::min(1.0f,guiShininess()/100.0f)));
419 m->transparency.setValue(std::max(0.0f,std::min(1.0f,guiTransparency()/100.0f)));
420 } else {
421 //Take values from stored "last" settings:
422 m->ambientColor.setValue(qcol2sbcol(lastapplied_ambient));
423 m->diffuseColor.setValue(qcol2sbcol(lastapplied_diffuse));
424 m->specularColor.setValue(qcol2sbcol(lastapplied_specular));
425 m->emissiveColor.setValue(qcol2sbcol(lastapplied_emissive));
426 m->shininess.setValue(std::max(0.0f,std::min(1.0f,lastapplied_shininess/100.0f)));
427 m->transparency.setValue(std::max(0.0f,std::min(1.0f,lastapplied_transparency/100.0f)));
428 }
429 if (save) {
430 m->enableNotify(true);
431 m->touch();
432 }
433}
434
435//____________________________________________________________________
437{
438 if (!m||m_d->handledmaterials.contains(m))
439 return false;
440 m->ref();
441 m_d->handledmaterials << m;
442 m_d->applyValuesToMaterial(m);
443 return true;
444}
445
446//____________________________________________________________________
448{
449 if (!m)
450 return false;
451 m->ref();
453 bool ok = handleMaterial(m);
454 m->unrefNoDelete();
455 return ok;
456}
457
458//____________________________________________________________________
460{
461 if (!m||!m_d->handledmaterials.contains(m))
462 return false;
463 m_d->handledmaterials.removeAll(m);
464 m->unref();
465 return true;
466}
467
468//____________________________________________________________________
470{
471 for (SoMaterial * m : m_d->handledmaterials)
472 m->unref();
473 m_d->handledmaterials.clear();
474}
475
476//____________________________________________________________________
478{
479 if (!m_d->editwindow)
480 return;
481 if (m_d->preview_material)
482 m_d->applyValuesToMaterial(m_d->preview_material,true);
483 m_d->updateApplyResetButtons();
484}
485
486//____________________________________________________________________
488{
489 if (!m_d->editwindow||!m_d->renderarea||!m_d->previewswitch)
490 return;
491
492 if (m_d->editwindow_ui.radioButton_box->isChecked())
493 m_d->previewswitch->whichChild = 0;
494 else
495 m_d->previewswitch->whichChild = (m_d->editwindow_ui.radioButton_cone->isChecked() ? 1 : 2);
496}
497
498//____________________________________________________________________
499SbColor VP1MaterialButton::Imp::qcol2sbcol(const QColor& col)
500{
501 return SbColor( col.red()/255.0, col.green()/255.0, col.blue()/255.0 );
502}
503
504//____________________________________________________________________
505QColor VP1MaterialButton::Imp::sbcol2qcol(const SbColor& col)
506{
507 float r,g,b;
508 col.getValue(r,g,b);
509 return QColor::fromRgbF( r,g,b );
510}
511
512//____________________________________________________________________
513double VP1MaterialButton::Imp::distSq(const QColor& a, const QColor& b)
514{
515 const double dRed(a.redF()-b.redF());
516 const double dGreen(a.greenF()-b.greenF());
517 const double dBlue(a.blueF()-b.blueF());
518 return dRed*dRed+dGreen*dGreen+dBlue*dBlue;
519}
520
521//____________________________________________________________________
522bool VP1MaterialButton::Imp::equal(const QColor& a, const QColor& b, const double& tol)
523{
524 return a == b || distSq(a,b) < tol;
525}
526
527//____________________________________________________________________
528QColor VP1MaterialButton::Imp::emissiveColourFromSimpleParameters(const QColor& simpleColour, const double& brightness) const
529{
530 return QColor::fromRgbF(std::min(1.0,std::max(0.0,brightness*simpleColour.redF())),
531 std::min(1.0,std::max(0.0,brightness*simpleColour.greenF())),
532 std::min(1.0,std::max(0.0,brightness*simpleColour.blueF())));
533}
534
535//____________________________________________________________________
536double VP1MaterialButton::Imp::brightnessEstimateFromDetailedParameters( const QColor& diffuseColour, const QColor& emissiveColour ) const
537{
538 double df_r(diffuseColour.redF()),df_g(diffuseColour.greenF()),df_b(diffuseColour.blueF());
539 double em_r(emissiveColour.redF()),em_g(emissiveColour.greenF()),em_b(emissiveColour.blueF());
540 const double dotp = em_r*df_r + em_g*df_g + em_b*df_b;
541 const double df_mag2 = df_r*df_r + df_g*df_g + df_b*df_b;
542 return std::max<double>(0.0,std::min<double>(100.0,dotp/df_mag2));
543}
544
545//____________________________________________________________________
547{
548 return simplemode ? simpleAmbient() : editwindow_ui.colbutton_ambient->color();
549}
550
551//____________________________________________________________________
553{
554 return simplemode ? editwindow_ui.colbutton_simple_colour->color() : editwindow_ui.colbutton_diffuse->color();
555}
556
557//____________________________________________________________________
559{
560 return simplemode ? simpleSpecular() : editwindow_ui.colbutton_specular->color();
561}
562
563//____________________________________________________________________
565{
566 if (simplemode)
567 return emissiveColourFromSimpleParameters(editwindow_ui.colbutton_simple_colour->color(),editwindow_ui.slider_simple_brightness->value()/100.0);
568 else
569 return editwindow_ui.colbutton_emissive->color();
570}
571
572//____________________________________________________________________
574{
575 return simplemode ? editwindow_ui.slider_transparency->value() : editwindow_ui.slider_simple_transparency->value();
576}
577
578
579//____________________________________________________________________
581{
582 return simplemode ? simpleShininess() : editwindow_ui.slider_shininess->value();
583}
584
585//____________________________________________________________________
602
603//____________________________________________________________________
615
616//____________________________________________________________________
618{
619 if (!editwindow)
620 return;
622 editwindow_ui.pushButton_apply->setEnabled(false);
623 editwindow_ui.pushButton_reset->setEnabled(false);
624 } else {
625 editwindow_ui.pushButton_apply->setEnabled(true);
626 editwindow_ui.pushButton_reset->setEnabled(true);
627 }
628
629}
630
631//____________________________________________________________________
633{
634 m_d->setLastAppliedFromCurrent();
635 for (SoMaterial * m : m_d->handledmaterials)
636 m_d->applyValuesToMaterial(m);
637 updateButton();
638}
639
640//____________________________________________________________________
642{
643 m_d->adaptGuiAndMaterialsToLastApplied();
644}
645
646//____________________________________________________________________
647const QList<SoMaterial*>& VP1MaterialButton::handledMaterials() const
648{
649 return m_d->handledmaterials;
650}
651
652//____________________________________________________________________
653void VP1MaterialButton::setText ( const QString & s )
654{
655 if (!s.isEmpty())
656 messageDebug("VP1MaterialButton::setText() called (with '"+s+"'), but not allowed");
657 //Forbidden!! Only here since Designer generated code needs it in public.
658}
659
660//____________________________________________________________________
662{
663 if (objectName().isEmpty()){
664 setObjectName("VP1MaterialButton");
665 }
666 if(VP1Msg::verbose()){
667 messageVerbose("setColButtonProperties: color=" + str(m_d->lastapplied_diffuse));
668 }
669 VP1ColorSelectButton::setColButtonProperties(this,m_d->lastapplied_diffuse,m_d->dim);
670}
671
672//____________________________________________________________________
674{
675 if (m_d->dim == dim)
676 return;
677 m_d->dim = dim;
678 updateButton();
679}
680
681//____________________________________________________________________
683{
684 QSlider * slider1(0);
685 QSlider * slider2(0);
686 if (sender()==m_d->editwindow_ui.slider_simple_transparency) {
687 slider1 = m_d->editwindow_ui.slider_simple_transparency;
688 slider2 = m_d->editwindow_ui.slider_transparency;
689 } else {
690 slider1 = m_d->editwindow_ui.slider_transparency;
691 slider2 = m_d->editwindow_ui.slider_simple_transparency;
692 }
693 bool save = slider2->blockSignals(true);
694 slider2->setValue(slider1->value());
695 slider2->blockSignals(save);
696 m_d->editwindow_ui.label_num_transparency->setNum(slider1->value());
697 m_d->editwindow_ui.label_num_simple_transparency->setNum(slider1->value());
698
700}
701
702//____________________________________________________________________
704{
705 if (!editwindow)
706 return;
707 editwindow_ui.stackedWidget->setCurrentWidget(simplemode?editwindow_ui.page_simple:editwindow_ui.page_detailed);
708 editwindow_ui.pushButton_switch_mode->setText("&Switch to "+QString(simplemode?"detailed":"simple")+" mode");
709 if (simplemode)
710 editwindow_ui.pushButton_switch_mode->setToolTip("Switch to detailed material editing for more options.");
711 else
712 editwindow_ui.pushButton_switch_mode->setToolTip("Switch to a simpler material editing. This might discard some information.");
713}
714
715//____________________________________________________________________
717{
718 if (!editwindow)
719 return;
720
721 bool lastappliedaresimple(false);
722
726 //Could be simple - test if emissive can be described as a
727 //brightness multiplied by diffusive:
729 if (brightness<1.0e-4) {
730 lastappliedaresimple = equal(lastapplied_emissive,Qt::black);
731 } else if (brightness>(1.0-1.0e-4)) {
732 lastappliedaresimple = equal(lastapplied_emissive,lastapplied_diffuse);
733 } else {
734 lastappliedaresimple = equal(lastapplied_emissive,
736 }
737 }
738
739 if (lastappliedaresimple!=simplemode)
740 theclass->switchMode();
741}
742
743
744//____________________________________________________________________
746{
747 if (!m_d->editwindow)
748 return;
749
750 const bool new_simplemode = !m_d->simplemode;
751
752 //Transparency sliders should already be updated.
753
754 m_d->blockGuiSignals(true);
755
756 if (new_simplemode) {
757 //Update detailed gui elements from simple gui elements. NB: All
758 //the m_d->guiXX() methods returns detailed parameters until we
759 //update m_d->simplemode below.
760 double brightness = m_d->brightnessEstimateFromDetailedParameters(m_d->guiDiffuseColour(),m_d->guiEmissiveColour());
761 int brightness_i = std::max<int>(0,std::min<int>(100,static_cast<int>(brightness*100+0.5)));
762 QColor col = m_d->guiDiffuseColour();
763 m_d->editwindow_ui.colbutton_simple_colour->setColor(col);
764 m_d->editwindow_ui.slider_simple_brightness->setValue(brightness_i);
765 m_d->editwindow_ui.label_num_simple_brightness->setNum(brightness_i);
766 } else {
767 //Update detailed gui elements from simple gui elements. NB: All
768 //the m_d->guiXX() methods returns simple parameters until we
769 //update m_d->simplemode below.
770 m_d->editwindow_ui.colbutton_ambient->setColor(m_d->guiAmbientColour());
771 m_d->editwindow_ui.colbutton_diffuse->setColor(m_d->guiDiffuseColour());
772 m_d->editwindow_ui.colbutton_specular->setColor(m_d->guiSpecularColour());
773 m_d->editwindow_ui.colbutton_emissive->setColor(m_d->guiEmissiveColour());
774 m_d->editwindow_ui.slider_shininess->setValue(m_d->guiShininess());
775 m_d->editwindow_ui.label_num_shininess->setNum(m_d->guiShininess());
776 }
777
778 m_d->simplemode = new_simplemode;
779 m_d->adaptGuiForMode();
780
781 m_d->blockGuiSignals(false);
783}
784
785//____________________________________________________________________
786SoMaterial* VP1MaterialButton::createMaterial( const QColor& col, const double& brightness, const double& transp )
787{
788 SoMaterial * m = new SoMaterial;
789 setMaterialParameters(m,col,brightness,transp);
790 return m;
791}
792
793//____________________________________________________________________
794SoMaterial* VP1MaterialButton::createMaterial( const double& r, const double& g, double b, const double& brightness,const double& transp )
795{
796 SoMaterial * m = new SoMaterial;
797 setMaterialParameters(m,r,g,b,brightness,transp);
798 return m;
799}
800
801//____________________________________________________________________
802void VP1MaterialButton::setMaterialParameters( SoMaterial * m, const QColor& col, const double& brightness, const double& transp )
803{
804 setMaterialParameters( m, col.redF(), col.greenF(), col.blueF(), brightness, transp);
805}
806
807//____________________________________________________________________
808void VP1MaterialButton::setMaterialParameters( SoMaterial * m, const double& in_r, const double& in_g, const double& in_b,
809 const double& in_brightness, const double& in_transp )
810{
811 if (!m)
812 return;
813
814 m->ref();
815 bool save = m->enableNotify(false);
816
817 const double r(std::max(0.0,std::min(1.0,in_r)));
818 const double g(std::max(0.0,std::min(1.0,in_g)));
819 const double b(std::max(0.0,std::min(1.0,in_b)));
820 const double brightness(std::max(0.0,std::min(1.0,in_brightness)));
821
822
823 m->diffuseColor.setValue(SbColor(r,g,b));
824 m->emissiveColor.setValue(SbColor(std::max(0.0f,std::min(1.0f,float(brightness*r))),
825 std::max(0.0f,std::min(1.0f,float(brightness*g))),
826 std::max(0.0f,std::min(1.0f,float(brightness*b)))));
827 m->transparency.setValue(std::max<float>(0.0f,std::min<float>(1.0f,in_transp)));
828 m->shininess.setValue(std::max<float>(0.0f,std::min<float>(1.0f,Imp::simpleShininess()/100.0f)));
829 m->ambientColor.setValue(Imp::qcol2sbcol(Imp::simpleAmbient()));
830 m->specularColor.setValue(Imp::qcol2sbcol(Imp::simpleSpecular()));
831
832 if (save) {
833 m->enableNotify(true);
834 m->touch();
835 }
836 m->unrefNoDelete();
837}
838
839//____________________________________________________________________
841{
842 if (event->button() == Qt::LeftButton)
843 m_d->dragStartPosition = event->pos();
844 QPushButton::mousePressEvent(event);
845}
846
847//____________________________________________________________________
848void VP1MaterialButton::mouseMoveEvent(QMouseEvent *event)
849{
850 if (!(event->buttons() & Qt::LeftButton))
851 return;
852 if ((event->pos() - m_d->dragStartPosition).manhattanLength()
853 < QApplication::startDragDistance())
854 return;
855
856 QDrag *drag = new QDrag(this);
857 QMimeData *mimeData = new QMimeData;
858
860 // For dragging state onto other material buttons: //
862
863 QByteArray byteArray;
864 QBuffer buffer(&byteArray);
865 buffer.open(QIODevice::WriteOnly);
866 QDataStream out(&buffer);
867 out << m_d->lastapplied_ambient;
868 out << m_d->lastapplied_diffuse;
869 out << m_d->lastapplied_specular;
870 out << m_d->lastapplied_emissive;
871 out << m_d->lastapplied_shininess;
872 out << m_d->lastapplied_transparency;
873 out << m_d->lastapplied_brightness;
874 buffer.close();
875 mimeData->setData("vp1/material", byteArray);
876
878 // For dragging c++ code for defining this material //
879 // into e.g. an editor: //
881
882 QString s = "SoMaterial * mat = new SoMaterial;\n";
883 QString str_ambient = m_d->toSbColTxt(m_d->lastapplied_ambient);
884 if (str_ambient!="SbColor(0.2,0.2,0.2)")
885 s += "mat->ambientColor.setValue("+str_ambient+");\n";
886 QString str_diffuse = m_d->toSbColTxt(m_d->lastapplied_diffuse);
887 if (str_diffuse!="SbColor(0.8,0.8,0.8)")
888 s += "mat->diffuseColor.setValue("+str_diffuse+");\n";
889 QString str_specular = m_d->toSbColTxt(m_d->lastapplied_specular);
890 if (str_specular!="SbColor(0,0,0)")
891 s += "mat->specularColor.setValue("+str_specular+");\n";
892 QString str_emissive = m_d->toSbColTxt(m_d->lastapplied_emissive);
893 if (str_emissive!="SbColor(0,0,0)")
894 s += "mat->emissiveColor.setValue("+str_emissive+");\n";
895 QString str_shininess = m_d->printFloat(m_d->lastapplied_shininess/100.0);
896 if (str_shininess!="0.2")
897 s += "mat->shininess.setValue("+str_shininess+");\n";
898 QString str_transparency = m_d->printFloat(m_d->lastapplied_transparency/100.0);
899 if (str_transparency!="0")
900 s += "mat->transparency.setValue("+str_transparency+");\n";
901 mimeData->setText(s);
902
903 //Execute drag:
904 drag->setMimeData(mimeData);//drag assumes ownership of mimeData
905 drag->exec(Qt::CopyAction | Qt::MoveAction);
906}
907
908//____________________________________________________________________
909void VP1MaterialButton::dragEnterEvent(QDragEnterEvent *event)
910{
911 if (event->source()!=this && event->mimeData()->hasFormat("vp1/material"))
912 event->acceptProposedAction();
913}
914
915//____________________________________________________________________
916void VP1MaterialButton::dropEvent(QDropEvent *event)
917{
918 QByteArray data = event->mimeData()->data("vp1/material");
919 event->acceptProposedAction();
920
921 QBuffer buffer(&data);
922 buffer.open(QIODevice::ReadOnly);
923 QDataStream state(&buffer);
924 state >> m_d->lastapplied_ambient;
925 state >> m_d->lastapplied_diffuse;
926 state >> m_d->lastapplied_specular;
927 state >> m_d->lastapplied_emissive;
928 state >> m_d->lastapplied_shininess;
929 state >> m_d->lastapplied_transparency;
930 state >> m_d->lastapplied_brightness;
931 buffer.close();
932 m_d->adaptGuiAndMaterialsToLastApplied();
933}
934
936 VP1Serialise serialise(1/*version*/);
937 serialise.save(this);
938 return serialise.result();
939}
940
941void VP1MaterialButton::restoreFromState( const QByteArray& ba){
942 VP1Deserialise state(ba,systemBase());
943 if (state.version()<0||state.version()>1)
944 return;//Ignore silently
945 state.restore(this);
946}
char data[hepevt_bytes_allocation_ATLAS]
Definition HepEvt.cxx:11
static Double_t a
static void setColButtonProperties(QPushButton *, const QColor &col, int dim)
void restore(QCheckBox *sb)
qint32 version() const
virtual void removeDecorationMenuOption()
virtual void setTransparencyType(SoGLRenderAction::TransparencyType)
void messageVerbose(const QString &) const
void message(const QString &) const
IVP1System * systemBase() const
void messageDebug(const QString &) const
VP1MaterialButtonBase(QWidget *parent, IVP1System *sys=0, const QString &helpername="")
QColor emissiveColourFromSimpleParameters(const QColor &simpleColour, const double &brightness) const
static SbColor qcol2sbcol(const QColor &)
Ui::VP1MaterialButtonForm editwindow_ui
QString toSbColTxt(const QColor &c)
static bool equal(const QColor &a, const QColor &b, const double &tol=1.0e-6)
VP1MaterialButton * theclass
static double distSq(const QColor &a, const QColor &b)
double brightnessEstimateFromDetailedParameters(const QColor &diffuseColour, const QColor &emissiveColour) const
QString printFloat(const double &d)
static QColor sbcol2qcol(const SbColor &)
void applyValuesToMaterial(SoMaterial *, bool preview=false)
QList< SoMaterial * > handledmaterials
void setText(const QString &)
bool stopHandlingMaterial(SoMaterial *)
static void setMaterialParameters(SoMaterial *m, const QColor &, const double &brightness=0.0, const double &transp=0.0)
void setMaterialText(const QString &)
void mousePressEvent(QMouseEvent *event)
void dragEnterEvent(QDragEnterEvent *event)
QColor lastAppliedEmissiveColour() const
static SoMaterial * createMaterial(const QColor &, const double &brightness=0.0, const double &transp=0.0)
const QList< SoMaterial * > & handledMaterials() const
QColor lastAppliedAmbientColour() const
bool setMaterial(SoMaterial *)
void dropEvent(QDropEvent *event)
double lastAppliedBrightness() const
void copyValuesFromMaterial(SoMaterial *)
VP1MaterialButton(QWidget *parent=0, int dim=25)
void lastAppliedChanged()
void mouseMoveEvent(QMouseEvent *event)
QByteArray saveState() const
fill out with the state of the object (used for drag and drop etc)
void restoreFromState(const QByteArray &)
double lastAppliedTransparency() const
QColor lastAppliedDiffuseColour() const
QColor lastAppliedSpecularColour() const
bool handleMaterial(SoMaterial *)
double lastAppliedShininess() const
static bool verbose()
Definition VP1Msg.h:31
static bool environmentVariableIsOn(const QString &name)
static bool expertSettingIsOn(const QString &type, const QString &name)
int r
Definition globals.cxx:22