Logo ROOT  
Reference Guide
 
Loading...
Searching...
No Matches
xRooNode_interactive.cxx
Go to the documentation of this file.
1/*
2 * Project: xRooFit
3 * Author:
4 * Will Buttinger, RAL 2022
5 *
6 * Copyright (c) 2022, CERN
7 *
8 * Redistribution and use in source and binary forms,
9 * with or without modification, are permitted according to the terms
10 * listed in LICENSE (http://roofit.sourceforge.net/license.txt)
11 */
12
13// Interactive methods of xRooNode
14
15#include "xRooFit/xRooNode.h"
16
17#include "RooArgList.h"
18#include "RooArgSet.h"
19
20#include "TCanvas.h"
21#include "TVirtualX.h"
22#include "TH1F.h"
23#include "TStyle.h"
24#include "TGraphAsymmErrors.h"
25#include "TMultiGraph.h"
26#include "TSystem.h"
27
29
30void xRooNode::Interactive_Pull()
31{
32 static bool doRestore = false;
33 auto select = dynamic_cast<TGraph *>(gPad->GetSelected());
34 // if (!select) return;
35 int event = gPad->GetEvent();
36 if (event == 1) {
37 doRestore = false;
38 // if this is one of the 'black' points, color it temporarily
39 } else if (event == 11 || doRestore) {
40 if (!select || doRestore) {
41 // now need to assemble a snapshot corresponding to the current variation
42 auto _h = static_cast<TGraph *>(gPad->GetPrimitive("nominal"))->GetHistogram();
43 for (int i = 1; i <= _h->GetNbinsX(); i++) {
44 std::string parName = _h->GetXaxis()->GetBinLabel(i);
45 // ensure point is back .. sometimes editing mode allows point to drift
46 auto _gr = static_cast<TGraph *>(static_cast<TMultiGraph *>(gPad->GetPrimitive("editables"))
47 ->GetListOfGraphs()
48 ->FindObject(parName.c_str()));
49 _gr->SetPoint(0, i - 1, static_cast<TGraph *>(gPad->GetPrimitive("nominal"))->GetPointY(i - 1));
50 }
51 gPad->GetMother()->GetMother()->cd();
52 doRestore = false;
53 return;
54 }
55 doRestore = true;
56 // mouse up event, if this was an original point it needs snapping back
57 // double _y = select->GetPointY(0);
58 TString _name = select->GetName();
59 TString _varyName = "";
60 if (_name.Contains(";")) {
61 _varyName = TString(_name(_name.Index(";") + 1, _name.Length()));
62 _name = _name(0, _name.Index(";"));
63 }
64 auto _h = static_cast<TH1 *>(gPad->GetPrimitive("nominal")->FindObject("scales"));
65 if (!_h)
66 return;
67 for (int i = 1; i <= _h->GetNbinsX(); i++) {
68 if (_name == _h->GetXaxis()->GetBinLabel(i)) {
69 auto _gr = static_cast<TGraph *>(gPad->GetPrimitive("nominal"));
70 if (_varyName == "") {
71 int vNum = 1;
72 TGraphAsymmErrors *newPoint = dynamic_cast<TGraphAsymmErrors *>(
73 gPad->GetPrimitive(TString::Format("%s;variation %d", select->GetName(), vNum)));
74 while (newPoint && newPoint->GetN() > 0) {
75 vNum++;
76 newPoint = static_cast<TGraphAsymmErrors *>(
77 gPad->GetPrimitive(TString::Format("%s;variation %d", select->GetName(), vNum)));
78 }
79 _varyName = TString::Format("variation %d", vNum);
80 if (!newPoint) {
81 newPoint = static_cast<TGraphAsymmErrors *>(
82 select->Clone(TString::Format("%s;%s", select->GetName(), _varyName.Data())));
83 }
84 newPoint->SetPointX(0, _gr->GetPointX(i - 1));
85 newPoint->SetMarkerColor(860 + (vNum - 1) * 20);
86 newPoint->SetLineColor(newPoint->GetMarkerColor());
87 newPoint->SetPointEYlow(0, 0);
88 newPoint->SetPointEYhigh(0, 0); // remove errors because currently meaningless!
89 newPoint->Draw("z0p");
90 select->SetPoint(0, _gr->GetPointX(i - 1), _gr->GetPointY(i - 1));
91 select = newPoint;
92 } else {
93 select->SetPointX(0, _gr->GetPointX(i - 1));
94 }
95 static_cast<TGraph *>(
96 static_cast<TMultiGraph *>(gPad->GetPrimitive("editables"))->GetListOfGraphs()->FindObject(_name))
97 ->SetPoint(0, i - 1, _gr->GetPointY(i - 1));
98 break;
99 }
100 }
101
102 // then do an overlay update
103 auto _node = dynamic_cast<xRooNode *>(gPad->GetPrimitive("node"));
104 if (!_node)
105 return;
106 RooArgSet _pars(_node->pars().argList());
107 std::unique_ptr<RooArgSet> snap(_pars.snapshot());
108
109 // now need to assemble a snapshot corresponding to the current variation
110 for (int i = 1; i <= _h->GetNbinsX(); i++) {
111 std::string parName = _h->GetXaxis()->GetBinLabel(i);
112 // ensure point is back .. sometimes editing mode allows point to drift
113 // dynamic_cast<TGraph*>(gPad->GetPrimitive(parName.c_str()))->SetPoint(0,i-1,dynamic_cast<TGraph*>(gPad->GetPrimitive("nominal"))->GetPointY(i-1));
114 if (auto g =
115 dynamic_cast<TGraph *>(gPad->GetPrimitive(TString::Format("%s;%s", parName.c_str(), _varyName.Data())));
116 g && g->GetN() > 0) {
117 double _val =
118 g->GetPointY(0) * _h->GetBinError(i) + _h->GetBinContent(i); // error is scale, content is offset
119 _pars.setRealValue(parName.c_str(), _val);
120 g->SetTitle(TString::Format("%s=%g", parName.c_str(), _val));
121 } else {
122 _pars.setRealValue(parName.c_str(), static_cast<TGraph *>(gPad->GetPrimitive("nominal"))->GetPointY(i - 1) *
123 _h->GetBinError(i) +
124 _h->GetBinContent(i));
125 }
126 }
127 TAttLine bak = *gStyle;
128 TAttFill bak2 = *gStyle;
131 gStyle->SetLineColor(select->GetMarkerColor());
132 auto _tmpPad = gPad;
133 gPad->GetMother()->GetMother()->cd(1);
134 _node->Draw(TString::Format("same overlay%s", _varyName.Data()));
135 // TODO: find the drawn variation and set its title equal to a _pars value string
136 static_cast<TAttLine &>(*gStyle) = bak;
137 static_cast<TAttFill &>(*gStyle) = bak2;
138 _pars = *snap;
139 _tmpPad->GetCanvas()->cd();
140 gPad->GetCanvas()->Paint();
141 gPad->GetCanvas()->Update();
142 }
143}
144
145void xRooNode::Interactive_PLLPlot()
146{
147
148 // TObject *select = gPad->GetSelected();
149 // if(!select) return;
150 // if (!select->InheritsFrom(TGraph::Class())) {gPad->SetUniqueID(0); return;}
151 // gPad->GetCanvas()->FeedbackMode(true);
152
153 auto _pull_pad = gPad->GetPad(1);
154 auto _hidden_pad = gPad->GetPad(2);
155
156 if (!_pull_pad || strcmp(_pull_pad->GetName(), "pulls") != 0)
157 return;
158 if (!_hidden_pad)
159 return;
160
161 // erase old position and draw a line at current position
162 // int pxold = gPad->GetUniqueID();
163 int px = gPad->GetEventX();
164 // int py = gPad->GetEventY();
165 // int pymin = gPad->YtoAbsPixel(gPad->GetUymin());
166 // int pymax = gPad->YtoAbsPixel(gPad->GetUymax());
167 // if(pxold) gVirtualX->DrawLine(pxold,pymin,pxold,pymax);
168 // gVirtualX->DrawLine(px,pymin,px,pymax);
169 gPad->SetUniqueID(px);
170 float upx = gPad->AbsPixeltoX(px);
171 float x = gPad->PadtoX(upx);
172
173 // find which graph in the hidden pad best reflects current x value
174 TObject *foundGraph = nullptr;
175 for (auto g : *_hidden_pad->GetListOfPrimitives()) {
176 double midpoint = TString(g->GetName()).Atof();
177 if (!foundGraph) {
178 foundGraph = g;
179 } else {
180 midpoint = (midpoint + TString(foundGraph->GetName()).Atof()) / 2.;
181 }
182 if (midpoint >= x)
183 break;
184 foundGraph = g;
185 }
186 if (foundGraph) {
187 auto _x = TString(foundGraph->GetName()).Atof();
188 if (auto line = dynamic_cast<TGraph *>(gPad->GetListOfPrimitives()->FindObject("markerLine")); line) {
189 line->SetPointX(0, _x);
190 line->SetPointX(1, _x);
191 } else {
192 line = new TGraph;
193 line->SetLineStyle(2);
194 line->SetName("markerLine");
196 line->SetPoint(0, _x, -100);
197 line->SetPoint(1, _x, 100);
198 line->Draw("Lsame");
199 }
200 gPad->Modified();
201 gPad->Update();
202 for (auto o : *_pull_pad->GetListOfPrimitives()) {
203 if (!o->InheritsFrom("TGraph"))
204 continue;
205 if (_hidden_pad->GetListOfPrimitives()->FindObject(o) || TString(o->GetName()).EndsWith("_pull")) {
206 // todo: might need to delete the "_pull" plot if removing for first time
207 _pull_pad->GetListOfPrimitives()->Remove(o);
208 break;
209 }
210 }
211 auto tmp = gPad;
212 _pull_pad->cd();
213 foundGraph->Draw("pz0 same");
214 tmp->cd();
215 _pull_pad->Modified();
216 _pull_pad->Update();
217 }
218}
219
220void xRooNode::InteractiveObject::Interactive_PLLPlot(TVirtualPad *pad, TObject *obj, Int_t x, Int_t /*y*/)
221{
222
223 if (auto g = dynamic_cast<TGraph *>(obj); g && pad && pad->GetMother() && pad->GetNumber() == 1) {
224 auto frPad = pad->GetMother()->GetPad(2);
225 if (frPad) {
226 if (!g->IsHighlight()) {
227 x = -1;
228 } else if (x >= 0) {
229 x += 1;
230 }
231 // x is the point index
232 TVirtualPad *_pad = frPad->GetPad(x);
233 auto selPad = dynamic_cast<TVirtualPad *>(frPad->GetPrimitive("selected"));
234 if (_pad && selPad) {
235 auto prim = selPad->GetListOfPrimitives();
236 prim->Remove(prim->At(0));
237 prim->Add(_pad);
238
239 // for (auto p: *pad->GetListOfPrimitives()) {
240 // if (auto _p = dynamic_cast<TPad *>(p)) {
241 // _p->Modified();
242 // }
243 // }
244 // pad->Modified();
245 // pad->Update();
246 selPad->Modified();
247 selPad->Update();
249 }
250 }
251 }
252}
253
#define g(i)
Definition RSha256.hxx:105
@ kCanDelete
Definition TObject.h:369
R__EXTERN TStyle * gStyle
Definition TStyle.h:433
R__EXTERN TSystem * gSystem
Definition TSystem.h:555
#define gPad
The xRooNode class is designed to wrap over a TObject and provide functionality to aid with interacti...
Definition xRooNode.h:51
bool setRealValue(const char *name, double newVal=0.0, bool verbose=false)
Set value of a RooAbsRealLValue stored in set with given name to newVal No error messages are printed...
RooArgSet is a container object that can hold multiple RooAbsArg objects.
Definition RooArgSet.h:55
RooArgSet * snapshot(bool deepCopy=true) const
Use RooAbsCollection::snapshot(), but return as RooArgSet.
Definition RooArgSet.h:178
Fill Area Attributes class.
Definition TAttFill.h:19
Line Attributes class.
Definition TAttLine.h:18
virtual void SetLineStyle(Style_t lstyle)
Set the line style.
Definition TAttLine.h:42
virtual void SetLineWidth(Width_t lwidth)
Set the line width.
Definition TAttLine.h:43
virtual void SetLineColor(Color_t lcolor)
Set the line color.
Definition TAttLine.h:40
virtual void SetMarkerColor(Color_t mcolor=1)
Set the marker color.
Definition TAttMarker.h:38
virtual Color_t GetMarkerColor() const
Return the marker color.
Definition TAttMarker.h:31
const char * GetBinLabel(Int_t bin) const
Return label for bin.
Definition TAxis.cxx:440
TGraph with asymmetric error bars.
virtual void SetPointEYlow(Int_t i, Double_t eyl)
Set EYlow for point i.
virtual void SetPointEYhigh(Int_t i, Double_t eyh)
Set EYhigh for point i.
A TGraph is an object made of two arrays X and Y with npoints each.
Definition TGraph.h:41
virtual void SetPoint(Int_t i, Double_t x, Double_t y)
Set x and y values for point number i.
Definition TGraph.cxx:2319
Int_t GetN() const
Definition TGraph.h:131
void Draw(Option_t *chopt="") override
Draw this graph with its current attributes.
Definition TGraph.cxx:809
TAxis * GetXaxis() const
Get x axis of the graph.
Definition TGraph.cxx:1544
virtual void SetPointX(Int_t i, Double_t x)
Set x value for point i.
Definition TGraph.cxx:2343
TH1 is the base class of all histogram classes in ROOT.
Definition TH1.h:59
TObject * Remove(TObject *obj) override
Remove object from the list.
Definition TList.cxx:820
A TMultiGraph is a collection of TGraph (or derived) objects.
Definition TMultiGraph.h:34
Mother of all ROOT objects.
Definition TObject.h:41
virtual const char * GetName() const
Returns name of object.
Definition TObject.cxx:439
virtual TObject * FindObject(const char *name) const
Must be redefined in derived classes.
Definition TObject.cxx:403
void SetBit(UInt_t f, Bool_t set)
Set or unset the user status bits as specified in f.
Definition TObject.cxx:780
virtual void Draw(Option_t *option="")
Default Draw method for all objects.
Definition TObject.cxx:274
virtual void Paint(Option_t *option="")
This method must be overridden if a class wants to paint itself.
Definition TObject.cxx:607
Basic string class.
Definition TString.h:139
Ssiz_t Length() const
Definition TString.h:417
Bool_t EndsWith(const char *pat, ECaseCompare cmp=kExact) const
Return true if string ends with the specified string.
Definition TString.cxx:2244
Double_t Atof() const
Return floating-point value contained in string.
Definition TString.cxx:2054
const char * Data() const
Definition TString.h:376
static TString Format(const char *fmt,...)
Static method which formats a string using a printf style format descriptor and return a TString.
Definition TString.cxx:2378
Bool_t Contains(const char *pat, ECaseCompare cmp=kExact) const
Definition TString.h:632
Ssiz_t Index(const char *pat, Ssiz_t i=0, ECaseCompare cmp=kExact) const
Definition TString.h:651
virtual Bool_t ProcessEvents()
Process pending events (GUI, timers, sockets).
Definition TSystem.cxx:416
TVirtualPad is an abstract base class for the Pad and Canvas classes.
Definition TVirtualPad.h:51
virtual TList * GetListOfPrimitives() const =0
virtual TVirtualPad * GetMother() const =0
virtual TVirtualPad * GetPad(Int_t subpadnumber) const =0
virtual Int_t GetNumber() const =0
TLine * line
Double_t x[n]
Definition legend1.C:17
BEGIN_XROOFIT_NAMESPACE