diff -r d6c2f028d8c9 -r f650994ec543 shader/rectangle_frag.glsl --- a/shader/rectangle_frag.glsl Tue Jun 17 19:00:20 2025 +0200 +++ b/shader/rectangle_frag.glsl Tue Jun 17 20:11:53 2025 +0200 @@ -6,15 +6,91 @@ #ifndef FILL uniform float thickness; #endif +#ifdef ROUNDED_CORNERS +uniform float radius; +#endif void main(void) { -#ifdef FILL +#ifdef ROUNDED_CORNERS + // Calculate distances from each corner + vec2 corner_distances[4]; + corner_distances[0] = uvcoord - vec2(radius, radius); // top-left + corner_distances[1] = uvcoord - vec2(size.x - radius, radius); // top-right + corner_distances[2] = uvcoord - vec2(radius, size.y - radius); // bottom-left + corner_distances[3] = uvcoord - vec2(size.x - radius, size.y - radius); // bottom-right + + // Check if we're in a corner region + bool in_corner_region = false; + int corner_idx = -1; + + for (int i = 0; i < 4; i++) { + vec2 test_point = corner_distances[i]; + vec2 corner_test = vec2(0.0); + + if (i == 0 && test_point.x < 0.0 && test_point.y < 0.0) { // top-left + corner_test = test_point; + corner_idx = i; + in_corner_region = true; + break; + } else if (i == 1 && test_point.x > 0.0 && test_point.y < 0.0) { // top-right + corner_test = test_point; + corner_idx = i; + in_corner_region = true; + break; + } else if (i == 2 && test_point.x < 0.0 && test_point.y > 0.0) { // bottom-left + corner_test = test_point; + corner_idx = i; + in_corner_region = true; + break; + } else if (i == 3 && test_point.x > 0.0 && test_point.y > 0.0) { // bottom-right + corner_test = test_point; + corner_idx = i; + in_corner_region = true; + break; + } + } + + #ifdef FILL + // For filled rectangle with rounded corners + if (in_corner_region) { + float dist = length(corner_distances[corner_idx]); + if (dist > radius) { + discard; // Outside the rounded corner + } + } else if (uvcoord.x < 0.0 || uvcoord.y < 0.0 || uvcoord.x > size.x || uvcoord.y > size.y) { + discard; // Outside the rectangle + } diffuse = color; -#else + #else // no FILL + // For outlined rectangle with rounded corners + if (in_corner_region) { + float dist = length(corner_distances[corner_idx]); + if (dist > radius) { + discard; // Outside the rounded corner + } else if (dist < radius - thickness) { + discard; // Inside the outline + } + diffuse = color; + } else if (any(lessThan(uvcoord, vec2(thickness))) || any(greaterThan(uvcoord, size - thickness))) { + // On a straight edge + if (uvcoord.x >= 0.0 && uvcoord.y >= 0.0 && uvcoord.x <= size.x && uvcoord.y <= size.y) { + diffuse = color; + } else { + discard; + } + } else { + discard; // Inside the outline + } + #endif // FILL +#else // no ROUNDED_CORNERS + #ifdef FILL + diffuse = color; + #else // no FILL if (any(notEqual(1.0-step(thickness, uvcoord)+step(size-thickness, uvcoord), vec2(0.0)))) { diffuse = color; } else { discard; } -#endif + #endif // FILL +#endif // ROUNDED_CORNERS }