- Shipped
- September 16, 2026 at 4:59 PM UTC
- Author
- Kamo
- Commit
- 59a13aa
With one send in progress, the In-Progress tab was a single thin row in a pane with room for far more, at the moment the widget matters most. When every campaign on a tab is sending or paused, and the panel gives each at least its minimum height, each now gets a card: - how far through the list it is, in a large number rounded down, so it never says 100% with anything left; - its lane at 10px, the head and the sheen visible; - pace and time left, and "N of total"; - delivered, opened, clicked and bounced, as a funnel beside the pace chart on a card with height to spare (true bar lengths and rates), or as a row of figures on a shorter or narrower one; - its pace over the last 5 minutes, a bar per 15 seconds on the clock's own boundaries. The bar still filling is lit, and time before the pane saw the send is a stub, not a zero. The card has the row's link and pause/resume (both now shared, from CampaignRow). It holds through the finish it celebrates. Two sends sit side by side in a wide pane. The choice reads only the panel's size, which nothing inside it can change, so it cannot flicker. A card that overflows anyway is remembered for that panel size, which then shows rows. The layouts inside the card are container queries on the card's own size. Model: paceBuckets spreads what moved between two frames over the time between them. pushSample takes a window, and the hook keeps five minutes per live send, through a pause and a finish. Checked headless on a 10x clock with a varying pace, in regular, wide, tall, 460 and 668x420 panes, and with two sends in the wide and tall panes: cards fit with no overflow, and the pace bars follow the frames, including a quiet stretch. Nothing moves under reduced motion.