I encountered that when drawing a THStack and accessing the axis information, changes all results regarding pad coordinates, going from normal pad coordinates (0 to 1), to axis coordinates.
In this example I calculate the width of a TLatex label in different parts of the code:
Before creating a canvas
After creating a canvas
After drawing the stack
After modifying the axis of the stack
------------------------------- before everything
SM total 0.0
#gamma + jets Pythia 0.0
jet#rightarrow#gamma fake 0.0
------------------------------- after creating canvas
SM total 0.12781954887218044
#gamma + jets Pythia 0.21553884711779447
jet#rightarrow#gamma fake 0.15914786967418545
------------------------------- after drawing stack
SM total 0.12781954887218044
#gamma + jets Pythia 0.21553884711779447
jet#rightarrow#gamma fake 0.15914786967418545
------------------------------- after modified axis
SM total 15.977443847105032
#gamma + jets Pythia 26.942356291196724
jet#rightarrow#gamma fake 19.893484005709208
As you can see, in the last step the width now is given in user coordinates in the X axis.
Is this a bug, or how can I circumvent this issue?
The reason I came across with this problem is because I have a plotting framework that will automatically calculate sizes of legends and labels so they are automatically accommodated in the room they have. Changing the text precision would indeed save me from doing this calculation, and directly placing everything by using the size in pixels. However I don’t want to move to precision 3 in my framework since it would break other things. BTW, I found a way to have the legend and labels placed before accessing the TAxis attributes of the stack in my framework without changing precision.
However, I want to know if this behavior is expected or not.
I tried changing the text precision and it’s still changing sizes:
------------------------------- before everything
SM total 0.0
#gamma + jets Pythia 0.0
jet#rightarrow#gamma fake 0.0
------------------------------- after creating canvas
SM total 0.05513784461152882
#gamma + jets Pythia 0.09147869674185463
jet#rightarrow#gamma fake 0.06641604010025062
------------------------------- after drawing stack
SM total 0.05513784461152882
#gamma + jets Pythia 0.09147869674185463
jet#rightarrow#gamma fake 0.06641604010025062
------------------------------- after modified axis
SM total 6.892230679143347
#gamma + jets Pythia 11.43483726312419
jet#rightarrow#gamma fake 8.302005136240851
On the other hand, I tried this for a simple TH1 for two cases:
Having ROOT.gPad.Modified(); ROOT.gPad.Update() in the code after accessing the TAxis attributes.
In this case the result is the SAME as for the THStack case (changing sizes to user coordinates)
Not adding ROOT.gPad.Modified(); ROOT.gPad.Update().
Here the result is the EXPECTED one (having the size in pad coordinates)
------------------------------- before everything
SM total 0.0
#gamma + jets Pythia 0.0
jet#rightarrow#gamma fake 0.0
------------------------------- after creating canvas
SM total 0.12781954887218044
#gamma + jets Pythia 0.21553884711779447
jet#rightarrow#gamma fake 0.15914786967418545
------------------------------- after drawing stack
SM total 15.977443847105032
#gamma + jets Pythia 26.942356291196724
jet#rightarrow#gamma fake 19.893484005709208
------------------------------- after modified axis
SM total 15.977443847105032
#gamma + jets Pythia 26.942356291196724
jet#rightarrow#gamma fake 19.893484005709208
I wrote the code in C++. I leave the macro here: test2.C (4.0 KB)
void textxsize() {
auto t = new TLatex(.5,.5,"Hello");
printf("No canvas %g\n",t->GetXsize());
auto C = new TCanvas();
printf("Empty canvas %g\n",t->GetXsize());
C->DrawFrame(0.,0., 1.,1.);
t->Draw();
printf("Canvas with coordinates %g\n",t->GetXsize());
}
As the text size use the canvas coordinate to be computed this behavior is fine.
Looking at the documentation of the TLatexTLatex::GetXsize function, it clearly states that the size is calculated in pad coordinates, but this behavior changes if there are axes plotted as you and I have shown. Can this be said in the documentation?, since this is misleading.
Also, is there a way to consistently get the size? This method gets sizes in user and pad coordinates, but it’s not possible to convert USER coordinates to NDC coordinates as shown here. Would it be possible to have a way to either get the size of a label in a fixed coordinate system or to convert USER → NDC coordinates values?
You you draw plot which define/draw the axis it defines the user coordinates also. “Drawing a plot” , “Drawing Axis”, “defining user coordinates” re kind of synonyms.
Make sure the plot is drawn or use pixel size.
void textxsize() {
auto t = new TLatex(.5,.5,"Hello");
printf("No canvas Xsize = %5.2g\n",t->GetXsize());
auto C = new TCanvas();
printf("Empty canvas Xsize = %5.2g X1 = %g X2 = %g\n",t->GetXsize(),C->GetX1(), C->GetX2());
C->DrawFrame(0.,0., 1.,1.);
t->Draw();
printf("Canvas with coordinates Xsize = %5.2g X1 = %g X2 = %g\n",t->GetXsize(),C->GetX1(), C->GetX2());
}