#include using namespace std; #include "util.h" #include "entity.h" #include "oct.h" #include "view.h" entity_base::entity_base () : parent(0) { } entity_base::~entity_base () { hide (); } void entity_base::update () { if (parent) parent->update (); } void entity_base::hide () { for (vector::iterator i = o.end (); i-- != o.begin (); ) (*i)->remove (this); o.clear (); } void entity_base::display (draw_context &ctx) { if (ctx.may_draw (this)) draw (ctx); } ///////////////////////////////////////////////////////////////////////////// void entity_filter::update () { bbox = translate (e->bbox, e->orig, orig); entity_base::update (); } void entity_filter::show () { entity_base::show (); e->show (); } void entity_filter::draw (draw_context &ctx) { e->display (ctx); } entity_filter::~entity_filter () { delete e; } ///////////////////////////////////////////////////////////////////////////// void entity_container::update () { bbox.reset (); for (iterator i = end (); i-- != begin (); ) bbox.add ((*i)->bbox); entity_base::update (); } void entity_container::show () { entity_base::show (); for (iterator i = end (); i-- != begin (); ) (*i)->show (); } void entity_container::draw (draw_context &ctx) { for (iterator i = end (); i-- != begin (); ) (*i)->display (ctx); } entity_container::~entity_container () { hide (); for (iterator i = end (); i-- != begin (); ) delete *i; clear (); } ///////////////////////////////////////////////////////////////////////////// entity_opengl::entity_opengl () { list = glGenLists (1); } entity_opengl::~entity_opengl () { glDeleteLists (list, 1); } template class entity_opengl1d; template class entity_opengl1d; template class entity_opengl1d; template class entity_opengl1d; template class entity_opengl2d; template class entity_opengl2d; template class entity_opengl2d; template class entity_opengl2d; template class entity_opengl2d; template class entity_opengl2d; template void entity_opengl1d::update () { bbox.reset (); for (vector::iterator i = end (); i-- != begin (); ) bbox.add (i->p); entity_base::update (); } template void entity_opengl1d::draw (draw_context &ctx) { glBegin (type); for (iterator i = begin (); i < end (); ++i) { glColor3fv ((GLfloat *)&i->c); glVertex3fv ((GLfloat *)&i->p); } glEnd (); } template void entity_opengl2d::set (const vector &v) { bbox.reset (); for (vector::const_iterator i = v.end (); i-- != v.begin (); ) bbox.add (i->p); update (); glNewList (list, GL_COMPILE); glMaterialfv (GL_FRONT, GL_DIFFUSE, (GLfloat *)&m.diffuse); glMaterialfv (GL_FRONT, GL_SPECULAR, (GLfloat *)&m.specular); glMaterialfv (GL_FRONT, GL_EMISSION, (GLfloat *)&m.emission); glMaterialf (GL_FRONT, GL_SHININESS, m.shininess); #if 0 glBegin (type); for (vector::const_iterator i = v.begin (); i < v.end (); ++i) { glTexCoord2fv ((GLfloat *)&i->t); glNormal3fv ((GLfloat *)&i->n); glVertex3fv ((GLfloat *)&i->p); } glEnd (); #else glEnableClientState (GL_VERTEX_ARRAY); glVertexPointer (3, GL_FLOAT, sizeof (vertex2d), (void *)&v.begin ()->p); glEnableClientState (GL_NORMAL_ARRAY); glNormalPointer (GL_FLOAT, sizeof (vertex2d), (void *)&v.begin ()->n); glEnableClientState (GL_TEXTURE_COORD_ARRAY); glTexCoordPointer (2, GL_FLOAT, sizeof (vertex2d), (void *)&v.begin ()->t); glDrawArrays (type, 0, v.size ()); #endif glEndList (); } template void entity_opengl2d::draw (draw_context &ctx) { const matrix save_mv = ctx.modelview; const sector &corig = ctx.v.orig; ctx.transform (matrix::translation (vec3 (orig.x - corig.x, orig.y - corig.y, orig.z - corig.z))); glCallList (list); ctx.modelview = save_mv; } ///////////////////////////////////////////////////////////////////////////// entity_transform::entity_transform () { m.identity (); } void entity_transform::update () { box sub = translate (e->bbox, e->orig, orig); bbox.reset (); bbox.add (m * vec3 (sub.a.x, sub.a.y, sub.a.z)); bbox.add (m * vec3 (sub.b.x, sub.a.y, sub.a.z)); bbox.add (m * vec3 (sub.a.x, sub.b.y, sub.a.z)); bbox.add (m * vec3 (sub.b.x, sub.b.y, sub.a.z)); bbox.add (m * vec3 (sub.a.x, sub.a.y, sub.b.z)); bbox.add (m * vec3 (sub.b.x, sub.a.y, sub.b.z)); bbox.add (m * vec3 (sub.a.x, sub.b.y, sub.b.z)); bbox.add (m * vec3 (sub.b.x, sub.b.y, sub.b.z)); entity_base::update (); } void entity_transform::renormalize () { #if 0 point trans(m(0,0), m(1,0), m(2,0)); ::renormalize (orig, trans); m(0,0) = trans.x; m(1,0) = trans.y; m(2,0) = trans.z; #endif } void entity_transform::update (const matrix &xfrm) { m = m * xfrm; renormalize (); update (); } void entity_transform::set_matrix (const matrix &xfrm) { m = xfrm; renormalize (); update (); } void entity_transform::show () { entity_base::show (); } void entity_transform::draw (draw_context &ctx) { const matrix save_mv = ctx.modelview; const sector &corig = ctx.v.orig; #if 0 glTranslatef (orig.x - corig.x, orig.y - corig.y, orig.z - corig.z); ctx.transform (matrix::translation (vec3 (orig.x - corig.x, orig.y - corig.y, orig.z - corig.z))); #endif ctx.transform (m); e->draw (ctx); ctx.modelview = save_mv; } void entity_anim::draw (draw_context &ctx) { matrix save_m = m; update (matrix::rotation (vx * timer.now, vec3 (1, 0, 0)) * matrix::rotation (vy * timer.now, vec3 (0, 1, 0)) * matrix::rotation (vz * timer.now, vec3 (0, 0, 1))); entity_transform::draw (ctx); m = save_m; }