Warnings on vc14 were eliminated
[occt.git] / src / MeshVS / MeshVS_Tool.cxx
1 // Created on: 2003-12-17
2 // Created by: Alexander SOLOVYOV
3 // Copyright (c) 2003-2014 OPEN CASCADE SAS
4 //
5 // This file is part of Open CASCADE Technology software library.
6 //
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
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.
12 //
13 // Alternatively, this file may be used under the terms of Open CASCADE
14 // commercial license or contractual agreement.
15
16
17 #include <Font_NameOfFont.hxx>
18 #include <gp_Vec.hxx>
19 #include <Graphic3d_AspectFillArea3d.hxx>
20 #include <Graphic3d_AspectLine3d.hxx>
21 #include <Graphic3d_AspectMarker3d.hxx>
22 #include <Graphic3d_AspectText3d.hxx>
23 #include <Graphic3d_MaterialAspect.hxx>
24 #include <MeshVS_Drawer.hxx>
25 #include <MeshVS_DrawerAttribute.hxx>
26 #include <MeshVS_Tool.hxx>
27 #include <Precision.hxx>
28
29 //================================================================
30 // Function : CreateAspectFillArea3d
31 // Purpose  :
32 //================================================================
33 Handle( Graphic3d_AspectFillArea3d ) MeshVS_Tool::CreateAspectFillArea3d
34 (  const Handle(MeshVS_Drawer)& theDr,
35    const Graphic3d_MaterialAspect& Mat,
36    const Standard_Boolean UseDefaults )
37 {
38   Handle( Graphic3d_AspectFillArea3d ) anAsp;
39   if ( theDr.IsNull() )
40     return anAsp;
41
42   Aspect_InteriorStyle     anIntStyle    = Aspect_IS_EMPTY;
43   Quantity_Color           anIntColor    = Quantity_NOC_CYAN1,
44                            anEdgeColor   = Quantity_NOC_WHITE;
45   Aspect_TypeOfLine        anEdgeType    = Aspect_TOL_SOLID;
46   Standard_Real            anEdgeWidth   = 1.0;
47   Aspect_HatchStyle        aHStyle       = Aspect_HS_HORIZONTAL;
48   Graphic3d_MaterialAspect aFrMat        = Mat,
49                            aBackMat      = Mat;
50
51   Standard_Integer         anIntStyleI   = (Standard_Integer)Aspect_IS_EMPTY;
52   Standard_Integer         anEdgeTypeI   = (Standard_Integer)Aspect_TOL_SOLID;
53   Standard_Integer         aHStyleI      = (Standard_Integer)Aspect_HS_HORIZONTAL;
54
55   if ( !theDr->GetColor ( MeshVS_DA_InteriorColor, anIntColor ) && !UseDefaults )
56     return anAsp;
57
58   Quantity_Color aBackIntColor = anIntColor;
59   if ( !theDr->GetColor ( MeshVS_DA_BackInteriorColor, aBackIntColor ) && !UseDefaults )
60     return anAsp;
61
62   if ( !theDr->GetColor ( MeshVS_DA_EdgeColor, anEdgeColor ) && !UseDefaults )
63     return anAsp;
64
65   if ( !theDr->GetDouble ( MeshVS_DA_EdgeWidth, anEdgeWidth ) && !UseDefaults )
66     return anAsp;
67
68   if ( !theDr->GetInteger ( MeshVS_DA_InteriorStyle, anIntStyleI ) && !UseDefaults )
69     return anAsp;
70   else
71     anIntStyle = (Aspect_InteriorStyle) anIntStyleI;
72
73   if ( !theDr->GetInteger ( MeshVS_DA_EdgeType, anEdgeTypeI ) && !UseDefaults )
74     return anAsp;
75   else
76     anEdgeType = (Aspect_TypeOfLine) anEdgeTypeI;
77
78   if ( !theDr->GetInteger ( MeshVS_DA_HatchStyle, aHStyleI ) && !UseDefaults )
79     return anAsp;
80   else
81     aHStyle = (Aspect_HatchStyle) aHStyleI;
82
83   anAsp = new Graphic3d_AspectFillArea3d ( anIntStyle, anIntColor, anEdgeColor, anEdgeType,
84     anEdgeWidth, aFrMat, aBackMat );
85   anAsp->SetBackInteriorColor ( aBackIntColor );
86   anAsp->SetHatchStyle ( aHStyle );
87
88   return anAsp;
89 }
90
91 //================================================================
92 // Function : CreateAspectFillArea3d
93 // Purpose  :
94 //================================================================
95 Handle( Graphic3d_AspectFillArea3d ) MeshVS_Tool::CreateAspectFillArea3d
96 (  const Handle(MeshVS_Drawer)& theDr,
97    const Standard_Boolean UseDefaults )
98 {
99   Graphic3d_MaterialAspect aFrMat   = Graphic3d_NOM_BRASS;
100   Graphic3d_MaterialAspect aBackMat = Graphic3d_NOM_BRASS;
101   Standard_Integer aFrMatI = (Standard_Integer)Graphic3d_NOM_BRASS;
102   Standard_Integer aBackMatI = (Standard_Integer)Graphic3d_NOM_BRASS;
103
104   if ( !theDr->GetInteger ( MeshVS_DA_FrontMaterial, aFrMatI ) && !UseDefaults )
105     return 0;
106   else
107     aFrMat = (Graphic3d_MaterialAspect)(Graphic3d_NameOfMaterial)aFrMatI;
108
109   if ( !theDr->GetInteger ( MeshVS_DA_BackMaterial, aBackMatI ) && !UseDefaults )
110     return 0;
111   else
112     aBackMat = (Graphic3d_MaterialAspect)(Graphic3d_NameOfMaterial)aBackMatI;
113
114   Handle( Graphic3d_AspectFillArea3d ) aFill =
115     CreateAspectFillArea3d ( theDr, aFrMat, UseDefaults );
116   aFill->SetBackMaterial ( aBackMat );
117
118   return aFill;
119 }
120 //================================================================
121 // Function : CreateAspectLine3d
122 // Purpose  :
123 //================================================================
124 Handle( Graphic3d_AspectLine3d ) MeshVS_Tool::CreateAspectLine3d
125 (  const Handle(MeshVS_Drawer)& theDr,
126  const Standard_Boolean UseDefaults )
127 {
128   Handle( Graphic3d_AspectLine3d ) anAsp;
129   if ( theDr.IsNull() )
130     return anAsp;
131
132   Quantity_Color           aBeamColor   = Quantity_NOC_YELLOW;
133   Aspect_TypeOfLine        aBeamType    = Aspect_TOL_SOLID;
134   Standard_Real            aBeamWidth   = 1.0;
135   Standard_Integer         aBeamTypeI   = (Standard_Integer)Aspect_TOL_SOLID;
136
137   if ( !theDr->GetColor ( MeshVS_DA_BeamColor, aBeamColor ) && !UseDefaults )
138     return anAsp;
139
140   if ( !theDr->GetDouble ( MeshVS_DA_BeamWidth, aBeamWidth ) && !UseDefaults )
141     return anAsp;
142
143   if ( !theDr->GetInteger ( MeshVS_DA_BeamType, aBeamTypeI ) && !UseDefaults )
144     return anAsp;
145   else
146     aBeamType = (Aspect_TypeOfLine) aBeamTypeI;
147
148   anAsp = new Graphic3d_AspectLine3d ( aBeamColor, aBeamType, aBeamWidth );
149
150   return anAsp;
151 }
152
153 //================================================================
154 // Function : CreateAspectMarker3d
155 // Purpose  :
156 //================================================================
157 Handle( Graphic3d_AspectMarker3d ) MeshVS_Tool::CreateAspectMarker3d
158 (  const Handle(MeshVS_Drawer)& theDr,
159  const Standard_Boolean UseDefaults )
160 {
161   Handle( Graphic3d_AspectMarker3d ) anAsp;
162   if ( theDr.IsNull() )
163     return anAsp;
164
165   Quantity_Color           aMColor   = Quantity_NOC_YELLOW;
166   Aspect_TypeOfMarker      aMType    = Aspect_TOM_X;
167   Standard_Real            aMScale   = 1.0;
168   Standard_Integer         aMTypeI   = (Standard_Integer)Aspect_TOM_X;
169
170   if ( !theDr->GetColor ( MeshVS_DA_MarkerColor, aMColor ) && !UseDefaults )
171     return anAsp;
172
173   if ( !theDr->GetDouble ( MeshVS_DA_MarkerScale, aMScale ) && !UseDefaults )
174     return anAsp;
175
176   if ( !theDr->GetInteger ( MeshVS_DA_MarkerType, aMTypeI ) && !UseDefaults )
177     return anAsp;
178   else
179     aMType = (Aspect_TypeOfMarker) aMTypeI;
180
181   anAsp = new Graphic3d_AspectMarker3d ( aMType, aMColor, aMScale );
182
183   return anAsp;
184 }
185
186 //================================================================
187 // Function : CreateAspectText3d
188 // Purpose  :
189 //================================================================
190 Handle( Graphic3d_AspectText3d ) MeshVS_Tool::CreateAspectText3d
191 (  const Handle(MeshVS_Drawer)& theDr,
192    const Standard_Boolean UseDefaults )
193 {
194   Handle( Graphic3d_AspectText3d ) anAsp;
195   if ( theDr.IsNull() )
196     return anAsp;
197
198   Quantity_Color            aTColor       = Quantity_NOC_YELLOW;
199   Standard_Real             anExpFactor   = 1.0,
200                             aSpace        = 0.0;
201   Standard_CString          aFont         = Font_NOF_ASCII_MONO;
202   Aspect_TypeOfStyleText    aStyle        = Aspect_TOST_NORMAL;
203   Aspect_TypeOfDisplayText  aDispText     = Aspect_TODT_NORMAL;
204   TCollection_AsciiString   aFontString   = Font_NOF_ASCII_MONO;
205   Font_FontAspect           aFontAspect   = Font_FA_Regular;
206   Standard_Integer          aStyleI       = (Standard_Integer)Aspect_TOST_NORMAL;
207   Standard_Integer          aDispTextI    = (Standard_Integer)Aspect_TODT_NORMAL;
208   // Bold font is used by default for better text readability
209   Standard_Integer          aFontAspectI  = (Standard_Integer)Font_FA_Bold;
210
211   if ( !theDr->GetColor ( MeshVS_DA_TextColor, aTColor ) && !UseDefaults )
212     return anAsp;
213
214   if ( !theDr->GetDouble ( MeshVS_DA_TextExpansionFactor, anExpFactor ) && !UseDefaults )
215     return anAsp;
216
217   if ( !theDr->GetDouble ( MeshVS_DA_TextSpace, aSpace ) && !UseDefaults )
218     return anAsp;
219
220   if ( !theDr->GetAsciiString ( MeshVS_DA_TextFont, aFontString ) && !UseDefaults )
221     return anAsp;
222   else
223     aFont = aFontString.ToCString();
224
225   if ( !theDr->GetInteger ( MeshVS_DA_TextStyle, aStyleI ) && !UseDefaults )
226     return anAsp;
227   else
228     aStyle = (Aspect_TypeOfStyleText) aStyleI;
229
230   if ( !theDr->GetInteger ( MeshVS_DA_TextDisplayType, aDispTextI ) && !UseDefaults )
231     return anAsp;
232   else
233     aDispText = (Aspect_TypeOfDisplayText) aDispTextI;
234
235   if ( !theDr->GetInteger ( MeshVS_DA_TextFontAspect, aFontAspectI ) && !UseDefaults )
236     return anAsp;
237   else 
238     aFontAspect = (Font_FontAspect) aFontAspectI;
239
240   anAsp = new Graphic3d_AspectText3d ( aTColor, aFont, anExpFactor, aSpace, aStyle, aDispText );
241   anAsp->SetTextFontAspect( aFontAspect );
242   return anAsp;
243 }
244
245 //================================================================
246 // Function : GetNormal
247 // Purpose  :
248 //================================================================
249 Standard_Boolean MeshVS_Tool::GetNormal( const TColStd_Array1OfReal& Nodes,
250                                         gp_Vec& Norm )
251 {
252   Standard_Integer first = Nodes.Lower(),
253     last  = Nodes.Upper(),
254     count = (last-first+1)/3, i, j;
255   if( first==0 )
256   {
257     first = 1;
258     count = Standard_Integer( Nodes.Value( 0 ) );
259   }
260
261   if( count<3 )
262     return Standard_False;
263
264   Standard_Boolean res = Standard_True;
265
266
267   Standard_Real normal[3], first_vec[3], cur_vec[3], xx, yy, zz,
268     conf = Precision::Confusion();
269
270   for( i=0; i<3; i++ )
271   {
272     normal[i] = 0.0;
273     first_vec[i] = Nodes.Value( first+3+i ) - Nodes.Value( first+i );
274   }
275
276   for( i=2; i<count; i++ )
277   {
278     for( j=0; j<3; j++ )
279       cur_vec[j] = Nodes.Value( first+3*i+j ) - Nodes.Value( first+j );
280
281     xx = first_vec[1] * cur_vec[2] - first_vec[2] * cur_vec[1];
282     yy = first_vec[2] * cur_vec[0] - first_vec[0] * cur_vec[2];
283     zz = first_vec[0] * cur_vec[1] - first_vec[1] * cur_vec[0];
284
285     cur_vec[0] = xx;
286     cur_vec[1] = yy;
287     cur_vec[2] = zz;
288
289     if( fabs( cur_vec[0] ) > conf ||
290       fabs( cur_vec[1] ) > conf ||
291       fabs( cur_vec[2] ) > conf )
292     {
293       Standard_Real cur = Sqrt( cur_vec[0]*cur_vec[0] + cur_vec[1]*cur_vec[1] + cur_vec[2]*cur_vec[2] );
294       for( Standard_Integer k=0; k<3; k++ )
295         cur_vec[k] /= cur;
296     }
297
298     if( fabs( normal[0] ) <= conf &&
299       fabs( normal[1] ) <= conf &&
300       fabs( normal[2] ) <= conf )
301       for( Standard_Integer k=0; k<3; k++ )
302         normal[k] = cur_vec[k];
303
304     if( fabs( normal[0]-cur_vec[0] ) > conf ||
305       fabs( normal[1]-cur_vec[1] ) > conf ||
306       fabs( normal[2]-cur_vec[2] ) > conf    )
307     {
308       res = Standard_False;
309       break;
310     }
311   }
312
313   if( res )
314     Norm.SetCoord( normal[0], normal[1], normal[2] );
315
316   return res;
317 }
318
319
320 //================================================================
321 // Function : GetAverageNormal
322 // Purpose  :
323 //================================================================
324 Standard_Boolean MeshVS_Tool::GetAverageNormal( const TColStd_Array1OfReal& Nodes,
325                                                gp_Vec& Norm )
326 {
327   Standard_Integer first = Nodes.Lower(),
328     last  = Nodes.Upper(),
329     count = (last-first+1)/3, i, j;
330   if( first==0 )
331   {
332     first = 1;
333     count = Standard_Integer( Nodes.Value( 0 ) );
334   }
335
336   if( count<3 )
337     return Standard_False;
338
339   Standard_Boolean res = Standard_True;
340
341
342   Standard_Real normal[3], first_vec[3], cur_vec[3], xx, yy, zz,
343     conf = Precision::Confusion();
344
345   for( i=0; i<3; i++ )
346   {
347     normal[i] = 0.0;
348     first_vec[i] = Nodes.Value( first+3+i ) - Nodes.Value( first+i );
349   }
350
351   gp_XYZ* norm_vec = new gp_XYZ[count-2];
352   for ( i = 0; i < count-2; i++ )
353     norm_vec[i].SetCoord(0, 0, 0);
354
355   for( i=2; i<count; i++ )
356   {
357     for( j=0; j<3; j++ )
358       cur_vec[j] = Nodes.Value( first+3*i+j ) - Nodes.Value( first+j );
359
360     xx = first_vec[1] * cur_vec[2] - first_vec[2] * cur_vec[1];
361     yy = first_vec[2] * cur_vec[0] - first_vec[0] * cur_vec[2];
362     zz = first_vec[0] * cur_vec[1] - first_vec[1] * cur_vec[0];
363
364     cur_vec[0] = xx;
365     cur_vec[1] = yy;
366     cur_vec[2] = zz;
367
368     if( fabs( cur_vec[0] ) > conf ||
369       fabs( cur_vec[1] ) > conf ||
370       fabs( cur_vec[2] ) > conf )
371     {
372       Standard_Real cur = Sqrt( cur_vec[0]*cur_vec[0] + cur_vec[1]*cur_vec[1] + cur_vec[2]*cur_vec[2] );
373       for( Standard_Integer k=0; k<3; k++ )
374         cur_vec[k] /= cur;
375     }
376
377     norm_vec[i-2].SetCoord(cur_vec[0], cur_vec[1], cur_vec[2]);
378
379     if( fabs( normal[0] ) <= conf &&
380       fabs( normal[1] ) <= conf &&
381       fabs( normal[2] ) <= conf )
382       for( Standard_Integer k=0; k<3; k++ )
383         normal[k] = cur_vec[k];
384
385     if( fabs( normal[0]-cur_vec[0] ) > conf ||
386       fabs( normal[1]-cur_vec[1] ) > conf ||
387       fabs( normal[2]-cur_vec[2] ) > conf    )
388     {
389       res = Standard_False;
390     }
391   }
392
393   if( !res ) {
394     for( j=0; j<3; j++ ) {
395       normal[j] = 0.0;
396       for (i = 0; i < count-2; i++)
397         normal[j] += norm_vec[i].Coord(j+1);
398       normal[j] /= (count-2);
399     }
400   }
401   delete [] norm_vec;
402
403   Norm.SetCoord( normal[0], normal[1], normal[2] );
404
405   return res;
406 }