625e1958 |
1 | // Created on: 2015-12-23 |
2 | // Created by: Anastasia BORISOVA |
3 | // Copyright (c) 2015 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 | #include <AIS_Manipulator.hxx> |
17 | |
18 | #include <AIS_InteractiveContext.hxx> |
19 | #include <AIS_ManipulatorOwner.hxx> |
20 | #include <gce_MakeDir.hxx> |
21 | #include <GeomAPI_ExtremaCurveCurve.hxx> |
22 | #include <GeomAPI_IntCS.hxx> |
23 | #include <Geom_Circle.hxx> |
24 | #include <Geom_Line.hxx> |
25 | #include <Geom_Plane.hxx> |
26 | #include <Geom_Transformation.hxx> |
27 | #include <Prs3d_Root.hxx> |
28 | #include <Prs3d_ShadingAspect.hxx> |
29 | #include <Select3D_SensitiveCircle.hxx> |
30 | #include <Select3D_SensitivePoint.hxx> |
31 | #include <Select3D_SensitiveSegment.hxx> |
32 | #include <Select3D_SensitiveTriangulation.hxx> |
33 | #include <SelectMgr_SequenceOfOwner.hxx> |
34 | #include <StdPrs_ToolDisk.hxx> |
35 | #include <StdPrs_ToolCylinder.hxx> |
36 | #include <StdPrs_ToolSphere.hxx> |
37 | #include <TColgp_Array1OfPnt.hxx> |
38 | #include <V3d_View.hxx> |
39 | |
40 | IMPLEMENT_STANDARD_HANDLE (AIS_Manipulator, AIS_InteractiveObject) |
41 | IMPLEMENT_STANDARD_RTTIEXT(AIS_Manipulator, AIS_InteractiveObject) |
42 | |
43 | IMPLEMENT_HSEQUENCE(AIS_ManipulatorObjectSequence) |
44 | |
45 | //======================================================================= |
46 | //function : init |
47 | //purpose : |
48 | //======================================================================= |
49 | void AIS_Manipulator::init() |
50 | { |
51 | // Create axis in the default coordinate system. The custom position is applied in local transformation. |
52 | myAxes[0] = Axis (gp::OX(), Quantity_NOC_RED); |
53 | myAxes[1] = Axis (gp::OY(), Quantity_NOC_GREEN); |
54 | myAxes[2] = Axis (gp::OZ(), Quantity_NOC_BLUE1); |
55 | |
56 | Graphic3d_MaterialAspect aShadingMaterial; |
57 | aShadingMaterial.SetReflectionModeOff (Graphic3d_TOR_SPECULAR); |
58 | aShadingMaterial.SetMaterialType (Graphic3d_MATERIAL_ASPECT); |
59 | |
60 | myDrawer->SetShadingAspect (new Prs3d_ShadingAspect()); |
61 | myDrawer->ShadingAspect()->Aspect()->SetInteriorStyle (Aspect_IS_SOLID); |
62 | myDrawer->ShadingAspect()->SetColor (Quantity_NOC_WHITE); |
63 | myDrawer->ShadingAspect()->SetMaterial (aShadingMaterial); |
64 | |
65 | Graphic3d_MaterialAspect aHilightMaterial; |
66 | aHilightMaterial.SetColor (Quantity_NOC_AZURE); |
67 | aHilightMaterial.SetReflectionModeOff (Graphic3d_TOR_AMBIENT); |
68 | aHilightMaterial.SetReflectionModeOff (Graphic3d_TOR_DIFFUSE); |
69 | aHilightMaterial.SetReflectionModeOff (Graphic3d_TOR_SPECULAR); |
70 | aHilightMaterial.SetReflectionModeOff (Graphic3d_TOR_EMISSION); |
71 | aHilightMaterial.SetMaterialType (Graphic3d_MATERIAL_ASPECT); |
72 | |
73 | myHighlightAspect = new Prs3d_ShadingAspect(); |
74 | myHighlightAspect->Aspect()->SetInteriorStyle (Aspect_IS_SOLID); |
75 | myHighlightAspect->SetMaterial (aHilightMaterial); |
76 | |
77 | SetSize (100); |
78 | SetZLayer (Graphic3d_ZLayerId_Topmost); |
79 | } |
80 | |
81 | //======================================================================= |
82 | //function : getHighlightPresentation |
83 | //purpose : |
84 | //======================================================================= |
85 | Handle(Prs3d_Presentation) AIS_Manipulator::getHighlightPresentation (const Handle(SelectMgr_EntityOwner)& theOwner) const |
86 | { |
87 | Handle(Prs3d_Presentation) aDummyPrs; |
88 | Handle(AIS_ManipulatorOwner) anOwner = Handle(AIS_ManipulatorOwner)::DownCast (theOwner); |
89 | if (anOwner.IsNull()) |
90 | { |
91 | return aDummyPrs; |
92 | } |
93 | |
94 | switch (anOwner->Mode()) |
95 | { |
96 | case AIS_MM_Translation: return myAxes[anOwner->Index()].TranslatorHighlightPrs(); |
97 | case AIS_MM_Rotation : return myAxes[anOwner->Index()].RotatorHighlightPrs(); |
98 | case AIS_MM_Scaling : return myAxes[anOwner->Index()].ScalerHighlightPrs(); |
99 | case AIS_MM_None : break; |
100 | } |
101 | |
102 | return aDummyPrs; |
103 | } |
104 | |
105 | //======================================================================= |
106 | //function : getGroup |
107 | //purpose : |
108 | //======================================================================= |
109 | Handle(Graphic3d_Group) AIS_Manipulator::getGroup (const Standard_Integer theIndex, const AIS_ManipulatorMode theMode) const |
110 | { |
111 | Handle(Graphic3d_Group) aDummyGroup; |
112 | |
113 | if (theIndex < 0 || theIndex > 2) |
114 | { |
115 | return aDummyGroup; |
116 | } |
117 | |
118 | switch (theMode) |
119 | { |
120 | case AIS_MM_Translation: return myAxes[theIndex].TranslatorGroup(); |
121 | case AIS_MM_Rotation : return myAxes[theIndex].RotatorGroup(); |
122 | case AIS_MM_Scaling : return myAxes[theIndex].ScalerGroup(); |
123 | case AIS_MM_None : break; |
124 | } |
125 | |
126 | return aDummyGroup; |
127 | } |
128 | |
129 | //======================================================================= |
130 | //function : Constructor |
131 | //purpose : |
132 | //======================================================================= |
133 | AIS_Manipulator::AIS_Manipulator() |
134 | : myPosition (gp::XOY()), |
135 | myCurrentIndex (-1), |
136 | myCurrentMode (AIS_MM_None), |
137 | myIsActivationOnDetection (Standard_False), |
138 | myIsZoomPersistentMode (Standard_True), |
139 | myHasStartedTransformation (Standard_False), |
140 | myStartPosition (gp::XOY()), |
141 | myStartPick (0.0, 0.0, 0.0), |
142 | myPrevState (0.0) |
143 | { |
144 | SetInfiniteState(); |
145 | SetMutable (Standard_True); |
146 | SetDisplayMode (AIS_Shaded); |
147 | init(); |
148 | } |
149 | |
150 | //======================================================================= |
151 | //function : Constructor |
152 | //purpose : |
153 | //======================================================================= |
154 | AIS_Manipulator::AIS_Manipulator (const gp_Ax2& thePosition) |
155 | : myPosition (thePosition), |
156 | myCurrentIndex (-1), |
157 | myCurrentMode (AIS_MM_None), |
158 | myIsActivationOnDetection (Standard_False), |
159 | myIsZoomPersistentMode (Standard_True), |
160 | myHasStartedTransformation (Standard_False), |
161 | myStartPosition (gp::XOY()), |
162 | myStartPick (0.0, 0.0, 0.0), |
163 | myPrevState (0.0) |
164 | { |
165 | SetInfiniteState(); |
166 | SetMutable (Standard_True); |
167 | SetDisplayMode (AIS_Shaded); |
168 | init(); |
169 | } |
170 | |
171 | //======================================================================= |
172 | //function : SetPart |
173 | //purpose : |
174 | //======================================================================= |
175 | void AIS_Manipulator::SetPart (const Standard_Integer theAxisIndex, const AIS_ManipulatorMode theMode, const Standard_Boolean theIsEnabled) |
176 | { |
177 | Standard_ProgramError_Raise_if (theAxisIndex < 0 || theAxisIndex > 2, "AIS_Manipulator::SetMode(): axis index should be between 0 and 2"); |
178 | switch (theMode) |
179 | { |
180 | case AIS_MM_Translation: |
181 | myAxes[theAxisIndex].SetTranslation (theIsEnabled); |
182 | break; |
183 | |
184 | case AIS_MM_Rotation: |
185 | myAxes[theAxisIndex].SetRotation (theIsEnabled); |
186 | break; |
187 | |
188 | case AIS_MM_Scaling: |
189 | myAxes[theAxisIndex].SetScaling (theIsEnabled); |
190 | break; |
191 | |
192 | case AIS_MM_None: |
193 | break; |
194 | } |
195 | } |
196 | |
197 | //======================================================================= |
198 | //function : EnableMode |
199 | //purpose : |
200 | //======================================================================= |
201 | void AIS_Manipulator::EnableMode (const AIS_ManipulatorMode theMode) |
202 | { |
203 | if (!IsAttached()) |
204 | { |
205 | return; |
206 | } |
207 | |
208 | const Handle(AIS_InteractiveContext)& aContext = GetContext(); |
209 | if (aContext.IsNull()) |
210 | { |
211 | return; |
212 | } |
213 | |
214 | aContext->Activate (this, theMode); |
215 | } |
216 | |
217 | //======================================================================= |
218 | //function : attachToBox |
219 | //purpose : |
220 | //======================================================================= |
221 | void AIS_Manipulator::attachToBox (const Bnd_Box& theBox) |
222 | { |
223 | if (theBox.IsVoid()) |
224 | { |
225 | return; |
226 | } |
227 | |
228 | Standard_Real anXmin = 0.0, anYmin = 0.0, aZmin = 0.0, anXmax = 0.0, anYmax = 0.0, aZmax = 0.0; |
229 | theBox.Get (anXmin, anYmin, aZmin, anXmax, anYmax, aZmax); |
230 | |
231 | gp_Ax2 aPosition = gp::XOY(); |
232 | aPosition.SetLocation (gp_Pnt ((anXmin + anXmax) * 0.5, (anYmin + anYmax) * 0.5, (aZmin + aZmax) * 0.5)); |
233 | SetPosition (aPosition); |
234 | } |
235 | |
236 | //======================================================================= |
237 | //function : adjustSize |
238 | //purpose : |
239 | //======================================================================= |
240 | void AIS_Manipulator::adjustSize (const Bnd_Box& theBox) |
241 | { |
242 | Standard_Real aXmin = 0., aYmin = 0., aZmin = 0., aXmax = 0., aYmax = 0., aZmax = 0.0; |
243 | theBox.Get (aXmin, aYmin, aZmin, aXmax, aYmax, aZmax); |
244 | Standard_Real aXSize = aXmax - aXmin; |
245 | Standard_Real aYSize = aYmax - aYmin; |
246 | Standard_Real aZSize = aZmax - aZmin; |
247 | |
248 | SetSize ((Standard_ShortReal) (Max (aXSize, Max (aYSize, aZSize)) * 0.5)); |
249 | } |
250 | |
251 | //======================================================================= |
252 | //function : Attach |
253 | //purpose : |
254 | //======================================================================= |
255 | void AIS_Manipulator::Attach (const Handle(AIS_InteractiveObject)& theObject, const OptionsForAttach& theOptions) |
256 | { |
257 | if (theObject->IsKind (STANDARD_TYPE(AIS_Manipulator))) |
258 | { |
259 | return; |
260 | } |
261 | |
262 | Handle(AIS_ManipulatorObjectSequence) aSeq = new AIS_ManipulatorObjectSequence(); |
263 | aSeq->Append (theObject); |
264 | Attach (aSeq, theOptions); |
265 | } |
266 | |
267 | //======================================================================= |
268 | //function : Attach |
269 | //purpose : |
270 | //======================================================================= |
271 | void AIS_Manipulator::Attach (const Handle(AIS_ManipulatorObjectSequence)& theObjects, const OptionsForAttach& theOptions) |
272 | { |
273 | if (theObjects->Size() < 1) |
274 | { |
275 | return; |
276 | } |
277 | |
278 | SetOwner (theObjects); |
279 | Bnd_Box aBox; |
280 | const Handle(AIS_InteractiveObject)& aCurObject = theObjects->Value (theObjects->Lower()); |
281 | aCurObject->BoundingBox (aBox); |
282 | |
283 | if (theOptions.AdjustPosition) |
284 | { |
285 | attachToBox (aBox); |
286 | } |
287 | |
288 | if (theOptions.AdjustSize) |
289 | { |
290 | adjustSize (aBox); |
291 | } |
292 | |
293 | const Handle(AIS_InteractiveContext)& aContext = Object()->GetContext(); |
294 | if (!aContext.IsNull()) |
295 | { |
296 | if (!aContext->IsDisplayed (this)) |
297 | { |
298 | aContext->Display (this, Standard_False); |
299 | } |
300 | else |
301 | { |
302 | aContext->Update (this, Standard_False); |
303 | aContext->RecomputeSelectionOnly (this); |
304 | } |
305 | |
306 | aContext->Load (this); |
307 | aContext->CurrentViewer()->RedrawImmediate(); |
308 | } |
309 | |
310 | if (theOptions.EnableModes) |
311 | { |
312 | EnableMode (AIS_MM_Rotation); |
313 | EnableMode (AIS_MM_Translation); |
314 | EnableMode (AIS_MM_Scaling); |
315 | } |
316 | } |
317 | |
318 | //======================================================================= |
319 | //function : Detach |
320 | //purpose : |
321 | //======================================================================= |
322 | void AIS_Manipulator::Detach() |
323 | { |
324 | DeactivateCurrentMode(); |
325 | |
326 | if (!IsAttached()) |
327 | { |
328 | return; |
329 | } |
330 | |
331 | Handle(AIS_InteractiveObject) anObject = Object(); |
332 | const Handle(AIS_InteractiveContext)& aContext = anObject->GetContext(); |
333 | if (!aContext.IsNull()) |
334 | { |
335 | aContext->Remove (this, Standard_False); |
336 | } |
337 | |
338 | SetOwner (NULL); |
339 | } |
340 | |
341 | //======================================================================= |
342 | //function : Objects |
343 | //purpose : |
344 | //======================================================================= |
345 | Handle(AIS_ManipulatorObjectSequence) AIS_Manipulator::Objects() const |
346 | { |
347 | return Handle(AIS_ManipulatorObjectSequence)::DownCast (GetOwner()); |
348 | } |
349 | |
350 | //======================================================================= |
351 | //function : Object |
352 | //purpose : |
353 | //======================================================================= |
354 | Handle(AIS_InteractiveObject) AIS_Manipulator::Object (const Standard_Integer theIndex) const |
355 | { |
356 | Handle(AIS_ManipulatorObjectSequence) anOwner = Handle(AIS_ManipulatorObjectSequence)::DownCast (GetOwner()); |
357 | |
358 | Standard_ProgramError_Raise_if (theIndex < anOwner->Lower() || theIndex > anOwner->Upper(), "AIS_Manipulator::Object(): wrong index value"); |
359 | |
360 | if (anOwner.IsNull() || anOwner->IsEmpty()) |
361 | { |
362 | return NULL; |
363 | } |
364 | |
365 | return anOwner->Value (theIndex); |
366 | } |
367 | |
368 | //======================================================================= |
369 | //function : Object |
370 | //purpose : |
371 | //======================================================================= |
372 | Handle(AIS_InteractiveObject) AIS_Manipulator::Object() const |
373 | { |
374 | return Object (1); |
375 | } |
376 | |
377 | //======================================================================= |
378 | //function : ObjectTransformation |
379 | //purpose : |
380 | //======================================================================= |
381 | Standard_Boolean AIS_Manipulator::ObjectTransformation (const Standard_Integer theMaxX, const Standard_Integer theMaxY, |
382 | const Handle(V3d_View)& theView, gp_Trsf& theTrsf) |
383 | { |
384 | // Initialize start reference data |
385 | if (!myHasStartedTransformation) |
386 | { |
387 | Handle(AIS_ManipulatorObjectSequence) anObjects = Objects(); |
388 | myStartTrsfs.Clear(); |
389 | for (Standard_Integer anIt = anObjects->Lower(); anIt <= anObjects->Upper(); ++anIt) |
390 | { |
391 | myStartTrsfs.Append (anObjects->Value (anIt)->LocalTransformation()); |
392 | } |
393 | myStartPosition = myPosition; |
394 | } |
395 | |
396 | // Get 3d point with projection vector |
397 | Graphic3d_Vec3d anInputPoint; |
398 | Graphic3d_Vec3d aProj; |
399 | theView->ConvertWithProj (theMaxX, theMaxY, anInputPoint.x(), anInputPoint.y(), anInputPoint.z(), aProj.x(), aProj.y(), aProj.z()); |
400 | gp_Lin anInputLine (gp_Pnt (anInputPoint.x(), anInputPoint.y(), anInputPoint.z()), gp_Dir (aProj.x(), aProj.y(), aProj.z())); |
401 | gp_Pnt aNewPosition = gp::Origin(); |
402 | |
403 | switch (myCurrentMode) |
404 | { |
405 | case AIS_MM_Translation: |
406 | { |
407 | gp_Lin aLine (myStartPick, myAxes[myCurrentIndex].Position().Direction()); |
408 | Handle(Geom_Curve) anInputCurve = new Geom_Line (anInputLine); |
409 | Handle(Geom_Curve) aCurve = new Geom_Line (aLine); |
410 | GeomAPI_ExtremaCurveCurve anExtrema (anInputCurve, aCurve); |
411 | gp_Pnt aP1, aP2; |
412 | anExtrema.NearestPoints (aP1, aP2); |
413 | aNewPosition = aP2; |
414 | |
415 | if (!myHasStartedTransformation) |
416 | { |
417 | myStartPick = aNewPosition; |
418 | myHasStartedTransformation = Standard_True; |
419 | return Standard_True; |
420 | } |
421 | |
422 | if (aNewPosition.Distance (myStartPick) < Precision::Confusion()) |
423 | { |
424 | return Standard_False; |
425 | } |
426 | |
427 | gp_Trsf aNewTrsf; |
428 | aNewTrsf.SetTranslation (gp_Vec(myStartPick, aNewPosition)); |
429 | theTrsf *= aNewTrsf; |
430 | break; |
431 | } |
432 | case AIS_MM_Rotation: |
433 | { |
434 | Handle(Geom_Curve) anInputCurve = new Geom_Line (anInputLine); |
435 | Handle(Geom_Surface) aSurface = new Geom_Plane (myPosition.Location(), myAxes[myCurrentIndex].Position().Direction()); |
436 | GeomAPI_IntCS aIntersector (anInputCurve, aSurface); |
437 | if (!aIntersector.IsDone() || aIntersector.NbPoints() < 1) |
438 | { |
439 | return Standard_False; |
440 | } |
441 | |
442 | aNewPosition = aIntersector.Point (1); |
443 | |
444 | if (!myHasStartedTransformation) |
445 | { |
446 | myStartPick = aNewPosition; |
447 | myHasStartedTransformation = Standard_True; |
448 | gp_Dir aStartAxis = gce_MakeDir (myPosition.Location(), myStartPick); |
449 | myPrevState = aStartAxis.AngleWithRef (gce_MakeDir(myPosition.Location(), aNewPosition), myAxes[myCurrentIndex].Position().Direction()); |
450 | return Standard_True; |
451 | } |
452 | |
453 | if (aNewPosition.Distance (myStartPick) < Precision::Confusion()) |
454 | { |
455 | return Standard_False; |
456 | } |
457 | |
458 | gp_Dir aStartAxis = myPosition.Location().IsEqual (myStartPick, Precision::Confusion()) |
459 | ? myAxes[(myCurrentIndex + 1) % 3].Position().Direction() |
460 | : gce_MakeDir (myPosition.Location(), myStartPick); |
461 | |
462 | gp_Dir aCurrentAxis = gce_MakeDir (myPosition.Location(), aNewPosition); |
463 | Standard_Real anAngle = aStartAxis.AngleWithRef (aCurrentAxis, myAxes[myCurrentIndex].Position().Direction()); |
464 | |
465 | // Change value of an angle if it should have different sign. |
466 | if (anAngle * myPrevState < 0 && Abs (anAngle) < M_PI_2) |
467 | { |
468 | Standard_ShortReal aSign = myPrevState > 0 ? -1.0f : 1.0f; |
469 | anAngle = aSign * (M_PI * 2 - anAngle); |
470 | } |
471 | |
472 | if (Abs (anAngle) < Precision::Confusion()) |
473 | { |
474 | return Standard_False; |
475 | } |
476 | |
477 | gp_Trsf aNewTrsf; |
478 | aNewTrsf.SetRotation (myAxes[myCurrentIndex].Position(), anAngle); |
479 | theTrsf *= aNewTrsf; |
480 | myPrevState = anAngle; |
481 | break; |
482 | } |
483 | case AIS_MM_Scaling: |
484 | { |
485 | gp_Lin aLine (myStartPosition.Location(), myAxes[myCurrentIndex].Position().Direction()); |
486 | Handle(Geom_Curve) anInputCurve = new Geom_Line (anInputLine); |
487 | Handle(Geom_Curve) aCurve = new Geom_Line (aLine); |
488 | GeomAPI_ExtremaCurveCurve anExtrema (anInputCurve, aCurve); |
489 | gp_Pnt aTmp; |
490 | anExtrema.NearestPoints (aTmp, aNewPosition); |
491 | |
492 | if (!myHasStartedTransformation) |
493 | { |
494 | myStartPick = aNewPosition; |
495 | myHasStartedTransformation = Standard_True; |
496 | return Standard_True; |
497 | } |
498 | |
499 | if (aNewPosition.Distance (myStartPick) < Precision::Confusion() |
500 | || aNewPosition.Distance (myStartPosition.Location()) < Precision::Confusion()) |
501 | { |
502 | return Standard_False; |
503 | } |
504 | |
505 | Standard_Real aCoeff = myStartPosition.Location().Distance (aNewPosition) |
506 | / myStartPosition.Location().Distance (myStartPick); |
507 | gp_Trsf aNewTrsf; |
508 | aNewTrsf.SetScale (myPosition.Location(), aCoeff); |
509 | |
510 | theTrsf = aNewTrsf; |
511 | break; |
512 | } |
513 | case AIS_MM_None: |
514 | return Standard_False; |
515 | } |
516 | |
517 | return Standard_True; |
518 | } |
519 | |
520 | //======================================================================= |
521 | //function : StartTransform |
522 | //purpose : |
523 | //======================================================================= |
524 | void AIS_Manipulator::StartTransform (const Standard_Integer theX, const Standard_Integer theY, const Handle(V3d_View)& theView) |
525 | { |
526 | if (myHasStartedTransformation) |
527 | { |
528 | return; |
529 | } |
530 | |
531 | gp_Trsf aTrsf; |
532 | ObjectTransformation (theX, theY, theView, aTrsf); |
533 | } |
534 | |
535 | //======================================================================= |
536 | //function : StopTransform |
537 | //purpose : |
538 | //======================================================================= |
539 | void AIS_Manipulator::StopTransform (const Standard_Boolean theToApply) |
540 | { |
541 | if (!IsAttached() || !myHasStartedTransformation) |
542 | { |
543 | return; |
544 | } |
545 | |
546 | myHasStartedTransformation = Standard_False; |
547 | |
548 | if (!theToApply) |
549 | { |
550 | Handle(AIS_ManipulatorObjectSequence) anObjects = Objects(); |
551 | |
552 | for (Standard_Integer anIt = anObjects->Lower(); anIt <= anObjects->Upper(); ++anIt) |
553 | { |
554 | anObjects->Value (anIt)->SetLocalTransformation (myStartTrsfs(anIt)); |
555 | } |
556 | |
557 | SetPosition (myStartPosition); |
558 | } |
559 | } |
560 | |
561 | //======================================================================= |
562 | //function : Transform |
563 | //purpose : |
564 | //======================================================================= |
565 | void AIS_Manipulator::Transform (const gp_Trsf& theTrsf) |
566 | { |
567 | if (!IsAttached() || !myHasStartedTransformation) |
568 | { |
569 | return; |
570 | } |
571 | |
572 | Handle(AIS_ManipulatorObjectSequence) anObjects = Objects(); |
573 | |
574 | for (Standard_Integer anIt = anObjects->Lower(); anIt <= anObjects->Upper(); ++anIt) |
575 | { |
576 | anObjects->Value (anIt)->SetLocalTransformation (theTrsf * myStartTrsfs(anIt)); |
577 | } |
578 | |
579 | if ((myCurrentMode == AIS_MM_Translation && myBehaviorOnTransform.FollowTranslation) |
580 | || (myCurrentMode == AIS_MM_Rotation && myBehaviorOnTransform.FollowRotation)) |
581 | { |
582 | gp_Pnt aPos = myStartPosition.Location().Transformed (theTrsf); |
583 | gp_Dir aVDir = myStartPosition.Direction().Transformed (theTrsf); |
584 | gp_Dir aXDir = myStartPosition.XDirection().Transformed (theTrsf); |
585 | SetPosition (gp_Ax2 (aPos, aVDir, aXDir)); |
586 | } |
587 | } |
588 | |
589 | //======================================================================= |
590 | //function : Transform |
591 | //purpose : |
592 | //======================================================================= |
593 | gp_Trsf AIS_Manipulator::Transform (const Standard_Integer thePX, const Standard_Integer thePY, |
594 | const Handle(V3d_View)& theView) |
595 | { |
596 | gp_Trsf aTrsf; |
597 | if (ObjectTransformation (thePX, thePY, theView, aTrsf)) |
598 | { |
599 | Transform (aTrsf); |
600 | } |
601 | |
602 | return aTrsf; |
603 | } |
604 | |
605 | //======================================================================= |
606 | //function : SetPosition |
607 | //purpose : |
608 | //======================================================================= |
609 | void AIS_Manipulator::SetPosition (const gp_Ax2& thePosition) |
610 | { |
611 | if (!myPosition.Location().IsEqual (thePosition.Location(), Precision::Confusion()) |
612 | || !myPosition.Direction().IsEqual (thePosition.Direction(), Precision::Angular()) |
613 | || !myPosition.XDirection().IsEqual (thePosition.XDirection(), Precision::Angular())) |
614 | { |
615 | myPosition = thePosition; |
616 | myAxes[0].SetPosition (gp_Ax1 (myPosition.Location(), myPosition.XDirection())); |
617 | myAxes[1].SetPosition (gp_Ax1 (myPosition.Location(), myPosition.YDirection())); |
618 | myAxes[2].SetPosition (gp_Ax1 (myPosition.Location(), myPosition.Direction())); |
619 | |
620 | updateTransformation(); |
621 | } |
622 | } |
623 | |
624 | //======================================================================= |
625 | //function : updateTransformation |
626 | //purpose : set local transformation to avoid graphics recomputation |
627 | //======================================================================= |
628 | void AIS_Manipulator::updateTransformation() |
629 | { |
630 | gp_Trsf aTrsf; |
631 | |
632 | if (!myIsZoomPersistentMode) |
633 | { |
634 | aTrsf.SetTransformation (myPosition, gp::XOY()); |
635 | } |
636 | else |
637 | { |
638 | const gp_Dir& aVDir = myPosition.Direction(); |
639 | const gp_Dir& aXDir = myPosition.XDirection(); |
640 | aTrsf.SetTransformation (gp_Ax2 (gp::Origin(), aVDir, aXDir), gp::XOY()); |
641 | } |
642 | |
643 | AIS_InteractiveObject::SetLocalTransformation (aTrsf); |
644 | |
645 | Handle(Geom_Transformation) aGeomTrsf = new Geom_Transformation (this->Transformation()); |
646 | |
647 | for (Standard_Integer anIt = 0; anIt < 3; ++anIt) |
648 | { |
649 | myAxes[anIt].Transform (aGeomTrsf); |
650 | } |
651 | |
652 | if (myIsZoomPersistentMode) |
653 | { |
654 | if (!(GetTransformPersistenceMode () == Graphic3d_TMF_ZoomPers |
655 | && GetTransformPersistencePoint().IsEqual (myPosition.Location(), 0.))) |
656 | { |
657 | setTransformPersistence (Graphic3d_TMF_ZoomPers, myPosition.Location()); |
658 | } |
659 | } |
660 | } |
661 | |
662 | //======================================================================= |
663 | //function : SetSize |
664 | //purpose : |
665 | //======================================================================= |
666 | void AIS_Manipulator::SetSize (const Standard_ShortReal theSideLength) |
667 | { |
668 | for (Standard_Integer anIt = 0; anIt < 3; ++anIt) |
669 | { |
670 | myAxes[anIt].SetSize (theSideLength); |
671 | } |
672 | |
673 | SetToUpdate(); |
674 | } |
675 | |
676 | //======================================================================= |
677 | //function : SetGap |
678 | //purpose : |
679 | //======================================================================= |
680 | void AIS_Manipulator::SetGap (const Standard_ShortReal theValue) |
681 | { |
682 | for (Standard_Integer anIt = 0; anIt < 3; ++anIt) |
683 | { |
684 | myAxes[anIt].SetIndent (theValue); |
685 | } |
686 | |
687 | SetToUpdate(); |
688 | } |
689 | |
690 | //======================================================================= |
691 | //function : DeactivateCurrentMode |
692 | //purpose : |
693 | //======================================================================= |
694 | void AIS_Manipulator::DeactivateCurrentMode() |
695 | { |
696 | if (!myIsActivationOnDetection) |
697 | { |
698 | Handle(Graphic3d_Group) aGroup = getGroup (myCurrentIndex, myCurrentMode); |
699 | if (aGroup.IsNull()) |
700 | { |
701 | return; |
702 | } |
703 | |
704 | Handle(Prs3d_ShadingAspect) anAspect = new Prs3d_ShadingAspect(); |
705 | anAspect->Aspect()->SetInteriorStyle (Aspect_IS_SOLID); |
706 | anAspect->SetMaterial (myDrawer->ShadingAspect()->Material()); |
707 | anAspect->SetTransparency (myDrawer->ShadingAspect()->Transparency()); |
708 | anAspect->SetColor (myAxes[myCurrentIndex].Color()); |
709 | |
710 | aGroup->SetGroupPrimitivesAspect (anAspect->Aspect()); |
711 | } |
712 | |
713 | myCurrentIndex = -1; |
714 | myCurrentMode = AIS_MM_None; |
715 | |
716 | if (myHasStartedTransformation) |
717 | { |
718 | myHasStartedTransformation = Standard_False; |
719 | } |
720 | } |
721 | |
722 | //======================================================================= |
723 | //function : SetZoomPersistence |
724 | //purpose : |
725 | //======================================================================= |
726 | void AIS_Manipulator::SetZoomPersistence (const Standard_Boolean theToEnable) |
727 | { |
728 | if (myIsZoomPersistentMode != theToEnable) |
729 | { |
730 | SetToUpdate(); |
731 | } |
732 | |
733 | myIsZoomPersistentMode = theToEnable; |
734 | |
735 | if (!theToEnable) |
736 | { |
737 | setTransformPersistence (Graphic3d_TMF_None, gp::Origin()); |
738 | } |
739 | |
740 | updateTransformation(); |
741 | } |
742 | |
743 | //======================================================================= |
744 | //function : SetTransformPersistence |
745 | //purpose : |
746 | //======================================================================= |
747 | void AIS_Manipulator::SetTransformPersistence (const Graphic3d_TransModeFlags& theFlag, const gp_Pnt& thePoint) |
748 | { |
749 | Standard_ASSERT_RETURN (!myIsZoomPersistentMode, |
750 | "AIS_Manipulator::SetTransformPersistence: " |
751 | "Custom settings are not supported by this class in ZoomPersistence mode",); |
752 | |
753 | setTransformPersistence (theFlag, thePoint); |
754 | } |
755 | |
756 | //======================================================================= |
757 | //function : setTransformPersistence |
758 | //purpose : |
759 | //======================================================================= |
760 | void AIS_Manipulator::setTransformPersistence (const Graphic3d_TransModeFlags& theFlag, const gp_Pnt& thePoint) |
761 | { |
762 | AIS_InteractiveObject::SetTransformPersistence (theFlag, thePoint); |
763 | |
764 | for (Standard_Integer anIt = 0; anIt < 3; ++anIt) |
765 | { |
766 | myAxes[anIt].SetTransformPersistence (theFlag, thePoint); |
767 | } |
768 | } |
769 | |
770 | //======================================================================= |
771 | //function : SetLocalTransformation |
772 | //purpose : |
773 | //======================================================================= |
774 | void AIS_Manipulator::SetLocalTransformation (const gp_Trsf& /*theTransformation*/) |
775 | { |
776 | Standard_ASSERT_INVOKE ( |
777 | "AIS_Manipulator::SetLocalTransformation: " |
778 | "Custom transformation is not supported by this class"); |
779 | } |
780 | |
781 | //======================================================================= |
782 | //function : Compute |
783 | //purpose : |
784 | //======================================================================= |
785 | void AIS_Manipulator::Compute (const Handle(PrsMgr_PresentationManager3d)& thePrsMgr, |
786 | const Handle(Prs3d_Presentation)& thePrs, |
787 | const Standard_Integer theMode) |
788 | { |
789 | if (theMode != AIS_Shaded) |
790 | { |
791 | return; |
792 | } |
793 | |
794 | thePrs->SetInfiniteState (Standard_True); |
795 | thePrs->SetMutable (Standard_True); |
796 | Handle(Graphic3d_Group) aGroup; |
797 | Handle(Prs3d_ShadingAspect) anAspect = new Prs3d_ShadingAspect(); |
798 | anAspect->Aspect()->SetInteriorStyle (Aspect_IS_SOLID); |
799 | anAspect->SetMaterial (myDrawer->ShadingAspect()->Material()); |
800 | anAspect->SetTransparency (myDrawer->ShadingAspect()->Transparency()); |
801 | |
802 | // Display center |
803 | myCenter.Init (myAxes[0].AxisRadius() * 2.0f, gp::Origin()); |
804 | aGroup = Prs3d_Root::NewGroup (thePrs); |
805 | aGroup->SetPrimitivesAspect (myDrawer->ShadingAspect()->Aspect()); |
806 | aGroup->AddPrimitiveArray (myCenter.Array()); |
807 | |
808 | for (Standard_Integer anIt = 0; anIt < 3; ++anIt) |
809 | { |
810 | // Display axes |
811 | aGroup = Prs3d_Root::NewGroup (thePrs); |
b6472664 |
812 | |
813 | Handle(Prs3d_ShadingAspect) anAspectAx = new Prs3d_ShadingAspect (new Graphic3d_AspectFillArea3d(*anAspect->Aspect())); |
814 | anAspectAx->SetColor (myAxes[anIt].Color()); |
815 | aGroup->SetGroupPrimitivesAspect (anAspectAx->Aspect()); |
816 | myAxes[anIt].Compute (thePrsMgr, thePrs, anAspectAx); |
625e1958 |
817 | myAxes[anIt].SetTransformPersistence (GetTransformPersistenceMode(), |
818 | GetTransformPersistencePoint()); |
819 | } |
820 | |
821 | updateTransformation(); |
822 | } |
823 | |
824 | //======================================================================= |
825 | //function : HilightSelected |
826 | //purpose : |
827 | //======================================================================= |
828 | void AIS_Manipulator::HilightSelected (const Handle(PrsMgr_PresentationManager3d)& thePM, |
829 | const SelectMgr_SequenceOfOwner& theSeq) |
830 | { |
831 | if (theSeq.IsEmpty()) |
832 | { |
833 | return; |
834 | } |
835 | |
836 | if (myIsActivationOnDetection) |
837 | { |
838 | return; |
839 | } |
840 | |
841 | if (!theSeq (1)->IsKind (STANDARD_TYPE (AIS_ManipulatorOwner))) |
842 | { |
843 | thePM->Color (this, GetContext()->HilightColor(), 0); |
844 | return; |
845 | } |
846 | |
847 | Handle(AIS_ManipulatorOwner) anOwner = Handle(AIS_ManipulatorOwner)::DownCast (theSeq (1)); |
848 | myHighlightAspect->Aspect()->SetInteriorColor (GetContext()->HilightColor()); |
849 | Handle(Graphic3d_Group) aGroup = getGroup (anOwner->Index(), anOwner->Mode()); |
850 | if (aGroup.IsNull()) |
851 | { |
852 | return; |
853 | } |
854 | |
855 | aGroup->SetGroupPrimitivesAspect (myHighlightAspect->Aspect()); |
856 | |
857 | myCurrentIndex = anOwner->Index(); |
858 | myCurrentMode = anOwner->Mode(); |
859 | } |
860 | |
861 | //======================================================================= |
862 | //function : ClearSelected |
863 | //purpose : |
864 | //======================================================================= |
865 | void AIS_Manipulator::ClearSelected() |
866 | { |
867 | DeactivateCurrentMode(); |
868 | } |
869 | |
870 | //======================================================================= |
871 | //function : HilightOwnerWithColor |
872 | //purpose : |
873 | //======================================================================= |
874 | void AIS_Manipulator::HilightOwnerWithColor (const Handle(PrsMgr_PresentationManager3d)& thePM, const Quantity_NameOfColor theColor, const Handle(SelectMgr_EntityOwner)& theOwner) |
875 | { |
876 | Handle(AIS_ManipulatorOwner) anOwner = Handle(AIS_ManipulatorOwner)::DownCast (theOwner); |
877 | Handle(Prs3d_Presentation) aPresentation = getHighlightPresentation (anOwner); |
878 | if (aPresentation.IsNull()) |
879 | { |
880 | return; |
881 | } |
882 | aPresentation->Highlight (Aspect_TOHM_COLOR, theColor); |
2831708b |
883 | for (Graphic3d_SequenceOfGroup::Iterator aGroupIter (aPresentation->Groups()); |
884 | aGroupIter.More(); aGroupIter.Next()) |
885 | { |
886 | Handle(Graphic3d_Group)& aGrp = aGroupIter.ChangeValue(); |
887 | if (!aGrp.IsNull() |
888 | && aGrp->IsGroupPrimitivesAspectSet (Graphic3d_ASPECT_FILL_AREA)) |
889 | { |
890 | aGrp->SetGroupPrimitivesAspect (myHighlightAspect->Aspect()); |
891 | } |
892 | } |
625e1958 |
893 | aPresentation->SetZLayer (Graphic3d_ZLayerId_Topmost); |
894 | thePM->AddToImmediateList (aPresentation); |
895 | |
896 | if (myIsActivationOnDetection) |
897 | { |
898 | if (HasActiveMode()) |
899 | { |
900 | DeactivateCurrentMode(); |
901 | } |
902 | |
903 | myCurrentIndex = anOwner->Index(); |
904 | myCurrentMode = anOwner->Mode(); |
905 | } |
906 | } |
907 | |
908 | //======================================================================= |
909 | //function : ComputeSelection |
910 | //purpose : |
911 | //======================================================================= |
912 | void AIS_Manipulator::ComputeSelection (const Handle(SelectMgr_Selection)& theSelection, |
913 | const Standard_Integer theMode) |
914 | { |
915 | //Check mode |
916 | AIS_ManipulatorMode aMode = (AIS_ManipulatorMode) theMode; |
917 | if (aMode == AIS_MM_None) |
918 | { |
919 | return; |
920 | } |
921 | Handle(SelectMgr_EntityOwner) anOwner; |
922 | if (aMode == AIS_MM_None) |
923 | { |
924 | anOwner = new SelectMgr_EntityOwner (this, 5); |
925 | } |
926 | Handle(Select3D_SensitiveTriangulation) aTri; |
927 | if (aMode == AIS_MM_Translation || aMode == AIS_MM_None) |
928 | { |
929 | for (Standard_Integer anIt = 0; anIt < 3; ++anIt) |
930 | { |
931 | const Axis& anAxis = myAxes[anIt]; |
932 | if (aMode != AIS_MM_None) |
933 | { |
934 | anOwner = new AIS_ManipulatorOwner(this, anIt, AIS_MM_Translation, 9); |
935 | } |
936 | // define sensitivity by line |
937 | Handle(Select3D_SensitiveSegment) aLine = new Select3D_SensitiveSegment (anOwner, gp::Origin(), anAxis.TranslatorTipPosition()); |
938 | aLine->SetSensitivityFactor (15); |
939 | theSelection->Add (aLine); |
940 | // enlarge sensitivity by triangulation |
941 | aTri = new Select3D_SensitiveTriangulation (anOwner, anAxis.TranslatorCylinder().Triangulation(), TopLoc_Location(), Standard_True); |
942 | theSelection->Add (aTri); |
943 | aTri = new Select3D_SensitiveTriangulation (anOwner, anAxis.TranslatorArrow().Triangulation(), TopLoc_Location(), Standard_True); |
944 | theSelection->Add (aTri); |
945 | aTri = new Select3D_SensitiveTriangulation (anOwner, anAxis.TranslatorArrowBottom().Triangulation(), TopLoc_Location(), Standard_True); |
946 | theSelection->Add (aTri); |
947 | } |
948 | } |
949 | |
950 | if (aMode == AIS_MM_Rotation || aMode == AIS_MM_None) |
951 | { |
952 | for (Standard_Integer anIt = 0; anIt < 3; ++anIt) |
953 | { |
954 | const Axis& anAxis = myAxes[anIt]; |
955 | if (aMode != AIS_MM_None) |
956 | { |
957 | anOwner = new AIS_ManipulatorOwner (this, anIt, AIS_MM_Rotation, 9); |
958 | } |
959 | // define sensitivity by circle |
960 | Handle(Geom_Circle) aGeomCircle = new Geom_Circle (gp_Ax2 (gp::Origin(), anAxis.ReferenceAxis().Direction()), anAxis.RotatorDiskRadius()); |
961 | Handle(Select3D_SensitiveCircle) aCircle = new Select3D_SensitiveCircle (anOwner, aGeomCircle, Standard_False, anAxis.FacettesNumber()); |
962 | aCircle->SetSensitivityFactor (15); |
963 | theSelection->Add (aCircle); |
964 | // enlarge sensitivity by triangulation |
965 | aTri = new Select3D_SensitiveTriangulation (anOwner, myAxes[anIt].RotatorDisk().Triangulation(), TopLoc_Location(), Standard_True); |
966 | theSelection->Add (aTri); |
967 | } |
968 | } |
969 | |
970 | if (aMode == AIS_MM_Scaling || aMode == AIS_MM_None) |
971 | { |
972 | for (Standard_Integer anIt = 0; anIt < 3; ++anIt) |
973 | { |
974 | if (aMode != AIS_MM_None) |
975 | { |
976 | anOwner = new AIS_ManipulatorOwner (this, anIt, AIS_MM_Scaling, 9); |
977 | } |
978 | // define sensitivity by point |
979 | Handle(Select3D_SensitivePoint) aPnt = new Select3D_SensitivePoint (anOwner, myAxes[anIt].ScalerCubePosition()); |
980 | aPnt->SetSensitivityFactor (15); |
981 | theSelection->Add (aPnt); |
982 | // enlarge sensitivity by triangulation |
983 | aTri = new Select3D_SensitiveTriangulation (anOwner, myAxes[anIt].ScalerCube().Triangulation(), TopLoc_Location(), Standard_True); |
984 | theSelection->Add (aTri); |
985 | } |
986 | } |
987 | } |
988 | |
989 | //======================================================================= |
990 | //class : Cylinder |
991 | //function : Init |
992 | //purpose : |
993 | //======================================================================= |
994 | void AIS_Manipulator::Cylinder::Init (const Standard_ShortReal theBotRad, const Standard_ShortReal theTopRad, |
995 | const Standard_ShortReal theHeight, |
996 | const Standard_Integer theSlicesNb, const Standard_Integer theStacksNb, |
997 | const gp_Ax1& thePosition) |
998 | { |
999 | myPosition = thePosition; |
1000 | myBottomRad = theBotRad; |
1001 | myTopRad = theTopRad; |
1002 | myHeight = theHeight; |
1003 | |
1004 | StdPrs_ToolCylinder aTool (myBottomRad, myTopRad, myHeight, theSlicesNb, theStacksNb); |
1005 | gp_Ax3 aSystem (myPosition.Location(), myPosition.Direction()); |
1006 | gp_Trsf aTrsf; |
1007 | aTrsf.SetTransformation (aSystem, gp_Ax3()); |
1008 | |
1009 | aTool.FillArray (myArray, myTriangulation, aTrsf); |
1010 | } |
1011 | |
1012 | //======================================================================= |
1013 | //class : Disk |
1014 | //function : Init |
1015 | //purpose : |
1016 | //======================================================================= |
1017 | void AIS_Manipulator::Disk::Init (const Standard_ShortReal theInnerRadius, |
1018 | const Standard_ShortReal theOuterRadius, |
1019 | const gp_Ax1& thePosition, |
1020 | const Standard_Integer theSlicesNb, |
1021 | const Standard_Integer theStacksNb) |
1022 | { |
1023 | myPosition = thePosition; |
1024 | myInnerRad = theInnerRadius; |
1025 | myOuterRad = theOuterRadius; |
1026 | |
1027 | StdPrs_ToolDisk aTool (theInnerRadius, theOuterRadius, theSlicesNb, theStacksNb); |
1028 | gp_Ax3 aSystem (myPosition.Location(), myPosition.Direction()); |
1029 | gp_Trsf aTrsf; |
1030 | aTrsf.SetTransformation (aSystem, gp_Ax3()); |
1031 | aTool.FillArray (myArray, myTriangulation, aTrsf); |
1032 | } |
1033 | |
1034 | //======================================================================= |
1035 | //class : Sphere |
1036 | //function : Init |
1037 | //purpose : |
1038 | //======================================================================= |
1039 | void AIS_Manipulator::Sphere::Init (const Standard_ShortReal theRadius, |
1040 | const gp_Pnt& thePosition, |
1041 | const Standard_Integer theSlicesNb, |
1042 | const Standard_Integer theStacksNb) |
1043 | { |
1044 | myPosition = thePosition; |
1045 | myRadius = theRadius; |
1046 | |
1047 | StdPrs_ToolSphere aTool (theRadius, theSlicesNb, theStacksNb); |
1048 | gp_Trsf aTrsf; |
1049 | aTrsf.SetTranslation (gp_Vec(gp::Origin(), thePosition)); |
1050 | aTool.FillArray (myArray, myTriangulation, aTrsf); |
1051 | } |
1052 | |
1053 | //======================================================================= |
1054 | //class : Cube |
1055 | //function : Init |
1056 | //purpose : |
1057 | //======================================================================= |
1058 | void AIS_Manipulator::Cube::Init (const gp_Ax1& thePosition, const Standard_ShortReal theSize) |
1059 | { |
1060 | myArray = new Graphic3d_ArrayOfTriangles (12 * 3, 0, Standard_True); |
1061 | |
1062 | Poly_Array1OfTriangle aPolyTriangles (1, 12); |
1063 | TColgp_Array1OfPnt aPoints (1, 36); |
1064 | NCollection_Array1<gp_Dir> aNormals (1, 12); |
1065 | myTriangulation = new Poly_Triangulation (aPoints, aPolyTriangles); |
1066 | |
1067 | gp_Ax2 aPln (thePosition.Location(), thePosition.Direction()); |
1068 | gp_Pnt aBottomLeft = thePosition.Location().XYZ() - aPln.XDirection().XYZ() * theSize * 0.5 - aPln.YDirection().XYZ() * theSize * 0.5; |
1069 | gp_Pnt aV2 = aBottomLeft.XYZ() + aPln.YDirection().XYZ() * theSize; |
1070 | gp_Pnt aV3 = aBottomLeft.XYZ() + aPln.YDirection().XYZ() * theSize + aPln.XDirection().XYZ() * theSize; |
1071 | gp_Pnt aV4 = aBottomLeft.XYZ() + aPln.XDirection().XYZ() * theSize; |
1072 | gp_Pnt aTopRight = thePosition.Location().XYZ() + thePosition.Direction().XYZ() * theSize |
1073 | + aPln.XDirection().XYZ() * theSize * 0.5 + aPln.YDirection().XYZ() * theSize * 0.5; |
1074 | gp_Pnt aV5 = aTopRight.XYZ() - aPln.YDirection().XYZ() * theSize; |
1075 | gp_Pnt aV6 = aTopRight.XYZ() - aPln.YDirection().XYZ() * theSize - aPln.XDirection().XYZ() * theSize; |
1076 | gp_Pnt aV7 = aTopRight.XYZ() - aPln.XDirection().XYZ() * theSize; |
1077 | |
1078 | gp_Dir aRight ((gp_Vec(aTopRight, aV7) ^ gp_Vec(aTopRight, aV2)).XYZ()); |
1079 | gp_Dir aFront ((gp_Vec(aV3, aV4) ^ gp_Vec(aV3, aV5)).XYZ()); |
1080 | |
1081 | // Bottom |
1082 | addTriangle (0, aBottomLeft, aV2, aV3, -thePosition.Direction()); |
1083 | addTriangle (1, aBottomLeft, aV3, aV4, -thePosition.Direction()); |
1084 | |
1085 | // Front |
1086 | addTriangle (2, aV3, aV4, aV5, aFront); |
1087 | addTriangle (3, aV3, aV5, aTopRight, aFront); |
1088 | |
1089 | // Back |
1090 | addTriangle (4, aBottomLeft, aV2, aV7, -aFront); |
1091 | addTriangle (5, aBottomLeft, aV7, aV6, -aFront); |
1092 | |
1093 | // aTop |
1094 | addTriangle (6, aV7, aV6, aV5, thePosition.Direction()); |
1095 | addTriangle (7, aTopRight, aV7, aV5, thePosition.Direction()); |
1096 | |
1097 | //Left |
1098 | addTriangle (8, aV6, aV5, aV4, -aRight); |
1099 | addTriangle (9, aBottomLeft, aV6, aV4, -aRight); |
1100 | |
1101 | // Right |
1102 | addTriangle (10, aV3, aTopRight, aV7, aRight); |
1103 | addTriangle (11, aV3, aV7, aV2, aRight); |
1104 | } |
1105 | |
1106 | //======================================================================= |
1107 | //class : Cube |
1108 | //function : addTriangle |
1109 | //purpose : |
1110 | //======================================================================= |
1111 | void AIS_Manipulator::Cube::addTriangle (const Standard_Integer theIndex, |
1112 | const gp_Pnt& theP1, const gp_Pnt& theP2, const gp_Pnt& theP3, |
1113 | const gp_Dir& theNormal) |
1114 | { |
1115 | myTriangulation->ChangeNodes().SetValue (theIndex * 3 + 1, theP1); |
1116 | myTriangulation->ChangeNodes().SetValue (theIndex * 3 + 2, theP2); |
1117 | myTriangulation->ChangeNodes().SetValue (theIndex * 3 + 3, theP3); |
1118 | |
1119 | myTriangulation->ChangeTriangles().SetValue (theIndex + 1, Poly_Triangle (theIndex * 3 + 1, theIndex * 3 + 2, theIndex * 3 + 3)); |
1120 | myArray->AddVertex (theP1, theNormal); |
1121 | myArray->AddVertex (theP2, theNormal); |
1122 | myArray->AddVertex (theP3, theNormal); |
1123 | } |
1124 | |
1125 | //======================================================================= |
1126 | //class : Axis |
1127 | //function : Constructor |
1128 | //purpose : |
1129 | //======================================================================= |
1130 | AIS_Manipulator::Axis::Axis (const gp_Ax1& theAxis, |
1131 | const Quantity_Color& theColor, |
1132 | const Standard_ShortReal theLength) |
1133 | : myReferenceAxis (theAxis), |
1134 | myPosition (theAxis), |
1135 | myColor (theColor), |
1136 | myHasTranslation (Standard_True), |
1137 | myLength (theLength), |
1138 | myAxisRadius (0.5f), |
1139 | myHasScaling (Standard_True), |
1140 | myBoxSize (2.0f), |
1141 | myHasRotation (Standard_True), |
1142 | myInnerRadius (myLength + myBoxSize), |
1143 | myDiskThickness (myBoxSize * 0.5f), |
1144 | myIndent (0.2f), |
1145 | myFacettesNumber (20), |
1146 | myCircleRadius (myLength + myBoxSize + myBoxSize * 0.5f * 0.5f) |
1147 | { |
1148 | // |
1149 | } |
1150 | |
1151 | //======================================================================= |
1152 | //class : Axis |
1153 | //function : Compute |
1154 | //purpose : |
1155 | //======================================================================= |
1156 | void AIS_Manipulator::Axis::Compute (const Handle_PrsMgr_PresentationManager3d& thePrsMgr, |
1157 | const Handle(Prs3d_Presentation)& thePrs, |
1158 | const Handle(Prs3d_ShadingAspect)& theAspect) |
1159 | { |
1160 | Handle(Graphic3d_Group) aGroup; |
1161 | |
1162 | if (myHasTranslation) |
1163 | { |
1164 | const Standard_ShortReal anArrowLength = 0.25f * myLength; |
1165 | const Standard_ShortReal aCylinderLength = myLength - anArrowLength; |
1166 | |
1167 | myCylinder.Init (myAxisRadius, myAxisRadius, aCylinderLength, myFacettesNumber, 2, gp_Ax1 (gp::Origin(), myReferenceAxis.Direction())); |
1168 | |
1169 | gp_Pnt anArrowBottom (0.0, 0.0, 0.0); |
1170 | anArrowBottom.Translate (myReferenceAxis.Direction().XYZ() * aCylinderLength); |
1171 | |
1172 | myArrow.Init (myAxisRadius * 1.5f, 0.0f, anArrowLength, myFacettesNumber, 2, gp_Ax1 (anArrowBottom, myReferenceAxis.Direction())); |
1173 | myArrowBottom.Init (myAxisRadius, myAxisRadius * 1.5f, gp_Ax1 (anArrowBottom, myReferenceAxis.Direction()), myFacettesNumber); |
1174 | myArrowTipPos = anArrowBottom; |
1175 | |
1176 | myTranslatorGroup = Prs3d_Root::NewGroup (thePrs); |
1177 | myTranslatorGroup->SetGroupPrimitivesAspect (theAspect->Aspect()); |
1178 | myTranslatorGroup->AddPrimitiveArray (myCylinder.Array()); |
1179 | myTranslatorGroup->AddPrimitiveArray (myArrow.Array()); |
1180 | myTranslatorGroup->AddPrimitiveArray (myArrowBottom.Array()); |
1181 | |
1182 | if (myHighlightTranslator.IsNull()) |
1183 | { |
1184 | myHighlightTranslator = new Prs3d_Presentation (thePrsMgr->StructureManager()); |
1185 | } |
1186 | |
1187 | myHighlightTranslator->Clear(); |
1188 | aGroup = Prs3d_Root::CurrentGroup (myHighlightTranslator); |
1189 | aGroup->AddPrimitiveArray (myCylinder.Array()); |
1190 | aGroup->AddPrimitiveArray (myArrow.Array()); |
1191 | aGroup->AddPrimitiveArray (myArrowBottom.Array()); |
1192 | } |
1193 | |
1194 | if (myHasScaling) |
1195 | { |
1196 | myCubePos = myReferenceAxis.Direction().XYZ() * (myLength + myIndent); |
1197 | myCube.Init (gp_Ax1 (myCubePos, myReferenceAxis.Direction()), myBoxSize); |
1198 | |
1199 | myScalerGroup = Prs3d_Root::NewGroup (thePrs); |
1200 | myScalerGroup->SetGroupPrimitivesAspect (theAspect->Aspect()); |
1201 | myScalerGroup->AddPrimitiveArray (myCube.Array()); |
1202 | |
1203 | if (myHighlightScaler.IsNull()) |
1204 | { |
1205 | myHighlightScaler = new Prs3d_Presentation (thePrsMgr->StructureManager()); |
1206 | } |
1207 | |
1208 | myHighlightScaler->Clear(); |
1209 | aGroup = Prs3d_Root::CurrentGroup (myHighlightScaler); |
1210 | aGroup->AddPrimitiveArray (myCube.Array()); |
1211 | } |
1212 | |
1213 | if (myHasRotation) |
1214 | { |
1215 | myCircleRadius = myInnerRadius + myIndent * 2 + myDiskThickness * 0.5f; |
1216 | myCircle.Init (myInnerRadius + myIndent * 2, myInnerRadius + myDiskThickness + myIndent * 2, gp_Ax1(gp::Origin(), myReferenceAxis.Direction()), myFacettesNumber * 2); |
1217 | myRotatorGroup = Prs3d_Root::NewGroup (thePrs); |
1218 | myRotatorGroup->SetGroupPrimitivesAspect (theAspect->Aspect()); |
1219 | myRotatorGroup->AddPrimitiveArray (myCircle.Array()); |
1220 | |
1221 | if (myHighlightRotator.IsNull()) |
1222 | { |
1223 | myHighlightRotator = new Prs3d_Presentation (thePrsMgr->StructureManager()); |
1224 | } |
1225 | |
1226 | myHighlightRotator->Clear(); |
1227 | aGroup = Prs3d_Root::CurrentGroup (myHighlightRotator); |
1228 | Prs3d_Root::CurrentGroup (myHighlightRotator)->AddPrimitiveArray (myCircle.Array()); |
1229 | } |
1230 | } |