Logo ROOT  
Reference Guide
REveManager.cxx
Go to the documentation of this file.
1// @(#)root/eve7:$Id$
2// Authors: Matevz Tadel & Alja Mrak-Tadel: 2006, 2007
3
4/*************************************************************************
5 * Copyright (C) 1995-2019, 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 <ROOT/REveManager.hxx>
13
14#include <ROOT/REveUtil.hxx>
16#include <ROOT/REveViewer.hxx>
17#include <ROOT/REveScene.hxx>
19#include <ROOT/REveClient.hxx>
20#include <ROOT/RWebWindow.hxx>
21#include <ROOT/RFileDialog.hxx>
22#include <ROOT/RLogger.hxx>
23#include <ROOT/REveSystem.hxx>
24
25#include "TGeoManager.h"
26#include "TGeoMatrix.h"
27#include "TObjString.h"
28#include "TROOT.h"
29#include "TSystem.h"
30#include "TFile.h"
31#include "TMap.h"
32#include "TExMap.h"
33#include "TEnv.h"
34#include "TColor.h"
35#include "TPRegexp.h"
36#include "TClass.h"
37#include "TMethod.h"
38#include "TMethodCall.h"
39#include "THttpServer.h"
40#include "TTimer.h"
41#include "TApplication.h"
42
43#include <fstream>
44#include <sstream>
45#include <iostream>
46#include <regex>
47
48#include <nlohmann/json.hpp>
49
50using namespace ROOT::Experimental;
51namespace REX = ROOT::Experimental;
52
53REveManager *REX::gEve = nullptr;
54
56{
57 std::vector<REveScene*> addedWatch;
58 std::vector<REveScene*> removedWatch;
59
60 void reset() {
61 addedWatch.clear();
62 removedWatch.clear();
63 }
64};
65
66thread_local std::vector<RLogEntry> gEveLogEntries;
68
69/** \class REveManager
70\ingroup REve
71Central application manager for Eve.
72Manages elements, GUI, GL scenes and GL viewers.
73
74Following parameters can be specified in .rootrc file
75
76WebEve.GLViewer: Three # kind of GLViewer, either Three, JSRoot or RCore
77WebEve.DisableShow: 1 # do not start new web browser when REveManager::Show is called
78WebEve.HTimeout: 200 # timeout in ms for elements highlight
79WebEve.DblClick: Off # mouse double click handling in GL viewer: Off or Reset
80WebEve.TableRowHeight: 33 # size of each row in pixels in the Table view, can be used to make design more compact
81*/
82
83////////////////////////////////////////////////////////////////////////////////
84
85REveManager::REveManager()
86 : // (Bool_t map_window, Option_t* opt) :
87 fExcHandler(nullptr), fVizDB(nullptr), fVizDBReplace(kTRUE), fVizDBUpdate(kTRUE), fGeometries(nullptr),
88 fGeometryAliases(nullptr),
89 fKeepEmptyCont(kFALSE)
90{
91 // Constructor.
92
93 static const REveException eh("REveManager::REveManager ");
94
95 if (REX::gEve)
96 throw eh + "There can be only one REve!";
97
98 REX::gEve = this;
99
101 fServerStatus.fTStart = std::time(nullptr);
102
104
105 fGeometries = new TMap;
109 fVizDB = new TMap;
111
112 fElementIdMap[0] = nullptr; // do not increase count for null element.
113
114 fWorld = new REveScene("EveWorld", "Top-level Eve Scene");
117
118 fSelectionList = new REveElement("Selection List");
119 fSelectionList->SetChildClass(TClass::GetClass<REveSelection>());
122 fSelection = new REveSelection("Global Selection", "", kRed, kViolet);
123 fSelection->SetIsMaster(true);
126 fHighlight = new REveSelection("Global Highlight", "", kGreen, kCyan);
127 fHighlight->SetIsMaster(true);
131
132 fViewers = new REveViewerList("Viewers");
135
136 fScenes = new REveSceneList("Scenes");
139
140 fGlobalScene = new REveScene("Geometry scene");
143
144 fEventScene = new REveScene("Event scene");
147
148 {
149 REveViewer *v = SpawnNewViewer("Default Viewer");
150 v->AddScene(fGlobalScene);
151 v->AddScene(fEventScene);
152 }
153
154 // !!! AMT increase threshold to enable color pick on client
156
158 fWebWindow->UseServerThreads();
159 fWebWindow->SetDefaultPage("file:rootui5sys/eve7/index.html");
160
161 const char *gl_viewer = gEnv->GetValue("WebEve.GLViewer", "RCore");
162 const char *gl_dblclick = gEnv->GetValue("WebEve.DblClick", "Off");
163 Int_t htimeout = gEnv->GetValue("WebEve.HTimeout", 250);
164 Int_t table_row_height = gEnv->GetValue("WebEve.TableRowHeight", 0);
165 fWebWindow->SetUserArgs(Form("{ GLViewer: \"%s\", DblClick: \"%s\", HTimeout: %d, TableRowHeight: %d }", gl_viewer,
166 gl_dblclick, htimeout, table_row_height));
167
168 if (strcmp(gl_viewer, "RCore") == 0)
169 fIsRCore = true;
170
171 // this is call-back, invoked when message received via websocket
172 fWebWindow->SetCallBacks([this](unsigned connid) { WindowConnect(connid); },
173 [this](unsigned connid, const std::string &arg) { WindowData(connid, arg); },
174 [this](unsigned connid) { WindowDisconnect(connid); });
175 fWebWindow->SetGeometry(900, 700); // configure predefined window geometry
176 fWebWindow->SetConnLimit(100); // maximal number of connections
177 fWebWindow->SetMaxQueueLength(1000); // number of allowed entries in the window queue
178
179 fMIRExecThread = std::thread{[this] { MIRExecThread(); }};
180
181 // activate interpreter error report
182 gInterpreter->ReportDiagnosticsToErrorHandler();
184}
185
186////////////////////////////////////////////////////////////////////////////////
187/// Destructor.
188
190{
191 fMIRExecThread.join();
192
193 // QQQQ How do we stop THttpServer / fWebWindow?
194
199 // Not needed - no more top-items: fScenes->Destroy();
200 fScenes = nullptr;
201
204 // Not needed - no more top-items: fViewers->Destroy();
205 fViewers = nullptr;
206
207 // fWindowManager->DestroyWindows();
208 // fWindowManager->DecDenyDestroy();
209 // fWindowManager->Destroy();
210 // fWindowManager = 0;
211
214
215 delete fGeometryAliases;
216 delete fGeometries;
217 delete fVizDB;
218 delete fExcHandler;
219}
220
221////////////////////////////////////////////////////////////////////////////////
222/// Create a new GL viewer.
223
224REveViewer *REveManager::SpawnNewViewer(const char *name, const char *title)
225{
226 REveViewer *v = new REveViewer(name, title);
228 return v;
229}
230
231////////////////////////////////////////////////////////////////////////////////
232/// Create a new scene.
233
234REveScene *REveManager::SpawnNewScene(const char *name, const char *title)
235{
236 REveScene *s = new REveScene(name, title);
238 return s;
239}
240
242{
243 printf("REveManager::RegisterRedraw3D() obsolete\n");
244}
245
246////////////////////////////////////////////////////////////////////////////////
247/// Perform 3D redraw of scenes and viewers whose contents has
248/// changed.
249
251{
252 printf("REveManager::DoRedraw3D() obsolete\n");
253}
254
255////////////////////////////////////////////////////////////////////////////////
256/// Perform 3D redraw of all scenes and viewers.
257
258void REveManager::FullRedraw3D(Bool_t /*resetCameras*/, Bool_t /*dropLogicals*/)
259{
260 printf("REveManager::FullRedraw3D() obsolete\n");
261}
262
263////////////////////////////////////////////////////////////////////////////////
264/// Clear all selection objects. Can make things easier for EVE when going to
265/// the next event. Still, destruction os selected object should still work
266/// correctly as long as it is executed within a change cycle.
267
269{
270 for (auto el : fSelectionList->fChildren) {
271 dynamic_cast<REveSelection *>(el)->ClearSelection();
272 }
273}
274
275////////////////////////////////////////////////////////////////////////////////
276/// Add an element. If parent is not specified it is added into
277/// current event (which is created if does not exist).
278
280{
281 if (parent == nullptr) {
282 // XXXX
283 }
284
285 parent->AddElement(element);
286}
287
288////////////////////////////////////////////////////////////////////////////////
289/// Add a global element, i.e. one that does not change on each
290/// event, like geometry or projection manager.
291/// If parent is not specified it is added to a global scene.
292
294{
295 if (!parent)
296 parent = fGlobalScene;
297
298 parent->AddElement(element);
299}
300
301////////////////////////////////////////////////////////////////////////////////
302/// Remove element from parent.
303
305{
306 parent->RemoveElement(element);
307}
308
309////////////////////////////////////////////////////////////////////////////////
310/// Lookup ElementId in element map and return corresponding REveElement*.
311/// Returns nullptr if the id is not found
312
314{
315 auto it = fElementIdMap.find(id);
316 return (it != fElementIdMap.end()) ? it->second : nullptr;
317}
318
319////////////////////////////////////////////////////////////////////////////////
320/// Assign a unique ElementId to given element.
321
323{
324 static const REveException eh("REveManager::AssignElementId ");
325
327 throw eh + "ElementId map is full.";
328
329next_free_id:
330 while (fElementIdMap.find(++fLastElementId) != fElementIdMap.end())
331 ;
332 if (fLastElementId == 0)
333 goto next_free_id;
334 // MT - alternatively, we could spawn a thread to find next thousand or so ids and
335 // put them in a vector of ranges. Or collect them when they are freed.
336 // Don't think this won't happen ... online event display can run for months
337 // and easily produce 100000 objects per minute -- about a month to use up all id space!
338
339 element->fElementId = fLastElementId;
340 fElementIdMap.insert(std::make_pair(fLastElementId, element));
342}
343
344////////////////////////////////////////////////////////////////////////////////
345/// Activate EVE browser (summary view) for specified element id
346
348{
349 nlohmann::json msg = {};
350 msg["content"] = "BrowseElement";
351 msg["id"] = id;
352
353 fWebWindow->Send(0, msg.dump());
354}
355
356////////////////////////////////////////////////////////////////////////////////
357/// Called from REveElement prior to its destruction so the
358/// framework components (like object editor) can unreference it.
359
361{
362 if (el->fImpliedSelected > 0) {
363 for (auto slc : fSelectionList->fChildren) {
364 REveSelection *sel = dynamic_cast<REveSelection *>(slc);
365 sel->RemoveImpliedSelectedReferencesTo(el);
366 }
367
368 if (el->fImpliedSelected != 0)
369 Error("REveManager::PreDeleteElement", "ImpliedSelected not zero (%d) after cleanup of selections.",
370 el->fImpliedSelected);
371 }
372 // Primary selection deregistration is handled through Niece removal from Aunts.
373
374 if (el->fElementId != 0) {
375 auto it = fElementIdMap.find(el->fElementId);
376 if (it != fElementIdMap.end()) {
377 if (it->second == el) {
378 fElementIdMap.erase(it);
380 } else
381 Error("PreDeleteElement", "element ptr in ElementIdMap does not match the argument element.");
382 } else
383 Error("PreDeleteElement", "element id %u was not registered in ElementIdMap.", el->fElementId);
384 } else
385 Error("PreDeleteElement", "element with 0 ElementId passed in.");
386}
387
388////////////////////////////////////////////////////////////////////////////////
389/// Insert a new visualization-parameter database entry. Returns
390/// true if the element is inserted successfully.
391/// If entry with the same key already exists the behaviour depends on the
392/// 'replace' flag:
393/// - true - The old model is deleted and new one is inserted (default).
394/// Clients of the old model are transferred to the new one and
395/// if 'update' flag is true (default), the new model's parameters
396/// are assigned to all clients.
397/// - false - The old model is kept, false is returned.
398///
399/// If insert is successful, the ownership of the model-element is
400/// transferred to the manager.
401
403{
404 TPair *pair = (TPair *)fVizDB->FindObject(tag);
405 if (pair) {
406 if (replace) {
407 model->IncDenyDestroy();
408 model->SetRnrChildren(kFALSE);
409
410 REveElement *old_model = dynamic_cast<REveElement *>(pair->Value());
411 if (old_model) {
412 while (old_model->HasChildren()) {
413 REveElement *el = old_model->FirstChild();
414 el->SetVizModel(model);
415 if (update) {
416 el->CopyVizParams(model);
418 }
419 }
420 old_model->DecDenyDestroy();
421 }
422 pair->SetValue(dynamic_cast<TObject *>(model));
423 return kTRUE;
424 } else {
425 return kFALSE;
426 }
427 } else {
428 model->IncDenyDestroy();
429 model->SetRnrChildren(kFALSE);
430 fVizDB->Add(new TObjString(tag), dynamic_cast<TObject *>(model));
431 return kTRUE;
432 }
433}
434
435////////////////////////////////////////////////////////////////////////////////
436/// Insert a new visualization-parameter database entry with the default
437/// parameters for replace and update, as specified by members
438/// fVizDBReplace(default=kTRUE) and fVizDBUpdate(default=kTRUE).
439/// See docs of the above function.
440
442{
443 return InsertVizDBEntry(tag, model, fVizDBReplace, fVizDBUpdate);
444}
445
446////////////////////////////////////////////////////////////////////////////////
447/// Find a visualization-parameter database entry corresponding to tag.
448/// If the entry is not found 0 is returned.
449
451{
452 return dynamic_cast<REveElement *>(fVizDB->GetValue(tag));
453}
454
455////////////////////////////////////////////////////////////////////////////////
456/// Load visualization-parameter database from file filename. The
457/// replace, update arguments replace the values of fVizDBReplace
458/// and fVizDBUpdate members for the duration of the macro
459/// execution.
460
462{
463 Bool_t ex_replace = fVizDBReplace;
464 Bool_t ex_update = fVizDBUpdate;
465 fVizDBReplace = replace;
467
469
470 fVizDBReplace = ex_replace;
471 fVizDBUpdate = ex_update;
472}
473
474////////////////////////////////////////////////////////////////////////////////
475/// Load visualization-parameter database from file filename.
476/// State of data-members fVizDBReplace and fVizDBUpdate determine
477/// how the registered entries are handled.
478
480{
482 Redraw3D();
483}
484
485////////////////////////////////////////////////////////////////////////////////
486/// Save visualization-parameter database to file filename.
487
489{
490 TPMERegexp re("(.+)\\.\\w+");
491 if (re.Match(filename) != 2) {
492 Error("SaveVizDB", "filename does not match required format '(.+)\\.\\w+'.");
493 return;
494 }
495
496 TString exp_filename(filename);
497 gSystem->ExpandPathName(exp_filename);
498
499 std::ofstream out(exp_filename, std::ios::out | std::ios::trunc);
500 out << "void " << re[1] << "()\n";
501 out << "{\n";
502 out << " REveManager::Create();\n";
503
505
506 Int_t var_id = 0;
507 TString var_name;
508 TIter next(fVizDB);
509 TObjString *key;
510 while ((key = (TObjString *)next())) {
511 REveElement *mdl = dynamic_cast<REveElement *>(fVizDB->GetValue(key));
512 if (mdl) {
513 var_name.Form("x%03d", var_id++);
514 mdl->SaveVizParams(out, key->String(), var_name);
515 } else {
516 Warning("SaveVizDB", "Saving failed for key '%s'.", key->String().Data());
517 }
518 }
519
520 out << "}\n";
521 out.close();
522}
523
524////////////////////////////////////////////////////////////////////////////////
525/// Get geometry with given filename.
526/// This is cached internally so the second time this function is
527/// called with the same argument the same geo-manager is returned.
528/// gGeoManager is set to the return value.
529
531{
532 static const REveException eh("REveManager::GetGeometry ");
533
534 TString exp_filename = filename;
535 gSystem->ExpandPathName(exp_filename);
536 printf("REveManager::GetGeometry loading: '%s' -> '%s'.\n", filename.Data(), exp_filename.Data());
537
539 if (gGeoManager) {
541 } else {
542 Bool_t locked = TGeoManager::IsLocked();
543 if (locked) {
544 Warning("REveManager::GetGeometry", "TGeoManager is locked ... unlocking it.");
546 }
547 if (TGeoManager::Import(filename) == 0) {
548 throw eh + "TGeoManager::Import() failed for '" + exp_filename + "'.";
549 }
550 if (locked) {
552 }
553
555
556 // Import colors exported by Gled, if they exist.
557 {
558 TFile f(exp_filename, "READ");
559 TObjArray *collist = (TObjArray *)f.Get("ColorList");
560 f.Close();
561 if (collist) {
563 TGeoVolume *vol;
564 while ((vol = (TGeoVolume *)next()) != nullptr) {
565 Int_t oldID = vol->GetLineColor();
566 TColor *col = (TColor *)collist->At(oldID);
567 Float_t r, g, b;
568 col->GetRGB(r, g, b);
569 Int_t newID = TColor::GetColor(r, g, b);
570 vol->SetLineColor(newID);
571 }
572 }
573 }
574
576 }
577 return gGeoManager;
578}
579
580////////////////////////////////////////////////////////////////////////////////
581/// Get geometry with given alias.
582/// The alias must be registered via RegisterGeometryAlias().
583
585{
586 static const REveException eh("REveManager::GetGeometry ");
587
588 TObjString *full_name = (TObjString *)fGeometryAliases->GetValue(alias);
589 if (!full_name)
590 throw eh + "geometry alias '" + alias + "' not registered.";
591 return GetGeometry(full_name->String());
592}
593
594////////////////////////////////////////////////////////////////////////////////
595/// Get the default geometry.
596/// It should be registered via RegisterGeometryName("Default", `<URL>`).
597
599{
600 return GetGeometryByAlias("Default");
601}
602
603////////////////////////////////////////////////////////////////////////////////
604/// Register 'name' as an alias for geometry file 'filename'.
605/// The old aliases are silently overwritten.
606/// After that the geometry can be retrieved also by calling:
607/// REX::gEve->GetGeometryByName(name);
608
610{
612}
613
614////////////////////////////////////////////////////////////////////////////////
615/// Work-around uber ugly hack used in SavePrimitive and co.
616
618{
619 TIter nextcl(gROOT->GetListOfClasses());
620 TClass *cls;
621 while ((cls = (TClass *)nextcl())) {
623 }
624}
625
626////////////////////////////////////////////////////////////////////////////////
627/// Register new directory to THttpServer
628// For example: AddLocation("mydir/", "/test/EveWebApp/ui5");
629//
630void REveManager::AddLocation(const std::string &locationName, const std::string &path)
631{
632 fWebWindow->GetServer()->AddLocation(locationName.c_str(), path.c_str());
633}
634
635////////////////////////////////////////////////////////////////////////////////
636/// Set content of default window HTML page
637// Got example: SetDefaultHtmlPage("file:currentdir/test.html")
638//
639void REveManager::SetDefaultHtmlPage(const std::string &path)
640{
641 fWebWindow->SetDefaultPage(path.c_str());
642}
643
644////////////////////////////////////////////////////////////////////////////////
645/// Set client version, used as prefix in scripts URL
646/// When changed, web browser will reload all related JS files while full URL will be different
647/// Default is empty value - no extra string in URL
648/// Version should be string like "1.2" or "ver1.subv2" and not contain any special symbols
649void REveManager::SetClientVersion(const std::string &version)
650{
651 fWebWindow->SetClientVersion(version);
652}
653
654////////////////////////////////////////////////////////////////////////////////
655/// If global REveManager* REX::gEve is not set initialize it.
656/// Returns REX::gEve.
657
659{
660 static const REveException eh("REveManager::Create ");
661
662 if (!REX::gEve) {
663 // XXXX Initialize some server stuff ???
664
665 REX::gEve = new REveManager();
666 }
667 return REX::gEve;
668}
669
670////////////////////////////////////////////////////////////////////////////////
671/// Properly terminate global REveManager.
672
674{
675 if (!REX::gEve)
676 return;
677
678 delete REX::gEve;
679 REX::gEve = nullptr;
680}
681
683{
684 class XThreadTimer : public TTimer {
685 std::function<void()> foo_;
686 public:
687 XThreadTimer(std::function<void()> f) : foo_(f)
688 {
689 SetTime(0);
691 gSystem->AddTimer(this);
692 }
693 Bool_t Notify() override
694 {
695 foo_();
696 gSystem->RemoveTimer(this);
697 delete this;
698 return kTRUE;
699 }
700 };
701
702 new XThreadTimer(func);
703}
704
706{
708 // QQQQ Should call Terminate() but it needs to:
709 // - properly stop MIRExecThread;
710 // - shutdown civet/THttp/RWebWindow
712 });
713}
714
715////////////////////////////////////////////////////////////////////////////////
716/// Process new connection from web window
717
718void REveManager::WindowConnect(unsigned connid)
719{
720 std::unique_lock<std::mutex> lock(fServerState.fMutex);
721
723 {
724 fServerState.fCV.wait(lock);
725 }
726
727 fConnList.emplace_back(connid);
728 printf("connection established %u\n", connid);
729
730 // QQQQ do we want mir-time here as well? maybe set it at the end of function?
731 // Note, this is all under lock, so nobody will get state out in between.
732 fServerStatus.fTLastMir = fServerStatus.fTLastConnect = std::time(nullptr);
734
735 // This prepares core and render data buffers.
736 printf("\nEVEMNG ............. streaming the world scene.\n");
737
738 fWorld->AddSubscriber(std::make_unique<REveClient>(connid, fWebWindow));
740
741 printf(" sending json, len = %d\n", (int)fWorld->fOutputJson.size());
742 Send(connid, fWorld->fOutputJson);
743 printf(" for now assume world-scene has no render data, binary-size=%d\n", fWorld->fTotalBinarySize);
744 assert(fWorld->fTotalBinarySize == 0);
745
746 for (auto &c : fScenes->RefChildren()) {
747 REveScene *scene = dynamic_cast<REveScene *>(c);
748 if (!scene->GetMandatory())
749 continue;
750
751 scene->AddSubscriber(std::make_unique<REveClient>(connid, fWebWindow));
752 printf("\nEVEMNG ............. streaming scene %s [%s]\n", scene->GetCTitle(), scene->GetCName());
753
754 // This prepares core and render data buffers.
755 scene->StreamElements();
756
757 printf(" sending json, len = %d\n", (int)scene->fOutputJson.size());
758 Send(connid, scene->fOutputJson);
759
760 if (scene->fTotalBinarySize > 0) {
761 printf(" sending binary, len = %d\n", scene->fTotalBinarySize);
762 SendBinary(connid, &scene->fOutputBinary[0], scene->fTotalBinarySize);
763 } else {
764 printf(" NOT sending binary, len = %d\n", scene->fTotalBinarySize);
765 }
766 }
767
768 fServerState.fCV.notify_all();
769}
770
771////////////////////////////////////////////////////////////////////////////////
772/// Process disconnect of web window
773
774void REveManager::WindowDisconnect(unsigned connid)
775{
776 std::unique_lock<std::mutex> lock(fServerState.fMutex);
777 auto conn = fConnList.end();
778 for (auto i = fConnList.begin(); i != fConnList.end(); ++i) {
779 if (i->fId == connid) {
780 conn = i;
781 break;
782 }
783 }
784 // this should not happen, just check
785 if (conn == fConnList.end()) {
786 printf("error, connection not found!");
787 } else {
788 printf("connection closed %u\n", connid);
789 fConnList.erase(conn);
790 for (auto &c : fScenes->RefChildren()) {
791 REveScene *scene = dynamic_cast<REveScene *>(c);
792 scene->RemoveSubscriber(connid);
793 }
794 fWorld->RemoveSubscriber(connid);
795 }
796
797 // User case: someone can close browser tab as clients are updateding
798 // note if scene changes are in progess the new serverstate will be changes after finish those
800 {
802 }
803
804 fServerStatus.fTLastDisconnect = std::time(nullptr);
806
807 fServerState.fCV.notify_all();
808}
809
810////////////////////////////////////////////////////////////////////////////////
811/// Process data from web window
812
813void REveManager::WindowData(unsigned connid, const std::string &arg)
814{
815 static const REveException eh("REveManager::WindowData ");
816
817 // find connection object
818 bool found = false;
819 for (auto &conn : fConnList) {
820 if (conn.fId == connid) {
821 found = true;
822 break;
823 }
824 }
825
826 // this should not happen, just check
827 if (!found) {
828 R__LOG_ERROR(REveLog()) << "Internal error - no connection with id " << connid << " found";
829 return;
830 }
831
832
833 if (arg.compare("__REveDoneChanges") == 0)
834 {
835 // client status data
836 std::unique_lock<std::mutex> lock(fServerState.fMutex);
837
838 for (auto &conn : fConnList) {
839 if (conn.fId == connid) {
840 conn.fState = Conn::Free;
841 break;
842 }
843 }
844
847 fServerState.fCV.notify_all();
848 }
849
850 return;
851 }
852 else if (arg.compare( 0, 10, "FILEDIALOG") == 0)
853 {
854 // file dialog
856 return;
857 }
858
859 nlohmann::json cj = nlohmann::json::parse(arg);
860 if (gDebug > 0)
861 ::Info("REveManager::WindowData", "MIR test %s\n", cj.dump().c_str());
862
863 std::string cmd = cj["mir"];
864 int id = cj["fElementId"];
865 std::string ctype = cj["class"];
866
867 ScheduleMIR(cmd, id, ctype, connid);
868}
869
870//
871//____________________________________________________________________
872void REveManager::ScheduleMIR(const std::string &cmd, ElementId_t id, const std::string& ctype, unsigned connid)
873{
874 std::unique_lock<std::mutex> lock(fServerState.fMutex);
875 fServerStatus.fTLastMir = std::time(nullptr);
876 fMIRqueue.push(std::shared_ptr<MIR>(new MIR(cmd, id, ctype, connid)));
877
878 if (fMIRqueue.size() > 5)
879 std::cout << "Warning, REveManager::ScheduleMIR(). queue size " << fMIRqueue.size() << std::endl;
880
882 fServerState.fCV.notify_all();
883}
884
885//
886//____________________________________________________________________
887void REveManager::ExecuteMIR(std::shared_ptr<MIR> mir)
888{
889 static const REveException eh("REveManager::ExecuteMIR ");
890
891 //if (gDebug > 0)
892 ::Info("REveManager::ExecuteCommand", "MIR cmd %s", mir->fCmd.c_str());
893
894 try {
895 REveElement *el = FindElementById(mir->fId);
896 if ( ! el) throw eh + "Element with id " + mir->fId + " not found";
897
898 static const std::regex cmd_re("^(\\w[\\w\\d]*)\\(\\s*(.*)\\s*\\)\\s*;?\\s*$", std::regex::optimize);
899 std::smatch m;
900 std::regex_search(mir->fCmd, m, cmd_re);
901 if (m.size() != 3)
902 throw eh + "Command string parse error: '" + mir->fCmd + "'.";
903
904 static const TClass *elem_cls = TClass::GetClass<REX::REveElement>();
905
906 TClass *call_cls = TClass::GetClass(mir->fCtype.c_str());
907 if ( ! call_cls)
908 throw eh + "Class '" + mir->fCtype + "' not found.";
909
910 void *el_casted = call_cls->DynamicCast(elem_cls, el, false);
911 if ( ! el_casted)
912 throw eh + "Dynamic cast from REveElement to '" + mir->fCtype + "' failed.";
913
914 std::string tag(mir->fCtype + "::" + m.str(1));
915 std::shared_ptr<TMethodCall> mc;
916
917 auto mmi = fMethCallMap.find(tag);
918 if (mmi != fMethCallMap.end())
919 {
920 mc = mmi->second;
921 }
922 else
923 {
924 const TMethod *meth = call_cls->GetMethodAllAny(m.str(1).c_str());
925 if ( ! meth)
926 throw eh + "Can not find TMethod matching '" + m.str(1) + "'.";
927 mc = std::make_shared<TMethodCall>(meth);
928 fMethCallMap.insert(std::make_pair(tag, mc));
929 }
930
932 mc->Execute(el_casted, m.str(2).c_str());
933
934 // Alternative implementation through Cling. "Leaks" 200 kB per call.
935 // This might be needed for function calls that involve data-types TMethodCall
936 // can not handle.
937 // std::stringstream cmd;
938 // cmd << "((" << mir->fCtype << "*)" << std::hex << std::showbase << (size_t)el << ")->" << mir->fCmd << ";";
939 // std::cout << cmd.str() << std::endl;
940 // gROOT->ProcessLine(cmd.str().c_str());
941 } catch (std::exception &e) {
942 R__LOG_ERROR(REveLog()) << "REveManager::ExecuteCommand " << e.what() << std::endl;
943 } catch (...) {
944 R__LOG_ERROR(REveLog()) << "REveManager::ExecuteCommand unknow execption \n";
945 }
946}
947
948// Write scene change into scenes's internal json member
950{
952
953 for (auto &el : fScenes->RefChildren())
954 {
955 REveScene* s = dynamic_cast<REveScene*>(el);
956 if (s->IsChanged()) s->StreamRepresentationChanges();
957 }
958}
959
960// Send json and binary data to scene's connections
962{
963 // send begin message
964 nlohmann::json jobj = {};
965 jobj["content"] = "BeginChanges";
966 fWebWindow->Send(0, jobj.dump());
967
968 // send the change json
970
971 for (auto &el : fScenes->RefChildren())
972 {
973 REveScene* s = dynamic_cast<REveScene*>(el);
974 s->SendChangesToSubscribers();
975 }
976
977 // send end changes message and log messages
978 jobj["content"] = "EndChanges";
979
980 if (!gEveLogEntries.empty()) {
981 constexpr static int numLevels = static_cast<int>(ELogLevel::kDebug) + 1;
982 constexpr static std::array<const char *, numLevels> sTag{
983 {"{unset-error-level please report}", "FATAL", "Error", "Warning", "Info", "Debug"}};
984
985 jobj["log"] = nlohmann::json::array();
986 std::stringstream strm;
987 for (auto entry : gEveLogEntries) {
988 nlohmann::json item = {};
989 item["lvl"] = entry.fLevel;
990 int cappedLevel = std::min(static_cast<int>(entry.fLevel), numLevels - 1);
991 strm << "Server " << sTag[cappedLevel] << ":";
992
993 if (!entry.fLocation.fFuncName.empty())
994 strm << " " << entry.fLocation.fFuncName;
995 strm << " " << entry.fMessage;
996 item["msg"] = strm.str();
997 jobj["log"].push_back(item);
998 strm.clear();
999 }
1000 gEveLogEntries.clear();
1001 }
1002
1003 fWebWindow->Send(0, jobj.dump());
1004}
1005
1006//
1007//____________________________________________________________________
1009{
1010#if defined(R__LINUX)
1011 pthread_setname_np(pthread_self(), "mir_exec");
1012#endif
1013 while (true)
1014 {
1015 std::unique_lock<std::mutex> lock(fServerState.fMutex);
1016 underlock:
1018 {
1019 fServerState.fCV.wait(lock);
1020 goto underlock;
1021 }
1022 else
1023 {
1024 // set server state and update the queue under lock
1025 //
1027 std::shared_ptr<MIR> mir = fMIRqueue.front();
1028
1029 // reset local thread related data
1030 gMIRData.reset();
1031 fMIRqueue.pop();
1032
1033 lock.unlock();
1034
1035 // allow scenes to accept changes in the element
1037 gEve->GetScenes()->AcceptChanges(true);
1038
1039 ExecuteMIR(mir);
1040
1041 // disable scene's element changing
1042 gEve->GetScenes()->AcceptChanges(false);
1044
1046
1047 // send changes (need to access client connection list) and set the state under lock
1048 //
1049 lock.lock();
1050
1051 // disconnect requested scene from clients
1052 for (auto &scene : gMIRData.removedWatch)
1053 scene->RemoveSubscriber(mir->fConnId);
1054
1055
1056 // connect and stream scenes to new clients
1057 for (auto &scene : gMIRData.addedWatch) {
1058 scene->AddSubscriber(std::make_unique<REveClient>(mir->fConnId, fWebWindow));
1059 scene->StreamElements();
1060 Send(mir->fConnId, scene->fOutputJson);
1061 if (scene->fTotalBinarySize > 0)
1062 SendBinary(mir->fConnId, &scene->fOutputBinary[0], scene->fTotalBinarySize);
1063 }
1064
1066
1068 fServerState.fCV.notify_all();
1069 }
1070 }
1071}
1072
1073//____________________________________________________________________
1075{
1076 for (auto &c : view->RefChildren()) {
1077 REveSceneInfo *sinfo = dynamic_cast<REveSceneInfo *>(c);
1078 std::cout << "Disconnect scee " << sinfo->GetScene()->GetName();
1079 gMIRData.removedWatch.push_back(sinfo->GetScene());
1080 }
1081}
1082//____________________________________________________________________
1084{
1085 view->StampObjProps();
1086 for (auto &c : view->RefChildren()) {
1087 REveSceneInfo *sinfo = dynamic_cast<REveSceneInfo *>(c);
1088 std::cout << "Connect scene " << sinfo->GetScene()->GetName();
1089 gMIRData.addedWatch.push_back(sinfo->GetScene());
1090 }
1091}
1092
1093//____________________________________________________________________
1094void REveManager::Send(unsigned connid, const std::string &data)
1095{
1096 fWebWindow->Send(connid, data);
1097}
1098
1099void REveManager::SendBinary(unsigned connid, const void *data, std::size_t len)
1100{
1101 fWebWindow->SendBinary(connid, data, len);
1102}
1103
1105{
1106 for (auto &conn : fConnList) {
1107 if (conn.fState != Conn::Free)
1108 return false;
1109 }
1110
1111 return true;
1112}
1113
1114// called from REveScene::SendChangesToSubscribers
1116{
1117 for (auto &conn : fConnList) {
1118 if (conn.fId == cinnId)
1119 {
1120 conn.fState = Conn::WaitingResponse;
1121 break;
1122 }
1123 }
1124}
1125
1126//////////////////////////////////////////////////////////////////
1127/// Show eve manager in specified browser.
1128
1129/// If rootrc variable WebEve.DisableShow is set, HTTP server will be
1130/// started and access URL printed on stdout.
1131
1133{
1134 if (gEnv->GetValue("WebEve.DisableShow", 0) != 0) {
1135 std::string url = fWebWindow->GetUrl(true);
1136 printf("EVE URL %s\n", url.c_str());
1137 } else {
1138 fWebWindow->Show(args);
1139 }
1140}
1141
1142
1143//____________________________________________________________________
1145{
1146 // set server state and tag scenes to begin accepting changees
1147 {
1148 std::unique_lock<std::mutex> lock(fServerState.fMutex);
1150 fServerState.fCV.wait(lock);
1151 }
1153 }
1155 GetScenes()->AcceptChanges(true);
1156}
1157
1158//____________________________________________________________________
1160{
1161 // tag scene to disable accepting chages, write the change json
1162 GetScenes()->AcceptChanges(false);
1164
1166
1167 // set new server state under lock
1168 std::unique_lock<std::mutex> lock(fServerState.fMutex);
1171 fServerState.fCV.notify_all();
1172}
1173
1174//____________________________________________________________________
1176{
1177 std::unique_lock<std::mutex> lock(fServerState.fMutex);
1179#if defined(_MSC_VER)
1180 std::timespec_get(&fServerStatus.fTReport, TIME_UTC);
1181#else
1182 fServerStatus.fTReport = std::time_t(nullptr);
1183#endif
1184 st = fServerStatus;
1185}
1186
1187/** \class REveManager::ChangeGuard
1188\ingroup REve
1189RAII guard for locking Eve manager (ctor) and processing changes (dtor).
1190*/
1191
1192//////////////////////////////////////////////////////////////////////
1193//
1194// Helper struct to guard update mechanism
1195//
1197{
1198 gEve->BeginChange();
1199}
1200
1202{
1203 gEve->EndChange();
1204}
1205
1206// Error handler streams error-level messages to client log
1207void REveManager::ErrorHandler(Int_t level, Bool_t abort, const char * location, const char *msg)
1208{
1209 if (level >= kError)
1210 {
1212 entry.fMessage = msg;
1213 gEveLogEntries.emplace_back(entry);
1214 }
1215 ::DefaultErrorHandler(level, abort, location, msg);
1216}
1217
1218/** \class REveManager::RExceptionHandler
1219\ingroup REve
1220Exception handler for Eve exceptions.
1221*/
1222
1223////////////////////////////////////////////////////////////////////////////////
1224/// Handle exceptions deriving from REveException.
1225
1227{
1228 REveException *ex = dynamic_cast<REveException *>(&exc);
1229 if (ex) {
1230 Info("Handle", "Exception %s", ex->what());
1231 // REX::gEve->SetStatusLine(ex->Data());
1232 gSystem->Beep();
1233 return kSEHandled;
1234 }
1235 return kSEProceed;
1236}
1237
1238
1239////////////////////////////////////////////////////////////////////////////////
1240/// Utility to stream loggs to client.
1241
1243{
1244 gEveLogEntries.emplace_back(entry);
1245 return true;
1246}
thread_local MIR_TL_Data_t gMIRData
Definition: REveManager.cxx:67
thread_local std::vector< RLogEntry > gEveLogEntries
Definition: REveManager.cxx:66
#define R__LOG_ERROR(...)
Definition: RLogger.hxx:362
#define f(i)
Definition: RSha256.hxx:104
#define c(i)
Definition: RSha256.hxx:101
#define e(i)
Definition: RSha256.hxx:103
static void update(gsl_integration_workspace *workspace, double a1, double b1, double area1, double error1, double a2, double b2, double area2, double error2)
const Bool_t kFALSE
Definition: RtypesCore.h:101
const Bool_t kTRUE
Definition: RtypesCore.h:100
@ kRed
Definition: Rtypes.h:66
@ kGreen
Definition: Rtypes.h:66
@ kCyan
Definition: Rtypes.h:66
@ kViolet
Definition: Rtypes.h:67
R__EXTERN TApplication * gApplication
Definition: TApplication.h:165
R__EXTERN TEnv * gEnv
Definition: TEnv.h:170
void DefaultErrorHandler(Int_t level, Bool_t abort_bool, const char *location, const char *msg)
The default error handler function.
constexpr Int_t kError
Definition: TError.h:46
void Info(const char *location, const char *msgfmt,...)
Use this function for informational messages.
Definition: TError.cxx:221
void Error(const char *location, const char *msgfmt,...)
Use this function in case an error occurred.
Definition: TError.cxx:188
void Warning(const char *location, const char *msgfmt,...)
Use this function in warning situations.
Definition: TError.cxx:232
ErrorHandlerFunc_t SetErrorHandler(ErrorHandlerFunc_t newhandler)
Set an errorhandler function. Returns the old handler.
Definition: TError.cxx:93
R__EXTERN TEveManager * gEve
Definition: TEveManager.h:243
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void data
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void char Point_t Rectangle_t WindowAttributes_t Float_t Float_t Float_t Int_t Int_t UInt_t UInt_t Rectangle_t Int_t Int_t Window_t TString Int_t GCValues_t GetPrimarySelectionOwner GetDisplay GetScreen GetColormap GetNativeEvent const char const char dpyName wid window const char font_name cursor keysym reg const char only_if_exist regb h Point_t winding char text const char depth char const char Int_t count const char ColorStruct_t color const char filename
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void char Point_t Rectangle_t WindowAttributes_t Float_t Float_t Float_t Int_t Int_t UInt_t UInt_t Rectangle_t Int_t Int_t Window_t TString Int_t GCValues_t GetPrimarySelectionOwner GetDisplay GetScreen GetColormap GetNativeEvent const char const char dpyName wid window const char font_name cursor keysym reg const char only_if_exist regb h Point_t winding char text const char depth char const char Int_t count const char ColorStruct_t color const char Pixmap_t Pixmap_t PictureAttributes_t attr const char char ret_data h unsigned char height h Atom_t Int_t ULong_t ULong_t unsigned char prop_list Atom_t sel
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void char Point_t Rectangle_t WindowAttributes_t Float_t Float_t Float_t b
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void char Point_t Rectangle_t WindowAttributes_t Float_t r
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize id
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void char Point_t Rectangle_t WindowAttributes_t Float_t Float_t Float_t Int_t Int_t UInt_t UInt_t Rectangle_t Int_t Int_t Window_t TString Int_t GCValues_t GetPrimarySelectionOwner GetDisplay GetScreen GetColormap GetNativeEvent const char const char dpyName wid window const char font_name cursor keysym reg const char only_if_exist regb h Point_t winding char text const char depth char const char Int_t count const char ColorStruct_t color const char Pixmap_t Pixmap_t PictureAttributes_t attr const char char ret_data h unsigned char height h Atom_t Int_t ULong_t ULong_t unsigned char prop_list Atom_t Atom_t Atom_t Time_t UChar_t len
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void char Point_t Rectangle_t WindowAttributes_t Float_t Float_t g
char name[80]
Definition: TGX11.cxx:110
R__EXTERN TGeoManager * gGeoManager
Definition: TGeoManager.h:602
R__EXTERN TGeoIdentity * gGeoIdentity
Definition: TGeoMatrix.h:478
R__EXTERN TVirtualMutex * gInterpreterMutex
Definition: TInterpreter.h:46
#define R__LOCKGUARD_CLING(mutex)
Definition: TInterpreter.h:51
#define gInterpreter
Definition: TInterpreter.h:564
Int_t gDebug
Definition: TROOT.cxx:585
#define gROOT
Definition: TROOT.h:406
char * Form(const char *fmt,...)
Formats a string in a circular formatting buffer.
Definition: TString.cxx:2468
R__EXTERN TVirtualMutex * gSystemMutex
Definition: TSystem.h:244
R__EXTERN TSystem * gSystem
Definition: TSystem.h:560
#define R__LOCKGUARD2(mutex)
void DecDenyDestroy()
Decreases the deny-destroy count of the element.
const std::string & GetName() const
void SaveVizParams(std::ostream &out, const TString &tag, const TString &var)
Save visualization parameters for this element with given tag.
const char * GetCTitle() const
const char * GetCName() const
virtual void AddElement(REveElement *el)
Add el to the list of children.
virtual Bool_t SetRnrChildren(Bool_t rnr)
Set render state of this element's children, i.e.
virtual void DestroyElements()
Destroy all children of this element.
REveElement * FirstChild() const
Returns the first child element or 0 if the list is empty.
void IncDenyDestroy()
Increases the deny-destroy count of the element.
virtual void CopyVizParams(const REveElement *el)
Copy visualization parameters from element el.
void SetVizModel(REveElement *model)
Set visualization-parameter model element.
virtual void RemoveElement(REveElement *el)
Remove el from the list of children.
virtual void PropagateVizParamsToProjecteds()
Propagate visualization parameters to dependent elements.
REveException Exception-type thrown by Eve classes.
Definition: REveTypes.hxx:41
bool Emit(const RLogEntry &entry) override
Utility to stream loggs to client.
virtual EStatus Handle(std::exception &exc)
Handle exceptions deriving from REveException.
void DisconnectEveViewer(REveViewer *)
void ScheduleMIR(const std::string &cmd, ElementId_t i, const std::string &ctype, unsigned connid)
void ClearROOTClassSaved()
Work-around uber ugly hack used in SavePrimitive and co.
void RegisterGeometryAlias(const TString &alias, const TString &filename)
Register 'name' as an alias for geometry file 'filename'.
void PreDeleteElement(REveElement *element)
Called from REveElement prior to its destruction so the framework components (like object editor) can...
void ExecuteMIR(std::shared_ptr< MIR > mir)
REveSceneList * GetScenes() const
void ClearAllSelections()
Clear all selection objects.
RExceptionHandler * fExcHandler
exception handler
void AssignElementId(REveElement *element)
Assign a unique ElementId to given element.
TGeoManager * GetDefaultGeometry()
Get the default geometry.
static void ExecuteInMainThread(std::function< void()> func)
void GetServerStatus(REveServerStatus &)
void SetDefaultHtmlPage(const std::string &path)
Set content of default window HTML page.
void AddLocation(const std::string &name, const std::string &path)
Register new directory to THttpServer.
void Send(unsigned connid, const std::string &data)
static void Terminate()
Properly terminate global REveManager.
REveElement * FindElementById(ElementId_t id) const
Lookup ElementId in element map and return corresponding REveElement*.
void SaveVizDB(const TString &filename)
Save visualization-parameter database to file filename.
TGeoManager * GetGeometryByAlias(const TString &alias)
Get geometry with given alias.
std::unordered_map< ElementId_t, REveElement * > fElementIdMap
static REveManager * Create()
If global REveManager* REX::gEve is not set initialize it.
std::unordered_map< std::string, std::shared_ptr< TMethodCall > > fMethCallMap
void WindowConnect(unsigned connid)
Process new connection from web window.
std::vector< Conn > fConnList
REveElement * FindVizDBEntry(const TString &tag)
Find a visualization-parameter database entry corresponding to tag.
TGeoManager * GetGeometry(const TString &filename)
Get geometry with given filename.
void ConnectEveViewer(REveViewer *)
static void ErrorHandler(Int_t level, Bool_t abort, const char *location, const char *msg)
std::shared_ptr< ROOT::Experimental::RWebWindow > fWebWindow
std::queue< std::shared_ptr< MIR > > fMIRqueue
void LoadVizDB(const TString &filename, Bool_t replace, Bool_t update)
Load visualization-parameter database from file filename.
void DoRedraw3D()
Perform 3D redraw of scenes and viewers whose contents has changed.
void SendBinary(unsigned connid, const void *data, std::size_t len)
void AddElement(REveElement *element, REveElement *parent=nullptr)
Add an element.
void SetClientVersion(const std::string &version)
Set client version, used as prefix in scripts URL When changed, web browser will reload all related J...
void AddGlobalElement(REveElement *element, REveElement *parent=nullptr)
Add a global element, i.e.
void Redraw3D(Bool_t resetCameras=kFALSE, Bool_t dropLogicals=kFALSE)
void SceneSubscriberWaitingResponse(unsigned cinnId)
REveScene * SpawnNewScene(const char *name, const char *title="")
Create a new scene.
void RemoveElement(REveElement *element, REveElement *parent)
Remove element from parent.
virtual ~REveManager()
Destructor.
void WindowDisconnect(unsigned connid)
Process disconnect of web window.
void FullRedraw3D(Bool_t resetCameras=kFALSE, Bool_t dropLogicals=kFALSE)
Perform 3D redraw of all scenes and viewers.
REveViewer * SpawnNewViewer(const char *name, const char *title="")
Create a new GL viewer.
Bool_t InsertVizDBEntry(const TString &tag, REveElement *model, Bool_t replace, Bool_t update)
Insert a new visualization-parameter database entry.
REveScene * GetWorld() const
void BrowseElement(ElementId_t id)
Activate EVE browser (summary view) for specified element id.
void WindowData(unsigned connid, const std::string &arg)
Process data from web window.
void Show(const RWebDisplayArgs &args="")
Show eve manager in specified browser.
REveSceneInfo Scene in a viewer.
void DestroyScenes()
Destroy all scenes and their contents.
Definition: REveScene.cxx:490
void AcceptChanges(bool)
Set accept changes flag on all scenes.
Definition: REveScene.cxx:504
void AddSubscriber(std::unique_ptr< REveClient > &&sub)
Definition: REveScene.cxx:67
std::vector< char > fOutputBinary
!
Definition: REveScene.hxx:78
void StreamRepresentationChanges()
Prepare data for sending element changes.
Definition: REveScene.cxx:234
void RemoveSubscriber(unsigned int)
Definition: REveScene.cxx:78
REveSelection Container for selected and highlighted elements.
static void Macro(const char *mac)
Execute macro 'mac'. Do not reload the macro.
Definition: REveUtil.cxx:94
REveViewerList List of Viewers providing common operations on REveViewer collections.
Definition: REveViewer.hxx:71
void AddElement(REveElement *el) override
Call base-class implementation.
Definition: REveViewer.cxx:178
REveViewer Reve representation of TGLViewer.
Definition: REveViewer.hxx:28
static std::shared_ptr< RFileDialog > Embedded(const std::shared_ptr< RWebWindow > &window, const std::string &args)
Create dialog instance to use as embedded dialog inside other widget Embedded dialog started on the c...
A diagnostic that can be emitted by the RLogManager.
Definition: RLogger.hxx:178
Holds different arguments for starting browser with RWebDisplayHandle::Display() method.
static std::shared_ptr< RWebWindow > Create()
Create new RWebWindow Using default RWebWindowsManager.
virtual void Terminate(Int_t status=0)
Terminate the application by call TSystem::Exit() unless application has been told to return from Run...
virtual Color_t GetLineColor() const
Return the line color.
Definition: TAttLine.h:33
TClass instances represent classes, structs and namespaces in the ROOT type system.
Definition: TClass.h:81
void * DynamicCast(const TClass *base, void *obj, Bool_t up=kTRUE)
Cast obj of this class type up to baseclass cl if up is true.
Definition: TClass.cxx:4904
TMethod * GetMethodAllAny(const char *method)
Return pointer to method without looking at parameters.
Definition: TClass.cxx:4373
@ kClassSaved
Definition: TClass.h:95
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:2968
The color creation and management class.
Definition: TColor.h:19
virtual void GetRGB(Float_t &r, Float_t &g, Float_t &b) const
Definition: TColor.h:52
static Int_t GetColor(const char *hexcolor)
Static method returning color number for color specified by hex color string of form: "#rrggbb",...
Definition: TColor.cxx:1823
static void SetColorThreshold(Float_t t)
This method specifies the color threshold used by GetColor to retrieve a color.
Definition: TColor.cxx:1895
virtual Int_t GetValue(const char *name, Int_t dflt) const
Returns the integer value for a resource.
Definition: TEnv.cxx:491
A ROOT file is a suite of consecutive data records (TKey instances) with a well defined format.
Definition: TFile.h:54
An identity transformation.
Definition: TGeoMatrix.h:384
The manager class for any TGeo geometry.
Definition: TGeoManager.h:45
static void UnlockGeometry()
Unlock current geometry.
TObjArray * GetListOfVolumes() const
Definition: TGeoManager.h:493
TObjArray * GetListOfMatrices() const
Definition: TGeoManager.h:490
static Bool_t IsLocked()
Check lock state.
static TGeoManager * Import(const char *filename, const char *name="", Option_t *option="")
static function Import a geometry from a gdml or ROOT file
static void LockGeometry()
Lock current geometry so that no other geometry can be imported.
TGeoVolume * GetTopVolume() const
Definition: TGeoManager.h:532
TGeoVolume, TGeoVolumeMulti, TGeoVolumeAssembly are the volume classes.
Definition: TGeoVolume.h:49
void VisibleDaughters(Bool_t vis=kTRUE)
set visibility for daughters
virtual void SetLineColor(Color_t lcolor)
Set the line color.
TMap implements an associative array of (key,value) pairs using a THashTable for efficient retrieval ...
Definition: TMap.h:40
void Add(TObject *obj) override
This function may not be used (but we need to provide it since it is a pure virtual in TCollection).
Definition: TMap.cxx:54
virtual void SetOwnerKeyValue(Bool_t ownkeys=kTRUE, Bool_t ownvals=kTRUE)
Set ownership for keys and values.
Definition: TMap.cxx:352
TObject * FindObject(const char *keyname) const override
Check if a (key,value) pair exists with keyname as name of the key.
Definition: TMap.cxx:215
TObject * GetValue(const char *keyname) const
Returns a pointer to the value associated with keyname as name of the key.
Definition: TMap.cxx:236
Each ROOT class (see TClass) has a linked list of methods.
Definition: TMethod.h:38
An array of TObjects.
Definition: TObjArray.h:31
TObject * At(Int_t idx) const override
Definition: TObjArray.h:164
Collectable string class.
Definition: TObjString.h:28
TString & String()
Definition: TObjString.h:48
Mother of all ROOT objects.
Definition: TObject.h:41
void ResetBit(UInt_t f)
Definition: TObject.h:200
Wrapper for PCRE library (Perl Compatible Regular Expressions).
Definition: TPRegexp.h:97
Int_t Match(const TString &s, UInt_t start=0)
Runs a match on s against the regex 'this' was created with.
Definition: TPRegexp.cxx:706
Class used by TMap to store (key,value) pairs.
Definition: TMap.h:102
void SetValue(TObject *val)
Definition: TMap.h:122
TObject * Value() const
Definition: TMap.h:121
Basic string class.
Definition: TString.h:136
const char * Data() const
Definition: TString.h:369
void Form(const char *fmt,...)
Formats a string using a printf style format descriptor.
Definition: TString.cxx:2335
void Beep(Int_t freq=-1, Int_t duration=-1, Bool_t setDefault=kFALSE)
Beep for duration milliseconds with a tone of frequency freq.
Definition: TSystem.cxx:327
virtual Bool_t ExpandPathName(TString &path)
Expand a pathname getting rid of special shell characters like ~.
Definition: TSystem.cxx:1277
virtual int GetPid()
Get process id.
Definition: TSystem.cxx:710
virtual void AddTimer(TTimer *t)
Add timer to list of system timers.
Definition: TSystem.cxx:474
virtual int GetProcInfo(ProcInfo_t *info) const
Returns cpu and memory used by this process into the ProcInfo_t structure.
Definition: TSystem.cxx:2490
virtual TTimer * RemoveTimer(TTimer *t)
Remove timer from list of system timers.
Definition: TSystem.cxx:484
Handles synchronous and a-synchronous timer events.
Definition: TTimer.h:51
RVec< PromoteType< T > > trunc(const RVec< T > &v)
Definition: RVec.hxx:1816
Double_t ex[n]
Definition: legend1.C:17
R__EXTERN REveManager * gEve
@ kDebug
Debug information; only useful for developers; can have added verbosity up to 255-kDebug.
RLogChannel & REveLog()
Log channel for Eve diagnostics.
Definition: REveTypes.cxx:47
void(off) SmallVectorTemplateBase< T
void function(const Char_t *name_, T fun, const Char_t *docstring=0)
Definition: RExports.h:167
static constexpr double s
basic_json<> json
Definition: REveElement.hxx:62
std::vector< REveScene * > removedWatch
Definition: REveManager.cxx:58
std::vector< REveScene * > addedWatch
Definition: REveManager.cxx:57
TMarker m
Definition: textangle.C:8