diff --git a/SukiUI.Demo/Features/ControlsLibrary/ProgressView.axaml b/SukiUI.Demo/Features/ControlsLibrary/ProgressView.axaml index f9f4605c2..f1a8b5856 100644 --- a/SukiUI.Demo/Features/ControlsLibrary/ProgressView.axaml +++ b/SukiUI.Demo/Features/ControlsLibrary/ProgressView.axaml @@ -136,8 +136,11 @@ + + + - + diff --git a/SukiUI/Content/Shaders/Loading/pellets.sksl b/SukiUI/Content/Shaders/Loading/pellets.sksl index f1c01e6d2..533839337 100644 --- a/SukiUI/Content/Shaders/Loading/pellets.sksl +++ b/SukiUI/Content/Shaders/Loading/pellets.sksl @@ -9,8 +9,8 @@ float A(vec2 p, float a) { a *= 3.14159;\ vec2 s = vec2(sin(a), cos(a)); p.x = abs(p.x); - return ((s.y * p.x > s.x * p.y) ? length(p - s * .7) : - abs(length(p) - .7)) - .13; + return ((s.y * p.x > s.x * p.y) ? length(p - s * .6) : + abs(length(p) - .6)) - .07; } mat2 D(float a) { @@ -21,10 +21,13 @@ mat2 D(float a) { vec4 main(vec2 fragCoord) { vec2 r = iResolution.xy, p = (2. * fragCoord - r) / r.y; - float T = iTime * 1., - d = A(p * D(1. - .125 * floor(T)), .4375), // distance to longest arc - i; - for (i = 0.; i < 1.; i += .5) - d = min(A(p * D(mix(-.5, .625, fract(T / 2. + i)) - .125 * T), .0625), d); // distance to shorter arcs ("pellets") - return vec4(smoothstep(.01, .0, d)) * vec4(iForeground, iAlpha); + float T = iTime * 1.0; + float d = A(p * D(1. - 0.125 * floor(T)), 0.4375); // distance to longest arc + float i; + for (i = 0.0; i < 1.0; i += 0.5) + d = min(A(p * D(mix(-0.5, 0.625, fract(T / 2.0 + i)) - 0.125 * T), 0.0625), d); // distance to shorter arcs ("pellets") + + // Ajustement de la largeur de la ligne + float widthReduction = 0.02; // RĂ©duit la largeur de la ligne + return vec4(smoothstep(widthReduction, 0.0, d)) * vec4(iForeground, iAlpha); } \ No newline at end of file diff --git a/SukiUI/Content/Shaders/Loading/simple.sksl b/SukiUI/Content/Shaders/Loading/simple.sksl new file mode 100644 index 000000000..be1eec6bd --- /dev/null +++ b/SukiUI/Content/Shaders/Loading/simple.sksl @@ -0,0 +1,72 @@ +uniform vec3 iForeground; + +const float pi = 3.14159265358979323846; + +float smoothstep(float a, float b, float x) { + float t = clamp((x - a) / (b - a), 0.0, 1.0); + return t * t * (3.0 - 2.0 * t); +} + +float atan(float y, float x) { + // Constants for the series expansion + const float pi_2 = pi / 2.0; + + // Handle special cases + if (x == 0.0) { + if (y > 0.0) return pi_2; + if (y < 0.0) return -pi_2; + return 0.0; // Undefined, but return 0 + } + + float abs_y = abs(y) + 1e-10; // Avoid division by zero + + // Compute the arctangent of y/x + float angle; + if (abs(x) > abs_y) { + float z = y / x; + float zz = z * z; + angle = z * (0.999866 + zz * (-0.3302995 + zz * (0.180141 + zz * (-0.085133 + zz * 0.020835)))); + if (x < 0.0) { + if (y < 0.0) { + angle -= pi; + } else { + angle += pi; + } + } + } else { + float z = x / y; + float zz = z * z; + angle = pi_2 - z * (0.999866 + zz * (-0.3302995 + zz * (0.180141 + zz * (-0.085133 + zz * 0.020835)))); + if (y < 0.0) { + angle -= pi; + } + } + + return angle; +} + +vec4 main(vec2 fragCoord) { + float radius = 0.3; + float lineWidth = 1.0; // en pixels + float glowSize = 1.0; // en pixels + + float pixelSize = 1.0 / min(iResolution.x, iResolution.y); + lineWidth *= pixelSize; + glowSize *= pixelSize; + glowSize *= 2.0; + + vec2 uv = (fragCoord.xy / iResolution.xy) - 0.5; + uv.x *= iResolution.x / iResolution.y; + + float len = length(uv); + float angle = atan(uv.y, uv.x); + + // Garde le fallOff pour l'animation mais n'affecte pas la largeur de la ligne + float fallOff = fract(-0.5 * (angle / pi) - iTime * 0.5); + + // Garde une largeur de ligne constante + float color = smoothstep(pixelSize, 0.0, abs(radius - len) - lineWidth) * fallOff; + color += smoothstep(glowSize, 0.0, abs(radius - len) - lineWidth) * fallOff * 0.5; + + return vec4(color) * vec4(iForeground, iAlpha); +} diff --git a/SukiUI/Controls/Loading.cs b/SukiUI/Controls/Loading.cs index 4362ae779..089fc2d07 100644 --- a/SukiUI/Controls/Loading.cs +++ b/SukiUI/Controls/Loading.cs @@ -13,7 +13,7 @@ namespace SukiUI.Controls public class Loading : Control { public static readonly StyledProperty LoadingStyleProperty = - AvaloniaProperty.Register(nameof(LoadingStyle), defaultValue: LoadingStyle.Glow); + AvaloniaProperty.Register(nameof(LoadingStyle), defaultValue: LoadingStyle.Simple); public LoadingStyle LoadingStyle { @@ -33,6 +33,7 @@ public IBrush? Foreground private static readonly IReadOnlyDictionary Effects = new Dictionary() { + { LoadingStyle.Simple, SukiEffect.FromEmbeddedResource("simple") }, { LoadingStyle.Glow, SukiEffect.FromEmbeddedResource("glow") }, { LoadingStyle.Pellets, SukiEffect.FromEmbeddedResource("pellets") }, }; @@ -106,6 +107,7 @@ protected override void RenderSoftware(SKCanvas canvas, SKRect rect) public enum LoadingStyle { + Simple, Glow, Pellets } diff --git a/SukiUI/SukiUI.csproj b/SukiUI/SukiUI.csproj index 48e620dd2..4a15849ec 100644 --- a/SukiUI/SukiUI.csproj +++ b/SukiUI/SukiUI.csproj @@ -101,6 +101,8 @@ + + diff --git a/SukiUI/Theme/Button.axaml b/SukiUI/Theme/Button.axaml index 4dbba241e..6ab22bb35 100644 --- a/SukiUI/Theme/Button.axaml +++ b/SukiUI/Theme/Button.axaml @@ -30,14 +30,14 @@ - + - +