Loading...
  OR  Zero-K Name:    Password:   

Post edit history

Qrow Esoterica

To display differences between versions, select one or more edits in the list using checkboxes and click "diff selected"
Post edit history
Date Editor Before After
5/27/2026 6:51:31 AMJPrankQrow before revert after revert
5/27/2026 6:51:16 AMJPrankQrow before revert after revert
5/27/2026 6:45:34 AMJPrankQrow before revert after revert
Before After
1 Calcs ( aka the Code, Math and You: A Beginner’s Guide) 1 Collision Calcs ( aka the Code, Math and You: A Beginner’s Guide)
2 \n 2 \n
3 1. Unit-vs-Unit Collision 3 1. Unit-vs-Unit Collision
4 \n 4 \n
5 Handled by the DoCollisionDamage() function, triggered when weaponDefID == -3 and an attackerID is present. 5 Handled by the DoCollisionDamage() function, triggered when weaponDefID == -3 and an attackerID is present.
6 \n 6 \n
7 Step 1, Speed check: Collision damage only activates if either unit's speed exceeds UNIT_UNIT_SPEED (5.5 elmos/frame). 7 Step 1, Speed check: Collision damage only activates if either unit's speed exceeds UNIT_UNIT_SPEED (5.5 elmos/frame).
8 \n 8 \n
9 Step 2, Relative speed: The relative velocity between the two units is calculated as: 9 Step 2, Relative speed: The relative velocity between the two units is calculated as:
10 \n 10 \n
11 relativeSpeed = sqrt((oVx-myVx)² + (oVy-myVy)² + (oVz-myVz)²) 11 relativeSpeed = sqrt((oVx-myVx)² + (oVy-myVy)² + (oVz-myVz)²)
12 \n 12 \n
13 Step 3, Damage per unit: Each unit's damage is calculated using LocalSpeedToDamage(): 13 Step 3, Damage per unit: Each unit's damage is calculated using LocalSpeedToDamage():
14 \n 14 \n
15 if relativeSpeed > velocityDamageThreshold (3): 15 if relativeSpeed > velocityDamageThreshold (3):
16 damage = (relativeSpeed - 3) × (mass × 0.6) 16 damage = (relativeSpeed - 3) × (mass × 0.6)
17 \n 17 \n
18 Buildings get a ×10 multiplier on their velocityDamageScale since they're treated as far more massive. 18 Buildings get a ×10 multiplier on their velocityDamageScale since they're treated as far more massive.
19 \n 19 \n
20 Step 4, Final damage dealt: The game deals the lesser of the two units' computed damages, multiplied by UNIT_UNIT_DAMAGE_FACTOR (0.8) so the smaller/lighter unit sets the damage ceiling. Both units take this same amount. 20 Step 4, Final damage dealt: The game deals the lesser of the two units' computed damages, multiplied by UNIT_UNIT_DAMAGE_FACTOR (0.8) so the smaller/lighter unit sets the damage ceiling. Both units take this same amount.
21 \n 21 \n
22 Step 5, Multipliers & immunity: The final damage is scaled by each unit's collisionDamageMult (set per-unit by other gadgets). Units can be immune (e.g. during jump/teleport), and allied units are protected from "no-ally-damage" flags. 22 Step 5, Multipliers & immunity: The final damage is scaled by each unit's collisionDamageMult (set per-unit by other gadgets). Units can be immune (e.g. during jump/teleport), and allied units are protected from "no-ally-damage" flags.
23 \n 23 \n
24 Step 6, Velocity correction: After collision, both units' velocities are blended toward a shared momentum-conserving average (a weighted sum based on their masses), simulating an inelastic collision. GitHub 24 Step 6, Velocity correction: After collision, both units' velocities are blended toward a shared momentum-conserving average (a weighted sum based on their masses), simulating an inelastic collision. GitHub
25 \n 25 \n
26 2. Unit-vs-Ground Collision (Fall Damage) 26 2. Unit-vs-Ground Collision (Fall Damage)
27 \n 27 \n
28 Triggered when weaponDefID == -2 with no attacker. This is the classic "fall damage." 28 Triggered when weaponDefID == -2 with no attacker. This is the classic "fall damage."
29 \n 29 \n
30 Step 1, Decompose velocity into normal and tangent: The unit's velocity is split into a component normal to the terrain surface and a tangential component (sliding along it). 30 Step 1, Decompose velocity into normal and tangent: The unit's velocity is split into a component normal to the terrain surface and a tangential component (sliding along it).
31 \n 31 \n
32 Step 2, Bounce physics: The normal component is reflected and scaled by elasticity (default 0.3), and the tangential component is scaled by friction (default 0.8), then an impulse is applied to simulate the bounce. 32 Step 2, Bounce physics: The normal component is reflected and scaled by elasticity (default 0.3), and the tangential component is scaled by friction (default 0.8), then an impulse is applied to simulate the bounce.
33 \n 33 \n
34 Step 3, Damage speed calculation: 34 Step 3, Damage speed calculation:
35 damageSpeed = magnitude of (normal + tangent × TANGENT_DAMAGE) 35 damageSpeed = magnitude of (normal + tangent × TANGENT_DAMAGE)
36 where TANGENT_DAMAGE = 0.5, so sliding impacts count for half. 36 where TANGENT_DAMAGE = 0.5, so sliding impacts count for half.
37 \n 37 \n
38 Step 4, Convert speed to damage (same LocalSpeedToDamage() as above): 38 Step 4, Convert speed to damage (same LocalSpeedToDamage() as above):
39 if damageSpeed > 3: 39 if damageSpeed > 3:
40 damage = (damageSpeed - 3) × (mass × 0.6) 40 damage = (damageSpeed - 3) × (mass × 0.6)
41 \n 41 \n
42 Step 5, Out-of-map bonus damage: If the unit is outside the map boundaries, additional damage is added proportional to how far out of bounds the unit is, scaled by unit.health / 800. 42 Step 5, Out-of-map bonus damage: If the unit is outside the map boundaries, additional damage is added proportional to how far out of bounds the unit is, scaled by unit.health / 800.
43 \n 43 \n
44 Step 6, Multiplier applied: Final damage × collisionDamageMult[unitID] (or 1 if unset). 44 Step 6, Multiplier applied: Final damage × collisionDamageMult[unitID] (or 1 if unset).
45 \n 45 \n
46 3. Unit-vs-Wreck/Feature Collision 46 3. Unit-vs-Wreck/Feature Collision
47 \n 47 \n
48 Triggered when weaponDefID == -3 and 48 Triggered when weaponDefID == -3 and
49 attackerID == nil (no unit attacker — a feature like debris). 49 attackerID == nil (no unit attacker — a feature like debris).
50 \n 50 \n
51 The engine's native damage value is taken and multiplied by DEBRIS_SPRING_DAMAGE_MULTIPLIER = 10 (described in the code as "tweaked arbitrarily"), then scaled by collisionDamageMult. The unit also gets a velocity-scaling impulse of 0.3 (i.e. it loses 70% of its speed). 51 The engine's native damage value is taken and multiplied by DEBRIS_SPRING_DAMAGE_MULTIPLIER = 10 (described in the code as "tweaked arbitrarily"), then scaled by collisionDamageMult. The unit also gets a velocity-scaling impulse of 0.3 (i.e. it loses 70% of its speed).
52 \n 52 \n
53 Note: Feature collisions still use the native engine value as a base, unlike unit-unit and ground collisions which are calculated entirely from scratch. 53 Note: Feature collisions still use the native engine value as a base, unlike unit-unit and ground collisions which are calculated entirely from scratch.
54 \n 54 \n