GoSnackbar — the message that places itself
Sits at the bottom (or the top), above the safe area and the keyboard, and leaves on its own. Without it you write the layer, the placement, the timer and the teardown on every screen that has to say "saved".
snack.show_text("Saved", GoTheme.SUCCESS)
# A chance to undo — 0 is the first button, -1 means it timed out
if await snack.post({"text": "Item dropped", "actions": ["Undo"]}) == 0:
restore_item()
Messages queue instead of overwriting each other, and repeats of the same line are merged — a server failing four times a second no longer stacks four minutes of alerts. A snackbar with no button lets input through, so the game underneath keeps running.
GoDialogs. Buttons here must be optional — Undo,
Details, Retry.
GoNotice is the other half of the pair: it never takes input or focus, and the screen that
owns it decides where it goes. It cannot hold a button; this can.
GoSpinner — a wait with no end in sight
Games that talk to a server need this more than anything else on this page: a screen that sits still reads as a crash. One call turns the button you pressed into a spinner in place.
GoSpinner.busy(buy_button, true)
var ok := await server.purchase(item)
GoSpinner.busy(buy_button, false)
The button keeps its size — the label goes transparent rather than away, so the row does not jump — and
it is disabled while it spins. That second part is the point: a purchase must not fire twice while you
await. With reduce_motion on it does not spin; three dots pulse instead.
Progress you can measure is a GoBar. A spinner promises nothing about when it ends.
GoBadge — the unread dot, the NEW tag, the 99+
GoBadge.attach(mail_button, unread_count) # hides itself at zero
GoBadge.attach(shop_button, 0, "NEW")
GoBadge.attach(friend_button, 3, "", true) # a dot — "something is there"
It hangs on the host's top-right corner with anchors, so it follows a host whose size is decided later, and attaching twice returns the same badge. Use a number when the count changes what the player does, a dot when only "there is something" matters.
Its text colour is chosen for contrast against whatever colour the skin painted the badge — never assumed white — and it carries an accessible name, because a coloured dot says nothing to a screen reader.