From 7d1f0a4b531afaea2bc95aef769c7ecfb655d2f5 Mon Sep 17 00:00:00 2001 From: Laurens Bezemer | DodoTech Date: Wed, 26 Aug 2026 16:18:34 +0200 Subject: [PATCH] Take the frozen bar off the splash, and leave the line that is true MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The indeterminate bar did not move, and it was never going to. Composition is a synchronous block and DodoSshApp posts it to the very dispatcher that would have to animate it: Background priority buys the splash its first paint and nothing after it, because once composition starts the UI thread is inside it until the main window is ready, and a ProgressBar's indeterminate animation is driven by that thread's clock. One frame, then ~2.4 seconds of stillness — the whole of the time the window is on screen. A frozen indeterminate bar does not read as indeterminate. It reads as a determinate bar stuck at zero, which is worse than no bar at all: it says the work has stalled at the moment the application is busiest, which is the one thing a splash must never say. Freeing the UI thread would have been the other fix, and it is a real one — the I/O in Compose has no business on that thread. It is also a rework of startup for the sake of an ornament. There is nothing here that can honestly be measured anyway: a SQLite open, a loopback bind, a TPM probe and an install-layout read report no progress between them. So the bar goes. "Starting…" was already on the card, it is true for as long as the card is up, it needs no clock to stay true, and the window closing is what says it finished. CouldNotStart is one assignment now — it used to have to stop the bar as well, so that nothing went on claiming to work over a process that had died, and there is no longer anything on the card that could. The window keeps its MinHeight, which is what stops two lines of content collapsing it, and the failure path keeps SizeToContent for the same reason it always had it. Co-Authored-By: Claude Opus 5 --- src/DodoSSH.Client.App/Views/SplashCard.axaml | 25 +++++++++++-------- .../Views/SplashCard.axaml.cs | 15 +++++------ 2 files changed, 21 insertions(+), 19 deletions(-) diff --git a/src/DodoSSH.Client.App/Views/SplashCard.axaml b/src/DodoSSH.Client.App/Views/SplashCard.axaml index 803b371..0f3ecb0 100644 --- a/src/DodoSSH.Client.App/Views/SplashCard.axaml +++ b/src/DodoSSH.Client.App/Views/SplashCard.axaml @@ -29,18 +29,23 @@ - diff --git a/src/DodoSSH.Client.App/Views/SplashCard.axaml.cs b/src/DodoSSH.Client.App/Views/SplashCard.axaml.cs index de29d6f..9e39cb6 100644 --- a/src/DodoSSH.Client.App/Views/SplashCard.axaml.cs +++ b/src/DodoSSH.Client.App/Views/SplashCard.axaml.cs @@ -19,14 +19,11 @@ internal sealed partial class SplashCard : UserControl /// Says why nothing is going to happen, and stops pretending otherwise. /// /// - /// The bar stopping is half the message. A composition that threw leaves this window as the only one - /// there is — there is no main window to hand over to — so an indeterminate bar would go on saying - /// "still going" over a process that has stopped, which is the one thing a splash must never do. + /// The line is the whole message now that the progress bar has gone — see the markup for why it went. + /// It used to have to stop the bar as well: a composition that threw leaves this window as the only one + /// there is, with no main window to hand over to, so anything still claiming to be working would be + /// doing it over a process that has stopped. One assignment says it instead, and there is nothing left + /// on this card that could contradict it. /// - internal void CouldNotStart(string why) - { - Line.Text = why; - Bar.IsIndeterminate = false; - Bar.Value = 0; - } + internal void CouldNotStart(string why) => Line.Text = why; }