7a324550 |
1 | // Created on: 2015-02-03 |
2 | // Copyright (c) 2015 OPEN CASCADE SAS |
3 | // |
4 | // This file is part of Open CASCADE Technology software library. |
5 | // |
6 | // This library is free software; you can redistribute it and/or modify it under |
7 | // the terms of the GNU Lesser General Public License version 2.1 as published |
8 | // by the Free Software Foundation, with special exception defined in the file |
9 | // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT |
10 | // distribution for complete text of the license and disclaimer of any warranty. |
11 | // |
12 | // Alternatively, this file may be used under the terms of Open CASCADE |
13 | // commercial license or contractual agreement. |
14 | |
15 | #include <AIS_ColorScale.hxx> |
16 | #include <AIS_InteractiveContext.hxx> |
17 | #include <Aspect_TypeOfColorScaleData.hxx> |
18 | #include <Aspect_TypeOfColorScalePosition.hxx> |
19 | #include <Aspect_Window.hxx> |
20 | #include <Geom_Line.hxx> |
21 | #include <GeomAdaptor_Curve.hxx> |
22 | #include <Graphic3d_ArrayOfPolygons.hxx> |
23 | #include <Graphic3d_ArrayOfPolylines.hxx> |
24 | #include <Graphic3d_AspectFillArea3d.hxx> |
25 | #include <Graphic3d_AspectText3d.hxx> |
26 | #include <Graphic3d_GraphicDriver.hxx> |
27 | #include <Graphic3d_ArrayOfTriangles.hxx> |
28 | #include <Prs3d_LineAspect.hxx> |
29 | #include <Prs3d_Root.hxx> |
30 | #include <Prs3d_ShadingAspect.hxx> |
31 | #include <Prs3d_Text.hxx> |
32 | #include <Prs3d_TextAspect.hxx> |
33 | #include <SelectMgr_EntityOwner.hxx> |
34 | #include <SelectMgr_Selection.hxx> |
35 | #include <Select3D_SensitiveBox.hxx> |
36 | #include <Select3D_SensitiveSegment.hxx> |
37 | #include <StdPrs_Curve.hxx> |
38 | #include <V3d_Viewer.hxx> |
39 | #include <V3d_View.hxx> |
40 | |
41 | |
92efcf78 |
42 | IMPLEMENT_STANDARD_RTTIEXT(AIS_ColorScale,AIS_InteractiveObject) |
43 | |
7a324550 |
44 | //======================================================================= |
45 | //function : AIS_ColorScale |
46 | //purpose : |
47 | //======================================================================= |
48 | AIS_ColorScale::AIS_ColorScale() : |
49 | myMin (0.0), |
50 | myMax (1.0), |
51 | myTitle (""), |
52 | myFormat ("%.4g"), |
53 | myInterval (10), |
54 | myColorType (Aspect_TOCSD_AUTO), |
55 | myLabelType (Aspect_TOCSD_AUTO), |
56 | myAtBorder (Standard_True), |
57 | myReversed (Standard_False), |
24a88697 |
58 | myIsLogarithmic (Standard_False), |
7a324550 |
59 | myLabelPos (Aspect_TOCSP_RIGHT), |
60 | myTitlePos (Aspect_TOCSP_CENTER), |
61 | myXPos (0), |
62 | myYPos (0), |
180f89a2 |
63 | myBreadth (0), |
b4b2ecca |
64 | myHeight (0), |
180f89a2 |
65 | myTextHeight(20) |
7a324550 |
66 | { |
67 | } |
68 | |
69 | //======================================================================= |
70 | //function : GetRange |
71 | //purpose : |
72 | //======================================================================= |
73 | void AIS_ColorScale::GetRange (Standard_Real& theMin, Standard_Real& theMax) const |
74 | { |
75 | theMin = myMin; |
76 | theMax = myMax; |
77 | } |
78 | |
79 | //======================================================================= |
80 | //function : GetLabel |
81 | //purpose : |
82 | //======================================================================= |
83 | TCollection_ExtendedString AIS_ColorScale::GetLabel (const Standard_Integer theIndex) const |
84 | { |
85 | if (GetLabelType() == Aspect_TOCSD_USER) |
86 | { |
180f89a2 |
87 | if (theIndex <= 0 || theIndex > myLabels.Length()) |
7a324550 |
88 | { |
89 | return ""; |
90 | } |
180f89a2 |
91 | return myLabels.Value (theIndex); |
7a324550 |
92 | } |
180f89a2 |
93 | |
94 | // value to be shown depends on label position |
95 | Standard_Real aVal = IsLabelAtBorder() ? GetIntervalValue (theIndex - 1) : |
96 | 0.5 * (GetIntervalValue (theIndex - 1) + GetIntervalValue (theIndex)); |
97 | |
7a324550 |
98 | const TCollection_AsciiString aFormat = Format(); |
99 | Standard_Character aBuf[1024]; |
100 | sprintf (aBuf, aFormat.ToCString(), aVal); |
101 | return TCollection_ExtendedString (aBuf); |
102 | } |
103 | |
104 | //======================================================================= |
180f89a2 |
105 | //function : GetIntervalColor |
7a324550 |
106 | //purpose : |
107 | //======================================================================= |
180f89a2 |
108 | Quantity_Color AIS_ColorScale::GetIntervalColor (const Standard_Integer theIndex) const |
7a324550 |
109 | { |
110 | if (GetColorType() == Aspect_TOCSD_USER) |
111 | { |
180f89a2 |
112 | if (theIndex <= 0 || theIndex > myColors.Length()) |
7a324550 |
113 | { |
114 | return Quantity_Color(); |
115 | } |
180f89a2 |
116 | return myColors.Value (theIndex); |
7a324550 |
117 | } |
180f89a2 |
118 | |
119 | return Quantity_Color (HueFromValue (theIndex - 1, 0, GetNumberOfIntervals() - 1), 1.0, 1.0, Quantity_TOC_HLS); |
7a324550 |
120 | } |
121 | |
122 | //======================================================================= |
123 | //function : GetLabels |
124 | //purpose : |
125 | //======================================================================= |
126 | void AIS_ColorScale::GetLabels (TColStd_SequenceOfExtendedString& theLabels) const |
127 | { |
128 | theLabels.Clear(); |
129 | for (Standard_Integer i = 1; i <= myLabels.Length(); i++) |
130 | theLabels.Append (myLabels.Value (i)); |
131 | } |
132 | |
133 | //======================================================================= |
134 | //function : GetColors |
135 | //purpose : |
136 | //======================================================================= |
137 | void AIS_ColorScale::GetColors (Aspect_SequenceOfColor& theColors) const |
138 | { |
139 | theColors.Clear(); |
140 | for (Standard_Integer i = 1; i <= myColors.Length(); i++) |
141 | theColors.Append (myColors.Value (i)); |
142 | } |
143 | |
144 | //======================================================================= |
145 | //function : SetMin |
146 | //purpose : |
147 | //======================================================================= |
148 | void AIS_ColorScale::SetMin (const Standard_Real theMin) |
149 | { |
150 | SetRange (theMin, GetMax()); |
151 | } |
152 | |
153 | //======================================================================= |
154 | //function : SetMax |
155 | //purpose : |
156 | //======================================================================= |
157 | void AIS_ColorScale::SetMax (const Standard_Real theMax) |
158 | { |
159 | SetRange (GetMin(), theMax); |
160 | } |
161 | |
162 | //======================================================================= |
163 | //function : SetRange |
164 | //purpose : |
165 | //======================================================================= |
166 | void AIS_ColorScale::SetRange (const Standard_Real theMin, const Standard_Real theMax) |
167 | { |
168 | if (myMin == theMin && myMax == theMax) |
169 | return; |
170 | |
171 | myMin = Min (theMin, theMax); |
172 | myMax = Max (theMin, theMax); |
173 | } |
174 | |
175 | //======================================================================= |
176 | //function : SetLabelType |
177 | //purpose : |
178 | //======================================================================= |
179 | void AIS_ColorScale::SetLabelType (const Aspect_TypeOfColorScaleData theType) |
180 | { |
181 | if (myLabelType == theType) |
182 | return; |
183 | |
184 | myLabelType = theType; |
185 | } |
186 | |
187 | //======================================================================= |
188 | //function : SetColorType |
189 | //purpose : |
190 | //======================================================================= |
191 | void AIS_ColorScale::SetColorType (const Aspect_TypeOfColorScaleData theType) |
192 | { |
193 | if (myColorType == theType) |
194 | return; |
195 | |
196 | myColorType = theType; |
197 | } |
198 | |
199 | //======================================================================= |
200 | //function : SetNumberOfIntervals |
201 | //purpose : |
202 | //======================================================================= |
203 | void AIS_ColorScale::SetNumberOfIntervals (const Standard_Integer theNum) |
204 | { |
205 | if (myInterval == theNum || theNum < 1) |
206 | return; |
207 | |
208 | myInterval = theNum; |
209 | } |
210 | |
211 | //======================================================================= |
212 | //function : SetTitle |
213 | //purpose : |
214 | //======================================================================= |
215 | void AIS_ColorScale::SetTitle (const TCollection_ExtendedString& theTitle) |
216 | { |
217 | if (myTitle == theTitle) |
218 | return; |
219 | |
220 | myTitle = theTitle; |
221 | } |
222 | |
223 | //======================================================================= |
224 | //function : SetFormat |
225 | //purpose : |
226 | //======================================================================= |
227 | void AIS_ColorScale::SetFormat (const TCollection_AsciiString& theFormat) |
228 | { |
229 | if (myFormat == theFormat) |
230 | return; |
231 | |
232 | myFormat = theFormat; |
233 | } |
234 | |
235 | //======================================================================= |
236 | //function : SetLabel |
237 | //purpose : |
238 | //======================================================================= |
239 | void AIS_ColorScale::SetLabel (const TCollection_ExtendedString& theLabel, const Standard_Integer theIndex) |
240 | { |
180f89a2 |
241 | Standard_Integer i = (theIndex <= 0 ? myLabels.Length() + 1 : theIndex); |
242 | while (i > myLabels.Length()) |
243 | myLabels.Append (TCollection_ExtendedString()); |
244 | myLabels.SetValue (i, theLabel); |
7a324550 |
245 | } |
246 | |
247 | //======================================================================= |
180f89a2 |
248 | //function : SetIntervalColor |
7a324550 |
249 | //purpose : |
250 | //======================================================================= |
180f89a2 |
251 | void AIS_ColorScale::SetIntervalColor (const Quantity_Color& theColor, const Standard_Integer theIndex) |
7a324550 |
252 | { |
180f89a2 |
253 | Standard_Integer i = (theIndex <= 0 ? myColors.Length() + 1 : theIndex); |
254 | while (i > myColors.Length()) |
255 | myColors.Append (Quantity_Color()); |
256 | myColors.SetValue (i, theColor); |
7a324550 |
257 | } |
258 | |
259 | //======================================================================= |
260 | //function : SetLabels |
261 | //purpose : |
262 | //======================================================================= |
263 | void AIS_ColorScale::SetLabels (const TColStd_SequenceOfExtendedString& theSeq) |
264 | { |
265 | myLabels.Clear(); |
266 | for (Standard_Integer i = 1; i <= theSeq.Length(); i++) |
267 | myLabels.Append (theSeq.Value (i)); |
268 | } |
269 | |
270 | //======================================================================= |
271 | //function : SetColors |
272 | //purpose : |
273 | //======================================================================= |
274 | void AIS_ColorScale::SetColors (const Aspect_SequenceOfColor& theSeq) |
275 | { |
276 | myColors.Clear(); |
277 | for (Standard_Integer i = 1; i <= theSeq.Length(); i++) |
278 | myColors.Append (theSeq.Value (i)); |
279 | } |
280 | |
281 | //======================================================================= |
282 | //function : SetLabelPosition |
283 | //purpose : |
284 | //======================================================================= |
285 | void AIS_ColorScale::SetLabelPosition (const Aspect_TypeOfColorScalePosition thePos) |
286 | { |
287 | if (myLabelPos == thePos) |
288 | return; |
289 | |
290 | myLabelPos = thePos; |
291 | } |
292 | |
293 | //======================================================================= |
294 | //function : SetTitlePosition |
295 | //purpose : |
296 | //======================================================================= |
297 | void AIS_ColorScale::SetTitlePosition (const Aspect_TypeOfColorScalePosition thePos) |
298 | { |
299 | if (myTitlePos == thePos) |
300 | return; |
301 | |
302 | myTitlePos = thePos; |
303 | } |
304 | |
305 | //======================================================================= |
306 | //function : SetReversed |
307 | //purpose : |
308 | //======================================================================= |
309 | void AIS_ColorScale::SetReversed (const Standard_Boolean theReverse) |
310 | { |
311 | if (myReversed == theReverse) |
312 | return; |
313 | |
314 | myReversed = theReverse; |
315 | } |
316 | |
317 | //======================================================================= |
318 | //function : SetLabelAtBorder |
319 | //purpose : |
320 | //======================================================================= |
321 | void AIS_ColorScale::SetLabelAtBorder (const Standard_Boolean theOn) |
322 | { |
323 | if (myAtBorder == theOn) |
324 | return; |
325 | |
326 | myAtBorder = theOn; |
327 | } |
328 | |
329 | //======================================================================= |
330 | //function : GetPosition |
331 | //purpose : |
332 | //======================================================================= |
333 | void AIS_ColorScale::GetPosition (Standard_Real& theX, Standard_Real& theY) const |
334 | { |
335 | theX = myXPos; |
336 | theY = myYPos; |
337 | } |
338 | |
339 | //======================================================================= |
340 | //function : SetPosition |
341 | //purpose : |
342 | //======================================================================= |
b4b2ecca |
343 | void AIS_ColorScale::SetPosition (const Standard_Integer theX, const Standard_Integer theY) |
7a324550 |
344 | { |
345 | if (myXPos == theX && myYPos == theY) |
346 | return; |
347 | |
348 | myXPos = theX; |
349 | myYPos = theY; |
350 | } |
351 | |
352 | //======================================================================= |
353 | //function : SetXPosition |
354 | //purpose : |
355 | //======================================================================= |
b4b2ecca |
356 | void AIS_ColorScale::SetXPosition (const Standard_Integer theX) |
7a324550 |
357 | { |
358 | SetPosition (theX, GetYPosition()); |
359 | } |
360 | |
361 | //======================================================================= |
362 | //function : SetYPosition |
363 | //purpose : |
364 | //======================================================================= |
b4b2ecca |
365 | void AIS_ColorScale::SetYPosition (const Standard_Integer theY) |
7a324550 |
366 | { |
367 | SetPosition (GetXPosition(), theY); |
368 | } |
369 | |
370 | //======================================================================= |
371 | //function : GetSize |
372 | //purpose : |
373 | //======================================================================= |
180f89a2 |
374 | void AIS_ColorScale::GetSize (Standard_Integer& theBreadth, Standard_Integer& theHeight) const |
7a324550 |
375 | { |
180f89a2 |
376 | theBreadth = myBreadth; |
7a324550 |
377 | theHeight = myHeight; |
378 | } |
379 | |
380 | //======================================================================= |
381 | //function : SetSize |
382 | //purpose : |
383 | //======================================================================= |
180f89a2 |
384 | void AIS_ColorScale::SetSize (const Standard_Integer theBreadth, const Standard_Integer theHeight) |
7a324550 |
385 | { |
180f89a2 |
386 | if (myBreadth == theBreadth && myHeight == theHeight) |
7a324550 |
387 | return; |
388 | |
180f89a2 |
389 | myBreadth = theBreadth; |
7a324550 |
390 | myHeight = theHeight; |
391 | } |
392 | |
393 | //======================================================================= |
180f89a2 |
394 | //function : SetBreadth |
7a324550 |
395 | //purpose : |
396 | //======================================================================= |
180f89a2 |
397 | void AIS_ColorScale::SetBreadth (const Standard_Integer theWidth) |
7a324550 |
398 | { |
399 | SetSize (theWidth, GetHeight()); |
400 | } |
401 | |
402 | //======================================================================= |
403 | //function : SetHeight |
404 | //purpose : |
405 | //======================================================================= |
b4b2ecca |
406 | void AIS_ColorScale::SetHeight (const Standard_Integer theHeight) |
7a324550 |
407 | { |
180f89a2 |
408 | SetSize (GetBreadth(), theHeight); |
7a324550 |
409 | } |
410 | |
411 | //======================================================================= |
412 | //function : SizeHint |
413 | //purpose : |
414 | //======================================================================= |
415 | void AIS_ColorScale::SizeHint (Standard_Integer& theWidth, Standard_Integer& theHeight) const |
416 | { |
417 | Standard_Integer aNum = GetNumberOfIntervals(); |
418 | |
419 | Standard_Integer aSpacer = 5; |
420 | Standard_Integer aTextWidth = 0; |
421 | Standard_Integer aTextHeight = TextHeight (""); |
422 | Standard_Integer aColorWidth = 20; |
423 | |
424 | if (GetLabelPosition() != Aspect_TOCSP_NONE) |
180f89a2 |
425 | { |
426 | for (Standard_Integer idx = (IsLabelAtBorder() ? 0 : 1); idx <= aNum; idx++) |
427 | aTextWidth = Max (aTextWidth, TextWidth (GetLabel (idx))); |
428 | } |
7a324550 |
429 | |
430 | Standard_Integer aScaleWidth = 0; |
431 | Standard_Integer aScaleHeight = 0; |
432 | |
7a324550 |
433 | aScaleWidth = aColorWidth + aTextWidth + ( aTextWidth ? 3 : 2 ) * aSpacer; |
180f89a2 |
434 | aScaleHeight = (Standard_Integer)( 1.5 * ( aNum + (IsLabelAtBorder() ? 2 : 1) ) * aTextHeight ); |
7a324550 |
435 | |
180f89a2 |
436 | Standard_Integer aTitleWidth = 0; |
437 | Standard_Integer aTitleHeight = 0; |
7a324550 |
438 | if (GetTitle().Length()) |
439 | { |
440 | aTitleHeight = TextHeight (GetTitle()) + aSpacer; |
441 | aTitleWidth = TextWidth (GetTitle()) + 10; |
442 | } |
443 | |
444 | theWidth = Max (aTitleWidth, aScaleWidth); |
445 | theHeight = aScaleHeight + aTitleHeight; |
446 | } |
447 | |
448 | //======================================================================= |
449 | //function : Format |
450 | //purpose : |
451 | //======================================================================= |
452 | TCollection_AsciiString AIS_ColorScale::Format() const |
453 | { |
454 | return GetFormat(); |
455 | } |
456 | |
457 | //======================================================================= |
180f89a2 |
458 | //function : GetIntervalValue |
7a324550 |
459 | //purpose : |
460 | //======================================================================= |
180f89a2 |
461 | Standard_Real AIS_ColorScale::GetIntervalValue (const Standard_Integer theIndex) const |
7a324550 |
462 | { |
180f89a2 |
463 | if (GetNumberOfIntervals() <= 0) |
464 | return 0.; |
7a324550 |
465 | |
180f89a2 |
466 | if (IsLogarithmic()) |
24a88697 |
467 | { |
468 | Standard_Real aMin = myMin > 0 ? myMin : 1.0; |
469 | Standard_Real aDivisor = std::pow (myMax/aMin, 1.0/myInterval); |
470 | return aMin*std::pow (aDivisor,theIndex); |
471 | } |
180f89a2 |
472 | |
473 | Standard_Real aNum = 0; |
474 | if (GetNumberOfIntervals() > 0) |
475 | aNum = GetMin() + theIndex * ( Abs (GetMax() - GetMin()) / GetNumberOfIntervals() ); |
476 | return aNum; |
24a88697 |
477 | } |
478 | |
479 | //======================================================================= |
7a324550 |
480 | //function : HueFromValue |
481 | //purpose : |
482 | //======================================================================= |
483 | Standard_Integer AIS_ColorScale::HueFromValue (const Standard_Integer theValue, |
484 | const Standard_Integer theMin, const Standard_Integer theMax) |
485 | { |
486 | Standard_Integer aMinLimit (0), aMaxLimit (230); |
487 | |
488 | Standard_Integer aHue = aMaxLimit; |
489 | if (theMin != theMax) |
490 | aHue = (Standard_Integer)( aMaxLimit - ( aMaxLimit - aMinLimit ) * ( theValue - theMin ) / ( theMax - theMin ) ); |
491 | |
492 | aHue = Min (Max (aMinLimit, aHue), aMaxLimit); |
493 | |
494 | return aHue; |
495 | } |
496 | |
497 | //======================================================================= |
498 | //function : FindColor |
499 | //purpose : |
500 | //======================================================================= |
501 | Standard_Boolean AIS_ColorScale::FindColor (const Standard_Real theValue, |
502 | Quantity_Color& theColor) const |
503 | { |
d5514578 |
504 | if (theValue < myMin || theValue > myMax || myMax < myMin) |
505 | { |
506 | theColor = Quantity_Color(); |
507 | return Standard_False; |
508 | } |
509 | |
510 | if (GetColorType() == Aspect_TOCSD_USER) |
511 | { |
512 | Standard_Integer anIndex = 0; |
513 | if (Abs (myMax - myMin) > Precision::Approximation()) |
514 | { |
515 | anIndex = (theValue - myMin < Precision::Confusion()) |
516 | ? 1 |
517 | : Standard_Integer (Ceiling (( theValue - myMin ) / ( (myMax - myMin) / myInterval))); |
518 | } |
519 | |
520 | if (anIndex <= 0 || anIndex > myColors.Length()) |
521 | { |
522 | theColor = Quantity_Color(); |
523 | return Standard_False; |
524 | } |
525 | |
526 | theColor = myColors.Value (anIndex); |
527 | return Standard_True; |
528 | } |
529 | |
7a324550 |
530 | return FindColor (theValue, myMin, myMax, myInterval, theColor); |
531 | } |
532 | |
533 | //======================================================================= |
534 | //function : FindColor |
535 | //purpose : |
536 | //======================================================================= |
537 | Standard_Boolean AIS_ColorScale::FindColor (const Standard_Real theValue, |
538 | const Standard_Real theMin, |
539 | const Standard_Real theMax, |
540 | const Standard_Integer theColorsCount, |
541 | Quantity_Color& theColor) |
542 | { |
543 | if (theValue < theMin || theValue > theMax || theMax < theMin) |
544 | return Standard_False; |
545 | |
546 | else |
547 | { |
548 | Standard_Real anIntervNumber = 0; |
549 | if(Abs (theMax-theMin) > Precision::Approximation()) |
550 | anIntervNumber = Floor (Standard_Real (theColorsCount) * ( theValue - theMin ) / ( theMax - theMin )); |
551 | |
552 | Standard_Integer anInterv = Standard_Integer (anIntervNumber); |
553 | |
554 | theColor = Quantity_Color (HueFromValue (anInterv, 0, theColorsCount - 1), 1.0, 1.0, Quantity_TOC_HLS); |
555 | |
556 | return Standard_True; |
557 | } |
558 | } |
559 | |
560 | //======================================================================= |
561 | //function : Compute |
562 | //purpose : |
563 | //======================================================================= |
564 | void AIS_ColorScale::Compute(const Handle(PrsMgr_PresentationManager3d)& /*thePresentationManager*/, |
565 | const Handle(Prs3d_Presentation)& thePresentation, |
566 | const Standard_Integer /*theMode*/) |
567 | { |
7a324550 |
568 | Handle(V3d_Viewer) aViewer= GetContext()->CurrentViewer(); |
569 | aViewer->InitActiveViews(); |
7a324550 |
570 | Standard_Integer aNum = GetNumberOfIntervals(); |
571 | Aspect_TypeOfColorScalePosition aLabPos = GetLabelPosition(); |
572 | |
573 | Standard_Integer aSpacer = 5; |
574 | Standard_Integer aTextWidth = 0; |
575 | Standard_Integer aTextHeight = myTextHeight; |
576 | Standard_Boolean toDrawLabel = GetLabelPosition() != Aspect_TOCSP_NONE; |
577 | TCollection_ExtendedString aTitle = GetTitle(); |
578 | Standard_Integer aTitleHeight = aSpacer; |
180f89a2 |
579 | Quantity_Color aFgColor (hasOwnColor ? myOwnColor : Quantity_NOC_WHITE); |
7a324550 |
580 | |
581 | // Draw title |
582 | if (aTitle.Length()) |
583 | { |
584 | aTitleHeight += myTextHeight + aSpacer; |
7c65581d |
585 | drawText (thePresentation, aTitle, (Standard_Integer)myXPos + aSpacer, myHeight - ((Standard_Integer)myYPos - 2 * aSpacer + aTitleHeight), aFgColor); |
7a324550 |
586 | } |
587 | |
588 | Standard_Boolean toReverse = IsReversed(); |
589 | |
590 | Aspect_SequenceOfColor aColors; |
180f89a2 |
591 | for (Standard_Integer i = 1; i <= aNum; i++) |
7a324550 |
592 | { |
593 | if (toReverse) |
594 | { |
180f89a2 |
595 | aColors.Prepend (GetIntervalColor (i)); |
7a324550 |
596 | } |
597 | else |
598 | { |
180f89a2 |
599 | aColors.Append (GetIntervalColor (i)); |
7a324550 |
600 | } |
601 | } |
602 | |
180f89a2 |
603 | TColStd_SequenceOfExtendedString aLabels; |
604 | Standard_Integer aLabCount = IsLabelAtBorder() ? aNum + 1 : aNum; |
605 | for (Standard_Integer i = 1; i <= aLabCount; i++) |
7a324550 |
606 | { |
607 | if (toReverse) |
180f89a2 |
608 | { |
609 | aLabels.Prepend (GetLabel (i)); |
610 | } |
7a324550 |
611 | else |
180f89a2 |
612 | { |
613 | aLabels.Append (GetLabel (i)); |
614 | } |
7a324550 |
615 | } |
616 | |
617 | if (toDrawLabel) |
618 | for (Standard_Integer i = 1; i <= aLabels.Length(); i++) |
619 | aTextWidth = Max (aTextWidth, TextWidth (aLabels.Value (i))); |
620 | |
b4b2ecca |
621 | Standard_Integer aSpc = ( myHeight - ( ( Min (aLabCount, 2) + Abs (aLabCount - aNum - 1) ) * aTextHeight ) - aTitleHeight ); |
7a324550 |
622 | Standard_Real aVal = aSpc != 0 ? 1.0 * ( aLabCount - Min (aLabCount, 0) ) * aTextHeight / aSpc : 0; |
623 | Standard_Real anIPart; |
624 | Standard_Real anFPart = modf (aVal, &anIPart); |
625 | Standard_Integer aFilter = (Standard_Integer)anIPart + ( anFPart != 0 ? 1 : 0 ); |
626 | |
b4b2ecca |
627 | Standard_Real aStep = 1.0 * ( myHeight - (aLabCount - aNum + Abs (aLabCount - aNum - 1)) * aTextHeight - aTitleHeight ) / aNum; |
7a324550 |
628 | |
629 | Standard_Integer anAscent = 0; |
180f89a2 |
630 | Standard_Integer aColorBreadth = Max (5, Min (20, myBreadth - aTextWidth - 3 * aSpacer)); |
7a324550 |
631 | if (aLabPos == Aspect_TOCSP_CENTER || !toDrawLabel) |
180f89a2 |
632 | aColorBreadth += aTextWidth; |
7a324550 |
633 | |
634 | // Draw colors |
635 | Standard_Integer aX = (Standard_Integer)myXPos + aSpacer; |
636 | if (aLabPos == Aspect_TOCSP_LEFT) |
637 | aX += aTextWidth + ( aTextWidth ? 1 : 0 ) * aSpacer; |
638 | |
639 | Standard_Real anOffset = 1.0 * aTextHeight / 2 * ( aLabCount - aNum + Abs (aLabCount - aNum - 1) ); |
640 | anOffset += 2*aSpacer; |
641 | Handle (Graphic3d_Group) aGroup = Prs3d_Root::CurrentGroup (thePresentation); |
642 | Handle (Graphic3d_ArrayOfTriangles) aPrim; |
643 | Standard_Integer anEdgesPerColor = 6; |
644 | Standard_Integer aVerticiesPerColor = 4; |
645 | aPrim = new Graphic3d_ArrayOfTriangles (aColors.Length()*aVerticiesPerColor, aColors.Length()*anEdgesPerColor, 0, 1); |
646 | Standard_Integer aVertIndex = 1; |
647 | for (Standard_Integer i = 1; i <= aColors.Length() && aStep > 0; i++) |
648 | { |
649 | Standard_Integer aY = (Standard_Integer)( myYPos + ( i - 1 )* aStep + anOffset ); |
650 | Standard_Integer aColorHeight = (Standard_Integer)( myYPos + ( i ) * aStep + anOffset ) - aY; |
651 | aPrim->AddVertex (gp_Pnt (aX, aY, 0.0), aColors.Value( i )); |
180f89a2 |
652 | aPrim->AddVertex (gp_Pnt (aX+aColorBreadth, aY, 0.0), aColors.Value( i )); |
7a324550 |
653 | aPrim->AddVertex (gp_Pnt (aX, aY+aColorHeight, 0.0), aColors.Value( i )); |
180f89a2 |
654 | aPrim->AddVertex (gp_Pnt (aX+aColorBreadth, aY+aColorHeight, 0.0), aColors.Value( i )); |
7a324550 |
655 | aPrim->AddEdge(aVertIndex); |
656 | aPrim->AddEdge(aVertIndex+1); |
657 | aPrim->AddEdge(aVertIndex+2); |
658 | aPrim->AddEdge(aVertIndex+1); |
659 | aPrim->AddEdge(aVertIndex+2); |
660 | aPrim->AddEdge(aVertIndex+3); |
661 | aVertIndex += 4; |
662 | } |
663 | aGroup->AddPrimitiveArray (aPrim); |
664 | |
665 | if (aStep > 0) |
7c65581d |
666 | drawFrame (thePresentation, aX - 1, (Standard_Integer)(myYPos + anOffset - 1), aColorBreadth + 2, (Standard_Integer)(aColors.Length() * aStep + 2), aFgColor); |
7a324550 |
667 | |
668 | // Draw Labels |
669 | anOffset = 1.0 * Abs (aLabCount - aNum - 1) * ( aStep - aTextHeight ) / 2 + 1.0 * Abs (aLabCount - aNum - 1) * aTextHeight / 2; |
670 | anOffset += 2*aSpacer; |
671 | if (toDrawLabel && aLabels.Length() && aFilter > 0) |
672 | { |
673 | Standard_Integer i1 = 0; |
674 | Standard_Integer i2 = aLabCount - 1; |
675 | Standard_Integer aLast1( i1 ), aLast2( i2 ); |
676 | aX = (Standard_Integer)myXPos + aSpacer; |
677 | switch (aLabPos) |
678 | { |
679 | case Aspect_TOCSP_NONE: |
680 | case Aspect_TOCSP_LEFT: |
681 | break; |
682 | case Aspect_TOCSP_CENTER: |
180f89a2 |
683 | aX += ( aColorBreadth - aTextWidth ) / 2; |
7a324550 |
684 | break; |
685 | case Aspect_TOCSP_RIGHT: |
180f89a2 |
686 | aX += aColorBreadth + aSpacer; |
7a324550 |
687 | break; |
688 | } |
689 | while (i2 - i1 >= aFilter || ( i2 == 0 && i1 == 0 )) |
690 | { |
691 | Standard_Integer aPos1 = i1; |
692 | Standard_Integer aPos2 = aLabCount - 1 - i2; |
693 | if (aFilter && !( aPos1 % aFilter )) |
694 | { |
7c65581d |
695 | drawText (thePresentation, aLabels.Value (i1 + 1), aX, (Standard_Integer)( myYPos + i1 * aStep + anAscent + anOffset ), aFgColor); |
7a324550 |
696 | aLast1 = i1; |
697 | } |
698 | if (aFilter && !( aPos2 % aFilter )) |
699 | { |
7c65581d |
700 | drawText (thePresentation, aLabels.Value (i2 + 1), aX, (Standard_Integer)( myYPos + i2 * aStep + anAscent + anOffset ), aFgColor); |
7a324550 |
701 | aLast2 = i2; |
702 | } |
703 | i1++; |
704 | i2--; |
705 | } |
706 | Standard_Integer aPos = i1; |
707 | Standard_Integer i0 = -1; |
708 | while (aPos <= i2 && i0 == -1) |
709 | { |
710 | if (aFilter && !( aPos % aFilter ) && Abs (aPos - aLast1) >= aFilter && Abs (aPos - aLast2) >= aFilter) |
711 | i0 = aPos; |
712 | aPos++; |
713 | } |
714 | |
715 | if (i0 != -1) |
7c65581d |
716 | drawText (thePresentation, aLabels.Value (i0 + 1), aX, (Standard_Integer)( myYPos + i0 * aStep + anAscent + anOffset ), aFgColor); |
7a324550 |
717 | } |
718 | } |
719 | |
720 | //======================================================================= |
7c65581d |
721 | //function : drawFrame |
7a324550 |
722 | //purpose : |
723 | //======================================================================= |
7c65581d |
724 | void AIS_ColorScale::drawFrame (const Handle(Prs3d_Presentation)& thePresentation, |
7a324550 |
725 | const Standard_Integer theX, const Standard_Integer theY, |
726 | const Standard_Integer theWidth, const Standard_Integer theHeight, |
727 | const Quantity_Color& theColor) |
728 | { |
729 | Handle (Graphic3d_Group) aGroup = Prs3d_Root::CurrentGroup (thePresentation); |
730 | Handle(Graphic3d_ArrayOfPolylines) aPrim = new Graphic3d_ArrayOfPolylines(5); |
731 | aPrim->AddVertex (theX,theY,0.0); |
732 | aPrim->AddVertex (theX+theWidth,theY,0.0); |
733 | aPrim->AddVertex (theX+theWidth,theY+theHeight,0.0); |
734 | aPrim->AddVertex (theX,theY+theHeight,0.0); |
735 | aPrim->AddVertex (theX,theY,0.0); |
180f89a2 |
736 | Handle(Prs3d_LineAspect) anAspect = |
737 | new Prs3d_LineAspect (theColor, Aspect_TOL_SOLID, 1.0); |
7a324550 |
738 | anAspect->SetColor (theColor); |
739 | aGroup->SetPrimitivesAspect (anAspect->Aspect()); |
740 | aGroup->AddPrimitiveArray (aPrim); |
741 | } |
742 | |
743 | //======================================================================= |
7c65581d |
744 | //function : drawText |
7a324550 |
745 | //purpose : |
746 | //======================================================================= |
7c65581d |
747 | void AIS_ColorScale::drawText (const Handle(Prs3d_Presentation)& thePresentation, |
7a324550 |
748 | const TCollection_ExtendedString& theText, |
749 | const Standard_Integer theX, const Standard_Integer theY, |
750 | const Quantity_Color& theColor) |
751 | { |
752 | if (!myDrawer->HasOwnTextAspect()) |
753 | { |
754 | myDrawer->SetTextAspect (new Prs3d_TextAspect()); |
755 | *myDrawer->TextAspect()->Aspect() = *myDrawer->Link()->TextAspect()->Aspect(); |
756 | } |
757 | Handle(Prs3d_TextAspect) anAspect = myDrawer->TextAspect(); |
758 | anAspect->SetColor (theColor); |
759 | anAspect->SetHeight (myTextHeight); |
760 | anAspect->SetHorizontalJustification (Graphic3d_HTA_LEFT); |
761 | anAspect->SetVerticalJustification (Graphic3d_VTA_BOTTOM); |
762 | anAspect->Aspect()->SetTextZoomable (Standard_True); |
763 | anAspect->Aspect()->SetTextAngle (0.0); |
764 | anAspect->Aspect()->SetTextFontAspect (Font_FA_Regular); |
765 | Prs3d_Text::Draw (thePresentation, anAspect, theText,gp_Pnt (theX,theY,0.0)); |
766 | } |
767 | |
768 | //======================================================================= |
769 | //function : TextWidth |
770 | //purpose : |
771 | //======================================================================= |
772 | Standard_Integer AIS_ColorScale::TextWidth (const TCollection_ExtendedString& theText) const |
773 | { |
774 | Standard_Integer aWidth, anAscent, aDescent; |
775 | TextSize (theText, GetTextHeight(), aWidth, anAscent, aDescent); |
776 | return aWidth; |
777 | } |
778 | |
779 | //======================================================================= |
780 | //function : TextHeight |
781 | //purpose : |
782 | //======================================================================= |
783 | Standard_Integer AIS_ColorScale::TextHeight (const TCollection_ExtendedString& theText) const |
784 | { |
785 | Standard_Integer aWidth, anAscent, aDescent; |
786 | TextSize (theText, GetTextHeight(), aWidth, anAscent, aDescent); |
787 | return anAscent+aDescent; |
788 | } |
789 | |
790 | //======================================================================= |
791 | //function : TextSize |
792 | //purpose : |
793 | //======================================================================= |
794 | void AIS_ColorScale::TextSize (const TCollection_ExtendedString& theText, const Standard_Integer theHeight, Standard_Integer& theWidth, Standard_Integer& theAscent, Standard_Integer& theDescent) const |
795 | { |
4b1c8733 |
796 | const Handle(Graphic3d_CView)& aView = GetContext()->CurrentViewer()->ActiveView()->View(); |
7a324550 |
797 | Standard_ShortReal aWidth(10.0), anAscent(1.0), aDescent(1.0); |
798 | TCollection_AsciiString aText (theText.ToExtString(), '?'); |
4b1c8733 |
799 | GetContext()->CurrentViewer()->Driver()->TextSize (aView, aText.ToCString(), (Standard_ShortReal)theHeight, aWidth, anAscent, aDescent); |
7a324550 |
800 | theWidth = (Standard_Integer)aWidth; |
801 | theAscent = (Standard_Integer)anAscent; |
802 | theDescent = (Standard_Integer)aDescent; |
803 | } |