4269bd1b |
1 | // Created on: 2013-08-15 |
2 | // Created by: Anton POLETAEV |
d5f74e42 |
3 | // Copyright (c) 2013-2014 OPEN CASCADE SAS |
4269bd1b |
4 | // |
973c2be1 |
5 | // This file is part of Open CASCADE Technology software library. |
4269bd1b |
6 | // |
d5f74e42 |
7 | // This library is free software; you can redistribute it and/or modify it under |
8 | // the terms of the GNU Lesser General Public License version 2.1 as published |
973c2be1 |
9 | // by the Free Software Foundation, with special exception defined in the file |
10 | // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT |
11 | // distribution for complete text of the license and disclaimer of any warranty. |
4269bd1b |
12 | // |
973c2be1 |
13 | // Alternatively, this file may be used under the terms of Open CASCADE |
14 | // commercial license or contractual agreement. |
4269bd1b |
15 | |
e1c659da |
16 | #include <NCollection_AlignedAllocator.hxx> |
4269bd1b |
17 | #include <OpenGl_CappingPlaneResource.hxx> |
18 | #include <OpenGl_Context.hxx> |
19 | #include <OpenGl_Vec.hxx> |
20 | #include <Precision.hxx> |
21 | |
e1c659da |
22 | namespace |
23 | { |
24 | //! 12 plane vertices, interleaved: |
25 | //! - 4 floats, position |
26 | //! - 4 floats, normal |
27 | //! - 4 floats, UV texture coordinates |
28 | static const GLfloat THE_CAPPING_PLN_VERTS[12 * (4 + 4 + 4)] = |
29 | { |
30 | 0.0f, 0.0f, 0.0f, 1.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 1.0f, |
31 | 1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f, |
44ef962b |
32 | 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f,-1.0f, 0.0f, 0.0f, |
e1c659da |
33 | |
34 | 0.0f, 0.0f, 0.0f, 1.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 1.0f, |
44ef962b |
35 | 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f,-1.0f, 0.0f, 0.0f, |
e1c659da |
36 | -1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, -1.0f, 0.0f, 0.0f, 0.0f, |
37 | |
38 | 0.0f, 0.0f, 0.0f, 1.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 1.0f, |
39 | -1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, -1.0f, 0.0f, 0.0f, 0.0f, |
44ef962b |
40 | 0.0f, 0.0f,-1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, |
e1c659da |
41 | |
42 | 0.0f, 0.0f, 0.0f, 1.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.0f, 1.0f, |
44ef962b |
43 | 0.0f, 0.0f,-1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, |
e1c659da |
44 | 1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f |
45 | }; |
f8ae3605 |
46 | |
47 | static const OpenGl_Matrix OpenGl_IdentityMatrix = |
48 | { |
49 | // mat[4][4] |
50 | { { 1.0f, 0.0f, 0.0f, 0.0f }, |
51 | { 0.0f, 1.0f, 0.0f, 0.0f }, |
52 | { 0.0f, 0.0f, 1.0f, 0.0f }, |
53 | { 0.0f, 0.0f, 0.0f, 1.0f } } |
54 | }; |
55 | |
e1c659da |
56 | } |
57 | |
4269bd1b |
58 | |
59 | // ======================================================================= |
60 | // function : OpenGl_CappingPlaneResource |
61 | // purpose : |
62 | // ======================================================================= |
63 | OpenGl_CappingPlaneResource::OpenGl_CappingPlaneResource (const Handle(Graphic3d_ClipPlane)& thePlane) |
e1c659da |
64 | : myPrimitives (NULL), |
65 | myOrientation (OpenGl_IdentityMatrix), |
8d3865d8 |
66 | myAspect (NULL), |
67 | myPlaneRoot (thePlane), |
68 | myEquationMod ((unsigned int )-1), |
69 | myAspectMod ((unsigned int )-1) |
e1c659da |
70 | { |
71 | // Fill primitive array |
72 | Handle(NCollection_AlignedAllocator) anAlloc = new NCollection_AlignedAllocator (16); |
73 | Handle(Graphic3d_Buffer) anAttribs = new Graphic3d_Buffer (anAlloc); |
74 | Graphic3d_Attribute anAttribInfo[] = |
75 | { |
76 | { Graphic3d_TOA_POS, Graphic3d_TOD_VEC4 }, |
77 | { Graphic3d_TOA_NORM, Graphic3d_TOD_VEC4 }, |
78 | { Graphic3d_TOA_UV, Graphic3d_TOD_VEC4 } |
79 | }; |
80 | if (anAttribs->Init (12, anAttribInfo, 3)) |
81 | { |
82 | memcpy (anAttribs->ChangeData(), THE_CAPPING_PLN_VERTS, sizeof(THE_CAPPING_PLN_VERTS)); |
83 | myPrimitives.InitBuffers (NULL, Graphic3d_TOPA_TRIANGLES, NULL, anAttribs, NULL); |
84 | } |
85 | } |
4269bd1b |
86 | |
87 | // ======================================================================= |
88 | // function : OpenGl_CappingPlaneResource |
89 | // purpose : |
90 | // ======================================================================= |
91 | OpenGl_CappingPlaneResource::~OpenGl_CappingPlaneResource() |
92 | { |
93 | Release (NULL); |
94 | } |
95 | |
96 | // ======================================================================= |
97 | // function : Update |
98 | // purpose : |
99 | // ======================================================================= |
100 | void OpenGl_CappingPlaneResource::Update (const Handle(OpenGl_Context)& theContext) |
101 | { |
102 | UpdateTransform(); |
103 | UpdateAspect (theContext); |
104 | } |
105 | |
106 | // ======================================================================= |
107 | // function : Release |
108 | // purpose : |
109 | // ======================================================================= |
10b9c7df |
110 | void OpenGl_CappingPlaneResource::Release (OpenGl_Context* theContext) |
4269bd1b |
111 | { |
112 | OpenGl_Element::Destroy (theContext, myAspect); |
e1c659da |
113 | myPrimitives.Release (theContext); |
8d3865d8 |
114 | myEquationMod = (unsigned int )-1; |
115 | myAspectMod = (unsigned int )-1; |
4269bd1b |
116 | } |
117 | |
118 | // ======================================================================= |
119 | // function : UpdateAspect |
120 | // purpose : |
121 | // ======================================================================= |
122 | void OpenGl_CappingPlaneResource::UpdateAspect (const Handle(OpenGl_Context)& theContext) |
123 | { |
124 | Handle(Graphic3d_AspectFillArea3d) aCappingAsp = myPlaneRoot->CappingAspect(); |
125 | if (myAspect != NULL && !aCappingAsp.IsNull()) |
126 | { |
127 | if (myAspectMod == myPlaneRoot->MCountAspect()) |
128 | return; // noting to update |
129 | |
fd4a6963 |
130 | myAspect->SetAspect (aCappingAsp); |
4269bd1b |
131 | myAspectMod = myPlaneRoot->MCountAspect(); |
132 | return; |
133 | } |
134 | |
135 | // no more used |
136 | if (myAspect != NULL && aCappingAsp.IsNull()) |
137 | { |
10b9c7df |
138 | OpenGl_Element::Destroy (theContext.operator->(), myAspect); |
4269bd1b |
139 | myAspectMod = myPlaneRoot->MCountAspect(); |
140 | return; |
141 | } |
142 | |
143 | // first created |
144 | if (myAspect == NULL && !aCappingAsp.IsNull()) |
145 | { |
146 | myAspect = new OpenGl_AspectFace(); |
fd4a6963 |
147 | myAspect->SetAspect (aCappingAsp); |
4269bd1b |
148 | myAspectMod = myPlaneRoot->MCountAspect(); |
149 | } |
150 | } |
151 | |
152 | // ======================================================================= |
153 | // function : UpdateTransform |
154 | // purpose : |
155 | // ======================================================================= |
156 | void OpenGl_CappingPlaneResource::UpdateTransform() |
157 | { |
158 | const Graphic3d_ClipPlane::Equation& anEquation = myPlaneRoot->GetEquation(); |
159 | if (myEquationMod == myPlaneRoot->MCountEquation()) |
160 | { |
161 | return; // nothing to update |
162 | } |
163 | |
164 | // re-evaluate infinite plane transformation matrix |
165 | Standard_ShortReal N[3] = |
166 | { (Standard_ShortReal)anEquation[0], |
167 | (Standard_ShortReal)anEquation[1], |
168 | (Standard_ShortReal)anEquation[2] }; |
169 | |
170 | Standard_ShortReal T[3] = |
171 | { (Standard_ShortReal)(anEquation[0] * -anEquation[3]), |
172 | (Standard_ShortReal)(anEquation[1] * -anEquation[3]), |
173 | (Standard_ShortReal)(anEquation[2] * -anEquation[3]) }; |
174 | |
175 | Standard_ShortReal L[3] = { 0.0f, 0.0f, 0.0f }; |
176 | Standard_ShortReal F[3] = { 0.0f, 0.0f, 0.0f }; |
177 | |
178 | // project plane normal onto OX to find left vector |
4269bd1b |
179 | Standard_ShortReal aProjLen = |
180 | sqrt ( (Standard_ShortReal)(anEquation[0] * anEquation[0]) |
181 | + (Standard_ShortReal)(anEquation[2] * anEquation[2])); |
79f4f036 |
182 | if (aProjLen < ShortRealSmall()) |
4269bd1b |
183 | { |
184 | L[0] = 1.0f; |
185 | } |
186 | else |
187 | { |
188 | L[0] = N[2] / aProjLen; |
189 | L[2] = -N[0] / aProjLen; |
190 | } |
191 | |
192 | // (-aLeft) x aNorm |
193 | F[0] = (-L[1])*N[2] - (-L[2])*N[1]; |
194 | F[1] = (-L[2])*N[0] - (-L[0])*N[2]; |
195 | F[2] = (-L[0])*N[1] - (-L[1])*N[0]; |
196 | |
197 | myOrientation.mat[0][0] = L[0]; |
198 | myOrientation.mat[0][1] = L[1]; |
199 | myOrientation.mat[0][2] = L[2]; |
200 | myOrientation.mat[0][3] = 0.0f; |
201 | |
202 | myOrientation.mat[1][0] = N[0]; |
203 | myOrientation.mat[1][1] = N[1]; |
204 | myOrientation.mat[1][2] = N[2]; |
205 | myOrientation.mat[1][3] = 0.0f; |
206 | |
207 | myOrientation.mat[2][0] = F[0]; |
208 | myOrientation.mat[2][1] = F[1]; |
209 | myOrientation.mat[2][2] = F[2]; |
210 | myOrientation.mat[2][3] = 0.0f; |
211 | |
212 | myOrientation.mat[3][0] = T[0]; |
213 | myOrientation.mat[3][1] = T[1]; |
214 | myOrientation.mat[3][2] = T[2]; |
215 | myOrientation.mat[3][3] = 1.0f; |
216 | |
217 | myEquationMod = myPlaneRoot->MCountEquation(); |
218 | } |