This repository has been archived on 2023-10-09. You can view files and clone it. You cannot open issues or pull requests or push a commit.
Files
blender-archive/intern/boolop/intern/BOP_Face.cpp
Ken Hughes 1b78333087 Tools
-----
Minor changes to boolean code; add an new include file to gather various
#defines global to the boolean system.  Currently, this just allows control
of whether some debugging code is compiled or not.

This is a precursor commit for some other boolean optimizations/cleanups.
But in case that commit is later reverted, this code should still remain.
2008-07-30 21:52:02 +00:00

426 lines
11 KiB
C++

/**
* ***** BEGIN GPL LICENSE BLOCK *****
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software Foundation,
* Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*
* The Original Code is Copyright (C) 2001-2002 by NaN Holding BV.
* All rights reserved.
*
* The Original Code is: all of this file.
*
* Contributor(s): none yet.
*
* ***** END GPL LICENSE BLOCK *****
*/
#include "BOP_Face.h"
/******************************************************************************/
/*** BOP_Face ***/
/******************************************************************************/
/**
* Constructs a new face.
* @param plane face plane
* @param originalFace index of the original face
*/
BOP_Face::BOP_Face(MT_Plane3 plane, BOP_Index originalFace)
{
m_plane = plane;
m_tag = UNCLASSIFIED;
m_originalFace = originalFace;
m_split = 0;
m_bbox = NULL;
}
/**
* Inverts this face.
*/
void BOP_Face::invert()
{
getPlane().Invert();
BOP_Index aux = m_indexs[0];
m_indexs[0] = m_indexs[2];
m_indexs[2] = aux;
}
/******************************************************************************/
/*** BOP_Face ***/
/******************************************************************************/
/**
* Constructs a new triangle face.
* @param v1 vertex index
* @param v2 vertex index
* @param v3 vertex index
* @param plane face plane
* @param originalFace index of the original face
*/
BOP_Face3::BOP_Face3(BOP_Index v1, BOP_Index v2, BOP_Index v3, MT_Plane3 plane, BOP_Index originalFace): BOP_Face(plane,originalFace)
{
m_indexs[0] = v1;
m_indexs[1] = v2;
m_indexs[2] = v3;
m_size = 3;
}
/**
* Returns the relative edge index (1,2,3) for the specified vertex indexs.
* @param v1 vertex index
* @param v2 vertex index
* @param e relative edge index (1,2,3)
* @return true if (v1,v2) is an edge of this face, false otherwise
*/
bool BOP_Face3::getEdgeIndex(BOP_Index v1, BOP_Index v2, unsigned int &e)
{
if (m_indexs[0] == v1) {
if (m_indexs[1] == v2) {
e = 1;
}
else if (m_indexs[2] == v2) {
e = 3;
}
else
return false;
}
else if (m_indexs[1] == v1) {
if (m_indexs[0] == v2) {
e = 1;
}
else if (m_indexs[2] == v2) {
e = 2;
}
else
return false;
}
else if (m_indexs[2] == v1) {
if (m_indexs[0] == v2) {
e = 3;
}
else if (m_indexs[1] == v2) {
e = 2;
}
else
return false;
}else {
return false;
}
return true;
}
/**
* Returns if this face contains the specified vertex index.
* @param v vertex index
* @return true if this face contains the specified vertex index, false otherwise
*/
bool BOP_Face3::containsVertex(BOP_Index v)
{
return (m_indexs[0] == v || m_indexs[1] == v || m_indexs[2] == v);
}
/**
* Returns the neighbours of the specified vertex index.
* @param v vertex index
* @param prev previous vertex index
* @param next next vertex index
* @return true if this face contains the vertex index v, false otherwise
*/
bool BOP_Face3::getNeighbours(BOP_Index v, BOP_Index &prev, BOP_Index &next)
{
if (m_indexs[0] == v) {
prev = m_indexs[2];
next = m_indexs[1];
}
else if (m_indexs[1] == v) {
prev = m_indexs[0];
next = m_indexs[2];
}
else if (m_indexs[2] == v) {
prev = m_indexs[1];
next = m_indexs[0];
}
else return false;
return true;
}
/**
* Returns the previous neighbour of the specified vertex index.
* @param v vertex index
* @param w previous vertex index
* @return true if this face contains the specified vertex index, false otherwise
*/
bool BOP_Face3::getPreviousVertex(BOP_Index v, BOP_Index &w)
{
if (m_indexs[0] == v) w = m_indexs[2];
else if (m_indexs[1] == v) w = m_indexs[0];
else if (m_indexs[2] == v) w = m_indexs[1];
else return false;
return true;
}
/**
* Returns the next neighbour of the specified vertex index.
* @param v vertex index
* @param w vertex index
* @return true if this face contains the specified vertex index, false otherwise
*/
bool BOP_Face3::getNextVertex(BOP_Index v, BOP_Index &w)
{
if (m_indexs[0] == v) w = m_indexs[1];
else if (m_indexs[1] == v) w = m_indexs[2];
else if (m_indexs[2] == v) w = m_indexs[0];
else return false;
return true;
}
/**
* Replaces a face vertex index.
* @param oldIndex old vertex index
* @param newIndex new vertex index
*/
void BOP_Face3::replaceVertexIndex(BOP_Index oldIndex, BOP_Index newIndex)
{
/* if the old index really exists, and new index also exists already,
* don't create an edge with both vertices == newIndex */
if( (m_indexs[0] == oldIndex || m_indexs[1] == oldIndex || m_indexs[2] == oldIndex) &&
(m_indexs[0] == newIndex || m_indexs[1] == newIndex || m_indexs[2] == newIndex) ) {
setTAG(BROKEN);
}
if (m_indexs[0] == oldIndex) m_indexs[0] = newIndex;
else if (m_indexs[1] == oldIndex) m_indexs[1] = newIndex;
else if (m_indexs[2] == oldIndex) m_indexs[2] = newIndex;
}
/******************************************************************************/
/*** BOP_Face4 ***/
/******************************************************************************/
/**
* Constructs a new quad face.
* @param v1 vertex index
* @param v2 vertex index
* @param v3 vertex index
* @param v4 vertex index
* @param plane face plane
* @param originalFace index of the original face
*/
BOP_Face4::BOP_Face4(BOP_Index v1, BOP_Index v2, BOP_Index v3, BOP_Index v4, MT_Plane3 plane,
BOP_Index originalFace):
BOP_Face(plane,originalFace)
{
m_indexs[0] = v1;
m_indexs[1] = v2;
m_indexs[2] = v3;
m_indexs[3] = v4;
m_size = 4;
}
/**
* Returns if this face contains the specified vertex index.
* @param v vertex index
* @return true if this face contains the specified vertex index, false otherwise
*/
bool BOP_Face4::containsVertex(BOP_Index v)
{
return (m_indexs[0] == v || m_indexs[1] == v || m_indexs[2] == v || m_indexs[3]==v);
}
/**
* Returns the neighbours of the specified vertex index.
* @param v vertex index
* @param prev previous vertex index
* @param next next vertex index
* @param opp opposite vertex index
* @return true if this face contains the vertex index v, false otherwise
*/
bool BOP_Face4::getNeighbours(BOP_Index v, BOP_Index &prev, BOP_Index &next, BOP_Index &opp)
{
if (m_indexs[0] == v) {
prev = m_indexs[3];
next = m_indexs[1];
opp = m_indexs[2];
}
else if (m_indexs[1] == v) {
prev = m_indexs[0];
next = m_indexs[2];
opp = m_indexs[3];
}
else if (m_indexs[2] == v) {
prev = m_indexs[1];
next = m_indexs[3];
opp = m_indexs[0];
}
else if (m_indexs[3] == v) {
prev = m_indexs[2];
next = m_indexs[0];
opp = m_indexs[1];
}
else return false;
return true;
}
/**
* Returns the previous neighbour of the specified vertex index.
* @param v vertex index
* @param w previous vertex index
* @return true if this face contains the specified vertex index, false otherwise
*/
bool BOP_Face4::getPreviousVertex(BOP_Index v, BOP_Index &w)
{
if (m_indexs[0] == v) w = m_indexs[3];
else if (m_indexs[1] == v) w = m_indexs[0];
else if (m_indexs[2] == v) w = m_indexs[1];
else if (m_indexs[3] == v) w = m_indexs[2];
else return false;
return true;
}
/**
* Returns the next neighbour of the specified vertex index.
* @param v vertex index
* @param w next vertex index
* @return true if this face contains the specified vertex index, false otherwise
*/
bool BOP_Face4::getNextVertex(BOP_Index v, BOP_Index &w)
{
if (m_indexs[0] == v) w = m_indexs[1];
else if (m_indexs[1] == v) w = m_indexs[2];
else if (m_indexs[2] == v) w = m_indexs[3];
else if (m_indexs[3] == v) w = m_indexs[0];
else return false;
return true;
}
/**
* Returns the opposite neighbour of the specified vertex index.
* @param v vertex index
* @param w opposite vertex index
* @return true if this face contains the specified vertex index, false otherwise
*/
bool BOP_Face4::getOppositeVertex(BOP_Index v, BOP_Index &w)
{
if (m_indexs[0] == v)
w = m_indexs[2];
else if (m_indexs[1] == v)
w = m_indexs[3];
else if (m_indexs[2] == v)
w = m_indexs[0];
else if (m_indexs[3] == v)
w = m_indexs[1];
else
return false;
return true;
}
/**
* Replaces a face vertex index.
* @param oldIndex old vertex index
* @param newIndex new vertex index
*/
void BOP_Face4::replaceVertexIndex(BOP_Index oldIndex, BOP_Index newIndex)
{
if (m_indexs[0] == oldIndex) m_indexs[0] = newIndex;
else if (m_indexs[1] == oldIndex) m_indexs[1] = newIndex;
else if (m_indexs[2] == oldIndex) m_indexs[2] = newIndex;
else if (m_indexs[3] == oldIndex) m_indexs[3] = newIndex;
}
/**
* Returns the relative edge index (1,2,3,4) for the specified vertex indexs.
* @param v1 vertex index
* @param v2 vertex index
* @param e relative edge index (1,2,3,4)
* @return true if (v1,v2) is an edge of this face, false otherwise
*/
bool BOP_Face4::getEdgeIndex(BOP_Index v1, BOP_Index v2, unsigned int &e)
{
if (m_indexs[0] == v1) {
if (m_indexs[1] == v2) {
e = 1;
}
else if (m_indexs[3] == v2) {
e = 4;
}
else
return false;
}
else if (m_indexs[1] == v1) {
if (m_indexs[0] == v2) {
e = 1;
}
else if (m_indexs[2] == v2) {
e = 2;
}
else
return false;
}
else if (m_indexs[2] == v1) {
if (m_indexs[1] == v2) {
e = 2;
}
else if (m_indexs[3] == v2) {
e = 3;
}
else
return false;
}
else if (m_indexs[3] == v1) {
if (m_indexs[2] == v2) {
e = 3;
}
else if (m_indexs[0] == v2) {
e = 4;
}
else
return false;
}
else return false;
return true;
}
#ifdef BOP_DEBUG
/**
* Implements operator <<.
*/
ostream &operator<<(ostream &stream, BOP_Face *f)
{
char aux[20];
BOP_stringTAG(f->m_tag,aux);
if (f->size()==3) {
stream << "Face[" << f->getVertex(0) << "," << f->getVertex(1) << ",";
stream << f->getVertex(2) << "] (" << aux << ") <-- " << f->m_originalFace;
}
else {
stream << "Face[" << f->getVertex(0) << "," << f->getVertex(1) << ",";
stream << f->getVertex(2) << "," << f->getVertex(3) << "] (" << aux;
stream << ") <-- " << f->m_originalFace;
}
return stream;
}
#endif