1
/***************************************************************************
2
* Copyright (c) 2005 Imetric 3D GmbH *
4
* This file is part of the FreeCAD CAx development system. *
6
* This library is free software; you can redistribute it and/or *
7
* modify it under the terms of the GNU Library General Public *
8
* License as published by the Free Software Foundation; either *
9
* version 2 of the License, or (at your option) any later version. *
11
* This library is distributed in the hope that it will be useful, *
12
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
13
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
14
* GNU Library General Public License for more details. *
16
* You should have received a copy of the GNU Library General Public *
17
* License along with this library; see the file COPYING.LIB. If not, *
18
* write to the Free Software Foundation, Inc., 59 Temple Place, *
19
* Suite 330, Boston, MA 02111-1307, USA *
21
***************************************************************************/
24
#include "PreCompiled.h"
26
#include "MeshKernel.h"
28
#include "Algorithm.h"
30
using namespace MeshCore;
33
unsigned long MeshKernel::VisitNeighbourFacets (MeshFacetVisitor &rclFVisitor, unsigned long ulStartFacet) const
35
unsigned long ulVisited = 0, j, ulLevel = 0;
36
unsigned long ulCount = _aclFacetArray.size();
37
std::vector<unsigned long> clCurrentLevel, clNextLevel;
38
std::vector<unsigned long>::iterator clCurrIter;
39
MeshFacetArray::_TConstIterator clCurrFacet, clNBFacet;
41
// Startpunke aufnehmen
42
clCurrentLevel.push_back(ulStartFacet);
43
_aclFacetArray[ulStartFacet].SetFlag(MeshFacet::VISIT);
45
// solange noch freie Nachbarn
46
while (clCurrentLevel.size() > 0)
48
// besuche alle Nachbarn des aktuellen Level
49
for (clCurrIter = clCurrentLevel.begin(); clCurrIter < clCurrentLevel.end(); clCurrIter++)
51
clCurrFacet = _aclFacetArray.begin() + *clCurrIter;
53
// alle Nachbarn des aktuellen Dreiecks besuchen wenn nicht schon besucht wurde
54
for (unsigned short i = 0; i < 3; i++)
56
j = clCurrFacet->_aulNeighbours[i]; // Index Nachbar-Facet
58
continue; // kein Nachbarn-Facet vorhanden
61
continue; // Fehler in der Datenstruktur
63
clNBFacet = _aclFacetArray.begin() + j;
65
if (!rclFVisitor.AllowVisit(*clNBFacet, *clCurrFacet, j, ulLevel, i))
68
if (clNBFacet->IsFlag(MeshFacet::VISIT) == true)
69
continue; // Nachbar-Facet schon besucht
71
{ // besuche und markiere
73
clNextLevel.push_back(j);
74
clNBFacet->SetFlag(MeshFacet::VISIT);
76
if (rclFVisitor.Visit(*clNBFacet, *clCurrFacet, j, ulLevel) == false)
81
clCurrentLevel = clNextLevel;
89
unsigned long MeshKernel::VisitNeighbourFacetsOverCorners (MeshFacetVisitor &rclFVisitor, unsigned long ulStartFacet) const
91
unsigned long ulVisited = 0, ulLevel = 0;
92
MeshRefPointToFacets clRPF(*this);
93
const MeshFacetArray& raclFAry = _aclFacetArray;
94
MeshFacetArray::_TConstIterator pFBegin = raclFAry.begin();
95
std::vector<unsigned long> aclCurrentLevel, aclNextLevel;
97
aclCurrentLevel.push_back(ulStartFacet);
98
raclFAry[ulStartFacet].SetFlag(MeshFacet::VISIT);
100
while (aclCurrentLevel.size() > 0)
102
// besuche alle Nachbarn des aktuellen Level
103
for (std::vector<unsigned long>::iterator pCurrFacet = aclCurrentLevel.begin(); pCurrFacet < aclCurrentLevel.end(); pCurrFacet++)
105
for (int i = 0; i < 3; i++)
107
const MeshFacet &rclFacet = raclFAry[*pCurrFacet];
108
std::set<MeshFacetArray::_TConstIterator> raclNB = clRPF[rclFacet._aulPoints[i]];
109
for (std::set<MeshFacetArray::_TConstIterator>::iterator pINb = raclNB.begin(); pINb != raclNB.end(); pINb++)
111
if ((*pINb)->IsFlag(MeshFacet::VISIT) == false) // nur besuchen wenn VISIT Flag nicht gesetzt
114
unsigned long ulFInd = *pINb - pFBegin;
115
aclNextLevel.push_back(ulFInd);
116
(*pINb)->SetFlag(MeshFacet::VISIT);
117
if (rclFVisitor.Visit(*(*pINb), raclFAry[*pCurrFacet], ulFInd, ulLevel) == false)
123
aclCurrentLevel = aclNextLevel;
124
aclNextLevel.clear();
131
unsigned long MeshKernel::VisitNeighbourPoints (MeshPointVisitor &rclPVisitor, unsigned long ulStartPoint) const
133
unsigned long ulVisited = 0, ulLevel = 0;
134
std::vector<unsigned long> aclCurrentLevel, aclNextLevel;
135
std::vector<unsigned long>::iterator clCurrIter;
136
MeshPointArray::_TConstIterator pPBegin = _aclPointArray.begin();
137
MeshRefPointToPoints clNPs(*this);
139
aclCurrentLevel.push_back(ulStartPoint);
140
(pPBegin + ulStartPoint)->SetFlag(MeshPoint::VISIT);
142
while (aclCurrentLevel.size() > 0)
144
// besuche alle Nachbarn des aktuellen Level
145
for (clCurrIter = aclCurrentLevel.begin(); clCurrIter < aclCurrentLevel.end(); ++clCurrIter)
147
std::set<MeshPointArray::_TConstIterator> raclNB = clNPs[*clCurrIter];
148
for (std::set<MeshPointArray::_TConstIterator>::iterator pINb = raclNB.begin(); pINb != raclNB.end(); ++pINb)
150
if ((*pINb)->IsFlag(MeshPoint::VISIT) == false) // nur besuchen wenn VISIT Flag nicht gesetzt
153
unsigned long ulPInd = *pINb - pPBegin;
154
aclNextLevel.push_back(ulPInd);
155
(*pINb)->SetFlag(MeshPoint::VISIT);
156
if (rclPVisitor.Visit(*(*pINb), *(pPBegin + (*clCurrIter)), ulPInd, ulLevel) == false)
161
aclCurrentLevel = aclNextLevel;
162
aclNextLevel.clear();
169
// -------------------------------------------------------------------------
171
MeshSearchNeighbourFacetsVisitor::MeshSearchNeighbourFacetsVisitor (const MeshKernel &rclMesh, float fRadius, unsigned long ulStartFacetIdx)
172
: _rclMeshBase(rclMesh),
173
_clCenter(rclMesh.GetFacet(ulStartFacetIdx).GetGravityPoint()),
176
_bFacetsFoundInCurrentLevel(false)
180
std::vector<unsigned long> MeshSearchNeighbourFacetsVisitor::GetAndReset (void)
182
MeshAlgorithm(_rclMeshBase).ResetFacetsFlag(_vecFacets, MeshFacet::VISIT);