Lot of bugfixes

* Adding clipper to generate the terrain's negative powder-contour offset.
* Fixing RDB issues (fracture, active trigger, performances)
* Fixing blood emission
* Fixing the freezing formula on liquids
* Fixing Steve spawning due to a missed test.
* Reaction table properly build
This commit is contained in:
Gaël committed 2026-10-21 20:46:13 +02:00
1 parent a34f42d53e
commit 00a9c1c26c
48 files changed
+5799 -435

No files matched your search

+27 -4
View File
@@ -29,6 +29,7 @@ layout(std430, set = 0, binding = 34) readonly buffer FxTex { uint fxtex[]; };
#include "fx_host.glsl"
#include "fx_state.glsl"
#include "hit_liquid.glsl"
// rigid bodies (read only): projectiles stop at them
layout(std430, set = 0, binding = 30) readonly buffer RShapes { uint rsh[]; };
struct RBody { vec4 p; vec4 v; ivec4 i; vec4 q; vec4 l; vec4 n; vec4 m; ivec4 jn; vec4 ja0; vec4 ja1; vec4 ja2; vec4 ja3; };
@@ -103,10 +104,30 @@ void note_block(int victim, float raw, float dealt) {
// A damage event on a body with a liquid inventory: the corpse part emits (entities.comp).
void body_damage(int slot, vec2 hit, float dmg) {
if (slot < 0 || ents[slot].ex7.y <= 0.0) return;
atomicAdd(ents[slot].ex8.z, max(1, int(dmg * 1000.0)));
const vec2 r = hit - ents[slot].a.xy; const float ca = cos(ents[slot].a.z), sa = sin(ents[slot].a.z);
const vec2 rel = vec2(ca * r.x + sa * r.y, -sa * r.x + ca * r.y); // in the body's frame (entities.comp turns the leak back with the rotation)
atomicExchange(ents[slot].ex8.x, int(rel.x * 1000.0)); atomicExchange(ents[slot].ex8.y, int(rel.y * 1000.0));
const HitLiquidPolicy policy = bloodPolicy[slot];
if ((policy.state.x & 1u) == 0u || policy.inventory.x <= 0.0 || dmg >= ents[slot].hp.x || dmg <= policy.inventory.y) return;
const uint serial = uint(atomicAdd(ents[slot].ex8.z, 1));
const uint seed = hash3(uint(slot), uint(pc.frame), serial + floatBitsToUint(hit.x));
const float probability = float(hash3(seed, 7u, 54u) & 32767u) / 32767.0;
if (probability >= policy.inventory.x || (policy.state.x & 16u) == 0u) return;
vec2 rel = hit - ents[slot].a.xy;
if (policy.inventory.z != 0.0) rel.x /= policy.inventory.z;
if (policy.inventory.w != 0.0) rel.y /= policy.inventory.w;
const float ca = cos(ents[slot].a.z), sa = sin(ents[slot].a.z);
rel = vec2(ca * rel.x + sa * rel.y, -sa * rel.x + ca * rel.y);
if ((policy.state.x & 4u) != 0u) rel = clamp(rel, policy.bounds.xz, policy.bounds.yw);
else if (dot(rel, rel) > 65536.0) rel = vec2(0.0);
const float dl = length(rel);
const vec2 direction = dl > 0.0 ? rel / dl : vec2(0.0);
float u[7];
for (int k = 0; k < 7; ++k) u[k] = float(hash3(seed, uint(k), 54u) & 32767u) / 32767.0;
const float speed = 100.0 * mix(policy.pressure.x, policy.pressure.y, u[2]);
const vec2 v = direction * (vec2(0.85) + 0.29999995 * vec2(u[0], u[1])) * speed;
ents[slot].ex = vec4(v.x * (0.6 + 0.39999998 * u[3]), v.x * (1.0 + 0.39999998 * u[4]),
v.y * (0.6 + 0.39999998 * u[5]), v.y * (1.0 + 0.39999998 * u[6]));
ents[slot].ex2.y = 2.0; // Keep the emitter's next scheduled frame.
atomicExchange(ents[slot].ex8.x, int(rel.x * 1000.0));
atomicExchange(ents[slot].ex8.y, int(rel.y * 1000.0));
}
// The damage multiplier the perks give a shooter; applied ONCE when the shot is made (Message_Shot, 00b06870: projectile damage, and the explosion damage unless not_scaled_by_gamefx)
@@ -206,3 +227,5 @@ float hit_damage(int k, float proj, int tb, vec4 f) {
+ c1.x * v.ex12.z + c1.y * v.ex12.y + c1.z * v.ex13.z + c1.w * v.ex13.w
+ c2.x * v.ex13.x + c2.y * v.ex14.y + c2.z * v.ex14.z + c2.w * v.ex9.y;
}
#include "hit_liquid_channels.glsl"