void Scene::clear() { // remove all elements from the scene Ped::Tscene::clear(); // remove all agents // note: we don't need to delete them, because Ped::Tscene did so already agents.clear(); // remove all waypoints // note: we don't need to delete them, because Ped::Tscene did so already waypoints.clear(); // remove all obstacles // note: we don't need to delete them, because Ped::Tscene did so already obstacles.clear(); // remove all agents groups foreach ( AttractionArea* attraction, attractions ) delete attraction; attractions.clear(); // remove all agents clusters foreach ( AgentCluster* agentCluster, agentClusters ) delete agentCluster; agentClusters.clear(); // remove all agents groups foreach ( AgentGroup* group, agentGroups ) delete group; agentGroups.clear(); // don't clear the grid, because we can reuse it // reset time sceneTime = 0; emit sceneTimeChanged ( sceneTime ); }
void GLView::paintEvent( QPaintEvent * event ) { makeCurrent(); QPainter painter; painter.begin( this ); painter.setRenderHint( QPainter::TextAntialiasing ); #else void GLView::paintGL() { #endif // Save GL state glPushAttrib( GL_ALL_ATTRIB_BITS ); glMatrixMode( GL_PROJECTION ); glPushMatrix(); glMatrixMode( GL_MODELVIEW ); glPushMatrix(); // Clear Viewport if ( scene->visMode & Scene::VisSilhouette ) { qglClearColor( QColor( 255, 255, 255, 255 ) ); } //glViewport( 0, 0, width(), height() ); glClear( GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT ); // Compile the model if ( doCompile ) { textures->setNifFolder( model->getFolder() ); scene->make( model ); scene->transform( Transform(), scene->timeMin() ); axis = (scene->bounds().radius <= 0) ? 1024.0 : scene->bounds().radius; if ( scene->timeMin() != scene->timeMax() ) { if ( time < scene->timeMin() || time > scene->timeMax() ) time = scene->timeMin(); emit sequencesUpdated(); } else if ( scene->timeMax() == 0 ) { // No Animations in this NIF emit sequencesDisabled( true ); } emit sceneTimeChanged( time, scene->timeMin(), scene->timeMax() ); doCompile = false; } // Center the model if ( doCenter ) { setCenter(); doCenter = false; } // Transform the scene Matrix ap; // TODO: Redo for new Settings class //if ( Options::upAxis() == Options::YAxis ) { // ap( 0, 0 ) = 0; ap( 0, 1 ) = 0; ap( 0, 2 ) = 1; // ap( 1, 0 ) = 1; ap( 1, 1 ) = 0; ap( 1, 2 ) = 0; // ap( 2, 0 ) = 0; ap( 2, 1 ) = 1; ap( 2, 2 ) = 0; //} else if ( Options::upAxis() == Options::XAxis ) { // ap( 0, 0 ) = 0; ap( 0, 1 ) = 1; ap( 0, 2 ) = 0; // ap( 1, 0 ) = 0; ap( 1, 1 ) = 0; ap( 1, 2 ) = 1; // ap( 2, 0 ) = 1; ap( 2, 1 ) = 0; ap( 2, 2 ) = 0; //} Transform viewTrans; viewTrans.rotation.fromEuler( Rot[0] / 180.0 * PI, Rot[1] / 180.0 * PI, Rot[2] / 180.0 * PI ); viewTrans.rotation = viewTrans.rotation * ap; viewTrans.translation = viewTrans.rotation * Pos; if ( view != ViewWalk ) viewTrans.translation[2] -= Dist * 2; scene->transform( viewTrans, time ); // Setup projection mode glProjection(); glLoadIdentity(); // Draw the grid if ( scene->options & Scene::ShowAxes ) { glDisable( GL_ALPHA_TEST ); glDisable( GL_BLEND ); glDisable( GL_LIGHTING ); glDisable( GL_COLOR_MATERIAL ); glEnable( GL_DEPTH_TEST ); glDepthMask( GL_TRUE ); glDepthFunc( GL_LESS ); glDisable( GL_TEXTURE_2D ); glDisable( GL_NORMALIZE ); glLineWidth( 2.0f ); glPushMatrix(); glLoadMatrix( viewTrans ); // TODO: Configurable grid in Settings // 1024 game units, major lines every 128, minor lines every 64 drawGrid( 1024, 128, 2 ); glPopMatrix(); } #ifndef QT_NO_DEBUG // Debug scene bounds glEnable( GL_DEPTH_TEST ); glDepthMask( GL_TRUE ); glDepthFunc( GL_LESS ); glPushMatrix(); glLoadMatrix( viewTrans ); if ( debugMode == DbgBounds ) { BoundSphere bs = scene->bounds(); bs |= BoundSphere( Vector3(), axis ); drawSphere( bs.center, bs.radius ); } glPopMatrix(); #endif GLfloat mat_spec[] = { 0.0f, 0.0f, 0.0f, 1.0f }; if ( scene->options & Scene::DoLighting ) { // Setup light Vector4 lightDir( 0.0, 0.0, 1.0, 0.0 ); if ( !frontalLight ) { float decl = declination / 180.0 * PI; Vector3 v( sin( decl ), 0, cos( decl ) ); Matrix m; m.fromEuler( 0, 0, planarAngle / 180.0 * PI ); v = m * v; lightDir = Vector4( viewTrans.rotation * v, 0.0 ); if ( scene->visMode & Scene::VisLightPos ) { glEnable( GL_BLEND ); glBlendFunc( GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA ); glEnable( GL_DEPTH_TEST ); glDepthMask( GL_TRUE ); glDepthFunc( GL_LESS ); glPushMatrix(); glLoadMatrix( viewTrans ); glLineWidth( 2.0f ); glColor4f( 1.0f, 1.0f, 1.0f, 0.5f ); // Scale the distance a bit float l = axis + 64.0; l = (l < 128) ? axis * 1.5 : l; l = (l > 2048) ? axis * 0.66 : l; l = (l > 1024) ? axis * 0.75 : l; drawDashLine( Vector3( 0, 0, 0 ), v * l, 30 ); drawSphere( v * l, axis / 10 ); glPopMatrix(); glDisable( GL_BLEND ); } } float amb = ambient; if ( (scene->visMode & Scene::VisNormalsOnly) && (scene->options & Scene::DoTexturing) && !(scene->options & Scene::DisableShaders) ) { amb = 0.1f; } GLfloat mat_amb[] = { amb, amb, amb, 1.0f }; GLfloat mat_diff[] = { brightness, brightness, brightness, 1.0f }; glShadeModel( GL_SMOOTH ); glEnable( GL_LIGHTING ); glEnable( GL_LIGHT0 ); glLightfv( GL_LIGHT0, GL_AMBIENT, mat_amb ); glLightfv( GL_LIGHT0, GL_DIFFUSE, mat_diff ); glLightfv( GL_LIGHT0, GL_SPECULAR, mat_diff ); glLightfv( GL_LIGHT0, GL_POSITION, lightDir.data() ); // Necessary? glLightModeli( GL_LIGHT_MODEL_TWO_SIDE, GL_TRUE ); } else { float amb = 0.5f; if ( scene->options & Scene::DisableShaders ) { amb = 0.0f; } GLfloat mat_amb[] = { amb, amb, amb, 1.0f }; GLfloat mat_diff[] = { 1.0f, 1.0f, 1.0f, 1.0f }; glShadeModel( GL_SMOOTH ); glEnable( GL_LIGHTING ); glEnable( GL_LIGHT0 ); glLightfv( GL_LIGHT0, GL_AMBIENT, mat_amb ); glLightfv( GL_LIGHT0, GL_DIFFUSE, mat_diff ); glLightfv( GL_LIGHT0, GL_SPECULAR, mat_spec ); } if ( scene->visMode & Scene::VisSilhouette ) { GLfloat mat_diff[] = { 0.0f, 0.0f, 0.0f, 1.0f }; GLfloat mat_amb[] = { 0.0f, 0.0f, 0.0f, 1.0f }; glShadeModel( GL_FLAT ); glEnable( GL_LIGHTING ); glEnable( GL_LIGHT0 ); glLightModelfv( GL_LIGHT_MODEL_AMBIENT, mat_diff ); glMaterialfv( GL_FRONT_AND_BACK, GL_AMBIENT_AND_DIFFUSE, mat_diff ); glLightfv( GL_LIGHT0, GL_AMBIENT, mat_amb ); glLightfv( GL_LIGHT0, GL_DIFFUSE, mat_diff ); glLightfv( GL_LIGHT0, GL_SPECULAR, mat_spec ); } if ( scene->options & Scene::DoMultisampling ) glEnable( GL_MULTISAMPLE_ARB ); #ifndef QT_NO_DEBUG // Color Key debug if ( debugMode == DbgColorPicker ) { glDisable( GL_MULTISAMPLE ); glDisable( GL_LINE_SMOOTH ); glDisable( GL_TEXTURE_2D ); glDisable( GL_BLEND ); glDisable( GL_DITHER ); glDisable( GL_LIGHTING ); glShadeModel( GL_FLAT ); glDisable( GL_FOG ); glDisable( GL_MULTISAMPLE_ARB ); glEnable( GL_DEPTH_TEST ); glDepthFunc( GL_LEQUAL ); glClear( GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT ); Node::SELECTING = 1; } else { Node::SELECTING = 0; } #endif // Draw the model scene->draw(); if ( scene->options & Scene::ShowAxes ) { // Resize viewport to small corner of screen int axesSize = std::min( width() / 10, 125 ); glViewport( 0, 0, axesSize, axesSize ); // Reset matrices glMatrixMode( GL_PROJECTION ); glLoadIdentity(); // Square frustum auto nr = 1.0; auto fr = 250.0; GLdouble h2 = tan( FOV / 360 * M_PI ) * nr; GLdouble w2 = h2; glFrustum( -w2, +w2, -h2, +h2, nr, fr ); // Reset matrices glMatrixMode( GL_MODELVIEW ); glLoadIdentity(); glPushMatrix(); // Store and reset viewTrans translation auto viewTransOrig = viewTrans.translation; // Zoom out slightly viewTrans.translation = { 0, 0, -150.0 }; // Load modified viewTrans glLoadMatrix( viewTrans ); // Restore original viewTrans translation viewTrans.translation = viewTransOrig; // Find direction of axes auto vtr = viewTrans.rotation; QVector<float> axesDots = { vtr( 2, 0 ), vtr( 2, 1 ), vtr( 2, 2 ) }; drawAxesOverlay( { 0, 0, 0 }, 50.0, sortAxes( axesDots ) ); glPopMatrix(); // Restore viewport size glViewport( 0, 0, width(), height() ); // Restore matrices glProjection(); } // Restore GL state glPopAttrib(); glMatrixMode( GL_MODELVIEW ); glPopMatrix(); glMatrixMode( GL_PROJECTION ); glPopMatrix(); // Check for errors GLenum err; while ( ( err = glGetError() ) != GL_NO_ERROR ) qDebug() << tr( "glview.cpp - GL ERROR (paint): " ) << (const char *)gluErrorString( err ); emit paintUpdate(); // Manually handle the buffer swap swapBuffers(); #ifdef USE_GL_QPAINTER painter.end(); #endif }