mirror of
https://github.com/storytold/effectcraft.git
synced 2026-10-24 10:09:32 -06:00
Keep CC Simple Wire Removal between points A and B (#1724)
This commit is contained in:
@@ -363,7 +363,9 @@ fn wire_removal(ctx: &EffectCtx, mut b: Buf) -> Buf {
|
||||
let (qx, qy) = (x as f64 + 0.5 - ax, y as f64 + 0.5 - ay);
|
||||
let d = qx * nx + qy * ny;
|
||||
let ad = d.abs();
|
||||
if ad > half + soft_w {
|
||||
// The wire is the segment A to B, not an endless line.
|
||||
let along = qx * tx + qy * ty;
|
||||
if !(0.0..=len).contains(&along) || ad > half + soft_w {
|
||||
continue;
|
||||
}
|
||||
// Positions just outside the wire on both sides.
|
||||
@@ -580,6 +582,24 @@ mod tests {
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn wire_removal_stays_between_a_and_b() {
|
||||
let mut img = Image::filled(20, 20, [0.5, 0.5, 0.5, 1.0]);
|
||||
for y in 0..20 {
|
||||
img.set(10, y, [0.0, 0.0, 0.0, 1.0]);
|
||||
}
|
||||
let out = run_fx(
|
||||
"ec.key.ccsimplewireremoval",
|
||||
&[("pointA", Value::Vec2([10.5, 5.0])), ("pointB", Value::Vec2([10.5, 15.0])), ("removalStyle", Value::Enum(0)), ("thickness", num(3.0))],
|
||||
img.clone(),
|
||||
0.0,
|
||||
EffectEnv::default(),
|
||||
);
|
||||
assert!((out.img.get(10, 10)[0] - 0.5).abs() < 0.05, "inside the segment");
|
||||
assert_eq!(out.img.get(10, 2), img.get(10, 2), "before A");
|
||||
assert_eq!(out.img.get(10, 18), img.get(10, 18), "after B");
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn wire_removal_frame_offset_uses_neighbour_frame() {
|
||||
use crate::{EffectHost, LayerPixels};
|
||||
|
||||
@@ -493,7 +493,7 @@ fn wire_removal(e: &mut Enc, ctx: &EffectCtx, b: GBuf) -> Option<GBuf> {
|
||||
let mut p = Params::default();
|
||||
p.u[0][0] = ctx.params.e("removalStyle");
|
||||
p.f[0] = [a.0 as f32, a.1 as f32, -ty as f32, tx as f32];
|
||||
p.f[1] = [half as f32, (half * slope as f64) as f32, mirror, 0.0];
|
||||
p.f[1] = [half as f32, (half * slope as f64) as f32, mirror, len as f32];
|
||||
run(e, "fp2_wire", &p, b, None, None)
|
||||
}
|
||||
|
||||
|
||||
@@ -828,7 +828,7 @@ fn fp2_io_final(@builtin(global_invocation_id) gid: vec3<u32>) {
|
||||
}
|
||||
|
||||
// ---------------------------------------------------------------- CC Simple Wire Removal (keying2::wire_removal)
|
||||
// u[0].x = style; f[0] = (ax, ay, nx, ny); f[1] = (hw thickness, soft width, mirror).
|
||||
// u[0].x = style; f[0] = (ax, ay, nx, ny); f[1] = (hw thickness, soft width, mirror, segment length).
|
||||
|
||||
fn fp2_wire_pos(base: vec2<f32>, nrm: vec2<f32>, s: f32) -> vec4<f32> {
|
||||
return sample_bilinear_clamped(src, base.x + nrm.x * s, base.y + nrm.y * s);
|
||||
@@ -851,7 +851,9 @@ fn fp2_wire(@builtin(global_invocation_id) gid: vec3<u32>) {
|
||||
let q = vec2<f32>(fx - a.x, fy - a.y);
|
||||
let d = q.x * nrm.x + q.y * nrm.y;
|
||||
let ad = abs(d);
|
||||
if (ad > hw + soft_w) {
|
||||
// The wire is the segment A to B: the tangent is the normal turned back by 90 degrees.
|
||||
let along = q.x * nrm.y - q.y * nrm.x;
|
||||
if (along < 0.0 || along > P.f[1].w || ad > hw + soft_w) {
|
||||
textureStore(out, p, px);
|
||||
return;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user