struct FragUniform { type_: u32, padding: vec3, blend_color: vec4, } @binding(1) @group(0) var ubos: array; @binding(2) @group(0) var mySampler: sampler; @binding(3) @group(0) var myTexture: texture_2d; @stage(fragment) fn main( @location(0) uv: vec2, @interpolate(linear) @location(1) bary: vec2, @interpolate(flat) @location(2) triangle_index: u32, ) -> @location(0) vec4 { // Example 1: Visualize barycentric coordinates: // return vec4(bary.x, bary.y, 0.0, 1.0); // return vec4(0.0, bary.x, 0.0, 1.0); // [1.0 (bottom-left vertex), 0.0 (bottom-right vertex)] // return vec4(0.0, bary.y, 0.0, 1.0); // [1.0 (bottom-left vertex), 1.0 (top-right face)] // Example 2: Render gkurve primitives // Concave (inverted quadratic bezier curve) // inversion = -1.0; // Convex (inverted quadratic bezier curve) // inversion = 1.0; let inversion = select( 1.0, -1.0, ubos[triangle_index].type_ == 1u); // Texture uvs // (These two could be cut with vec2(0.0,1.0) + uv * vec2(1.0,-1.0)) var correct_uv = uv; correct_uv.y = 1.0 - correct_uv.y; var color = textureSample(myTexture, mySampler, correct_uv) * ubos[triangle_index].blend_color; // Gradients let px = dpdx(bary.xy); let py = dpdy(bary.xy); // Chain rule let fx = (2.0 * bary.x) * px.x - px.y; let fy = (2.0 * bary.x) * py.x - py.y; // Signed distance var dist = (bary.x * bary.x - bary.y) / sqrt(fx * fx + fy * fy); dist *= inversion; dist /= 300.0; // Border rendering. let border_color = vec4(1.0, 0.0, 0.0, 1.0); let border_width = 3.0; let border_smoothing = 1.0; // if (dist > 0.0 && dist <= 0.1) { return vec4(1.0, 0.0, 0.0, 1.0); } // if (dist > 0.2 && dist <= 0.3) { return vec4(0.0, 0.0, 1.0, 1.0); } // // Wireframe rendering. // let right_face_dist = bary.y; // let bottom_face_dist = bary.x-bary.y; // let left_face_dist = 1.0 - ((bottom_face_dist*2.0) + bary.y); // let normal_bary = vec3(right_face_dist, bottom_face_dist, left_face_dist); // let fwd = fwidth(normal_bary); // let w = smoothstep(border_width * fwd, (border_width + border_smoothing) * fwd, normal_bary); // let width = 1.0 - min(min(w.x, w.y), w.z); // let epsilon = 0.001; // if (right_face_dist >= -epsilon && right_face_dist <= width // || left_face_dist >= -epsilon && left_face_dist <= width // || bottom_face_dist >= -epsilon && bottom_face_dist <= width) { // color = mix(color, border_color, width); // if (dist < 0.0 && ubos[triangle_index].type_ != 2u) { // return vec4(border_color.rgb, width); // } // } return color * f32(dist >= 0.0 || ubos[triangle_index].type_ == 2u); }