/* * NodeIndexedLineSet.cpp * * Copyright (C) 1999 Stephen F. White * * 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 (see the file "COPYING" for details); if * not, write to the Free Software Foundation, Inc., 675 Mass Ave, * Cambridge, MA 02139, USA. */ #include #include "stdafx.h" #include "NodeIndexedLineSet.h" #include "Proto.h" #include "FieldValue.h" #include "Scene.h" #include "SFNode.h" #include "MFInt32.h" #include "SFInt32.h" #include "SFBool.h" #include "MFColor.h" #include "MFVec3f.h" #include "NodeColor.h" #include "NodeCoordinate.h" #include "Util.h" ProtoIndexedLineSet::ProtoIndexedLineSet(Scene *scene) : Proto(scene, "IndexedLineSet") { addEventIn(MFINT32, "set_colorIndex"); addEventIn(MFINT32, "set_coordIndex"); color.set( addExposedField(SFNODE, "color", new SFNode(NULL), NODE_COLOR)); coord.set( addExposedField(SFNODE, "coord", new SFNode(NULL), NODE_COORDINATE)); colorIndex.set( addField(MFINT32, "colorIndex", new MFInt32(), new SFInt32(-1))); colorPerVertex.set( addField(SFBOOL, "colorPerVertex", new SFBool(true))); coordIndex.set( addField(MFINT32, "coordIndex", new MFInt32(), new SFInt32(-1))); } Node * ProtoIndexedLineSet::create(Scene *scene) { return new NodeIndexedLineSet(scene, this); } NodeIndexedLineSet::NodeIndexedLineSet(Scene *scene, Proto *def) : Node(scene, def) { } void NodeIndexedLineSet::draw() { Node *coord = ((SFNode *) getField(coord_Index(),true))->getValue(); MFInt32 *mfColorIndex = colorIndex(); // int numColorIndex = mfColorIndex->getSize(); MFInt32 *mfCoordIndex = coordIndex(); MFColor *colors = NULL; int colorSize = 0; float lineSize = TheApp->GetPointSetSize(); glPushAttrib(GL_ENABLE_BIT); glDisable(GL_LIGHTING); glDisable(GL_TEXTURE_2D); if (lineSize == 0.0) { glEnable(GL_LINE_SMOOTH); glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); glEnable(GL_BLEND); glLineWidth(1.0); } else { glDisable(GL_LINE_SMOOTH); glLineWidth(lineSize); } if (color()->getValue()) { if (color()->getValue()->getType() == NODE_COLOR) { colors = ((NodeColor *)(color()->getValue()))->color(); colorSize = colors->getSize(); if (mfColorIndex->getSize() != mfCoordIndex->getSize()) mfColorIndex = mfCoordIndex; } } if (colors == NULL) { float c[4]; glGetMaterialfv(GL_FRONT, GL_EMISSION, c); Util::myGlColor4fv(c); } if (!coord || ((NodeCoordinate *) coord)->point()->getType() != MFVEC3F) return; MFVec3f *coords = ((NodeCoordinate *) coord)->point(); int coordSize = coords->getSize(); bool inSet = false; int size = mfCoordIndex->getSize(); for (int i = 0; i < size; i++) { int index = mfCoordIndex->getValue(i); if (index == -1) { if (inSet) { glEnd(); inSet = false; } } else { if (!inSet) { glBegin(GL_LINE_STRIP); inSet = true; } if (colors != NULL) { int cindex = mfColorIndex->getValue(i); if (colorPerVertex()->getValue() && cindex < colorSize) { Util::myGlColor3fv(colors->getValue(cindex)); } } if (index < coordSize) { glVertex3fv(coords->getValue(index)); } } } if (inSet) glEnd(); glEnable(GL_LIGHTING); glPopAttrib(); } Node * NodeIndexedLineSet::toPointSet(void) { NodeIndexedLineSet *node = (NodeIndexedLineSet *) _scene->createNode("PointSet"); NodeCoordinate *lineCoord = (NodeCoordinate *)coord()->getValue(); if (lineCoord != NULL) { NodeCoordinate *ncoord = (NodeCoordinate *) _scene->createNode("Coordinate"); ncoord->point(new MFVec3f(*(lineCoord->point()))); node->coord(new SFNode(ncoord)); } NodeColor *lineColor = (NodeColor *)color()->getValue(); if (lineColor != NULL) { NodeColor *ncolor = (NodeColor *) _scene->createNode("Color"); ncolor->color(new MFColor(*(lineColor->color()))); node->color(new SFNode(ncolor)); } return node; } Vec3f NodeIndexedLineSet::getMinBoundingBox(void) { Vec3f ret(0, 0, 0); Node *coord = ((SFNode *) getField(coord_Index(),true))->getValue(); if (coord != NULL) { MFVec3f *coords = ((NodeCoordinate *)coord)->point(); if (coords != NULL) ret = coords->getMinBoundingBox(); } return ret; } Vec3f NodeIndexedLineSet::getMaxBoundingBox(void) { Vec3f ret(0, 0, 0); Node *coord = ((SFNode *) getField(coord_Index(),true))->getValue(); if (coord != NULL) { MFVec3f *coords = ((NodeCoordinate *)coord)->point(); if (coords != NULL) ret = coords->getMaxBoundingBox(); } return ret; } void NodeIndexedLineSet::flip(int index) { NodeCoordinate *ncoord = (NodeCoordinate *)coord()->getValue(); if (ncoord) if (ncoord->getType() == NODE_COORDINATE) { MFVec3f *coords = ncoord->point(); if (coords != NULL) coords->flip(index); } }