Logo ROOT  
Reference Guide
Loading...
Searching...
No Matches
TStructViewerGUI.cxx
Go to the documentation of this file.
1// @(#)root/gviz3d:$Id$
2// Author: Tomasz Sosnicki 18/09/09
3
4/************************************************************************
5* Copyright (C) 1995-2009, Rene Brun and Fons Rademakers. *
6* All rights reserved. *
7* *
8* For the licensing terms see $ROOTSYS/LICENSE. *
9* For the list of contributors see $ROOTSYS/README/CREDITS. *
10*************************************************************************/
11
12#include "TStructViewerGUI.h"
13#include "TStructViewer.h"
14#include "TStructNodeEditor.h"
15#include "TStructNodeProperty.h"
16#include "TStructNode.h"
17#include <TCanvas.h>
18#include <RQ_OBJECT.h>
19#include <TGLLogicalShape.h>
20#include <TGLPhysicalShape.h>
21#include <TGLWidget.h>
22#include <TGButtonGroup.h>
23#include <TGSplitter.h>
24#include <TList.h>
25#include <TClass.h>
26#include <TDataMember.h>
27#include <TExMap.h>
28#include <TPolyLine3D.h>
29#include <TGTab.h>
30#include <TGeoManager.h>
31#include <TGeoMatrix.h>
32#include <TMath.h>
33#include <TROOT.h>
34#include <TApplication.h>
35
36
37//________________________________________________________________________
38//////////////////////////////////////////////////////////////////////////
39//
40// TStructViewerGUI is main window of TStructViewer. It provides graphical
41// interface. In the window we can find panel with tabs and frame with
42// GLViewer. Tab "Info" serves information about node and is used to naviagate
43// backward and forward. Second tab "Options" is used to set few options
44// such as links visibility, scaling method or setting a pointer.
45// Last tab "Editor" is tab when the TStructNodeEditor is placed.
46//
47//////////////////////////////////////////////////////////////////////////
48
51
52////////////////////////////////////////////////////////////////////////////////
53/// Constructs window with "w" as width, "h" as height and given parent "p". Argument "parent" is a pointer to TStructViewer which contains this GUI.
54/// This constructor build window with all controls, build map with colors, init OpenGL Viewer and create TGeoVolumes.
55
58{
59 fParent = parent;
60 fNodePtr = nodePtr;
61
62 fMaxSlices = 10;
63 fMouseX = 0;
64 fMouseY = 0;
65 fSelectedObject = nullptr;
66 fMaxRatio = 0;
68
69 if (!gGeoManager) new TGeoManager("tmp","tmp");
70 if (!fgMedium) {
71 fgMedium = new TGeoMedium("MED",1,new TGeoMaterial("Mat", 26.98,13,2.7));
72 }
73
75 //////////////////////////////////////////////////////////////////////////
76 // layout
77 //////////////////////////////////////////////////////////////////////////
78 TGVerticalFrame* leftFrame = new TGVerticalFrame(this, 200, 200, kFixedWidth);
79 this->AddFrame(leftFrame, new TGLayoutHints(kFixedWidth, 1, 1, 1, 1));
80 TGTab* tabs = new TGTab(leftFrame);
81 TGLayoutHints* expandX = new TGLayoutHints(kLHintsLeft | kLHintsExpandX, 5,5,5,5);
82 //////////////////////////////////////////////////////////////////////////
83 // INFO
84 //////////////////////////////////////////////////////////////////////////
85 TGCompositeFrame* infoFrame = tabs->AddTab("Info");
86 TGGroupFrame* fInfoMenu = new TGGroupFrame(infoFrame, "Info");
87 fNodeNameLabel = new TGLabel(fInfoMenu, "Name:");
88 fInfoMenu->AddFrame(fNodeNameLabel, expandX);
89 fNodeTypelabel = new TGLabel(fInfoMenu, "Type:");
90 fInfoMenu->AddFrame(fNodeTypelabel, expandX);
91 fMembersCountLabel = new TGLabel(fInfoMenu, "Members:");
92 fInfoMenu->AddFrame(fMembersCountLabel, expandX);
93 fAllMembersCountLabel = new TGLabel(fInfoMenu, "All members:");
94 fInfoMenu->AddFrame(fAllMembersCountLabel, expandX);
95 fLevelLabel = new TGLabel(fInfoMenu, "Level:");
96 fInfoMenu->AddFrame(fLevelLabel, expandX);
97 fSizeLabel = new TGLabel(fInfoMenu, "Size:");
98 fInfoMenu->AddFrame(fSizeLabel, expandX);
99 fTotalSizeLabel = new TGLabel(fInfoMenu, "Total size:");
100 fInfoMenu->AddFrame(fTotalSizeLabel, expandX);
101 infoFrame->AddFrame(fInfoMenu, expandX);
102
103 //////////////////////////////////////////////////////////////////////////
104 // OPTIONS
105 //////////////////////////////////////////////////////////////////////////
106 TGCompositeFrame* options = tabs->AddTab("Options");
107
108 fShowLinksCheckButton = new TGCheckButton(options, "Show links");
109 fShowLinksCheckButton->Connect("Toggled(Bool_t)", "TStructViewerGUI", this, "ShowLinksToggled(Bool_t)");
111 fShowLinksCheckButton->SetOn();
112
113 TGVButtonGroup* scaleByGroup = new TGVButtonGroup(options, "Scale by");
114 fScaleBySizeButton = new TGRadioButton(scaleByGroup, "Size");
115 fScaleBySizeButton->Connect("Clicked()", "TStructViewerGUI", this, "ScaleByChangedSlot()");
116 fScaleBySizeButton->SetOn();
117 fScaleByMembersButton = new TGRadioButton(scaleByGroup, "Members count");
118 fScaleByMembersButton->Connect("Clicked()", "TStructViewerGUI", this, "ScaleByChangedSlot()");
119 options->AddFrame(scaleByGroup, expandX);
120
121 TGHorizontalFrame* defaultColorFrame = new TGHorizontalFrame(options);
122 options->AddFrame(defaultColorFrame, expandX);
123 TGLabel* defColorlabel = new TGLabel(defaultColorFrame, "Default color");
124 defaultColorFrame->AddFrame(defColorlabel, expandX);
125 TGColorSelect* defColorSelect = new TGColorSelect(defaultColorFrame, GetDefaultColor()->GetPixel());
126 defColorSelect->Connect("ColorSelected(Pixel_t)", "TStructViewerGUI", this, "ColorSelectedSlot(Pixel_t)");
127 defaultColorFrame->AddFrame(defColorSelect);
128
129 TGHorizontalFrame* boxHeightFrame = new TGHorizontalFrame(options);
130 options->AddFrame(boxHeightFrame, expandX);
131 TGLabel* boxHeightLabel = new TGLabel(boxHeightFrame, "Box height:");
132 boxHeightFrame->AddFrame(boxHeightLabel, expandX);
133 fBoxHeightEntry = new TGNumberEntry(boxHeightFrame, 0.1);
135 fBoxHeightEntry->Connect("ValueSet(Long_t)", "TStructViewerGUI", this, "BoxHeightValueSetSlot(Long_t)");
136 boxHeightFrame->AddFrame(fBoxHeightEntry);
137
138 TGHorizontalFrame* levelDistanceFrame = new TGHorizontalFrame(options);
139 options->AddFrame(levelDistanceFrame, expandX);
140 TGLabel* lvlDistLabel = new TGLabel(levelDistanceFrame, "Distance between levels");
141 levelDistanceFrame->AddFrame(lvlDistLabel, expandX);
142 fLevelDistanceEntry = new TGNumberEntry(levelDistanceFrame, 1.1);
144 fLevelDistanceEntry->Connect("ValueSet(Long_t)", "TStructViewerGUI", this, "LevelDistValueSetSlot(Long_t)");
145 levelDistanceFrame->AddFrame(fLevelDistanceEntry);
146
147 fAutoRefesh = new TGCheckButton(options, "Auto refresh");
148 fAutoRefesh->SetOn();
149 fAutoRefesh->Connect("Toggled(Bool_t)", "TStructViewerGUI", this, "AutoRefreshButtonSlot(Bool_t)");
150 options->AddFrame(fAutoRefesh, expandX);
151
152 TGLabel* pointerLabel = new TGLabel(options, "Pointer:");
153 options->AddFrame(pointerLabel, expandX);
154 fPointerTextEntry = new TGTextEntry(options, "0x0000000");
155 options->AddFrame(fPointerTextEntry, expandX);
156 TGLabel* fPointerTypeLabel = new TGLabel(options, "Pointer Type:");
157 options->AddFrame(fPointerTypeLabel, expandX);
158 fPointerTypeTextEntry = new TGTextEntry(options, "TObject");
159 options->AddFrame(fPointerTypeTextEntry, expandX);
160 TGTextButton* setPointerButton = new TGTextButton(options, "Set pointer");
161 setPointerButton->Connect("Clicked()", "TStructViewerGUI", this, "SetPointerButtonSlot()");
162 options->AddFrame(setPointerButton, expandX);
163
164 //////////////////////////////////////////////////////////////////////////
165 // EDITOR
166 //////////////////////////////////////////////////////////////////////////
167 TGCompositeFrame* editTab = tabs->AddTab("Editor");
168 fEditor = new TStructNodeEditor(fColors, editTab);
169 fEditor->Connect("Update(Bool_t)", "TStructViewerGUI", this, "Update(Bool_t)");
170 editTab->AddFrame(fEditor, expandX);
171
172 leftFrame->AddFrame(tabs, new TGLayoutHints(kLHintsExpandX | kLHintsExpandY, 1,1,1,1));
173
174 TGVSplitter* splitter = new TGVSplitter(this);
175 splitter->SetFrame(leftFrame, true);
176 this->AddFrame(splitter, new TGLayoutHints(kLHintsLeft | kLHintsExpandY));
177
178 //////////////////////////////////////////////////////////////////////////
179 // NAVIGATE
180 //////////////////////////////////////////////////////////////////////////
181 fUndoButton = new TGTextButton(leftFrame, "Undo");
182 fUndoButton->Connect("Clicked()", "TStructViewerGUI", this, "UndoButtonSlot()");
183 fUndoButton->SetEnabled(false);
184 leftFrame->AddFrame(fUndoButton, expandX);
185
186 fRedoButton = new TGTextButton(leftFrame, "Redo");
187 fRedoButton->Connect("Clicked()", "TStructViewerGUI", this, "RedoButtonSlot()");
188 fRedoButton->SetEnabled(false);
189 leftFrame->AddFrame(fRedoButton, expandX);
190
191 TGTextButton* resetCameraButton = new TGTextButton(leftFrame, "Reset camera");
192 leftFrame->AddFrame(resetCameraButton, expandX);
193 resetCameraButton->Connect("Clicked()", "TStructViewerGUI", this, "ResetButtonSlot()");
194
195 TGTextButton* updateButton = new TGTextButton(leftFrame, "Update");
196 updateButton->Connect("Clicked()", "TStructViewerGUI", this, "UpdateButtonSlot()");
197 leftFrame->AddFrame(updateButton, expandX);
198
199 TGTextButton* quitButton = new TGTextButton(leftFrame, "Quit");
200 leftFrame->AddFrame(quitButton, expandX);
201 quitButton->Connect("Clicked()", "TApplication", gApplication, "Terminate()");
202
203 fTopVolume = gGeoManager->MakeBox("TOPVolume", fgMedium,100, 100, 100);
204 gGeoManager->SetTopVolume(fTopVolume);
205 gGeoManager->SetNsegments(40);
206
207 fCanvas = new TCanvas("c", "c", 0, 0);
208 // drawing after creating canvas to avoid drawing in default canvas
210 AddFrame(fGLViewer->GetFrame(), new TGLayoutHints(kLHintsExpandX| kLHintsExpandY, 10,10,10,10));
211 fGLViewer->PadPaint(fCanvas);
212 fGLViewer->Connect("MouseOver(TGLPhysicalShape*)", "TStructViewerGUI", this, "MouseOverSlot(TGLPhysicalShape*)");
213 fGLViewer->GetGLWidget()->Connect("ProcessedEvent(Event_t*)", "TStructViewerGUI", this, "GLWidgetProcessedEventSlot(Event_t*))");
214 fGLViewer->Connect("DoubleClicked()", "TStructViewerGUI", this, "DoubleClickedSlot()");
215 fGLViewer->SetCurrentCamera(TGLViewer::kCameraPerspXOY);
216 Update();
217 fGLViewer->SetResetCamerasOnUpdate(false);
218
219 SetWindowName("Struct Viewer");
221 this->SetWMSizeHints(w, h, 2000, 2000, 0, 0);
223 MapWindow();
224
225 fToolTip = new TGToolTip(0, 0, "ToolTip", 500);
226}
227
228////////////////////////////////////////////////////////////////////////////////
229/// Destructor
230
235
236////////////////////////////////////////////////////////////////////////////////
237/// Activated when user chage condition
238
240{
241 if (on) {
242 Update();
243 }
244}
245
246////////////////////////////////////////////////////////////////////////////////
247/// Emmited when user changes height of boxes
248
250{
251 if(fAutoRefesh->IsOn()) {
252 Update();
253 }
254}
255
256////////////////////////////////////////////////////////////////////////////////
257/// Recursive method to calculating nodes posistion in 3D space
258
260{
261 // choose scaling method
262 if (fScaleBySizeButton->GetState() == kButtonDown) {
264 } else if (fScaleByMembersButton->GetState() == kButtonDown) {
266 }
267 Float_t ratio = (Float_t)((parent->GetLevel()+1.0) / parent->GetLevel());
268
269 // changing the angle between parent object and daughters
270 // if center of parent is 0 that is real piramid
271 parent->SetWidth(1);
272 parent->SetHeight(1);
273 parent->SetX(-parent->GetWidth()/2);
274 parent->SetY(-parent->GetHeight()/2);
275
276 fMaxRatio = parent->GetVolumeRatio();
277
278 // sorting list of members by size or number of members
279 parent->GetMembers()->Sort(kSortDescending);
280 Divide(parent->GetMembers(), (parent->GetX()) *ratio, (parent->GetX() + parent->GetWidth())* ratio, (parent->GetY())* ratio, (parent->GetY() + parent->GetHeight())*ratio);
281
282 // sclale all the objects
283 Scale(parent);
284}
285
286////////////////////////////////////////////////////////////////////////////////
287/// Check if all of nodes can be displayed on scene. Hides redendant nodes.
288
290{
291 UInt_t object = 0;
292
293 TList queue;
294 queue.Add(parent);
295 TStructNode* node;
296
297 while ((node = (TStructNode*) queue.First() )) {
298 object++;
299
300 if (object > fNodePtr->GetMaxObjects() || node->GetLevel() - fNodePtr->GetLevel() >= fNodePtr->GetMaxLevel()) {
301 break;
302 }
303
304 node->SetVisible(true);
305
306 queue.AddAll(node->GetMembers());
307 queue.RemoveFirst();
308
309 fVisibleObjects.Add(node);
310 }
311
313 TStructNode* member;
314 while ((node = (TStructNode*) it() )) {
315 if(node->GetLevel() - fNodePtr->GetLevel() == fNodePtr->GetMaxLevel()-1 && node->GetMembersCount() > 0) {
316 node->SetCollapsed(true);
317 continue;
318 }
319
320 TIter memIt(node->GetMembers());
321 while ((member = (TStructNode*) memIt() )) {
322 if(member->IsVisible() == false) {
323 node->SetCollapsed(true);
324 break;
325 }
326 }
327 }
328}
329
330////////////////////////////////////////////////////////////////////////////////
331/// Delete window
332
337
338////////////////////////////////////////////////////////////////////////////////
339/// Slot for default color selsect.
340/// Sets default colot to "pixel"
341
343{
345 if(prop) {
346 prop->SetColor(pixel);
347 Update();
348 }
349}
350
351////////////////////////////////////////////////////////////////////////////////
352/// Divides rectangle where the outlining box is placed.
353
355{
356 if (list->GetSize() > 1) { // spliting node into two lists
357 ULong_t sum1 = 0, sum = 0;
358
359 TStructNode* node;
360 TList list1, list2;
361 TIter it(list);
362
363 while((node = (TStructNode*) it() )) {
364 sum += node->GetVolume();
365 }
366 it.Reset();
367 while((node = (TStructNode*) it() )) {
368 if(sum1 >= sum/2.0) {
369 list2.Add(node);
370 } else {
371 sum1 += node->GetVolume();
372 list1.Add(node);
373 }
374 }
375
376 if (!sum) return;
377 Float_t ratio = (float)sum1/sum;
378
379 Float_t width = x2 - x1;
380 Float_t height = y2 - y1;
381 if (width < height) { // vertical split
382 Float_t split = y1 + ratio * height;
383 Divide(&list1, x1, x2, y1, split);
384 Divide(&list2, x1, x2, split, y2);
385 } else { // horizontal
386 Float_t split = x1 + ratio * width;
387 Divide(&list1, x1, split, y1, y2);
388 Divide(&list2, split, x2, y1, y2);
389 }
390 } else if (list->GetSize() == 1) { // divide place to node
391 TStructNode* node = (TStructNode*)(list->First());
392
393 node->SetWidth(x2 - x1);
394 node->SetHeight(y2 - y1);
395 node->SetX(x1);
396 node->SetY(y1);
397
398 if (node->GetVolumeRatio() > fMaxRatio) {
399 fMaxRatio = node->GetVolumeRatio();
400 }
401
402 Float_t ratio = (Float_t)((node->GetLevel()+1.0)/node->GetLevel());
404 Divide(node->GetMembers(), x1*ratio, x2*ratio, y1*ratio, y2*ratio);
405 }
406}
407
408////////////////////////////////////////////////////////////////////////////////
409/// Activated when user double click on objects on 3D scene. Sets clicked node to top node
410/// and updates scene with camers reset.
411
413{
414 if (fSelectedObject) {
416 return;
417 }
418
419 fUndoList.Add(fNodePtr);
421 fUndoButton->SetEnabled(true);
422
423 Update(kTRUE);
424 }
425}
426////////////////////////////////////////////////////////////////////////////////
427/// Check limits and draws nodes and links
428
430{
431 fVolumes.Clear();
433
436
437 if(fShowLinksCheckButton->GetState() == kButtonDown) {
439 }
440
442}
443
444////////////////////////////////////////////////////////////////////////////////
445/// Recursive method to draw links
446
448{
449 if(parent->GetLevel() - fNodePtr->GetLevel() >= fNodePtr->GetMaxLevel()) {
450 return;
451 }
452
453 if(parent->IsCollapsed()) {
454 return;
455 }
456
457 TIter it(parent->GetMembers());
458 TStructNode* node;
459 while((node = (TStructNode*) it())) {
460 TPolyLine3D *l = new TPolyLine3D(2);
461 l->SetPoint(0 ,node->GetCenter(), node->GetMiddle(), -(node->GetLevel() * fLevelDistanceEntry->GetNumber()));
462 l->SetPoint(1 ,parent->GetCenter(), parent->GetMiddle(), -(parent->GetLevel() * fLevelDistanceEntry->GetNumber()));
463
464 l->SetLineColor(GetColor(node));
465 l->SetLineWidth(1);
466 l->Draw();
467
468 if(!node->IsCollapsed()) {
469 DrawLink(node);
470 }
471 }
472}
473
474////////////////////////////////////////////////////////////////////////////////
475/// Creates and draws TGeoVolume from given "node"
476
478{
479 TGeoVolume* vol;
480
481 /*if(node->IsCollapsed())
482 {
483 //float r = (node->GetWidth() < node->GetHeight() ? 0.5 * node->GetWidth() : 0.5 * node->GetHeight());
484 //vol = gGeoManager->MakeTorus(node->GetName(),TStructNode::GetMedium(), 0.75*r, 0, r/4);
485
486 vol = gGeoManager->MakeBox(TString(node->GetName()) + "up",TStructNode::GetMedium(), 0.45*node->GetWidth(), 0.45*node->GetHeight(), (node->GetWidth() < node->GetHeight() ? 0.45 * node->GetWidth() : 0.45 * node->GetHeight()));
487 Double_t max = TMath::Max(0.22 * node->GetWidth(), 0.22 * node->GetHeight());
488 TGeoVolume* subvol = gGeoManager->MakeTrd2(node->GetName(), TStructNode::GetMedium(), 0, 0.45 * node->GetWidth(), 0, 0.45 * node->GetHeight(), max);
489 subvol->SetLineColor(GetColor(node));
490 subvol->SetNumber((Int_t)node);
491 TGeoTranslation* subtrans = new TGeoTranslation("subtranslation", 0, 0, -max);
492 vol->AddNodeOverlap(subvol, 1, subtrans);
493
494 subvol = gGeoManager->MakeTrd2(TString(node->GetName()) + "down", TStructNode::GetMedium(), 0.45 * node->GetWidth(), 0, 0.45 * node->GetHeight(), 0, max);
495 subvol->SetLineColor(GetColor(node));
496 subvol->SetNumber((Int_t)node);
497 subtrans = new TGeoTranslation("subtranslation", 0, 0, max);
498 vol->AddNodeOverlap(subvol, 1, subtrans);
499 }
500 else*/ if(node->GetNodeType() == kCollection) {
501 vol = gGeoManager->MakeBox(Form("%s_%d", node->GetName(), fgCounter++), fgMedium, 0.45*node->GetWidth(), 0.45*node->GetHeight(), fBoxHeightEntry->GetNumber());
502 // subboxes
503 Float_t slices = (Float_t)(node->GetMembersCount());
504 if (slices > fMaxSlices) {
505 slices = (Float_t)fMaxSlices;
506 }
507
508 for (Float_t i = -(slices-1)/2; i < slices/2; i++) {
509 TGeoVolume* sub = gGeoManager->MakeBox(Form("%s_%d", node->GetName(), fgCounter++), fgMedium,0.45*node->GetWidth() * 0.7 / slices, 0.45*node->GetHeight(), fBoxHeightEntry->GetNumber());
510 sub->SetLineColor(GetColor(node));
511 fVolumes.Add((Longptr_t)sub, (Longptr_t)node);
512 TGeoTranslation* subtrans = new TGeoTranslation("subtranslation", i * node->GetWidth() / slices, 0, 0);
513 vol->AddNodeOverlap(sub, 1, subtrans);
514 }
515 } else {
516 vol = gGeoManager->MakeBox(Form("%s_%d", node->GetName(), fgCounter++), fgMedium, 0.45*node->GetWidth(), 0.45*node->GetHeight(), fBoxHeightEntry->GetNumber());
517 }
518
519 vol->SetLineColor(GetColor(node));
520 vol->SetLineWidth(1);
521
522 TGeoTranslation* trans = new TGeoTranslation("translation", node->GetCenter(), node->GetMiddle(), -(node->GetLevel() * fLevelDistanceEntry->GetNumber()));
523 fVolumes.Add((Longptr_t)vol, (Longptr_t)node);
524
525 fTopVolume->AddNode(vol,1, trans);
526}
527
528////////////////////////////////////////////////////////////////////////////////
529/// Recursive method to draw GeoVolumes
530
532{
533 if(parent->GetLevel() - fNodePtr->GetLevel() >= fNodePtr->GetMaxLevel()) {
534 return;
535 }
536
537 DrawNode(parent);
538
539 if(parent->IsCollapsed()) {
540 return;
541 }
542
543 TIter nextVis(parent->GetMembers());
544 TStructNode* node;
545 while((node = (TStructNode*)nextVis())) {
546 DrawVolumes(node);
547 }
548}
549
550////////////////////////////////////////////////////////////////////////////////
551/// Returns pointer to property associated with node "node". If property is not found
552/// then it returns default property
553
555{
556 TIter it(fColors);
558 while ((prop = (TStructNodeProperty*) it() )) {
559 TString propName(prop->GetName());
560 if (propName.EndsWith("+")) {
561
562 if (TClass* cl = TClass::GetClass(node->GetTypeName())) {
563 propName.Remove(propName.Length()-1, 1);
564 if (cl->InheritsFrom(propName.Data())) {
565 return prop;
566 }
567 }
568 } else {
569 if (propName == TString(node->GetTypeName())) {
570 return prop;
571 }
572 }
573 }
574
575 return (TStructNodeProperty*)fColors->Last();
576}
577
578//________________________________________________________________________`
580{
581 // Returns canvas used to keep TGeoVolumes
582
583 return fCanvas;
584}
585////////////////////////////////////////////////////////////////////////////////
586/// Returns color form fColors for given "node"
587
589{
591 if (prop) {
592 return prop->GetColor().GetNumber();
593 }
594
595 return 2;
596}
597
598////////////////////////////////////////////////////////////////////////////////
599/// Return default color for nodes
600
605
606////////////////////////////////////////////////////////////////////////////////
607/// Returns true if links are visible, otherwise return false.
608
610{
611 if (fShowLinksCheckButton->GetState() == kButtonDown) {
612 return true;
613 } else {
614 return false;
615 }
616}
617
618////////////////////////////////////////////////////////////////////////////////
619/// Returns top node pointer
620
622{
623 return fNodePtr;
624}
625
626////////////////////////////////////////////////////////////////////////////////
627/// Handle events. Sets fMouseX and fMouseY when user move a mouse over viewer and hides ToolTip
628
630{
631 switch (event->fType) {
632 case kMotionNotify:
633 fMouseX = event->fXRoot + 15;
634 fMouseY = event->fYRoot + 15;
635 break;
636
637 case kButtonPress:
638 fToolTip->Hide();
639 if (fSelectedObject) {
641 fEditor->SetModel(fSelectedObject);
642 }
643 break;
644
645 default:
646 break;
647 }
648}
649
650////////////////////////////////////////////////////////////////////////////////
651/// Emmited when user changes distance between levels
652
654{
655 if(fAutoRefesh->IsOn()) {
656 Update(kTRUE);
657 }
658}
659
660////////////////////////////////////////////////////////////////////////////////
661/// MouseOver slot. Activated when user out mouse over object on scene.
662/// Sets ToolTip and updates labels
663
665{
666 fToolTip->Hide();
667 fSelectedObject = nullptr;
668 if (shape && shape->GetLogical()) {
669 fSelectedObject = (TStructNode*)(shape->GetLogical()->ID());
670 if (fSelectedObject) {
671 if (fSelectedObject->IsA()->InheritsFrom(TPolyLine3D::Class())) {
672 fSelectedObject = nullptr;
673 return;
674 }
675 Longptr_t shapeID = (Longptr_t)(shape->GetLogical()->ID());
676 Longptr_t volValue = (Longptr_t)fVolumes.GetValue(shapeID);
677 fSelectedObject = (TStructNode*)volValue;
678
679 fToolTip->SetText(TString(fSelectedObject->GetName()) + "\n" + fSelectedObject->GetTypeName());
680 fToolTip->SetPosition(fMouseX, fMouseY);
681 fToolTip->Reset();
683 }
684 }
685}
686
687////////////////////////////////////////////////////////////////////////////////
688/// Activated when user click Redo button. Repeat last Undo action.
689
691{
692 fUndoList.Add(fNodePtr);
693 fUndoButton->SetEnabled(true);
694 fNodePtr = (TStructNode*) fRedoList.Last();
695 fRedoList.RemoveLast();
696 if (!fRedoList.First()) {
697 fRedoButton->SetEnabled(false);
698 }
699 Update(kTRUE);
701}
702
703////////////////////////////////////////////////////////////////////////////////
704/// Resets camera
705
707{
708 fGLViewer->UpdateScene();
709 fGLViewer->ResetCurrentCamera();
710}
711
712////////////////////////////////////////////////////////////////////////////////
713/// Recursive method to scaling all modes on scene. We have to scale nodes to get real ratio between nodes.
714/// Uses fMaxRatio.
715
717{
718 // newRatio = sqrt(ratio/maxratio)
720 // set left top conner in the center
721 parent->SetX(parent->GetX() + parent->GetWidth()/2);
722 parent->SetY(parent->GetY() + parent->GetHeight()/2);
723 // set new size
724 Float_t min = (Float_t)TMath::Min(parent->GetWidth(), parent->GetHeight());
725 parent->SetWidth(parent->GetWidth() * newRatio);
726 parent->SetHeight(parent->GetHeight() * newRatio);
727 // fit the ratio -> height to width
728 Float_t sqrt = (Float_t)(TMath::Sqrt(parent->GetWidth() * parent->GetHeight()));
729 // it's a square
730 if (min > sqrt) {
731 parent->SetWidth(sqrt);
732 parent->SetHeight(sqrt);
733 } else { // it's rectangle
734 if (parent->GetHeight() > parent->GetWidth()) {
735 parent->SetWidth(min);
736 parent->SetHeight(sqrt * sqrt / min);
737 } else {
738 parent->SetWidth(sqrt * sqrt / min);
739 parent->SetHeight(min);
740 }
741 }
742 // move left top corner
743 parent->SetX(parent->GetX() - parent->GetWidth()/2);
744 parent->SetY(parent->GetY() - parent->GetHeight()/2);
745
746 // scale others nodes
747 TStructNode* node;
748 TIter it(parent->GetMembers());
749 while ((node = (TStructNode*) it() )) {
750 Scale(node);
751 }
752}
753
754////////////////////////////////////////////////////////////////////////////////
755/// Sets top node pointer and updates view
756
758{
759 fNodePtr = val;
760 Update(kTRUE);
761}
762
763////////////////////////////////////////////////////////////////////////////////
764/// Sets links visibility to "visible"
765
767{
768 if (visible) {
770 } else {
772 }
773}
774
775////////////////////////////////////////////////////////////////////////////////
776/// Sets pointer given in fPointerTestEntry to the main pointer
777
779{
780 void* obj = (void*)gROOT->ProcessLine(fPointerTextEntry->GetText());
781 fParent->SetPointer(obj, fPointerTypeTextEntry->GetText());
782}
783
784////////////////////////////////////////////////////////////////////////////////
785/// Changes links visibility and refresh view.
786
788{
789 if (fAutoRefesh->IsOn()) {
790 Update();
791 }
792}
793
794////////////////////////////////////////////////////////////////////////////////
795/// Shows hidden nodes
796
798{
799 TStructNode* node;
801
802 while ((node = (TStructNode*) it() )) {
803 node->SetCollapsed(false);
804 node->SetVisible(false);
805 }
806
807 fVisibleObjects.Clear();
808}
809
810////////////////////////////////////////////////////////////////////////////////
811/// Updates view. Clear all the nodes, call draw function and update scene. Doesn't reset camera.
812
814{
815 if (!fNodePtr)
816 return;
817
818 if (fCanvas && fCanvas->GetListOfPrimitives())
819 fCanvas->GetListOfPrimitives()->Clear();
820
821 if (fTopVolume)
822 fTopVolume->ClearNodes();
823
824 Draw();
825
826 if (fCanvas && fCanvas->GetListOfPrimitives())
827 fCanvas->GetListOfPrimitives()->Add(fTopVolume);
828
829 if (fGLViewer) {
830 fGLViewer->UpdateScene();
831 if(resetCamera)
832 fGLViewer->ResetCurrentCamera();
833 }
834}
835
836////////////////////////////////////////////////////////////////////////////////
837/// Update button slot. Updates scene
838
843
844////////////////////////////////////////////////////////////////////////////////
845/// Refresh information in labels when user put mouse over object
846
848{
849 fNodeNameLabel->SetText(node->GetName());
850 fNodeTypelabel->SetText(node->GetTypeName());
851
852 TString name = "Members: ";
853 name += node->GetMembersCount();
854 fMembersCountLabel->SetText(name);
855 name = "All members: ";
856 name += node->GetAllMembersCount();
857 fAllMembersCountLabel->SetText(name);
858 name = "Level: ";
859 name += node->GetLevel();
860 fLevelLabel->SetText(name);
861 name = "Size: ";
862 name += node->GetSize();
863 fSizeLabel->SetText(name);
864 name = "Total size: ";
865 name += node->GetTotalSize();
866 fTotalSizeLabel->SetText(name);
867}
868
869////////////////////////////////////////////////////////////////////////////////
870/// UndoButton Slot. Activated when user press Undo button. Restore last top node pointer.
871
873{
874 fRedoList.Add(fNodePtr);
875 fRedoButton->SetEnabled(true);
876 fNodePtr = (TStructNode*) fUndoList.Last();
877 fUndoList.RemoveLast();
878 if (!fUndoList.First()) {
879 fUndoButton->SetEnabled(false);
880 }
881 Update(kTRUE);
883}
884
885////////////////////////////////////////////////////////////////////////////////
886/// Activated when user press radio button
887
889{
890 if (fAutoRefesh->IsOn()) {
891 Update();
892 }
893}
@ kButtonPress
Definition GuiTypes.h:61
@ kMotionNotify
Definition GuiTypes.h:62
@ kFixedWidth
Definition GuiTypes.h:388
@ kHorizontalFrame
Definition GuiTypes.h:383
ULong_t Pixel_t
Pixel value.
Definition GuiTypes.h:41
#define h(i)
Definition RSha256.hxx:106
int Int_t
Signed integer 4 bytes (int).
Definition RtypesCore.h:59
long Longptr_t
Integer large enough to hold a pointer (platform-dependent).
Definition RtypesCore.h:89
unsigned int UInt_t
Unsigned integer 4 bytes (unsigned int).
Definition RtypesCore.h:60
unsigned long ULong_t
Unsigned long integer 4 bytes (unsigned long). Size depends on architecture.
Definition RtypesCore.h:69
long Long_t
Signed long integer 4 bytes (long). Size depends on architecture.
Definition RtypesCore.h:68
bool Bool_t
Boolean (0=false, 1=true) (bool).
Definition RtypesCore.h:77
float Float_t
Float 4 bytes (float).
Definition RtypesCore.h:71
constexpr Bool_t kTRUE
Definition RtypesCore.h:107
const char Option_t
Option string (const char).
Definition RtypesCore.h:80
externTApplication * gApplication
@ kButtonDown
Definition TGButton.h:54
@ kButtonUp
Definition TGButton.h:53
@ kDeepCleanup
Definition TGFrame.h:42
@ kLHintsExpandY
Definition TGLayout.h:31
@ kLHintsLeft
Definition TGLayout.h:24
@ kLHintsExpandX
Definition TGLayout.h:30
char name[80]
Definition TGX11.cxx:148
externTGeoManager * gGeoManager
const Bool_t kSortDescending
Definition TList.h:32
#define gROOT
Definition TROOT.h:417
char * Form(const char *fmt,...)
Formats a string in a circular formatting buffer.
Definition TString.cxx:2496
@ kSize
Definition TStructNode.h:26
@ kMembers
Definition TStructNode.h:27
@ kCollection
Definition TStructNode.h:21
Color * colors
Definition X3DBuffer.c:21
The Canvas class.
Definition TCanvas.h:23
TClass instances represent classes, structs and namespaces in the ROOT type system.
Definition TClass.h:84
static TClass * GetClass(const char *name, Bool_t load=kTRUE, Bool_t silent=kFALSE)
Static method returning pointer to TClass of the specified class name.
Definition TClass.cxx:2994
virtual void AddAll(const TCollection *col)
Add all objects from collection col to this collection.
Int_t GetNumber() const
Definition TColor.h:59
Selects different options.
Definition TGButton.h:264
Like a checkbutton but instead of the check mark there is color area with a little down arrow.
TGDimension GetDefaultSize() const override
std::cout << fWidth << "x" << fHeight << std::endl;
Definition TGFrame.h:318
virtual void AddFrame(TGFrame *f, TGLayoutHints *l=nullptr)
Add frame to the composite frame using the specified layout hints.
Definition TGFrame.cxx:1109
void MapSubwindows() override
Map all sub windows that are part of the composite frame.
Definition TGFrame.cxx:1156
TGCompositeFrame(const TGCompositeFrame &)=delete
void SetCleanup(Int_t mode=kLocalCleanup) override
Turn on automatic cleanup of child frames in dtor.
Definition TGFrame.cxx:1064
void Resize(UInt_t w=0, UInt_t h=0) override
Resize the frame.
Definition TGFrame.cxx:597
void MapWindow() override
map window
Definition TGFrame.h:206
virtual void DeleteWindow()
Delete window.
Definition TGFrame.cxx:268
A composite frame with a border and a title.
Definition TGFrame.h:532
A composite frame that layout their children in horizontal way.
Definition TGFrame.h:387
Minimal GL-viewer that can be embedded in a standard ROOT frames.
TObject * ID() const
Concrete physical shape - a GL drawable.
const TGLLogicalShape * GetLogical() const
@ kCameraPerspXOY
Definition TGLViewer.h:61
This class handles GUI labels.
Definition TGLabel.h:24
This class describes layout hints used by the layout classes.
Definition TGLayout.h:50
TGMainFrame(const TGMainFrame &)=delete
void SetWindowName(const char *name=nullptr) override
Set window name. This is typically done via the window manager.
Definition TGFrame.cxx:1780
void SetWMSizeHints(UInt_t wmin, UInt_t hmin, UInt_t wmax, UInt_t hmax, UInt_t winc, UInt_t hinc)
Give the window manager minimum and maximum size hints.
Definition TGFrame.cxx:1898
TGNumberEntry is a number entry input widget with up/down buttons.
@ kNELLimitMin
Lower limit only.
Selects different options.
Definition TGButton.h:321
A tab widget contains a set of composite frames each with a little tab with a name (like a set of fol...
Definition TGTab.h:46
virtual TGCompositeFrame * AddTab(TGString *text)
Add a tab to the tab widget.
Definition TGTab.cxx:373
Yield an action as soon as it is clicked.
Definition TGButton.h:142
A TGTextEntry is a one line text input widget.
Definition TGTextEntry.h:24
A tooltip can be a one or multiple lines help text that is displayed in a window when the mouse curso...
Definition TGToolTip.h:24
Organizes TGButton widgets in a group with one vertical column.
void SetFrame(TGFrame *frame, Bool_t left) override
Set frame to be resized.
A composite frame that layout their children in vertical way.
Definition TGFrame.h:376
ROOT GUI Window base class.
Definition TGWindow.h:23
The manager class for any TGeo geometry.
Definition TGeoManager.h:46
Base class describing materials.
Media are used to store properties related to tracking and which are useful only when using geometry ...
Definition TGeoMedium.h:23
Class describing translations.
Definition TGeoMatrix.h:117
TGeoVolume, TGeoVolumeMulti, TGeoVolumeAssembly are the volume classes.
Definition TGeoVolume.h:43
void SetLineWidth(Width_t lwidth) override
Set the line width.
virtual void AddNodeOverlap(TGeoVolume *vol, Int_t copy_no, TGeoMatrix *mat=nullptr, Option_t *option="")
Add a TGeoNode to the list of nodes.
void SetLineColor(Color_t lcolor) override
Set the line color.
void Reset()
A doubly linked list.
Definition TList.h:38
void Add(TObject *obj) override
Definition TList.h:81
TObject * First() const override
Return the first object in the list. Returns 0 when list is empty.
Definition TList.cxx:789
virtual void Sort(Bool_t order=kSortAscending)
Sort linked list.
Definition TList.cxx:1067
const char * GetName() const override
Returns name of object.
Definition TNamed.h:49
static TClass * Class()
Bool_t Connect(const char *signal, const char *receiver_class, void *receiver, const char *slot)
Non-static method is used to connect from the signal of this object to the receiver slot.
Definition TQObject.cxx:865
virtual void RemoveFirst()
Basic string class.
Definition TString.h:138
Ssiz_t Length() const
Definition TString.h:425
Bool_t EndsWith(const char *pat, ECaseCompare cmp=kExact) const
Return true if string ends with the specified string.
Definition TString.cxx:2250
const char * Data() const
Definition TString.h:384
TString & Remove(Ssiz_t pos)
Definition TString.h:694
TColor GetColor() const
Returns color of class.
void SetColor(const TColor &color)
Sets the color to "color".
const char * GetName() const override
Returns name of object.
ULong_t GetAllMembersCount() const
Returns number of all members in node.
void SetY(Float_t y)
Sets Y coordinate to "y".
ULong_t GetSize() const
Returns size of node.
TString GetTypeName() const
Returns name of class.
void SetX(Float_t x)
Sets X coordinate to "x".
void SetWidth(Float_t w)
Sets width of outlining box to "w".
void SetCollapsed(Bool_t collapsed)
Sets collapsing of node to "collapse".
ULong_t GetMembersCount() const
Returns numbers of members of node.
bool IsVisible() const
Returns true if node is visible.
Float_t GetCenter() const
Returns center of outlining box on x-axis.
ULong_t GetVolume() const
Returns size or number of members.
Float_t GetY() const
Returns Y coordinate.
void SetVisible(bool visible)
Sets visibility of node to "visible".
TList * GetMembers() const
Returns list with pointers to daughter nodes.
Float_t GetWidth() const
Returns width of outlining box.
Float_t GetVolumeRatio()
Returns ratio - volme of node to area taken by outlining box.
static void SetScaleBy(EScalingType type)
Sets scaling by to "type".
Float_t GetX() const
Returns X coordinate.
Float_t GetRelativeVolumeRatio()
Returns ratio - relative volume to area taken by utlining box.
Float_t GetMiddle() const
Returns center of outlining box on y-axis.
ENodeType GetNodeType() const
Returns type of node.
void SetHeight(Float_t h)
Sets width of outlining box to "w".
Float_t GetHeight() const
Returns height of outlining box.
UInt_t GetLevel() const
Returns actual level of node.
ULong_t GetTotalSize() const
Returns total size of allocated memory in bytes.
Bool_t IsCollapsed() const
Returns true if node is colllapsed.
TGLabel * fTotalSizeLabel
void SetNodePtr(TStructNode *val)
Sets top node pointer and updates view.
TGLabel * fAllMembersCountLabel
void ResetButtonSlot()
Resets camera.
TGTextEntry * fPointerTextEntry
~TStructViewerGUI() override
Destructor.
void DrawNode(TStructNode *node)
Creates and draws TGeoVolume from given "node".
void Scale(TStructNode *parent)
Recursive method to scaling all modes on scene.
void RedoButtonSlot()
Activated when user click Redo button. Repeat last Undo action.
TStructNodeProperty * FindNodeProperty(TStructNode *node)
Returns pointer to property associated with node "node".
void ColorSelectedSlot(Pixel_t pixel)
Slot for default color selsect.
TGTextButton * fRedoButton
void BoxHeightValueSetSlot(Long_t h)
Emmited when user changes height of boxes.
TGNumberEntry * fBoxHeightEntry
TGeoVolume * fTopVolume
TStructNode * fSelectedObject
TGRadioButton * fScaleByMembersButton
TStructNode * GetNodePtr() const
Returns top node pointer.
void CheckMaxObjects(TStructNode *parent)
Check if all of nodes can be displayed on scene. Hides redendant nodes.
TGLabel * fMembersCountLabel
void UpdateLabels(TStructNode *node)
Refresh information in labels when user put mouse over object.
void UpdateButtonSlot()
Update button slot. Updates scene.
void MouseOverSlot(TGLPhysicalShape *shape)
MouseOver slot.
Bool_t GetLinksVisibility() const
Returns true if links are visible, otherwise return false.
void DrawLink(TStructNode *parent)
Recursive method to draw links.
void SetLinksVisibility(Bool_t val)
Sets links visibility to "visible".
TGNumberEntry * fLevelDistanceEntry
static UInt_t fgCounter
void AutoRefreshButtonSlot(Bool_t on)
Activated when user chage condition.
TGCheckButton * fAutoRefesh
void DoubleClickedSlot()
Activated when user double click on objects on 3D scene.
void UnCheckMaxObjects()
Shows hidden nodes.
TGTextButton * fUndoButton
TStructNodeProperty * GetDefaultColor()
Return default color for nodes.
void DrawVolumes(TStructNode *visObj)
Recursive method to draw GeoVolumes.
void LevelDistValueSetSlot(Long_t dist)
Emmited when user changes distance between levels.
TGRadioButton * fScaleBySizeButton
Int_t GetColor(TStructNode *node)
Returns color form fColors for given "node".
TGLEmbeddedViewer * fGLViewer
TStructNodeEditor * fEditor
static TGeoMedium * fgMedium
void ScaleByChangedSlot()
Activated when user press radio button.
TStructViewerGUI(TStructViewer *parent, TStructNode *nodePtr, TList *colors, const TGWindow *p=nullptr, UInt_t w=800, UInt_t h=600)
Constructs window with "w" as width, "h" as height and given parent "p".
TGTextEntry * fPointerTypeTextEntry
void CloseWindow() override
Delete window.
void UndoButtonSlot()
UndoButton Slot. Activated when user press Undo button. Restore last top node pointer.
void Draw(Option_t *option="") override
Check limits and draws nodes and links.
void GLWidgetProcessedEventSlot(Event_t *event)
Handle events. Sets fMouseX and fMouseY when user move a mouse over viewer and hides ToolTip.
void ShowLinksToggled(Bool_t on)
Changes links visibility and refresh view.
void SetPointerButtonSlot()
Sets pointer given in fPointerTestEntry to the main pointer.
void Divide(TList *list, Float_t x1, Float_t x2, Float_t y1, Float_t y2)
Divides rectangle where the outlining box is placed.
TStructViewer * fParent
TGCheckButton * fShowLinksCheckButton
void CalculatePosistion(TStructNode *parent)
Recursive method to calculating nodes posistion in 3D space.
void Update(Bool_t resetCamera=false)
Updates view. Clear all the nodes, call draw function and update scene. Doesn't reset camera.
TStructNode * fNodePtr
Double_t Sqrt(Double_t x)
Returns the square root of x.
Definition TMath.h:673
Short_t Min(Short_t a, Short_t b)
Returns the smallest of a and b.
Definition TMathBase.h:197
Event structure.
Definition GuiTypes.h:175
EGEventType fType
of event (see EGEventType)
Definition GuiTypes.h:176
th1 Draw()
TLine l
Definition textangle.C:4
static uint64_t sum(uint64_t i)
Definition Factory.cxx:2338