void Render(ExampleClock& clock) { if(long(clock.Now().Seconds()) % 4 == 0) { status += clock.Interval().Seconds(); } else if(status != double(long(status))) { if(status - double(long(status)) < 0.5) status = double(long(status)); else status = 1.0 + double(long(status)); } gl.Clear().ColorBuffer().DepthBuffer(); point_prog.status = GLfloat(0.5 - 0.5 * CosineWave(status * 0.5)); CamMatrixf camera = CamMatrixf::Orbiting( Vec3f(), 5.5f, FullCircles(clock.Now().Seconds() / 19.0), Degrees(45 + SineWave(clock.Now().Seconds() / 15.0) * 40)); point_prog.camera_matrix.Set(camera); point_prog.model_matrix.Set( ModelMatrixf::RotationX(RightAngles(status))); shape.Draw(); }
// Updates the emitter // Changes its position, emits new particles void Update(ExampleClock& clock) { assert(positions.size() == directions.size()); assert(positions.size() == ages.size()); assert(positions.size() == ids.size()); double time_diff = clock.Interval().Seconds(); double drag = 0.1 * time_diff; if(drag > 1.0) drag = 1.0; // go through the existing particles for(std::size_t i=0, n=positions.size(); i!=n; ++i) { // update the age ages[i] += time_diff / lifetime; // if the particle is "too old" if(ages[i] > 1.0) { // try to spawn a new one in its place SpawnParticle( clock.Now().Seconds(), positions[i], directions[i], ages[i], ids[i] ); } else { // otherwise just update its motion directions[i] *= (1.0 - drag); positions[i] += directions[i] * time_diff; } } Vec3f position; Vec3f direction; float age; int id; // spawn new particles if necessary while(SpawnParticle(clock.Now().Seconds(), position, direction, age, id)) { positions.push_back(position); directions.push_back(direction); ages.push_back(age); ids.push_back(id); } }