0027670: Visualization - avoid duplication of structures defining primitive array...
[occt.git] / src / DsgPrs / DsgPrs_RadiusPresentation.cxx
1 // Created on: 1995-03-01
2 // Created by: Arnaud BOUZY
3 // Copyright (c) 1995-1999 Matra Datavision
4 // Copyright (c) 1999-2014 OPEN CASCADE SAS
5 //
6 // This file is part of Open CASCADE Technology software library.
7 //
8 // This library is free software; you can redistribute it and/or modify it under
9 // the terms of the GNU Lesser General Public License version 2.1 as published
10 // by the Free Software Foundation, with special exception defined in the file
11 // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
12 // distribution for complete text of the license and disclaimer of any warranty.
13 //
14 // Alternatively, this file may be used under the terms of Open CASCADE
15 // commercial license or contractual agreement.
16
17 #include <DsgPrs_RadiusPresentation.hxx>
18
19 #include <DsgPrs.hxx>
20 #include <ElCLib.hxx>
21 #include <gce_MakeDir.hxx>
22 #include <gce_MakeLin.hxx>
23 #include <gp_Circ.hxx>
24 #include <gp_Dir.hxx>
25 #include <gp_Lin.hxx>
26 #include <gp_Pnt.hxx>
27 #include <Graphic3d_ArrayOfSegments.hxx>
28 #include <Graphic3d_AspectLine3d.hxx>
29 #include <Graphic3d_AspectMarker3d.hxx>
30 #include <Graphic3d_Group.hxx>
31 #include <Precision.hxx>
32 #include <Prs3d_Arrow.hxx>
33 #include <Prs3d_ArrowAspect.hxx>
34 #include <Prs3d_DimensionAspect.hxx>
35 #include <Prs3d_LineAspect.hxx>
36 #include <Prs3d_Presentation.hxx>
37 #include <Prs3d_Text.hxx>
38 #include <TCollection_ExtendedString.hxx>
39
40 static Standard_Boolean DsgPrs_InDomain(const Standard_Real fpar,
41                                         const Standard_Real lpar,
42                                         const Standard_Real para)
43 {
44   if (fpar >= 0.)
45     return ((para >= fpar) && (para <= lpar));
46   if (para >= (fpar+2.*M_PI)) return Standard_True;
47   if (para <= lpar) return Standard_True;
48   return Standard_False;
49 }
50
51 //=======================================================================
52 //function : Add
53 //purpose  : 
54 //=======================================================================
55
56 void DsgPrs_RadiusPresentation::Add (const Handle(Prs3d_Presentation)& aPresentation,
57                                      const Handle(Prs3d_Drawer)& aDrawer,
58                                      const TCollection_ExtendedString& aText,
59                                      const gp_Pnt& AttachmentPoint,
60                                      const gp_Circ& aCircle,
61                                      const Standard_Real firstparam,
62                                      const Standard_Real lastparam,
63                                      const Standard_Boolean drawFromCenter,
64                                      const Standard_Boolean reverseArrow) 
65 {
66   Standard_Real fpara = firstparam;
67   Standard_Real lpara = lastparam;
68   while (lpara > 2.*M_PI) {
69     fpara -= 2.*M_PI;
70     lpara -= 2.*M_PI;
71   }
72   Handle(Prs3d_DimensionAspect) LA = aDrawer->DimensionAspect();
73   Prs3d_Root::CurrentGroup(aPresentation)->SetPrimitivesAspect(LA->LineAspect()->Aspect());
74
75   Standard_Real parat = ElCLib::Parameter(aCircle,AttachmentPoint);
76   gp_Pnt attpoint = AttachmentPoint;
77   Standard_Boolean otherside = Standard_False;
78   if ( !DsgPrs_InDomain(fpara,lpara,parat)) {
79     Standard_Real otherpar = parat + M_PI;
80     if (otherpar > 2.*M_PI) otherpar -= 2.*M_PI;
81     if (DsgPrs_InDomain(fpara,lpara,otherpar)) {
82       parat = otherpar;
83       otherside = Standard_True;
84     }
85     else {
86       const Standard_Real ecartpar = Min(Abs(fpara-parat),Abs(lpara-parat));
87       const Standard_Real ecartoth = Min(Abs(fpara-otherpar),Abs(lpara-otherpar));
88       if (ecartpar <= ecartoth) {
89         parat = (parat < fpara)? fpara : lpara;
90       }
91       else {
92         otherside = Standard_True;
93         parat = (otherpar < fpara)? fpara : lpara;
94       }
95       gp_Pnt ptdir = ElCLib::Value(parat,aCircle);
96       gp_Lin lsup(aCircle.Location(),gp_Dir(ptdir.XYZ()-aCircle.Location().XYZ()));
97       const Standard_Real parpos = ElCLib::Parameter(lsup,AttachmentPoint);
98       attpoint = ElCLib::Value(parpos,lsup);
99     }
100   }
101   gp_Pnt ptoncirc = ElCLib::Value(parat,aCircle);
102   gp_Lin L (aCircle.Location(),gp_Dir(attpoint.XYZ()-aCircle.Location().XYZ()));
103   gp_Pnt firstpoint = attpoint;
104   gp_Pnt drawtopoint = ptoncirc;
105   if (drawFromCenter && !otherside) {
106     const Standard_Real uatt = ElCLib::Parameter(L,attpoint);
107     const Standard_Real uptc = ElCLib::Parameter(L,ptoncirc);
108     if (Abs(uatt) > Abs(uptc))
109       drawtopoint = aCircle.Location();
110     else
111       firstpoint = aCircle.Location();
112   }
113
114   Handle(Graphic3d_ArrayOfSegments) aPrims = new Graphic3d_ArrayOfSegments(2);
115   aPrims->AddVertex(firstpoint);
116   aPrims->AddVertex(drawtopoint);
117   Prs3d_Root::CurrentGroup(aPresentation)->AddPrimitiveArray(aPrims);
118
119   gp_Dir arrdir = L.Direction();
120   if (reverseArrow)
121     arrdir.Reverse();
122
123   // fleche
124   Prs3d_Arrow::Draw(aPresentation,ptoncirc,arrdir,LA->ArrowAspect()->Angle(),LA->ArrowAspect()->Length());
125
126   // texte
127   Prs3d_Text::Draw(aPresentation,LA->TextAspect(),aText,attpoint);
128 }
129
130 //=======================================================================
131 //function : DsgPrs_RadiusPresentation::Add
132 //purpose  : SZY 20-february-98 
133 //         : adds radius representation according drawFromCenter value
134 //=======================================================================
135
136 void DsgPrs_RadiusPresentation::Add( const Handle(Prs3d_Presentation)& aPresentation,
137                                      const Handle(Prs3d_Drawer)& aDrawer,
138                                      const TCollection_ExtendedString& aText,
139                                      const gp_Pnt& AttachmentPoint,
140                                      const gp_Pnt& Center,
141                                      const gp_Pnt& EndOfArrow,
142                                      const DsgPrs_ArrowSide ArrowPrs,
143                                      const Standard_Boolean drawFromCenter,
144                                      const Standard_Boolean reverseArrow)
145 {
146   Handle( Prs3d_DimensionAspect ) LA = aDrawer->DimensionAspect();
147   Prs3d_Root::CurrentGroup( aPresentation )->SetPrimitivesAspect( LA->LineAspect()->Aspect() );
148
149   gp_Pnt LineOrigin, LineEnd;
150   DsgPrs::ComputeRadiusLine(Center, EndOfArrow, AttachmentPoint, drawFromCenter, LineOrigin, LineEnd);
151
152   Handle(Graphic3d_ArrayOfSegments) aPrims = new Graphic3d_ArrayOfSegments(2);
153   aPrims->AddVertex(LineOrigin);
154   aPrims->AddVertex(LineEnd);
155   Prs3d_Root::CurrentGroup(aPresentation)->AddPrimitiveArray(aPrims);
156
157   // text
158   Prs3d_Text::Draw( aPresentation, LA->TextAspect(), aText, AttachmentPoint );
159
160   gp_Dir ArrowDir = gce_MakeDir( LineOrigin , LineEnd );
161   if (reverseArrow)
162     ArrowDir.Reverse();
163   DsgPrs::ComputeSymbol( aPresentation, LA, Center, EndOfArrow, ArrowDir.Reversed(), ArrowDir, ArrowPrs, drawFromCenter );
164 }