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