220 likes | 337 Views
Particle Systems. Asst. Prof. Rujchai Ung-arunyawee COE, KKU. Laws of Motion. Position Velocity Acceleration Mass Force Newton’s Laws. Velocity. Differential. Integral. Code. Position += Velocity*time;. Acceleration. Differential. Integral. Code. Position += Velocity*time +
E N D
Particle Systems Asst. Prof. Rujchai Ung-arunyawee COE, KKU
Laws of Motion • Position • Velocity • Acceleration • Mass • Force • Newton’s Laws
Velocity • Differential • Integral • Code Position += Velocity*time;
Acceleration • Differential • Integral • Code Position += Velocity*time + acceleration*time*time* 0.5; OR Position += Velocity*time;
Force Equation • Code acceleration = inversemass*force;
Integrator for Particle Update public void Integrate(float duration) { // Update linear position position.X += velocity.X * duration; position.Y += velocity.Y * duration; position.Z += velocity.Z * duration; // Update linear velocity Vector3 resultingAcc = acceleration; resultingAcc.X += forceAccum.X * inverseMass; resultingAcc.Y += forceAccum.Y * inverseMass; resultingAcc.Z += forceAccum.Z * inverseMass; velocity.X += resultingAcc.X * duration; velocity.Y += resultingAcc.Y * duration; velocity.Z += resultingAcc.Z * duration; // Impose drag. float scale = (float)Math.Pow(damping, duration); velocity = Vector3.Multiply(velocity, scale); }
Game Update() protected override void Update(GameTime gameTime) { // Allows the game to exit if (GamePad.GetState(PlayerIndex.One).Buttons.Back == ButtonState.Pressed) this.Exit(); // TODO: Add your update logic here KeyboardState kb = Keyboard.GetState(); MouseState mouse = Mouse.GetState(); if (mouse.LeftButton == ButtonState.Pressed) fire(gameTime); float duration = gameTime.ElapsedGameTime.Milliseconds / (1000.0f); ammos.Integrate(duration); base.Update(gameTime); }
Fire() Method private void fire(GameTime gametime) { // Artillery ammos.Mass = 200.0f; // 200.0kg ammos.Velocity = new Vector3(0.0f, 30.0f, 40.0f);// 50m/s ammos.Acceleration = new Vector3(0.0f, -20.0f, 0.0f); ammos.Damping = 0.99f; ammos.Position = new Vector3(0.0f, 1.5f, 0.0f); ammos.clearAccumulator(); }
Draw the particle foreach (ModelMesh mesh in myModel.Meshes) { // Draw the current mesh foreach (BasicEffect eff in mesh.Effects) { eff.World = Matrix.CreateScale(0.03f); eff.World *= Matrix.CreateTranslation(ammos.Position); eff.View = effect.View; eff.Projection = effect.Projection; eff.EnableDefaultLighting(); } mesh.Draw(); }
Camera Settings // Set the Viewing Matrix effect.View = Matrix.CreateLookAt( new Vector3(-25.0f, 8.0f,-5.0f),new Vector3(0.0f, 5.0f, 22.0f), Vector3.Up); // Set the Projection Matrix effect.Projection = Matrix.CreatePerspectiveFieldOfView( MathHelper.ToRadians(60.0f), aspectRatio, 1.0f, 500.0f);
Other Particle Types // Laser //ammos.Mass = 0.1f; // 0.1kg - almost no weight //ammos.Velocity = new Vector3(0.0f, 0.0f, 100.0f);// 100m/s //ammos.Acceleration = new Vector3(0.0f, 0.0f, 0.0f); //No gravity //ammos.Damping = 0.99f; // Pistol //ammos.Mass = 2.0f; // 2.0kg //ammos.Velocity = new Vector3(0.0f, 0.0f, 35.0f);// 35m/s //ammos.Acceleration = new Vector3(0.0f, -1.0f, 0.0f); //ammos.Damping = 0.99f; // Fireball //ammos.Mass = 1.0f; // 1.0kg //ammos.Velocity = new Vector3(0.0f, 0.0f, 10.0f);// 10m/s //ammos.Acceleration = new Vector3(0.0f, 0.6f, 0.0f);// Floats up //ammos.Damping = 0.9f;
Particle Array • Declared as a field of the Game class const int ammoMax = 10; Particle[] ammos; • Created in Initialize() ammos = new Particle[ammoMax];
Timer in XNA MouseState mouse = Mouse.GetState(); m_gameTime = gameTime; if ((mouse.LeftButton == ButtonState.Pressed)&& (m_gameTime.TotalGameTime.TotalMilliseconds - lastTime > 200)) { // Do your mouse state logic here lastTime = m_gameTime.TotalGameTime.TotalMilliseconds; fire(gametime); }
Updating the Particles float duration = gameTime.ElapsedGameTime.Milliseconds / (1000.0f); for (int i = 0; i < ammoMax; i++) { if (ammos[i] != null) { if (ammos[i].Position.Y < 0) ammos[i] = null; else ammos[i].Integrate(duration); } }
Firing the Particles private void fire(GameTime gametime) { for (int i = 0; i < ammoMax; i++) { if (ammos[i] == null) { ammos[i] = new Particle(); // Artillery ammos[i].Mass = 200.0f; // 200.0kg ammos[i].Velocity = new Vector3(0.0f, 30.0f, 40.0f); ammos[i].Acceleration = new Vector3(0.0f, -20.0f, 0.0f); ammos[i].Damping = 0.99f; ammos[i].Position = new Vector3(0.0f, 1.5f, 0.0f); ammos[i].clearAccumulator(); break; } }
Drawing the Particles (1/2) protected override void Draw(GameTime gameTime) { ... ... ... draw_lines(device); for(int i =0 ; i < ammoMax; i++) if(ammos[i] != null) draw_ammo(i); base.Draw(gameTime); }
Drawing the Particles (2/2) private void draw_ammo(int i) { foreach (ModelMesh mesh in myModel.Meshes) { // Draw the current mesh foreach (BasicEffect eff in mesh.Effects) { eff.World = Matrix.CreateScale(0.03f); eff.World *= Matrix.CreateTranslation(ammos[i].Position); eff.View = effect.View; eff.Projection = effect.Projection; eff.EnableDefaultLighting(); } mesh.Draw(); } }