Logo ROOT   6.16/01
Reference Guide
TArrow.cxx
Go to the documentation of this file.
1// @(#)root/graf:$Id$
2// Author: Rene Brun 17/10/95
3
4/*************************************************************************
5 * Copyright (C) 1995-2000, 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 "Riostream.h"
13#include "TROOT.h"
14#include "TMath.h"
15#include "TArrow.h"
16#include "TVirtualPad.h"
17#include "TVirtualPS.h"
18
22
24
25/** \class TArrow
26\ingroup BasicGraphics
27
28Draw all kinds of Arrows.
29
30The different arrow's formats are explained in TArrow::TArrow.
31The picture below gives some examples.
32
33Once an arrow is drawn on the screen:
34
35- One can click on one of the edges and move this edge.
36- One can click on any other arrow part to move the entire arrow.
37
38Begin_Macro(source)
39../../../tutorials/graphics/arrows.C
40End_Macro
41*/
42
43////////////////////////////////////////////////////////////////////////////////
44/// Arrow default constructor.
45
47{
49 fArrowSize = 0.;
50}
51
52////////////////////////////////////////////////////////////////////////////////
53/// Arrow normal constructor.
54///
55/// Define an arrow between points x1,y1 and x2,y2
56/// the `arrowsize` is in percentage of the pad height
57/// Opening angle between the two sides of the arrow is fAngle (60 degrees)
58/// ~~~ {.cpp}
59/// option = ">" -------->
60/// option = "|->" |------->
61/// option = "<" <--------
62/// option = "<-|" <-------|
63/// option = "->-" ---->----
64/// option = "-<-" ----<----
65/// option = "-|>-" ---|>----
66/// option = "<>" <------->
67/// option = "<|>" <|-----|> arrow defined by a triangle
68/// ~~~
69/// Note:
70///
71/// - If FillColor == 0 an open triangle is drawn, otherwise a full triangle is
72/// drawn with the fill color. The default is filled with LineColor
73/// - The "Begin" and "end" bars options can be combined with any other options.
74/// - The 9 options described above cannot be mixed.
75
77 Float_t arrowsize ,Option_t *option)
78 :TLine(x1,y1,x2,y2), TAttFill(0,1001)
79{
80
82 fArrowSize = arrowsize;
83 fOption = option;
85}
86
87////////////////////////////////////////////////////////////////////////////////
88/// Arrow default destructor.
89
91{
92}
93
94////////////////////////////////////////////////////////////////////////////////
95/// Copy constructor.
96
98{
99
101 fArrowSize = 0.;
102 ((TArrow&)arrow).Copy(*this);
103}
104
105////////////////////////////////////////////////////////////////////////////////
106/// Copy this arrow to arrow
107
108void TArrow::Copy(TObject &obj) const
109{
110
111 TLine::Copy(obj);
112 TAttFill::Copy(((TArrow&)obj));
113 ((TArrow&)obj).fAngle = fAngle;
114 ((TArrow&)obj).fArrowSize = fArrowSize;
115 ((TArrow&)obj).fOption = fOption;
116}
117
118////////////////////////////////////////////////////////////////////////////////
119/// Draw this arrow with its current attributes.
120
122{
123
124 Option_t *opt;
125 if (option && strlen(option)) opt = option;
126 else opt = (char*)GetOption();
127
128 AppendPad(opt);
129
130}
131
132////////////////////////////////////////////////////////////////////////////////
133/// Draw this arrow with new coordinates.
134///
135/// - if `arrowsize` is <= 0, `arrowsize` will be the current arrow size
136/// - if `option=""`, `option` will be the current arrow option
137
139 Float_t arrowsize ,Option_t *option)
140{
141
142 Float_t size = arrowsize;
143 if (size <= 0) size = fArrowSize;
144 if (size <= 0) size = 0.05;
145 const char* opt = option;
146 if (!opt || !opt[0]) opt = fOption.Data();
147 if (!opt || !opt[0]) opt = "|>";
148 TArrow *newarrow = new TArrow(x1,y1,x2,y2,size,opt);
149 newarrow->SetAngle(fAngle);
150 TAttLine::Copy(*newarrow);
151 TAttFill::Copy(*newarrow);
152 newarrow->SetBit(kCanDelete);
153 newarrow->AppendPad(opt);
154}
155
156////////////////////////////////////////////////////////////////////////////////
157/// Paint this arrow with its current attributes.
158
160{
161
162 Option_t *opt;
163 if (option && strlen(option)) opt = option;
164 else opt = (char*)GetOption();
165 PaintArrow(gPad->XtoPad(fX1),gPad->YtoPad(fY1),gPad->XtoPad(fX2),gPad->YtoPad(fY2), fArrowSize, opt);
166}
167
168
169////////////////////////////////////////////////////////////////////////////////
170/// Draw this arrow
171
173 Float_t arrowsize, Option_t *option)
174{
175
176 Int_t i;
177
178 // Option and attributes
179 TString opt = option;
180 opt.ToLower();
183
184 // Compute the gPad coordinates in TRUE normalized space (NDC)
185 Int_t ix1,iy1,ix2,iy2;
186 Int_t iw = gPad->GetWw();
187 Int_t ih = gPad->GetWh();
188 Double_t x1p,y1p,x2p,y2p;
189 gPad->GetPadPar(x1p,y1p,x2p,y2p);
190 ix1 = (Int_t)(iw*x1p);
191 iy1 = (Int_t)(ih*y1p);
192 ix2 = (Int_t)(iw*x2p);
193 iy2 = (Int_t)(ih*y2p);
194 Double_t wndc = TMath::Min(1.,(Double_t)iw/(Double_t)ih);
195 Double_t hndc = TMath::Min(1.,(Double_t)ih/(Double_t)iw);
196 Double_t rh = hndc/(Double_t)ih;
197 Double_t rw = wndc/(Double_t)iw;
198 Double_t x1ndc = (Double_t)ix1*rw;
199 Double_t y1ndc = (Double_t)iy1*rh;
200 Double_t x2ndc = (Double_t)ix2*rw;
201 Double_t y2ndc = (Double_t)iy2*rh;
202
203 // Ratios to convert user space in TRUE normalized space (NDC)
204 Double_t rx1,ry1,rx2,ry2;
205 gPad->GetRange(rx1,ry1,rx2,ry2);
206 Double_t rx = (x2ndc-x1ndc)/(rx2-rx1);
207 Double_t ry = (y2ndc-y1ndc)/(ry2-ry1);
208
209 // Arrow position and arrow's middle in NDC space
210 Double_t x1n, y1n, x2n, y2n, xm, ym;
211 x1n = rx*(x1-rx1)+x1ndc;
212 x2n = rx*(x2-rx1)+x1ndc;
213 y1n = ry*(y1-ry1)+y1ndc;
214 y2n = ry*(y2-ry1)+y1ndc;
215 xm = (x1n+x2n)/2;
216 ym = (y1n+y2n)/2;
217
218 // Arrow heads size
219 Double_t length = TMath::Sqrt(Double_t((x2n-x1n)*(x2n-x1n)+(y2n-y1n)*(y2n-y1n)));
220 Double_t rSize = 0.7*arrowsize;
221 Double_t dSize = rSize*TMath::Tan(TMath::Pi()*fAngle/360);
222 Double_t cosT = 1;
223 Double_t sinT = 0;
224 if (length > 0) {
225 cosT = (x2n-x1n)/length;
226 sinT = (y2n-y1n)/length;
227 }
228 // Arrays holding the arrows coordinates
229 Double_t x1ar[4], y1ar[4];
230 Double_t x2ar[4], y2ar[4];
231
232 // Draw the start and end bars if needed
233 if (opt.BeginsWith("|-")) {
234 x1ar[0] = x1n-sinT*dSize;
235 y1ar[0] = y1n+cosT*dSize;
236 x1ar[1] = x1n+sinT*dSize;
237 y1ar[1] = y1n-cosT*dSize;
238 // NDC to user coordinates
239 for (i=0; i<2; i++) {
240 x1ar[i] = (1/rx)*(x1ar[i]-x1ndc)+rx1;
241 y1ar[i] = (1/ry)*(y1ar[i]-y1ndc)+ry1;
242 }
243 gPad->PaintLine(x1ar[0],y1ar[0],x1ar[1],y1ar[1]);
244 opt(0) = ' ';
245 }
246 if (opt.EndsWith("-|")) {
247 x2ar[0] = x2n-sinT*dSize;
248 y2ar[0] = y2n+cosT*dSize;
249 x2ar[1] = x2n+sinT*dSize;
250 y2ar[1] = y2n-cosT*dSize;
251 // NDC to user coordinates
252 for (i=0; i<2; i++) {
253 x2ar[i] = (1/rx)*(x2ar[i]-x1ndc)+rx1;
254 y2ar[i] = (1/ry)*(y2ar[i]-y1ndc)+ry1;
255 }
256 gPad->PaintLine(x2ar[0],y2ar[0],x2ar[1],y2ar[1]);
257 opt(opt.Length()-1) = ' ';
258 }
259
260 // Move arrow head's position if needed
261 Double_t x1h = x1n;
262 Double_t y1h = y1n;
263 Double_t x2h = x2n;
264 Double_t y2h = y2n;
265 if (opt.Contains("->-") || opt.Contains("-|>-")) {
266 x2h = xm + cosT*rSize/2;
267 y2h = ym + sinT*rSize/2;
268 }
269 if (opt.Contains("-<-") || opt.Contains("-<|-")) {
270 x1h = xm - cosT*rSize/2;
271 y1h = ym - sinT*rSize/2;
272 }
273
274 // Define the arrow's head coordinates
275 if (opt.Contains(">")) {
276 x2ar[0] = x2h - rSize*cosT - sinT*dSize;
277 y2ar[0] = y2h - rSize*sinT + cosT*dSize;
278 x2ar[1] = x2h;
279 y2ar[1] = y2h;
280 x2ar[2] = x2h - rSize*cosT + sinT*dSize;
281 y2ar[2] = y2h - rSize*sinT - cosT*dSize;
282 x2ar[3] = x2ar[0];
283 y2ar[3] = y2ar[0];
284 }
285
286 if (opt.Contains("<")) {
287 x1ar[0] = x1h + rSize*cosT + sinT*dSize;
288 y1ar[0] = y1h + rSize*sinT - cosT*dSize;
289 x1ar[1] = x1h;
290 y1ar[1] = y1h;
291 x1ar[2] = x1h + rSize*cosT - sinT*dSize;
292 y1ar[2] = y1h + rSize*sinT + cosT*dSize;
293 x1ar[3] = x1ar[0];
294 y1ar[3] = y1ar[0];
295 }
296
297 // Paint Arrow body
298 if (opt.Contains("|>") && !opt.Contains("-|>-")) {
299 x2n = x2n-cosT*rSize;
300 y2n = y2n-sinT*rSize;
301 }
302 if (opt.Contains("<|") && !opt.Contains("-<|-")) {
303 x1n = x1n+cosT*rSize;
304 y1n = y1n+sinT*rSize;
305 }
306 x1n = (1/rx)*(x1n-x1ndc)+rx1;
307 y1n = (1/ry)*(y1n-y1ndc)+ry1;
308 x2n = (1/rx)*(x2n-x1ndc)+rx1;
309 y2n = (1/ry)*(y2n-y1ndc)+ry1;
310 gPad->PaintLine(x1n,y1n,x2n,y2n);
311
312 // Draw the arrow's head(s)
313 if (opt.Contains(">")) {
314 // NDC to user coordinates
315 for (i=0; i<4; i++) {
316 x2ar[i] = (1/rx)*(x2ar[i]-x1ndc)+rx1;
317 y2ar[i] = (1/ry)*(y2ar[i]-y1ndc)+ry1;
318 }
319 if (opt.Contains("|>")) {
320 if (gVirtualX) gVirtualX->SetLineStyle(1);
322 if (GetFillColor()) {
323 gPad->PaintFillArea(3,x2ar,y2ar);
324 gPad->PaintPolyLine(4,x2ar,y2ar);
325 } else {
326 gPad->PaintPolyLine(4,x2ar,y2ar);
327 }
328 } else {
329 gPad->PaintPolyLine(3,x2ar,y2ar);
330 }
331 }
332 if (opt.Contains("<")) {
333 // NDC to user coordinates
334 for (i=0; i<4; i++) {
335 x1ar[i] = (1/rx)*(x1ar[i]-x1ndc)+rx1;
336 y1ar[i] = (1/ry)*(y1ar[i]-y1ndc)+ry1;
337 }
338 if (opt.Contains("<|")) {
339 if (gVirtualX) gVirtualX->SetLineStyle(1);
341 if (GetFillColor()) {
342 gPad->PaintFillArea(3,x1ar,y1ar);
343 gPad->PaintPolyLine(4,x1ar,y1ar);
344 } else {
345 gPad->PaintPolyLine(4,x1ar,y1ar);
346 }
347 } else {
348 gPad->PaintPolyLine(3,x1ar,y1ar);
349 }
350 }
351}
352
353////////////////////////////////////////////////////////////////////////////////
354/// Save primitive as a C++ statement(s) on output stream out
355
356void TArrow::SavePrimitive(std::ostream &out, Option_t * /*= ""*/)
357{
358
359 char quote = '"';
360 if (gROOT->ClassSaved(TArrow::Class())) {
361 out<<" ";
362 } else {
363 out<<" TArrow *";
364 }
365 out<<"arrow = new TArrow("<<fX1<<","<<fY1<<","<<fX2<<","<<fY2
366 <<","<<fArrowSize<<","<<quote<<GetDrawOption()<<quote<<");"<<std::endl;
367
368 SaveFillAttributes(out,"arrow",0,1);
369 SaveLineAttributes(out,"arrow",1,1,1);
370
371 if (fAngle !=60) {
372 out << " arrow->SetAngle(" << GetAngle() << ");" << std::endl;
373 }
374
375 out<<" arrow->Draw();"<<std::endl;
376}
377
378
379////////////////////////////////////////////////////////////////////////////////
380/// Set default angle.
381
383{
384
386}
387
388
389////////////////////////////////////////////////////////////////////////////////
390/// Set default arrow sive.
391
393{
394
395 fgDefaultArrowSize = ArrowSize;
396}
397
398
399////////////////////////////////////////////////////////////////////////////////
400/// Set default option.
401
403{
404
405 fgDefaultOption = Option;
406}
407
408
409////////////////////////////////////////////////////////////////////////////////
410/// Get default angle.
411
413{
414
415 return fgDefaultAngle;
416}
417
418
419////////////////////////////////////////////////////////////////////////////////
420/// Get default arrow size.
421
423{
424
425 return fgDefaultArrowSize;
426}
427
428
429////////////////////////////////////////////////////////////////////////////////
430/// Get default option.
431
433{
434
435 return fgDefaultOption.Data();
436}
void Class()
Definition: Class.C:29
static const double x2[5]
static const double x1[5]
int Int_t
Definition: RtypesCore.h:41
double Double_t
Definition: RtypesCore.h:55
float Float_t
Definition: RtypesCore.h:53
const char Option_t
Definition: RtypesCore.h:62
#define ClassImp(name)
Definition: Rtypes.h:363
#define gROOT
Definition: TROOT.h:410
R__EXTERN TVirtualPS * gVirtualPS
Definition: TVirtualPS.h:81
#define gPad
Definition: TVirtualPad.h:286
#define gVirtualX
Definition: TVirtualX.h:345
Draw all kinds of Arrows.
Definition: TArrow.h:29
Float_t GetAngle() const
Definition: TArrow.h:51
static Float_t GetDefaultAngle()
Get default angle.
Definition: TArrow.cxx:412
Float_t fArrowSize
Arrow Size.
Definition: TArrow.h:32
static void SetDefaultOption(Option_t *Option)
Set default option.
Definition: TArrow.cxx:402
static void SetDefaultArrowSize(Float_t ArrowSize)
Set default arrow sive.
Definition: TArrow.cxx:392
static void SetDefaultAngle(Float_t Angle)
Set default angle.
Definition: TArrow.cxx:382
static Float_t fgDefaultAngle
Default Arrow opening angle (degrees)
Definition: TArrow.h:35
virtual void DrawArrow(Double_t x1, Double_t y1, Double_t x2, Double_t y2, Float_t arrowsize=0, Option_t *option="")
Draw this arrow with new coordinates.
Definition: TArrow.cxx:138
static Option_t * GetDefaultOption()
Get default option.
Definition: TArrow.cxx:432
virtual void Draw(Option_t *option="")
Draw this arrow with its current attributes.
Definition: TArrow.cxx:121
void Copy(TObject &arrow) const
Copy this arrow to arrow.
Definition: TArrow.cxx:108
static Float_t fgDefaultArrowSize
Default Arrow Size.
Definition: TArrow.h:36
TArrow()
Arrow default constructor.
Definition: TArrow.cxx:46
virtual ~TArrow()
Arrow default destructor.
Definition: TArrow.cxx:90
Float_t fAngle
Arrow opening angle (degrees)
Definition: TArrow.h:31
Option_t * GetOption() const
Definition: TArrow.h:53
static TString fgDefaultOption
Default Arrow shapes.
Definition: TArrow.h:37
virtual void Paint(Option_t *option="")
Paint this arrow with its current attributes.
Definition: TArrow.cxx:159
TString fOption
Arrow shapes.
Definition: TArrow.h:33
virtual void PaintArrow(Double_t x1, Double_t y1, Double_t x2, Double_t y2, Float_t arrowsize=0.05, Option_t *option=">")
Draw this arrow.
Definition: TArrow.cxx:172
virtual void SavePrimitive(std::ostream &out, Option_t *option="")
Save primitive as a C++ statement(s) on output stream out.
Definition: TArrow.cxx:356
virtual void SetAngle(Float_t angle=60)
Definition: TArrow.h:58
static Float_t GetDefaultArrowSize()
Get default arrow size.
Definition: TArrow.cxx:422
Fill Area Attributes class.
Definition: TAttFill.h:19
virtual Color_t GetFillColor() const
Return the fill area color.
Definition: TAttFill.h:30
void Copy(TAttFill &attfill) const
Copy this fill attributes to a new TAttFill.
Definition: TAttFill.cxx:201
virtual void Modify()
Change current fill area attributes if necessary.
Definition: TAttFill.cxx:210
virtual void SetFillColor(Color_t fcolor)
Set the fill area color.
Definition: TAttFill.h:37
virtual void SaveFillAttributes(std::ostream &out, const char *name, Int_t coldef=1, Int_t stydef=1001)
Save fill attributes as C++ statement(s) on output stream out.
Definition: TAttFill.cxx:233
virtual Color_t GetLineColor() const
Return the line color.
Definition: TAttLine.h:33
virtual void SetLineStyle(Style_t lstyle)
Set the line style.
Definition: TAttLine.h:42
virtual void Modify()
Change current line attributes if necessary.
Definition: TAttLine.cxx:234
void Copy(TAttLine &attline) const
Copy this line attributes to a new TAttLine.
Definition: TAttLine.cxx:164
virtual void SaveLineAttributes(std::ostream &out, const char *name, Int_t coldef=1, Int_t stydef=1, Int_t widdef=1)
Save line attributes as C++ statement(s) on output stream out.
Definition: TAttLine.cxx:262
A simple line.
Definition: TLine.h:23
Double_t fY1
Y of 1st point.
Definition: TLine.h:27
Double_t fX1
X of 1st point.
Definition: TLine.h:26
Double_t fX2
X of 2nd point.
Definition: TLine.h:28
Double_t fY2
Y of 2nd point.
Definition: TLine.h:29
void Copy(TObject &line) const
Copy this line to line.
Definition: TLine.cxx:67
Mother of all ROOT objects.
Definition: TObject.h:37
virtual Option_t * GetDrawOption() const
Get option used by the graphics system to draw this object.
Definition: TObject.cxx:341
virtual void AppendPad(Option_t *option="")
Append graphics object to current pad.
Definition: TObject.cxx:105
void SetBit(UInt_t f, Bool_t set)
Set or unset the user status bits as specified in f.
Definition: TObject.cxx:694
@ kCanDelete
if object in a list can be deleted
Definition: TObject.h:58
Basic string class.
Definition: TString.h:131
Ssiz_t Length() const
Definition: TString.h:405
void ToLower()
Change string to lower-case.
Definition: TString.cxx:1100
Bool_t EndsWith(const char *pat, ECaseCompare cmp=kExact) const
Return true if string ends with the specified string.
Definition: TString.cxx:2152
const char * Data() const
Definition: TString.h:364
Bool_t BeginsWith(const char *s, ECaseCompare cmp=kExact) const
Definition: TString.h:610
Bool_t Contains(const char *pat, ECaseCompare cmp=kExact) const
Definition: TString.h:619
double Angle(const Vector1 &v1, const Vector2 &v2)
Find Angle between two vectors.
Definition: VectorUtil.h:138
Double_t Sqrt(Double_t x)
Definition: TMath.h:679
Short_t Min(Short_t a, Short_t b)
Definition: TMathBase.h:180
constexpr Double_t Pi()
Definition: TMath.h:38
Double_t Tan(Double_t)
Definition: TMath.h:633