00001
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032 #include "ShadowManager.h"
00033 #include "ObjectModel.h"
00034
00035
00036
00037
00038
00039 SbVec3f CObjectModel::prevNormal(1.0f, 1.0f, 1.0f);
00040
00044 CObjectModel::CObjectModel()
00045 {
00046 nTriangles = 0;
00047 modelIfs = NULL;
00048 modelCoord3 = NULL;
00049 objectModelRoot = new SoSeparator;
00050 }
00051
00052
00056 CObjectModel::~CObjectModel()
00057 {
00058 objectModelRoot->removeAllChildren();
00059 }
00060
00061
00073 SbVec3f CObjectModel::faceNormal(const SbVec3f p1, const SbVec3f p2, const SbVec3f p3)
00074 {
00075 SbVec3f vector1, vector2;
00076
00077 vector1 = p2 - p1;
00078 vector2 = p3 - p2;
00079
00080 if ( vector1.length() <= .0f ) {
00081 ONDEBUG(printf("Error: Length of a vector1 is 0. Correcting...\n"));
00082 }
00083 if ( vector2.length() <= .0f ) {
00084 ONDEBUG(printf("Error: Length of a vector2 is 0. Correcting...\n"));
00085 }
00086
00087 SbVec3f normal = vector1.cross(vector2);
00088 if ( normal.length() > .0f ) {
00089 normal.normalize();
00090 prevNormal = normal;
00091 } else {
00092 ONDEBUG(printf("Error: FaceNormal: Length of the normal is 0. Using previous.\n"));
00093 ONDEBUG(printf("prevNormal: %.2f %.2f %.2f \n",prevNormal[0], prevNormal[1], prevNormal[2]));
00094 normal = prevNormal;
00095
00096
00097 }
00098
00099 return normal;
00100 }
00101
00102
00114 void CObjectModel::TriangleCB(void * userdata,
00115 SoCallbackAction * action,
00116 const SoPrimitiveVertex * v1,
00117 const SoPrimitiveVertex * v2,
00118 const SoPrimitiveVertex * v3)
00119 {
00120 CObjectModel * sc = (CObjectModel *) userdata;
00121 sc->nTriangles++;
00122
00123
00124 SbColor ambient;
00125 SbColor diffuse;
00126 SbColor specular;
00127 SbColor emission;
00128 float shininess;
00129 float transparency;
00130 int index = 0;
00131 action->getMaterial(ambient, diffuse, specular, emission, shininess, transparency, index );
00132
00133
00134
00135
00136
00137
00138
00139
00140
00141 if ( transparency == 0.0f )
00142 {
00143
00144
00145
00146 const SbVec3f vtx[] = { v1->getPoint(), v2->getPoint(), v3->getPoint() };
00147
00148 const SbMatrix mm = action->getModelMatrix();
00149
00150
00151 SbVec3f vx[3];
00152 mm.multVecMatrix(vtx[0], vx[0]);
00153 mm.multVecMatrix(vtx[1], vx[1]);
00154 mm.multVecMatrix(vtx[2], vx[2]);
00155
00156
00157 sc->modelCoord3->point.setNum(sc->modelCoord3->point.getNum() + 3);
00158 sc->modelCoord3->point.setValues(sc->coord3idx, 3, vx);
00159
00160 int32_t indices[] = { sc->coord3idx, sc->coord3idx + 1, sc->coord3idx + 2, -1 };
00161 sc->coord3idx += 3;
00162
00163 int oldsize = sc->modelIfs->coordIndex.getNum();
00164 sc->modelIfs->coordIndex.setNum(oldsize + 4);
00165 sc->modelIfs->coordIndex.setValues(oldsize, 4, indices);
00166
00167
00168
00169 SbVec3f normal = faceNormal(vx[0], vx[1], vx[2]);
00170
00171
00172 int oldsizeN = sc->modelIfs->normalIndex.getNum();
00173 sc->modelNormal->vector.set1Value(oldsizeN, normal);
00174
00175 sc->modelIfs->normalIndex.set1Value(oldsizeN, oldsizeN);
00176 sc->modelIfs->normalIndex.setNum(oldsizeN + 1);
00177 }
00178 }
00179
00180
00186 void CObjectModel::createFaceModel(SoSeparator * object)
00187 {
00188 ONDEBUG(printf("creating face model...\n"));
00189 ONDEBUG( printf(" objectModelRoot has %d children\n",objectModelRoot->getNumChildren()) );
00190 objectModelRoot->removeAllChildren();
00191
00192 nTriangles = 0;
00193 coord3idx = 0;
00194
00195 modelCoord3 = new SoCoordinate3;
00196 modelCoord3->point.setNum(0);
00197
00198 modelIfs = new SoIndexedFaceSet;
00199 modelIfs->coordIndex.setNum(0);
00200 modelIfs->normalIndex.setNum(0);
00201
00202 modelNormal = new SoNormal;
00203 modelNormal->vector.setNum(0);
00204
00205 SoShapeHints * hints = new SoShapeHints;
00206 hints->shapeType = SoShapeHintsElement::SOLID;
00207 hints->vertexOrdering = SoShapeHintsElement::COUNTERCLOCKWISE;
00208
00209
00210
00211 SoCallbackAction ca;
00212 ca.addTriangleCallback(SoShape::getClassTypeId(), TriangleCB, this);
00213 ca.apply(object);
00214
00215
00216 SoNormalBinding *nbind = new SoNormalBinding;
00217 nbind->value.setValue(SoNormalBinding::PER_FACE_INDEXED);
00218
00219 objectModelRoot->addChild(modelNormal);
00220 objectModelRoot->addChild(nbind);
00221 objectModelRoot->addChild(hints);
00222
00223 objectModelRoot->addChild(modelCoord3);
00224 objectModelRoot->addChild(modelIfs);
00225
00226 ONDEBUG(printf("Face model created. Model consists of %d triangles.\n", this->nTriangles));
00227 }
00228
00229
00233 SoSeparator * CObjectModel::getFaceModelNode()
00234 {
00235 return objectModelRoot;
00236 }
00237
00238
00242 int32_t CObjectModel::getTrianglesCount()
00243 {
00244 return nTriangles;
00245 }