0030156: Visualization, TKV3d - Triangles outside of selection volume are selected
[occt.git] / src / Select3D / Select3D_SensitivePrimitiveArray.cxx
CommitLineData
8b9a309b 1// Created on: 2016-02-20
2// Created by: Kirill Gavrilov
3// Copyright (c) 2016 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 <Select3D_SensitivePrimitiveArray.hxx>
17
18#include <NCollection_AlignedAllocator.hxx>
a228288f 19#include <OSD_Parallel.hxx>
00af0ebb 20#include <Standard_Atomic.hxx>
8b9a309b 21
22IMPLEMENT_STANDARD_RTTIEXT(Select3D_SensitivePrimitiveArray, Select3D_SensitiveSet)
23
24namespace
25{
26
27 //! Auxiliary converter.
28 static inline gp_Pnt vecToPnt (const Graphic3d_Vec3& theVec)
29 {
30 return gp_Pnt (theVec.x(), theVec.y(), theVec.z());
31 }
32
33 //! Auxiliary converter.
34 static inline gp_Pnt vecToPnt (const Graphic3d_Vec2& theVec)
35 {
36 return gp_Pnt (theVec.x(), theVec.y(), 0.0);
37 }
38
39
40 //! Auxiliary function to find shared node between two triangles.
41 static inline bool hasSharedNode (const Standard_Integer* theTri1,
42 const Standard_Integer* theTri2)
43 {
44 return theTri1[0] == theTri2[0]
45 || theTri1[1] == theTri2[0]
46 || theTri1[2] == theTri2[0]
47 || theTri1[0] == theTri2[1]
48 || theTri1[1] == theTri2[1]
49 || theTri1[2] == theTri2[1]
50 || theTri1[0] == theTri2[2]
51 || theTri1[1] == theTri2[2]
52 || theTri1[2] == theTri2[2];
53 }
54
55 //! Fill in the triangle nodes indices.
56 static inline void getTriIndices (const Handle(Graphic3d_IndexBuffer)& theIndices,
57 const Standard_Integer theIndexOffset,
58 Standard_Integer* theNodes)
59 {
60 if (!theIndices.IsNull())
61 {
62 theNodes[0] = theIndices->Index (theIndexOffset + 0);
63 theNodes[1] = theIndices->Index (theIndexOffset + 1);
64 theNodes[2] = theIndices->Index (theIndexOffset + 2);
65 }
66 else
67 {
68 theNodes[0] = theIndexOffset + 0;
69 theNodes[1] = theIndexOffset + 1;
70 theNodes[2] = theIndexOffset + 2;
71 }
72 }
73
74}
75
a228288f 76//! Functor for initializing groups in parallel threads.
77struct Select3D_SensitivePrimitiveArray::Select3D_SensitivePrimitiveArray_InitFunctor
78{
79 Select3D_SensitivePrimitiveArray_InitFunctor (Select3D_SensitivePrimitiveArray& thePrimArray,
80 Standard_Integer theDivStep,
81 Standard_Boolean theToEvalMinMax)
82 : myPrimArray (thePrimArray),
83 myDivStep (theDivStep),
84 myToEvalMinMax (theToEvalMinMax),
85 myToComputeBvh (Standard_True),
86 myNbFailures (0) {}
87 void operator()(const Standard_Integer& theIndex) const
88 {
89 Handle(Select3D_SensitivePrimitiveArray)& anEntity = myPrimArray.myGroups->ChangeValue (theIndex);
90 const Standard_Integer aLower = myPrimArray.myIndexLower + theIndex * myDivStep;
91 const Standard_Integer anUpper = Min (aLower + myDivStep - 1, myPrimArray.myIndexUpper);
92 anEntity = new Select3D_SensitivePrimitiveArray (myPrimArray.myOwnerId);
93 anEntity->SetPatchSizeMax (myPrimArray.myPatchSizeMax);
94 anEntity->SetPatchDistance (myPrimArray.myPatchDistance);
95 anEntity->SetDetectElements (myPrimArray.myToDetectElem);
96 anEntity->SetDetectElementMap (myPrimArray.ToDetectElementMap());
97 anEntity->SetDetectNodes (myPrimArray.myToDetectNode);
98 anEntity->SetDetectNodeMap (myPrimArray.ToDetectNodeMap());
99 anEntity->SetSensitivityFactor(myPrimArray.SensitivityFactor());
100 switch (myPrimArray.myPrimType)
101 {
102 case Graphic3d_TOPA_POINTS:
103 {
104 if (!anEntity->InitPoints (myPrimArray.myVerts, myPrimArray.myIndices, myPrimArray.myInitLocation, aLower, anUpper, myToEvalMinMax, 1))
105 {
106 Standard_Atomic_Increment (&myNbFailures);
107 return;
108 }
109 break;
110 }
111 case Graphic3d_TOPA_TRIANGLES:
112 {
113 if (!anEntity->InitTriangulation (myPrimArray.myVerts, myPrimArray.myIndices, myPrimArray.myInitLocation, aLower, anUpper, myToEvalMinMax, 1))
114 {
115 Standard_Atomic_Increment (&myNbFailures);
116 return;
117 }
118 break;
119 }
120 default:
121 {
122 Standard_Atomic_Increment (&myNbFailures);
123 return;
124 }
125 }
126
127 if (myToComputeBvh)
128 {
129 anEntity->BVH();
130 }
131 }
132 Standard_Boolean IsDone() const { return myNbFailures == 0; }
133private:
134 Select3D_SensitivePrimitiveArray_InitFunctor operator= (Select3D_SensitivePrimitiveArray_InitFunctor& );
135private:
136 Select3D_SensitivePrimitiveArray& myPrimArray;
137 Standard_Integer myDivStep;
138 Standard_Boolean myToEvalMinMax;
139 Standard_Boolean myToComputeBvh;
140 mutable volatile Standard_Integer myNbFailures;
141};
142
143//! Functor for computing BVH in parallel threads.
144struct Select3D_SensitivePrimitiveArray::Select3D_SensitivePrimitiveArray_BVHFunctor
145{
146 Select3D_SensitivePrimitiveArray_BVHFunctor (NCollection_Array1<Handle(Select3D_SensitivePrimitiveArray)>& theGroups) : myGroups (theGroups) {}
147 void operator()(const Standard_Integer& theIndex) const { myGroups.ChangeValue (theIndex)->BVH(); }
148private:
149 Select3D_SensitivePrimitiveArray_BVHFunctor operator= (Select3D_SensitivePrimitiveArray_BVHFunctor& );
150private:
151 NCollection_Array1<Handle(Select3D_SensitivePrimitiveArray)>& myGroups;
152};
153
8b9a309b 154// =======================================================================
155// function : Select3D_SensitivePrimitiveArray
156// purpose :
157// =======================================================================
158Select3D_SensitivePrimitiveArray::Select3D_SensitivePrimitiveArray (const Handle(SelectBasics_EntityOwner)& theOwnerId)
159: Select3D_SensitiveSet (theOwnerId),
160 myPrimType (Graphic3d_TOPA_UNDEFINED),
161 myIndexLower (0),
162 myIndexUpper (0),
163 myPosOffset (Standard_Size(-1)),
164 myPatchSizeMax (1),
165 myPatchDistance (ShortRealLast()),
166 myIs3d (false),
167 myBvhIndices (new NCollection_AlignedAllocator(16)),
168 myMinDepthElem (RealLast()),
169 myMinDepthNode (RealLast()),
170 myMinDepthEdge (RealLast()),
171 myDetectedElem (-1),
172 myDetectedNode (-1),
173 myDetectedEdgeNode1 (-1),
174 myDetectedEdgeNode2 (-1),
175 myToDetectElem (true),
176 myToDetectNode (false),
177 myToDetectEdge (false)
178{
179 //
180}
181
a228288f 182// =======================================================================
183// function : SetDetectElementMap
184// purpose :
185// =======================================================================
186void Select3D_SensitivePrimitiveArray::SetDetectElementMap (bool theToDetect)
187{
188 if (!theToDetect)
189 {
190 myDetectedElemMap.Nullify();
191 return;
192 }
193
194 if (myDetectedElemMap.IsNull())
195 {
196 myDetectedElemMap = new TColStd_HPackedMapOfInteger();
197 }
198 else
199 {
200 myDetectedElemMap->ChangeMap().Clear();
201 }
202}
203
204// =======================================================================
205// function : SetDetectNodeMap
206// purpose :
207// =======================================================================
208void Select3D_SensitivePrimitiveArray::SetDetectNodeMap (bool theToDetect)
209{
210 if (!theToDetect)
211 {
212 myDetectedNodeMap.Nullify();
213 return;
214 }
215
216 if (myDetectedNodeMap.IsNull())
217 {
218 myDetectedNodeMap = new TColStd_HPackedMapOfInteger();
219 }
220 else
221 {
222 myDetectedNodeMap->ChangeMap().Clear();
223 }
224}
225
8b9a309b 226// =======================================================================
227// function : InitTriangulation
228// purpose :
229// =======================================================================
230bool Select3D_SensitivePrimitiveArray::InitTriangulation (const Handle(Graphic3d_Buffer)& theVerts,
231 const Handle(Graphic3d_IndexBuffer)& theIndices,
232 const TopLoc_Location& theInitLoc,
233 const Standard_Integer theIndexLower,
234 const Standard_Integer theIndexUpper,
a228288f 235 const bool theToEvalMinMax,
236 const Standard_Integer theNbGroups)
8b9a309b 237{
238 MarkDirty();
a228288f 239 myGroups.Nullify();
8b9a309b 240 myPrimType = Graphic3d_TOPA_TRIANGLES;
241 myBndBox.Clear();
242 myVerts.Nullify();
243 myIndices.Nullify();
244 myIndexLower = 0;
245 myIndexUpper = 0;
246 myPosOffset = Standard_Size(-1);
247 myBvhIndices.release();
248 myIs3d = false;
249 myInitLocation = theInitLoc;
a228288f 250 myCDG3D.SetCoord (0.0, 0.0, 0.0);
8b9a309b 251 if (theVerts.IsNull()
252 || theVerts->NbElements == 0)
253 {
254 return false;
255 }
256
257 for (Standard_Integer anAttribIter = 0; anAttribIter < theVerts->NbAttributes; ++anAttribIter)
258 {
259 const Graphic3d_Attribute& anAttrib = theVerts->Attribute (anAttribIter);
260 if (anAttrib.Id == Graphic3d_TOA_POS)
261 {
262 if (anAttrib.DataType == Graphic3d_TOD_VEC3
263 || anAttrib.DataType == Graphic3d_TOD_VEC4)
264 {
265 myIs3d = true;
266 }
267 else if (anAttrib.DataType != Graphic3d_TOD_VEC2)
268 {
269 return false;
270 }
271
272 myPosOffset = theVerts->AttributeOffset (anAttribIter);
273 break;
274 }
275 }
276 if (myPosOffset == Standard_Size(-1))
277 {
278 return false;
279 }
280
281 if (!theIndices.IsNull())
282 {
283 if (theIndexLower < 0
284 || theIndexUpper >= theIndices->NbElements
285 || theIndices->NbElements == 0)
286 {
287 return false;
288 }
289 }
290 else
291 {
292 if (theIndexLower < 0
293 || theIndexUpper >= theVerts->NbElements)
294 {
295 return false;
296 }
297 }
298
299 Standard_Integer aTriFrom = theIndexLower / 3;
300 Standard_Integer aNbTris = (theIndexUpper - theIndexLower + 1) / 3;
a228288f 301 const bool hasGroups = (theNbGroups > 1) && (aNbTris / theNbGroups > 10);
8b9a309b 302 if (aNbTris < 1)
303 {
304 return false;
305 }
a228288f 306 if (!myBvhIndices.Init (hasGroups ? theNbGroups : aNbTris, !hasGroups && myPatchSizeMax > 1))
8b9a309b 307 {
308 return false;
309 }
310
311 myVerts = theVerts;
312 myIndices = theIndices;
313 myIndexLower = theIndexLower;
314 myIndexUpper = theIndexUpper;
315 myInvInitLocation = myInitLocation.Transformation().Inverted();
a228288f 316 if (hasGroups)
317 {
318 myGroups = new Select3D_PrimArraySubGroupArray (0, theNbGroups - 1);
319 const Standard_Integer aDivStep = (aNbTris / theNbGroups) * 3;
320 Select3D_SensitivePrimitiveArray_InitFunctor anInitFunctor (*this, aDivStep, theToEvalMinMax);
321 OSD_Parallel::For (myGroups->Lower(), myGroups->Upper() + 1, anInitFunctor);
322 if (!anInitFunctor.IsDone())
323 {
324 return false;
325 }
326 for (Standard_Integer aGroupIter = 0; aGroupIter < theNbGroups; ++aGroupIter)
327 {
328 Handle(Select3D_SensitivePrimitiveArray)& anEntity = myGroups->ChangeValue (aGroupIter);
329 myBndBox.Combine (anEntity->BoundingBox());
330 myBvhIndices.SetIndex (aGroupIter, aGroupIter);
331 myCDG3D.ChangeCoord() += anEntity->CenterOfGeometry().XYZ();
332 }
333 myCDG3D.ChangeCoord().Divide (static_cast<Standard_Real> (myGroups->Size()));
334 if (theToEvalMinMax)
335 {
336 computeBoundingBox();
337 }
338 return true;
339 }
8b9a309b 340
341 Graphic3d_Vec3 aCenter (0.0f, 0.0f, 0.0f);
342 Standard_Integer aTriNodes1[3] = { -1, -1, -1 };
343 Standard_Integer aTriNodes2[3] = { -1, -1, -1 };
344 Standard_Integer* aTriNodesPrev = aTriNodes1;
345 Standard_Integer* aTriNodes = aTriNodes2;
346 Standard_Integer aPatchFrom = 0;
347 Standard_Integer aPatchSize = 0;
348 if (myBvhIndices.HasPatches())
349 {
350 myBvhIndices.NbElements = 0;
351 }
352 for (Standard_Integer aTriIter = 0; aTriIter < aNbTris; ++aTriIter)
353 {
354 const Standard_Integer anIndexOffset = (aTriFrom + aTriIter) * 3;
355 getTriIndices (myIndices, anIndexOffset, aTriNodes);
356 if (myIs3d)
357 {
358 const Graphic3d_Vec3& aNode1 = getPosVec3 (aTriNodes[0]);
359 const Graphic3d_Vec3& aNode2 = getPosVec3 (aTriNodes[1]);
360 const Graphic3d_Vec3& aNode3 = getPosVec3 (aTriNodes[2]);
361 aCenter += (aNode1 + aNode2 + aNode3) / 3.0;
362 }
363 else
364 {
365 const Graphic3d_Vec2& aNode1 = getPosVec2 (aTriNodes[0]);
366 const Graphic3d_Vec2& aNode2 = getPosVec2 (aTriNodes[1]);
367 const Graphic3d_Vec2& aNode3 = getPosVec2 (aTriNodes[2]);
bc379358 368 aCenter += Graphic3d_Vec3((aNode1 + aNode2 + aNode3) / 3.0);
8b9a309b 369 }
370 if (myBvhIndices.HasPatches())
371 {
372 std::swap (aTriNodes, aTriNodesPrev);
373 if (aPatchSize < myPatchSizeMax
374 && hasSharedNode (aTriNodes, aTriNodesPrev))
375 {
376 ++aPatchSize;
377 continue;
378 }
379 else
380 {
381 myBvhIndices.SetIndex (myBvhIndices.NbElements++, aTriFrom + aPatchFrom, aPatchSize);
382 aPatchFrom = aTriIter;
383 aPatchSize = 0;
384 }
385 }
386 else
387 {
388 myBvhIndices.SetIndex (aTriIter, aTriFrom + aTriIter);
389 }
390 }
391 if (aPatchSize != 0)
392 {
393 myBvhIndices.SetIndex (myBvhIndices.NbElements++, aTriFrom + aPatchFrom, aPatchSize);
394 }
395 aCenter /= float(aNbTris);
396
397 myCDG3D = vecToPnt (aCenter);
398 if (theToEvalMinMax)
399 {
400 computeBoundingBox();
401 }
402 return true;
403}
404
405// =======================================================================
406// function : InitPoints
407// purpose :
408// =======================================================================
409bool Select3D_SensitivePrimitiveArray::InitPoints (const Handle(Graphic3d_Buffer)& theVerts,
410 const Handle(Graphic3d_IndexBuffer)& theIndices,
411 const TopLoc_Location& theInitLoc,
412 const Standard_Integer theIndexLower,
413 const Standard_Integer theIndexUpper,
a228288f 414 const bool theToEvalMinMax,
415 const Standard_Integer theNbGroups)
8b9a309b 416{
417 MarkDirty();
a228288f 418 myGroups.Nullify();
8b9a309b 419 myPrimType = Graphic3d_TOPA_POINTS;
420 myBndBox.Clear();
421 myVerts.Nullify();
422 myIndices.Nullify();
423 myIndexLower = 0;
424 myIndexUpper = 0;
425 myPosOffset = Standard_Size(-1);
426 myBvhIndices.release();
427 myIs3d = false;
428 myInitLocation = theInitLoc;
429 if (theVerts.IsNull()
430 || theVerts->NbElements == 0)
431 {
432 return false;
433 }
434
435 for (Standard_Integer anAttribIter = 0; anAttribIter < theVerts->NbAttributes; ++anAttribIter)
436 {
437 const Graphic3d_Attribute& anAttrib = theVerts->Attribute (anAttribIter);
438 if (anAttrib.Id == Graphic3d_TOA_POS)
439 {
440 if (anAttrib.DataType == Graphic3d_TOD_VEC3
441 || anAttrib.DataType == Graphic3d_TOD_VEC4)
442 {
443 myIs3d = true;
444 }
445 else if (anAttrib.DataType != Graphic3d_TOD_VEC2)
446 {
447 return false;
448 }
449
450 myPosOffset = theVerts->AttributeOffset (anAttribIter);
451 break;
452 }
453 }
454 if (myPosOffset == Standard_Size(-1))
455 {
456 return false;
457 }
458
459 if (!theIndices.IsNull())
460 {
461 if (theIndexLower < 0
462 || theIndexUpper >= theIndices->NbElements
463 || theIndices->NbElements == 0)
464 {
465 return false;
466 }
467 }
468 else
469 {
470 if (theIndexLower < 0
471 || theIndexUpper >= theVerts->NbElements)
472 {
473 return false;
474 }
475 }
476
a228288f 477 const Standard_Integer aNbPoints = theIndexUpper - theIndexLower + 1;
478 const bool hasGroups = (theNbGroups > 1) && (aNbPoints / theNbGroups > 10);
8b9a309b 479 if (aNbPoints < 1)
480 {
481 return false;
482 }
a228288f 483 if (!myBvhIndices.Init (hasGroups ? theNbGroups : aNbPoints, !hasGroups && myPatchSizeMax > 1))
8b9a309b 484 {
485 return false;
486 }
487
488 myVerts = theVerts;
489 myIndices = theIndices;
490 myIndexLower = theIndexLower;
491 myIndexUpper = theIndexUpper;
492 myInvInitLocation = myInitLocation.Transformation().Inverted();
a228288f 493 if (hasGroups)
494 {
495 myGroups = new Select3D_PrimArraySubGroupArray (0, theNbGroups - 1);
496 const Standard_Integer aDivStep = aNbPoints / theNbGroups;
497 Select3D_SensitivePrimitiveArray_InitFunctor anInitFunctor (*this, aDivStep, theToEvalMinMax);
498 OSD_Parallel::For (myGroups->Lower(), myGroups->Upper() + 1, anInitFunctor);
499 if (!anInitFunctor.IsDone())
500 {
501 return false;
502 }
503 for (Standard_Integer aGroupIter = 0; aGroupIter < theNbGroups; ++aGroupIter)
504 {
505 Handle(Select3D_SensitivePrimitiveArray)& anEntity = myGroups->ChangeValue (aGroupIter);
506 myBndBox.Combine (anEntity->BoundingBox());
507 myBvhIndices.SetIndex (aGroupIter, aGroupIter);
508 myCDG3D.ChangeCoord() += anEntity->CenterOfGeometry().XYZ();
509 }
510 myCDG3D.ChangeCoord().Divide (static_cast<Standard_Real> (myGroups->Size()));
511 if (theToEvalMinMax)
512 {
513 computeBoundingBox();
514 }
515 return true;
516 }
8b9a309b 517
518 Graphic3d_Vec3 aCenter (0.0f, 0.0f, 0.0f);
519 Standard_Integer aPatchFrom = 0;
520 Standard_Integer aPatchSize = 0;
521 if (myBvhIndices.HasPatches())
522 {
523 myBvhIndices.NbElements = 0;
524 }
525 const float aPatchSize2 = myPatchDistance < ShortRealLast()
526 ? myPatchDistance * myPatchDistance
527 : myPatchDistance;
528 const Graphic3d_Vec3* aPnt3dPrev = NULL;
529 const Graphic3d_Vec3* aPnt3d = NULL;
530 const Graphic3d_Vec2* aPnt2dPrev = NULL;
531 const Graphic3d_Vec2* aPnt2d = NULL;
532 for (Standard_Integer aPointIter = 0; aPointIter < aNbPoints; ++aPointIter)
533 {
534 const Standard_Integer anIndexOffset = (theIndexLower + aPointIter);
535 const Standard_Integer aPointIndex = !myIndices.IsNull()
536 ? myIndices->Index (anIndexOffset)
537 : anIndexOffset;
538 if (myIs3d)
539 {
540 aPnt3d = &getPosVec3 (aPointIndex);
541 aCenter += *aPnt3d;
542 }
543 else
544 {
545 aPnt2d = &getPosVec2 (aPointIndex);
bc379358 546 aCenter += Graphic3d_Vec3(*aPnt2d);
8b9a309b 547 }
548
549 if (myBvhIndices.HasPatches())
550 {
551 if (myIs3d)
552 {
553 std::swap (aPnt3d, aPnt3dPrev);
554 if (aPatchSize < myPatchSizeMax
555 && aPnt3d != NULL
556 && (*aPnt3dPrev - *aPnt3d).SquareModulus() < aPatchSize2)
557 {
558 ++aPatchSize;
559 continue;
560 }
561 }
562 else
563 {
564 std::swap (aPnt2d, aPnt2dPrev);
565 if (aPatchSize < myPatchSizeMax
566 && aPnt2d != NULL
567 && (*aPnt2dPrev - *aPnt2d).SquareModulus() < aPatchSize2)
568 {
569 ++aPatchSize;
570 continue;
571 }
572 }
573
574 myBvhIndices.SetIndex (myBvhIndices.NbElements++, theIndexLower + aPatchFrom,
575 aPatchSize != 0 ? aPatchSize : 1);
576 aPatchFrom = aPointIter;
577 aPatchSize = 0;
578 }
579 else
580 {
581 myBvhIndices.SetIndex (aPointIter, theIndexLower + aPointIter);
582 }
583 }
584 if (aPatchSize != 0)
585 {
586 myBvhIndices.SetIndex (myBvhIndices.NbElements++, theIndexLower + aPatchFrom, aPatchSize);
587 }
588 aCenter /= float(aNbPoints);
589
590 myCDG3D = vecToPnt (aCenter);
591 if (theToEvalMinMax)
592 {
593 computeBoundingBox();
594 }
595 return true;
596}
597
598// =======================================================================
599// function : GetConnected
600// purpose :
601// =======================================================================
602Handle(Select3D_SensitiveEntity) Select3D_SensitivePrimitiveArray::GetConnected()
603{
604 Handle(Select3D_SensitivePrimitiveArray) aNewEntity = new Select3D_SensitivePrimitiveArray (myOwnerId);
605 switch (myPrimType)
606 {
607 case Graphic3d_TOPA_POINTS:
608 {
a228288f 609 aNewEntity->InitPoints (myVerts, myIndices, myInitLocation, myIndexLower, myIndexUpper, true, !myGroups.IsNull() ? myGroups->Size() : 1);
8b9a309b 610 break;
611 }
612 case Graphic3d_TOPA_TRIANGLES:
613 {
a228288f 614 aNewEntity->InitTriangulation (myVerts, myIndices, myInitLocation, myIndexLower, myIndexUpper, true, !myGroups.IsNull() ? myGroups->Size() : 1);
8b9a309b 615 break;
616 }
617 default: break;
618 }
619 return aNewEntity;
620}
621
a228288f 622//=======================================================================
623//function : Set
624//purpose :
625//=======================================================================
626void Select3D_SensitivePrimitiveArray::Set (const Handle(SelectBasics_EntityOwner)& theOwnerId)
627{
628 base_type::Set (theOwnerId);
629 if (!myGroups.IsNull())
630 {
631 for (Select3D_PrimArraySubGroupArray::Iterator aGroupIter (*myGroups); aGroupIter.More(); aGroupIter.Next())
632 {
633 aGroupIter.Value()->Set (theOwnerId);
634 }
635 }
636}
637
638// =======================================================================
639// function : BVH
640// purpose :
641// =======================================================================
642void Select3D_SensitivePrimitiveArray::BVH()
643{
644 if (!myContent.IsDirty())
645 {
646 return;
647 }
648
649 base_type::BVH();
650 if (myGroups.IsNull())
651 {
652 return;
653 }
654
655 Standard_Integer aNbToUpdate = 0;
656 for (Select3D_PrimArraySubGroupArray::Iterator aGroupIter (*myGroups); aGroupIter.More(); aGroupIter.Next())
657 {
658 if (aGroupIter.Value()->myContent.IsDirty())
659 {
660 ++aNbToUpdate;
661 }
662 }
663
664 if (aNbToUpdate > 0)
665 {
666 Select3D_SensitivePrimitiveArray_BVHFunctor aFunctor (*myGroups);
667 OSD_Parallel::For (myGroups->Lower(), myGroups->Upper() + 1, aFunctor, aNbToUpdate <= 1);
668 }
669}
670
8b9a309b 671// =======================================================================
672// function : Size
673// purpose :
674// =======================================================================
675Standard_Integer Select3D_SensitivePrimitiveArray::Size() const
676{
677 return myBvhIndices.NbElements;
678}
679
680// =======================================================================
681// function : Box
682// purpose :
683// =======================================================================
684Select3D_BndBox3d Select3D_SensitivePrimitiveArray::Box (const Standard_Integer theIdx) const
685{
686 const Standard_Integer anElemIdx = myBvhIndices.Index (theIdx);
687 const Standard_Integer aPatchSize = myBvhIndices.PatchSize (theIdx);
a228288f 688 if (!myGroups.IsNull())
689 {
690 return myGroups->Value (anElemIdx)->BoundingBox();
691 }
692
8b9a309b 693 Select3D_BndBox3d aBox;
694 switch (myPrimType)
695 {
696 case Graphic3d_TOPA_POINTS:
697 {
698 for (Standard_Integer anElemIter = 0; anElemIter < aPatchSize; ++anElemIter)
699 {
700 const Standard_Integer anIndexOffset = (anElemIdx + anElemIter);
701 const Standard_Integer aPointIndex = !myIndices.IsNull()
702 ? myIndices->Index (anIndexOffset)
703 : anIndexOffset;
704 if (myIs3d)
705 {
706 const Graphic3d_Vec3& aPoint = getPosVec3 (aPointIndex);
707 aBox.Add (SelectMgr_Vec3 (aPoint.x(), aPoint.y(), aPoint.z()));
708 }
709 else
710 {
711 const Graphic3d_Vec2& aPoint = getPosVec2 (aPointIndex);
712 aBox.Add (SelectMgr_Vec3 (aPoint.x(), aPoint.y(), 0.0));
713 }
714 }
715 break;
716 }
717 case Graphic3d_TOPA_TRIANGLES:
718 {
719 Standard_Integer aTriNodes[3];
720 if (myIs3d)
721 {
722 for (Standard_Integer anElemIter = 0; anElemIter < aPatchSize; ++anElemIter)
723 {
724 const Standard_Integer anIndexOffset = (anElemIdx + anElemIter) * 3;
725 getTriIndices (myIndices, anIndexOffset, aTriNodes);
726 const Graphic3d_Vec3& aNode1 = getPosVec3 (aTriNodes[0]);
727 const Graphic3d_Vec3& aNode2 = getPosVec3 (aTriNodes[1]);
728 const Graphic3d_Vec3& aNode3 = getPosVec3 (aTriNodes[2]);
729 Graphic3d_Vec3 aMinPnt = (aNode1.cwiseMin (aNode2)).cwiseMin (aNode3);
730 Graphic3d_Vec3 aMaxPnt = (aNode1.cwiseMax (aNode2)).cwiseMax (aNode3);
731 aBox.Add (SelectMgr_Vec3 (aMinPnt.x(), aMinPnt.y(), aMinPnt.z()));
732 aBox.Add (SelectMgr_Vec3 (aMaxPnt.x(), aMaxPnt.y(), aMaxPnt.z()));
733 }
734 }
735 else
736 {
737 for (Standard_Integer anElemIter = 0; anElemIter < aPatchSize; ++anElemIter)
738 {
739 const Standard_Integer anIndexOffset = (anElemIdx + anElemIter) * 3;
740 getTriIndices (myIndices, anIndexOffset, aTriNodes);
741 const Graphic3d_Vec2& aNode1 = getPosVec2 (aTriNodes[0]);
742 const Graphic3d_Vec2& aNode2 = getPosVec2 (aTriNodes[1]);
743 const Graphic3d_Vec2& aNode3 = getPosVec2 (aTriNodes[2]);
744 Graphic3d_Vec2 aMinPnt = (aNode1.cwiseMin (aNode2)).cwiseMin (aNode3);
745 Graphic3d_Vec2 aMaxPnt = (aNode1.cwiseMax (aNode2)).cwiseMax (aNode3);
746 aBox.Add (SelectMgr_Vec3 (aMinPnt.x(), aMinPnt.y(), 0.0));
747 aBox.Add (SelectMgr_Vec3 (aMaxPnt.x(), aMaxPnt.y(), 0.0));
748 }
749 }
750 break;
751 }
752 default:
753 {
754 return aBox;
755 }
756 }
757 return aBox;
758}
759
760// =======================================================================
761// function : Center
762// purpose :
763// =======================================================================
764Standard_Real Select3D_SensitivePrimitiveArray::Center (const Standard_Integer theIdx,
765 const Standard_Integer theAxis) const
766{
a228288f 767 if (!myGroups.IsNull())
768 {
769 const Standard_Integer anElemIdx = myBvhIndices.Index (theIdx);
770 const gp_Pnt aCenter = myGroups->Value (anElemIdx)->CenterOfGeometry();
771 return theAxis == 0 ? aCenter.X() : (theAxis == 1 ? aCenter.Y() : aCenter.Z());
772 }
773
8b9a309b 774 const Select3D_BndBox3d& aBox = Box (theIdx);
775 SelectMgr_Vec3 aCenter = (aBox.CornerMin() + aBox.CornerMax()) * 0.5;
776 return theAxis == 0 ? aCenter.x() : (theAxis == 1 ? aCenter.y() : aCenter.z());
777}
778
779// =======================================================================
780// function : Swap
781// purpose :
782// =======================================================================
783void Select3D_SensitivePrimitiveArray::Swap (const Standard_Integer theIdx1,
784 const Standard_Integer theIdx2)
785{
786 Standard_Integer anElemIdx1 = myBvhIndices.Index (theIdx1);
787 Standard_Integer anElemIdx2 = myBvhIndices.Index (theIdx2);
788 if (myBvhIndices.HasPatches())
789 {
790 Standard_Integer aPatchSize1 = myBvhIndices.PatchSize (theIdx1);
791 Standard_Integer aPatchSize2 = myBvhIndices.PatchSize (theIdx2);
792 myBvhIndices.SetIndex (theIdx1, anElemIdx2, aPatchSize2);
793 myBvhIndices.SetIndex (theIdx2, anElemIdx1, aPatchSize1);
794 }
795 else
796 {
797 myBvhIndices.SetIndex (theIdx1, anElemIdx2);
798 myBvhIndices.SetIndex (theIdx2, anElemIdx1);
799 }
800}
801
802// =======================================================================
803// function : BoundingBox
804// purpose :
805// =======================================================================
806Select3D_BndBox3d Select3D_SensitivePrimitiveArray::BoundingBox()
807{
808 if (!myBndBox.IsValid())
809 {
810 computeBoundingBox();
811 }
812 return applyTransformation();
813}
814
815// =======================================================================
816// function : computeBoundingBox
817// purpose :
818// =======================================================================
819void Select3D_SensitivePrimitiveArray::computeBoundingBox()
820{
821 myBndBox.Clear();
a228288f 822 if (!myGroups.IsNull())
823 {
824 for (Select3D_PrimArraySubGroupArray::Iterator aGroupIter (*myGroups); aGroupIter.More(); aGroupIter.Next())
825 {
826 myBndBox.Combine (aGroupIter.Value()->BoundingBox());
827 }
828 return;
829 }
830
8b9a309b 831 if (myVerts.IsNull())
832 {
833 return;
834 }
835
836 const Standard_Integer aNbVerts = myVerts->NbElements;
837 if (myIs3d)
838 {
839 for (Standard_Integer aVertIter = 0; aVertIter < aNbVerts; ++aVertIter)
840 {
841 const Graphic3d_Vec3& aVert = getPosVec3 (aVertIter);
842 myBndBox.Add (SelectMgr_Vec3 (aVert.x(), aVert.y(), aVert.z()));
843 }
844 }
845 else
846 {
847 for (Standard_Integer aVertIter = 0; aVertIter < aNbVerts; ++aVertIter)
848 {
849 const Graphic3d_Vec2& aVert = getPosVec2 (aVertIter);
850 myBndBox.Add (SelectMgr_Vec3 (aVert.x(), aVert.y(), 0.0));
851 }
852 }
853}
854
855// =======================================================================
856// function : applyTransformation
857// purpose :
858// =======================================================================
859Select3D_BndBox3d Select3D_SensitivePrimitiveArray::applyTransformation()
860{
861 if (!HasInitLocation())
862 {
863 return myBndBox;
864 }
865
866 Select3D_BndBox3d aBndBox;
867 for (Standard_Integer aX = 0; aX <=1; ++aX)
868 {
869 for (Standard_Integer aY = 0; aY <=1; ++aY)
870 {
871 for (Standard_Integer aZ = 0; aZ <= 1; ++aZ)
872 {
873 gp_Pnt aVertex = gp_Pnt (aX == 0 ? myBndBox.CornerMin().x() : myBndBox.CornerMax().x(),
874 aY == 0 ? myBndBox.CornerMin().y() : myBndBox.CornerMax().y(),
875 aZ == 0 ? myBndBox.CornerMin().z() : myBndBox.CornerMax().z());
876 aVertex.Transform (myInitLocation.Transformation());
877 aBndBox.Add (Select3D_Vec3 (aVertex.X(), aVertex.Y(), aVertex.Z()));
878 }
879 }
880 }
881 return aBndBox;
882}
883
884// =======================================================================
885// function : Matches
886// purpose :
887// =======================================================================
888Standard_Boolean Select3D_SensitivePrimitiveArray::Matches (SelectBasics_SelectingVolumeManager& theMgr,
889 SelectBasics_PickResult& thePickResult)
890{
a228288f 891 if (!myDetectedElemMap.IsNull())
892 {
893 myDetectedElemMap->ChangeMap().Clear();
894 }
895 if (!myDetectedNodeMap.IsNull())
896 {
897 myDetectedNodeMap->ChangeMap().Clear();
898 }
8b9a309b 899 myMinDepthElem = RealLast();
900 myMinDepthNode = RealLast();
901 myMinDepthEdge = RealLast();
902 myDetectedElem = -1;
903 myDetectedNode = -1;
904 myDetectedEdgeNode1 = -1;
905 myDetectedEdgeNode2 = -1;
a228288f 906 const bool toDetectRange = !myDetectedElemMap.IsNull() || !myDetectedNodeMap.IsNull();
907 if (myGroups.IsNull()
908 || theMgr.GetActiveSelectionType() == SelectBasics_SelectingVolumeManager::Point
909 || !toDetectRange)
910 {
4a056d20 911 if (!matches (theMgr, thePickResult, toDetectRange))
a228288f 912 {
913 return Standard_False;
914 }
915
916 if (!myGroups.IsNull() && myDetectedIdx != -1)
917 {
918 const Standard_Integer anIndex = myBvhIndices.Index (myDetectedIdx);
919 const Handle(Select3D_SensitivePrimitiveArray)& aLastGroup = myGroups->Value (anIndex);
920 myMinDepthElem = aLastGroup->myMinDepthElem;
921 myMinDepthNode = aLastGroup->myMinDepthNode;
922 myMinDepthEdge = aLastGroup->myMinDepthEdge;
923 myDetectedElem = aLastGroup->myDetectedElem;
924 myDetectedNode = aLastGroup->myDetectedNode;
925 myDetectedEdgeNode1 = aLastGroup->myDetectedEdgeNode1;
926 myDetectedEdgeNode2 = aLastGroup->myDetectedEdgeNode2;
927 }
928 return Standard_True;
929 }
930
17017555 931 SelectBasics_PickResult aPickResult;
4a056d20 932 bool hasResults = false;
a228288f 933 for (Standard_Integer aGroupIter = 0; aGroupIter < myBvhIndices.NbElements; ++aGroupIter)
934 {
935 const Standard_Integer anElemIdx = myBvhIndices.Index (aGroupIter);
a228288f 936 Handle(Select3D_SensitivePrimitiveArray)& aChild = myGroups->ChangeValue (anElemIdx);
4a056d20 937 if (aChild->Matches (theMgr, aPickResult))
a228288f 938 {
4a056d20 939 hasResults = true;
940 if (!myDetectedElemMap.IsNull())
a228288f 941 {
4a056d20 942 myDetectedElemMap->ChangeMap().Unite (aChild->myDetectedElemMap->Map());
943 }
944 if (!myDetectedNodeMap.IsNull())
945 {
946 myDetectedNodeMap->ChangeMap().Unite (aChild->myDetectedNodeMap->Map());
a228288f 947 }
17017555 948 if (thePickResult.Depth() > aPickResult.Depth())
a228288f 949 {
950 myDetectedIdx = aGroupIter;
17017555 951 thePickResult = aPickResult;
a228288f 952 }
953 }
954 }
4a056d20 955 if (!hasResults)
a228288f 956 {
a228288f 957 return Standard_False;
958 }
17017555 959 thePickResult.SetDistToGeomCenter(theMgr.DistToGeometryCenter(CenterOfGeometry()));
a228288f 960 return Standard_True;
8b9a309b 961}
962
963// =======================================================================
964// function : overlapsElement
965// purpose :
966// =======================================================================
4a056d20 967Standard_Boolean Select3D_SensitivePrimitiveArray::overlapsElement (SelectBasics_PickResult& thePickResult,
968 SelectBasics_SelectingVolumeManager& theMgr,
8b9a309b 969 Standard_Integer theElemIdx,
4a056d20 970 Standard_Boolean theIsFullInside)
8b9a309b 971{
a228288f 972 const Standard_Integer anElemIdx = myBvhIndices.Index (theElemIdx);
973 if (!myGroups.IsNull())
974 {
4a056d20 975 return myGroups->Value (anElemIdx)->Matches (theMgr, thePickResult);
a228288f 976 }
977
8b9a309b 978 const Standard_Integer aPatchSize = myBvhIndices.PatchSize (theElemIdx);
979 Select3D_BndBox3d aBox;
980 Standard_Boolean aResult = Standard_False;
17017555 981 SelectBasics_PickResult aPickResult;
8b9a309b 982 switch (myPrimType)
983 {
984 case Graphic3d_TOPA_POINTS:
985 {
986 for (Standard_Integer anElemIter = 0; anElemIter < aPatchSize; ++anElemIter)
987 {
988 const Standard_Integer anIndexOffset = (anElemIdx + anElemIter);
989 const Standard_Integer aPointIndex = !myIndices.IsNull()
990 ? myIndices->Index (anIndexOffset)
991 : anIndexOffset;
992 gp_Pnt aPoint;
993 if (myIs3d)
994 {
995 aPoint = vecToPnt (getPosVec3 (aPointIndex));
996 }
997 else
998 {
999 aPoint = vecToPnt (getPosVec2 (aPointIndex));
1000 }
1001
8b9a309b 1002 if (myToDetectNode
1003 || myToDetectElem)
1004 {
4a056d20 1005 if (theIsFullInside || theMgr.Overlaps (aPoint, aPickResult))
8b9a309b 1006 {
17017555 1007 if (aPickResult.Depth() <= myMinDepthNode)
8b9a309b 1008 {
1009 myDetectedElem = myDetectedNode = aPointIndex;
17017555 1010 myMinDepthElem = myMinDepthNode = aPickResult.Depth();
8b9a309b 1011 }
a228288f 1012 if (theMgr.GetActiveSelectionType() != SelectBasics_SelectingVolumeManager::Point)
1013 {
1014 if (!myDetectedElemMap.IsNull())
1015 {
1016 myDetectedElemMap->ChangeMap().Add (aPointIndex);
1017 }
1018 if (!myDetectedNodeMap.IsNull())
1019 {
1020 myDetectedNodeMap->ChangeMap().Add (aPointIndex);
1021 }
1022 }
8b9a309b 1023 aResult = Standard_True;
1024 }
1025 }
17017555 1026 thePickResult = SelectBasics_PickResult::Min (thePickResult, aPickResult);
8b9a309b 1027 }
1028 break;
1029 }
1030 case Graphic3d_TOPA_TRIANGLES:
1031 {
1032 Graphic3d_Vec3i aTriNodes;
1033 for (Standard_Integer anElemIter = 0; anElemIter < aPatchSize; ++anElemIter)
1034 {
a228288f 1035 const Standard_Integer aTriIndex = anElemIdx + anElemIter;
1036 const Standard_Integer anIndexOffset = aTriIndex * 3;
8b9a309b 1037 getTriIndices (myIndices, anIndexOffset, aTriNodes);
1038 gp_Pnt aPnts[3];
1039 if (myIs3d)
1040 {
1041 aPnts[0] = vecToPnt (getPosVec3 (aTriNodes[0]));
1042 aPnts[1] = vecToPnt (getPosVec3 (aTriNodes[1]));
1043 aPnts[2] = vecToPnt (getPosVec3 (aTriNodes[2]));
1044 }
1045 else
1046 {
1047 aPnts[0] = vecToPnt (getPosVec2 (aTriNodes[0]));
1048 aPnts[1] = vecToPnt (getPosVec2 (aTriNodes[1]));
1049 aPnts[2] = vecToPnt (getPosVec2 (aTriNodes[2]));
1050 }
1051
8b9a309b 1052 if (myToDetectElem)
1053 {
4a056d20 1054 if (theIsFullInside || theMgr.Overlaps (aPnts[0], aPnts[1], aPnts[2], Select3D_TOS_INTERIOR, aPickResult))
8b9a309b 1055 {
17017555 1056 if (aPickResult.Depth() <= myMinDepthElem)
8b9a309b 1057 {
a228288f 1058 myDetectedElem = aTriIndex;
17017555 1059 myMinDepthElem = aPickResult.Depth();
8b9a309b 1060 }
1061 aResult = Standard_True;
f2eaecb2 1062 if (!myDetectedElemMap.IsNull()
1063 && theMgr.GetActiveSelectionType() != SelectBasics_SelectingVolumeManager::Point)
1064 {
1065 myDetectedElemMap->ChangeMap().Add(aTriIndex);
1066 }
a228288f 1067 }
8b9a309b 1068 }
1069 if (myToDetectNode)
1070 {
1071 for (int aNodeIter = 0; aNodeIter < 3; ++aNodeIter)
1072 {
4a056d20 1073 if (theIsFullInside || theMgr.Overlaps (aPnts[aNodeIter], aPickResult))
8b9a309b 1074 {
17017555 1075 if (aPickResult.Depth() <= myMinDepthNode)
8b9a309b 1076 {
1077 myDetectedNode = aTriNodes[aNodeIter];
17017555 1078 myMinDepthNode = aPickResult.Depth();
8b9a309b 1079 }
a228288f 1080 if (!myDetectedNodeMap.IsNull()
1081 && theMgr.GetActiveSelectionType() != SelectBasics_SelectingVolumeManager::Point)
1082 {
1083 myDetectedNodeMap->ChangeMap().Add (aTriNodes[aNodeIter]);
1084 }
8b9a309b 1085 aResult = Standard_True;
1086 }
1087 }
1088 }
1089 if (myToDetectEdge)
1090 {
1091 for (int aNodeIter = 0; aNodeIter < 3; ++aNodeIter)
1092 {
1093 int aNode1 = aNodeIter == 0 ? 2 : (aNodeIter - 1);
1094 int aNode2 = aNodeIter;
4a056d20 1095 if (theIsFullInside || theMgr.Overlaps (aPnts[aNode1], aPnts[aNode2], aPickResult))
8b9a309b 1096 {
17017555 1097 if (aPickResult.Depth() <= myMinDepthEdge)
8b9a309b 1098 {
1099 myDetectedEdgeNode1 = aTriNodes[aNode1];
1100 myDetectedEdgeNode2 = aTriNodes[aNode2];
17017555 1101 myMinDepthEdge = aPickResult.Depth();
8b9a309b 1102 }
1103 aResult = Standard_True;
1104 }
1105 }
1106 }
17017555 1107 thePickResult = SelectBasics_PickResult::Min (thePickResult, aPickResult);
8b9a309b 1108 }
1109 break;
1110 }
1111 default:
1112 {
1113 return Standard_False;
1114 }
1115 }
1116
8b9a309b 1117 return aResult;
1118}
1119
1120// =======================================================================
1121// function : distanceToCOG
1122// purpose :
1123// =======================================================================
1124Standard_Real Select3D_SensitivePrimitiveArray::distanceToCOG (SelectBasics_SelectingVolumeManager& theMgr)
1125{
1126 return theMgr.DistToGeometryCenter (myCDG3D);
1127}
1128
1129// =======================================================================
1130// function : elementIsInside
1131// purpose :
1132// =======================================================================
1133Standard_Boolean Select3D_SensitivePrimitiveArray::elementIsInside (SelectBasics_SelectingVolumeManager& theMgr,
4a056d20 1134 Standard_Integer theElemIdx,
1135 Standard_Boolean theIsFullInside)
8b9a309b 1136{
a228288f 1137 const Standard_Integer anElemIdx = myBvhIndices.Index (theElemIdx);
1138 if (!myGroups.IsNull())
1139 {
17017555 1140 SelectBasics_PickResult aDummy;
4a056d20 1141 return myGroups->Value (anElemIdx)->Matches (theMgr, aDummy);
a228288f 1142 }
1143
8b9a309b 1144 const Standard_Integer aPatchSize = myBvhIndices.PatchSize (theElemIdx);
1145 switch (myPrimType)
1146 {
1147 case Graphic3d_TOPA_POINTS:
1148 {
1149 for (Standard_Integer anElemIter = 0; anElemIter < aPatchSize; ++anElemIter)
1150 {
1151 const Standard_Integer anIndexOffset = (anElemIdx + anElemIter);
1152 const Standard_Integer aPointIndex = !myIndices.IsNull()
1153 ? myIndices->Index (anIndexOffset)
1154 : anIndexOffset;
1155 gp_Pnt aPoint;
1156 if (myIs3d)
1157 {
1158 aPoint = vecToPnt (getPosVec3 (aPointIndex));
1159 }
1160 else
1161 {
1162 aPoint = vecToPnt (getPosVec2 (aPointIndex));
1163 }
4a056d20 1164 if (!theIsFullInside && !theMgr.Overlaps (aPoint))
8b9a309b 1165 {
1166 return Standard_False;
1167 }
a228288f 1168
1169 if (theMgr.GetActiveSelectionType() != SelectBasics_SelectingVolumeManager::Point)
1170 {
1171 if (!myDetectedElemMap.IsNull())
1172 {
1173 myDetectedElemMap->ChangeMap().Add (aPointIndex);
1174 }
1175 if (!myDetectedNodeMap.IsNull())
1176 {
1177 myDetectedNodeMap->ChangeMap().Add (aPointIndex);
1178 }
1179 }
8b9a309b 1180 }
1181 return Standard_True;
1182 }
1183 case Graphic3d_TOPA_TRIANGLES:
1184 {
1185 Graphic3d_Vec3i aTriNodes;
1186 for (Standard_Integer anElemIter = 0; anElemIter < aPatchSize; ++anElemIter)
1187 {
a228288f 1188 const Standard_Integer aTriIndex = anElemIdx + anElemIter;
1189 const Standard_Integer anIndexOffset = aTriIndex * 3;
8b9a309b 1190 getTriIndices (myIndices, anIndexOffset, aTriNodes);
1191 gp_Pnt aPnts[3];
1192 if (myIs3d)
1193 {
1194 aPnts[0] = vecToPnt (getPosVec3 (aTriNodes[0]));
1195 aPnts[1] = vecToPnt (getPosVec3 (aTriNodes[1]));
1196 aPnts[2] = vecToPnt (getPosVec3 (aTriNodes[2]));
1197 }
1198 else
1199 {
1200 aPnts[0] = vecToPnt (getPosVec2 (aTriNodes[0]));
1201 aPnts[1] = vecToPnt (getPosVec2 (aTriNodes[1]));
1202 aPnts[2] = vecToPnt (getPosVec2 (aTriNodes[2]));
1203 }
1204
4a056d20 1205 if (!theIsFullInside && ( !theMgr.Overlaps (aPnts[0])
1206 || !theMgr.Overlaps (aPnts[1])
1207 || !theMgr.Overlaps (aPnts[2])))
8b9a309b 1208 {
1209 return Standard_False;
1210 }
a228288f 1211
1212 if (theMgr.GetActiveSelectionType() != SelectBasics_SelectingVolumeManager::Point)
1213 {
1214 if (!myDetectedElemMap.IsNull())
1215 {
1216 myDetectedElemMap->ChangeMap().Add (aTriIndex);
1217 }
1218 if (!myDetectedNodeMap.IsNull())
1219 {
1220 myDetectedNodeMap->ChangeMap().Add (aTriNodes[0]);
1221 myDetectedNodeMap->ChangeMap().Add (aTriNodes[1]);
1222 myDetectedNodeMap->ChangeMap().Add (aTriNodes[2]);
1223 }
1224 }
8b9a309b 1225 }
1226 return Standard_True;
1227 }
1228 default:
1229 {
1230 return Standard_False;
1231 }
1232 }
1233}