EgtGeomKernel :

- correzioni a triangolazione Zmap per caso 7 con sottocasi da gestire.
This commit is contained in:
Dario Sassi
2018-10-26 07:26:50 +00:00
parent cee2ae0c77
commit bdd889c74a
2 changed files with 623 additions and 365 deletions
+387 -361
View File
File diff suppressed because it is too large Load Diff
+236 -4
View File
@@ -1388,10 +1388,9 @@ VolZmap::ExtMarchingCubes( int nBlock, TRIA3DEXLIST& lstTria, VoxelContainer& vV
for ( int i = nLimits[0] ; i < nLimits[1] ; ++ i) {
for ( int j = nLimits[2] ; j < nLimits[3] ; ++ j) {
for ( int k = nLimits[4] ; k < nLimits[5] ; ++ k) {
if ( m_nShape == BOX && ! IsVoxelOnBoxEdge( i, j, k))
continue ;
// Classificazione dei vertici: interni o esterni al materiale
int nIndex = CalcIndex( i, j, k) ;
@@ -1674,7 +1673,7 @@ VolZmap::ExtMarchingCubes( int nBlock, TRIA3DEXLIST& lstTria, VoxelContainer& vV
// Configurazione 6
else if ( nAllConfig[nIndex] == 6) {
// Test sulla topologia
// Test sulla topologia
bool bDefTopology = false ;
bool bNewTopology = false ;
int nCount = 0 ;
@@ -1808,7 +1807,239 @@ VolZmap::ExtMarchingCubes( int nBlock, TRIA3DEXLIST& lstTria, VoxelContainer& vV
}
}
}
// Configurazione 7
else if ( nAllConfig[nIndex] == 7) {
// !!! Versione provvisoria, deve essere riveduta e semplificata !!!
// Test sulla topologia
bool bMatOnSliceYZ = false ;
bool bMatOnSliceXZ = false ;
bool bMatOnSliceXY = false ;
bool bDefSliceYZ = false ;
bool bDefSliceXZ = false ;
bool bDefSliceXY = false ;
int nCount = 0 ;
while ( nIndexConfig7[nCount] != nIndex)
++ nCount ;
// Vedo se la topologia è definita: se sì uso l'informazione già posseduta,
// altrimenti devo calcolare la topologia
// Numerazione delle facce del voxel: 0: XZ- 1: YZ+ 2: XZ+ 3: YZ- 4: XY- 5: XY+
// - 1 faccia non in gioco, 0 faccia in gioco ma con topologia non definita,
// 1 faccia in gioco con topologia definita
int nFace[6] = { -1, -1, -1, -1, -1, -1} ;
// Facce in gioco
int nCurFaceYZ = 3 ;
int nCurFaceXZ = 0 ;
int nCurFaceXY = 4 ;
int nIJKSlYZ[3] = { i, j, k} ;
if ( nAdjVox7[nCount][0] == 1) {
++ nIJKSlYZ[0] ;
nCurFaceYZ = 1 ;
}
int nIJKSlXZ[3] = { i, j, k} ;
if ( nAdjVox7[nCount][1] == 1) {
++ nIJKSlXZ[1] ;
nCurFaceXZ = 2 ;
}
int nIJKSlXY[3] = { i, j, k} ;
if ( nAdjVox7[nCount][2] == 1) {
++ nIJKSlXY[2] ;
nCurFaceXY = 5 ;
}
nFace[nCurFaceYZ] = 0 ;
nFace[nCurFaceXZ] = 0 ;
nFace[nCurFaceXY] = 0 ;
int nSlYZN ;
int nSlYZBlockN ;
if ( GetVoxNFromIJK( nIJKSlYZ[0], nIJKSlYZ[1], nIJKSlYZ[2], nSlYZN)) {
// Slice interna al blocco
auto it = SliceYZ.find( nSlYZN) ;
// Topologia definita
if ( it != SliceYZ.end()) {
bMatOnSliceYZ = it->second ;
bDefSliceYZ = true ;
nFace[nCurFaceYZ] = 1 ;
}
// Slice sulla frontiera
int nSlBlockIJK[3] ;
GetVoxelBlockIJK( nIJKSlYZ, nSlBlockIJK) ;
if ( GetBlockNFromIJK( nSlBlockIJK, nSlYZBlockN)) {
auto it = m_SliceYZ[nSlYZBlockN].find( nSlYZN) ;
// Topologia definita
if ( it != m_SliceYZ[nSlYZBlockN].end()) {
bMatOnSliceYZ = it->second ;
bDefSliceYZ = true ;
nFace[nCurFaceYZ] = 1 ;
}
}
}
int nSlXZN ;
int nSlXZBlockN ;
if ( GetVoxNFromIJK( nIJKSlXZ[0], nIJKSlXZ[1], nIJKSlXZ[2], nSlXZN)) {
// Slice interna al blocco
auto it = SliceXZ.find( nSlXZN) ;
// Topologia definita
if ( it != SliceXZ.end()) {
bMatOnSliceXZ = it->second ;
bDefSliceXZ = true ;
nFace[nCurFaceXZ] = 1 ;
}
// Slice sulla frontiera
int nSlBlockIJK[3] ;
GetVoxelBlockIJK( nIJKSlXZ, nSlBlockIJK) ;
if ( GetBlockNFromIJK( nSlBlockIJK, nSlXZBlockN)) {
auto it = m_SliceYZ[nSlXZBlockN].find( nSlXZN) ;
// Topologia definita
if ( it != m_SliceYZ[nSlXZBlockN].end()) {
bMatOnSliceXZ = it->second ;
bDefSliceXZ = true ;
nFace[nCurFaceXZ] = 1 ;
}
}
}
int nSlXYN ;
int nSlXYBlockN ;
if ( GetVoxNFromIJK( nIJKSlXY[0], nIJKSlXY[1], nIJKSlXY[2], nSlXYN)) {
// Slice interna al blocco
auto it = SliceXY.find( nSlXYN) ;
// Topologia definita
if ( it != SliceXY.end()) {
bMatOnSliceXY = it->second ;
bDefSliceXY = true ;
nFace[nCurFaceXY] = 1 ;
}
// Slice sulla frontiera
int nSlBlockIJK[3] ;
GetVoxelBlockIJK( nIJKSlXY, nSlBlockIJK) ;
if ( GetBlockNFromIJK( nSlBlockIJK, nSlXYBlockN)) {
auto it = m_SliceYZ[nSlXYBlockN].find( nSlXYN) ;
// Topologia definita
if ( it != m_SliceYZ[nSlXYBlockN].end()) {
bMatOnSliceXY = it->second ;
bDefSliceXY = true ;
nFace[nCurFaceXY] = 1 ;
}
}
}
// Numerazione delle facce del voxel 0: XZ- 1: YZ+ 2: XZ+ 3: YZ- 4: XY- 5: XY+
// Gli spigoli sono ordinati in senso antiorario dal punto di vista di un osservatore esterno del voxel
static int nSliceEdges[6][4] = { { 0, 9, 4, 8}, { 1, 10, 5, 9}, { 2, 11, 6, 10},
{ 3, 8, 7, 11}, { 0, 3, 2, 1}, { 4, 5, 6, 7}} ;
// nFace[nCurFaceXY] * nFace[nCurFaceXZ] * nFace[nCurFaceYZ] == 0
if ( ( nFace[nCurFaceXY] == 0 || nFace[nCurFaceXZ] == 0 || nFace[nCurFaceYZ] == 0) && bReg) {
// Ciclo sulle facce
for ( int nFaceN = 0 ; nFaceN < 6 ; ++ nFaceN) {
// Faccia da analizzare
if ( nFace[nFaceN] == 0) {
// Dalla tabella determino le due componenti connesse che si appoggiano alla faccia
int nFaceCompo1 = 0 ;
int nFaceCompo2 = 0 ;
// Ciclo sulle componenti connesse del voxel
for ( int nCurComp = 1 ; nCurComp <= 3 ; ++ nCurComp) {
int nMatchEdge = 0 ;
// Ciclo sugli edge della componente
for ( int nEdge = 0 ; nEdge < 3 ; ++ nEdge) {
// Ciclo sugli edge della faccia
for ( int nFaceEdge = 0 ; nFaceEdge < 3 ; ++ nFaceEdge) {
// Edge della componente coincide con quello della faccia
if ( nSliceEdges[nFaceN][nFaceEdge] == TriangleTableEn[nIndex][1][3 + nCurComp - 1 + nEdge]) {
++ nMatchEdge ;
break ;
}
}
// La componente corrente ha due edge sulla faccia,
// interrompiamo la ricerca di edge corrispondenti
if ( nMatchEdge == 2)
break ;
}
// Abbiamo trovato una nuova componente con due edge sulla faccia
if ( nMatchEdge == 2) {
if ( nFaceCompo1 == 0)
nFaceCompo1 = nCurComp ;
else
nFaceCompo2 = nCurComp ;
}
// Se le componenti con due edge sulla faccia sono due, interrompiamo la ricerca
if ( nFaceCompo2 != 0)
break ;
}
// Valuto la topologia VecField[EdgeIndex] edgeIndex = 0, 1, ..., 11
double dDotSum = 0 ;
for ( int nV = 0 ; nV < 3 ; ++ nV) {
Vector3d vtV1 = VecField[TriangleTableEn[nIndex][1][3 + nFaceCompo1 - 1 + nV]].vtVec ;
Vector3d vtV2 = VecField[TriangleTableEn[nIndex][1][3 + nFaceCompo2 - 1 + nV]].vtVec ;
dDotSum += ( vtV1 * vtV2) ;
}
if ( nFace[nFaceN] == 0 || nFace[nFaceN] == 2)
bMatOnSliceXZ = dDotSum > 0. ;
else if ( nFace[nFaceN] == 1 || nFace[nFaceN] == 3)
bMatOnSliceYZ = dDotSum > 0. ;
else
bMatOnSliceXY = dDotSum > 0. ;
}
}
int nFaceWithMatNum = 0 ;
if ( bMatOnSliceXZ)
++ nFaceWithMatNum ;
if ( bMatOnSliceYZ)
++ nFaceWithMatNum ;
if ( bMatOnSliceXY)
++ nFaceWithMatNum ;
if ( nFaceWithMatNum == 1) {
int nFaceCase = ( bMatOnSliceYZ ? 0 : ( bMatOnSliceXZ ? 1 : 2)) ;
// Aggiorno numero di componenti
nComponents = Cases7Plus[nCount][nFaceCase][1][0] ;
// Riaggiorno gli offsets
nExtTabOff = nComponents ;
nStdTabOff = 0 ;
// Modifico le matrici
for ( int nC = 1 ; nC <= nComponents ; ++ nC) {
// Numero vertici per componenti
nVertComp[nC - 1] = Cases7Plus[nCount][nFaceCase][1][nC] ;
// Matrice dei vertici della base del fan
for ( int nFanVert = 0 ; nFanVert < nVertComp[nC - 1] ; ++ nFanVert)
CompoVert[nC - 1][nFanVert] = VecField[Cases7Plus[nCount][nFaceCase][1][nFanVert + nExtTabOff + 1]] ;
// Matrici dei vertici dei triangoli in assenza di sharp feature
for ( int nTriVert = 0 ; nTriVert < 3 * ( nVertComp[nC - 1] - 2) ; nTriVert += 3) {
CompoTriVert[nC - 1][nTriVert] = VecField[Cases7Plus[nCount][nFaceCase][0][nStdTabOff + nTriVert+2]] ;
CompoTriVert[nC - 1][nTriVert+1] = VecField[Cases7Plus[nCount][nFaceCase][0][nStdTabOff + nTriVert+1]] ;
CompoTriVert[nC - 1][nTriVert+2] = VecField[Cases7Plus[nCount][nFaceCase][0][nStdTabOff + nTriVert]] ;
}
// Aggiorno gli offsets per raggiungere i vertici della componente successiva.
nExtTabOff += nVertComp[nC - 1] ;
nStdTabOff += 3 * ( nVertComp[nC - 1] - 2) ;
}
}
else if ( nFaceWithMatNum == 2) {
;
}
}
// Conservo l'informazione
if ( GetVoxNFromIJK( nIJKSlYZ[0], nIJKSlYZ[1], nIJKSlYZ[2], nSlYZN)) {
if ( nSlYZBlockN == nBlock)
SliceYZ.emplace( nSlYZN, bMatOnSliceYZ) ;
else
m_SliceYZ[nSlYZBlockN].emplace( nSlYZN, bMatOnSliceYZ) ;
}
if ( GetVoxNFromIJK( nIJKSlXZ[0], nIJKSlXZ[1], nIJKSlXZ[2], nSlXZN)) {
if ( nSlXZBlockN == nBlock)
SliceXZ.emplace( nSlXZN, bMatOnSliceXZ) ;
else
m_SliceXZ[nSlXZBlockN].emplace( nSlXZN, bMatOnSliceXZ) ;
}
if ( GetVoxNFromIJK( nIJKSlXY[0], nIJKSlXY[1], nIJKSlXY[2], nSlXYN)) {
if ( nSlXYBlockN == nBlock)
SliceXY.emplace( nSlXYN, bMatOnSliceXY) ;
else
m_SliceXY[nSlXYBlockN].emplace( nSlXYN, bMatOnSliceXY) ;
}
}
// Configurazione 10
else if ( nAllConfig[nIndex] == 10) {
// Test sulla topologia
@@ -1928,6 +2159,7 @@ VolZmap::ExtMarchingCubes( int nBlock, TRIA3DEXLIST& lstTria, VoxelContainer& vV
}
}
}
Voxel VoxConf ;
VoxConf.nNumComp = 0 ;
@@ -2030,7 +2262,7 @@ VolZmap::ExtMarchingCubes( int nBlock, TRIA3DEXLIST& lstTria, VoxelContainer& vV
else if ( m_nShape != BOX) {
vector<Triangle3dEx> vTria ;
// Costruzione dei triangoli
for ( int TriIndex = 0; TriIndex < ( nVertComp[nComp] - 2) * 3 ; TriIndex += 3) {
for ( int TriIndex = 0 ; TriIndex < ( nVertComp[nComp] - 2) * 3 ; TriIndex += 3) {
// Il triangolo è pronto
Triangle3dEx CurrentTriangle ;
CurrentTriangle.Set( CompoTriVert[nComp][TriIndex].ptPApp,