/// <summary> /// Inherited from Controller /// Depending on the TimingMode perform timing logic and call ApplyForce() /// </summary> /// <param name="dt"></param> public override void Update(float dt) { switch (TimingMode) { case TimingModes.Switched: { if (Enabled) { ApplyForce(dt, Strength); } break; } case TimingModes.Triggered: { if (Enabled && Triggered) { if (ImpulseTime < ImpulseLength) { ApplyForce(dt, Strength); ImpulseTime += dt; } else { Triggered = false; } } break; } case TimingModes.Curve: { if (Enabled && Triggered) { if (ImpulseTime < ImpulseLength) { ApplyForce(dt, Strength * StrengthCurve.Evaluate(ImpulseTime)); ImpulseTime += dt; } else { Triggered = false; } } break; } default: break; } }
/// <summary> /// Calculate the Decay for a given body. Meant to ease force /// development and stick to the DRY principle and provide unified and /// predictable decay math. /// </summary> /// <param name="body">The body to calculate decay for</param> /// <returns>A multiplier to multiply the force with to add decay /// support in inheriting classes</returns> protected float GetDecayMultiplier(Body body) { //TODO: Consider ForceType in distance calculation! float distance = (body.Position - Position).Length(); switch (DecayMode) { case DecayModes.None: { return(1.0f); } case DecayModes.Step: { if (distance < DecayEnd) { return(1.0f); } else { return(0.0f); } } case DecayModes.Linear: { if (distance < DecayStart) { return(1.0f); } if (distance > DecayEnd) { return(0.0f); } return(DecayEnd - DecayStart / distance - DecayStart); } case DecayModes.InverseSquare: { if (distance < DecayStart) { return(1.0f); } else { return(1.0f / ((distance - DecayStart) * (distance - DecayStart))); } } case DecayModes.Curve: { if (distance < DecayStart) { return(1.0f); } else { return(DecayCurve.Evaluate(distance - DecayStart)); } } default: return(1.0f); } }