Loading files
// Created on: 1995-03-06
// Created by: Laurent PAINNOT
// Copyright (c) 1995-1999 Matra Datavision
// Copyright (c) 1999-2014 OPEN CASCADE SAS
//
// This file is part of Open CASCADE Technology software library.
//
// This library is free software; you can redistribute it and/or modify it under
// the terms of the GNU Lesser General Public License version 2.1 as published
// by the Free Software Foundation, with special exception defined in the file
// OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT
// distribution for complete text of the license and disclaimer of any warranty.
//
// Alternatively, this file may be used under the terms of Open CASCADE
// commercial license or contractual agreement.
#include <Poly_Connect.hxx>
#include <NCollection_IncAllocator.hxx>
#include <Poly_Triangulation.hxx>
// this structure records one of the edges starting from a node
struct polyedge
{
polyedge* next; // the next edge in the list
int nt[2]; // the two adjacent triangles
int nn[2]; // the two adjacent nodes
int nd; // the second node of the edge
DEFINE_STANDARD_ALLOC
};
//=================================================================================================
Poly_Connect::Poly_Connect()
: mytr(0),
myfirst(0),
mynode(0),
myothernode(0),
mysense(false),
mymore(false)
{
}
//=================================================================================================
Poly_Connect::Poly_Connect(const occ::handle<Poly_Triangulation>& theTriangulation)
: myTriangulation(theTriangulation),
myTriangles(1, theTriangulation->NbNodes()),
myAdjacents(1, 6 * theTriangulation->NbTriangles()),
mytr(0),
myfirst(0),
mynode(0),
myothernode(0),
mysense(false),
mymore(false)
{
Load(theTriangulation);
}
//=================================================================================================
void Poly_Connect::Load(const occ::handle<Poly_Triangulation>& theTriangulation)
{
myTriangulation = theTriangulation;
mytr = 0;
myfirst = 0;
mynode = 0;
myothernode = 0;
mysense = false;
mymore = false;
const int aNbNodes = myTriangulation->NbNodes();
const int aNbTris = myTriangulation->NbTriangles();
{
const int aNbAdjs = 6 * aNbTris;
if (myTriangles.Length() != aNbNodes)
{
myTriangles.Resize(1, aNbNodes, false);
}
if (myAdjacents.Length() != aNbAdjs)
{
myAdjacents.Resize(1, aNbAdjs, false);
}
}
myTriangles.Init(0);
myAdjacents.Init(0);
// We first build an array of the list of edges connected to the nodes
// create an array to store the edges starting from the vertices
NCollection_Array1<polyedge*> anEdges(1, aNbNodes);
anEdges.Init(nullptr);
// use incremental allocator for small allocations
occ::handle<NCollection_IncAllocator> anIncAlloc = new NCollection_IncAllocator();
// loop on the triangles
NCollection_Vec3<int> aTriNodes;
NCollection_Vec2<int> anEdgeNodes;
for (int aTriIter = 1; aTriIter <= aNbTris; ++aTriIter)
{
// get the nodes
myTriangulation->Triangle(aTriIter).Get(aTriNodes[0], aTriNodes[1], aTriNodes[2]);
// Update the myTriangles array
myTriangles.SetValue(aTriNodes[0], aTriIter);
myTriangles.SetValue(aTriNodes[1], aTriIter);
myTriangles.SetValue(aTriNodes[2], aTriIter);
// update the edge lists
for (int aNodeInTri = 0; aNodeInTri < 3; ++aNodeInTri)
{
const int aNodeNext = (aNodeInTri + 1) % 3; // the following node of the edge
if (aTriNodes[aNodeInTri] < aTriNodes[aNodeNext])
{
anEdgeNodes[0] = aTriNodes[aNodeInTri];
anEdgeNodes[1] = aTriNodes[aNodeNext];
}
else
{
anEdgeNodes[0] = aTriNodes[aNodeNext];
anEdgeNodes[1] = aTriNodes[aNodeInTri];
}
// edge from node 0 to node 1 with node 0 < node 1
// insert in the list of node 0
polyedge* ced = anEdges[anEdgeNodes[0]];
for (; ced != nullptr; ced = ced->next)
{
// the edge already exists
if (ced->nd == anEdgeNodes[1])
{
// just mark the adjacency if found
ced->nt[1] = aTriIter;
ced->nn[1] = aTriNodes[3 - aNodeInTri - aNodeNext]; // the third node
break;
}
}
if (ced == nullptr)
{
// create the edge if not found
ced = (polyedge*)anIncAlloc->Allocate(sizeof(polyedge));
ced->next = anEdges[anEdgeNodes[0]];
anEdges[anEdgeNodes[0]] = ced;
ced->nd = anEdgeNodes[1];
ced->nt[0] = aTriIter;
ced->nn[0] = aTriNodes[3 - aNodeInTri - aNodeNext]; // the third node
ced->nt[1] = 0;
ced->nn[1] = 0;
}
}
}
// now complete the myAdjacents array
int anAdjIndex = 1;
for (int aTriIter = 1; aTriIter <= aNbTris; ++aTriIter)
{
// get the nodes
myTriangulation->Triangle(aTriIter).Get(aTriNodes[0], aTriNodes[1], aTriNodes[2]);
// for each edge in triangle
for (int aNodeInTri = 0; aNodeInTri < 3; ++aNodeInTri)
{
const int aNodeNext = (aNodeInTri + 1) % 3; // the following node of the edge
if (aTriNodes[aNodeInTri] < aTriNodes[aNodeNext])
{
anEdgeNodes[0] = aTriNodes[aNodeInTri];
anEdgeNodes[1] = aTriNodes[aNodeNext];
}
else
{
anEdgeNodes[0] = aTriNodes[aNodeNext];
anEdgeNodes[1] = aTriNodes[aNodeInTri];
}
// edge from node 0 to node 1 with node 0 < node 1
// find in the list of node 0
const polyedge* ced = anEdges[anEdgeNodes[0]];
while (ced->nd != anEdgeNodes[1])
{
ced = ced->next;
}
// Find the adjacent triangle
const int l = ced->nt[0] == aTriIter ? 1 : 0;
myAdjacents.SetValue(anAdjIndex, ced->nt[l]);
myAdjacents.SetValue(anAdjIndex + 3, ced->nn[l]);
++anAdjIndex;
}
anAdjIndex += 3;
}
// destroy the edges array - can be skipped when using NCollection_IncAllocator
/*for (int aNodeIter = anEdges.Lower(); aNodeIter <= anEdges.Upper(); ++aNodeIter)
{
for (polyedge* anEdgeIter = anEdges[aNodeIter]; anEdgeIter != NULL;)
{
polyedge* aTmp = anEdgeIter->next;
anIncAlloc->Free (anEdgeIter);
anEdgeIter = aTmp;
}
}*/
}
//=================================================================================================
void Poly_Connect::Initialize(const int N)
{
mynode = N;
myfirst = Triangle(N);
mytr = myfirst;
mysense = true;
mymore = (myfirst != 0);
myPassedTr.Clear();
myPassedTr.Add(mytr);
if (mymore)
{
int i, no[3];
myTriangulation->Triangle(myfirst).Get(no[0], no[1], no[2]);
for (i = 0; i < 3; i++)
{
if (no[i] == mynode)
{
break;
}
}
myothernode = no[(i + 2) % 3];
}
}
//=================================================================================================
void Poly_Connect::Next()
{
int i, j;
int n[3];
int t[3];
Triangles(mytr, t[0], t[1], t[2]);
if (mysense)
{
for (i = 0; i < 3; i++)
{
if (t[i] != 0)
{
myTriangulation->Triangle(t[i]).Get(n[0], n[1], n[2]);
for (j = 0; j < 3; j++)
{
if ((n[j] == mynode) && (n[(j + 1) % 3] == myothernode))
{
mytr = t[i];
myothernode = n[(j + 2) % 3];
mymore = !myPassedTr.Contains(mytr);
myPassedTr.Add(mytr);
return;
}
}
}
}
// sinon, depart vers la gauche.
myTriangulation->Triangle(myfirst).Get(n[0], n[1], n[2]);
for (i = 0; i < 3; i++)
{
if (n[i] == mynode)
{
break;
}
}
myothernode = n[(i + 1) % 3];
mysense = false;
mytr = myfirst;
Triangles(mytr, t[0], t[1], t[2]);
}
if (!mysense)
{
for (i = 0; i < 3; i++)
{
if (t[i] != 0)
{
myTriangulation->Triangle(t[i]).Get(n[0], n[1], n[2]);
for (j = 0; j < 3; j++)
{
if ((n[j] == mynode) && (n[(j + 2) % 3] == myothernode))
{
mytr = t[i];
myothernode = n[(j + 1) % 3];
mymore = !myPassedTr.Contains(mytr);
myPassedTr.Add(mytr);
return;
}
}
}
}
}
mymore = false;
}
f2929057eThis file is pinned to the selected release. Download the original to open it in your design tool.