# Como mostrar spinner e barra de progresso (Progress)

> Usar Progress nos três modos — ícone girando, barra determinada e indeterminada.

Source: https://crossfly.dev/pt/docs/cookbook/ui/spinner-e-progresso — CrossFly documentation. Full docs as one file: https://crossfly.dev/llms-full.txt

# Como mostrar spinner e barra de progresso (Progress)

**Propósito.** Indicar que algo está em andamento. O `Progress` tem **três modos**,
escolhidos pelo construtor: ícone girando (spinner), barra **determinada** (0–100% com
valor conhecido) e **indeterminada** (loop infinito, quando não se sabe o tempo). Use
determinada quando você tem uma fração conhecida (upload, download); indeterminada/spinner
para "carregando..." sem fração.

## APIs usadas
- `new Progress(Icon icon)` — **Modo spinning**: gira o ícone continuamente.
- `new Progress(float min, float max)` — **Modo barra determinada**: cria a barra com a faixa `[min, max]`; valor inicial = `min`.
- `progress.setValue(float v)` — atualiza o valor (clampeado a `[min, max]`); recomputa a fração preenchida. Fluente.
- `new Progress(ProgressType type)` — **Modo indeterminado**: barra/spinner infinito no estilo dado.
- `ProgressType.MATERIAL`, `ProgressType.FLUTTER`, `ProgressType.IOS`, `ProgressType.STRIPED` — variantes visuais do modo indeterminado (`IOS` é um spinner circular; os demais são barras).
- `progress.pivot(int px, int py)` — (modo spinning) pivô de rotação customizado; `-1,-1` = centro do ícone.

> Comportamento não óbvio (confirmado na fonte): a animação **começa sozinha** quando o
> `Progress` é adicionado a um pai (`onAdd`) e **para** quando é removido (`onRemove`).
> Não há `start()`/`stop()` público — para "esconder" o progresso, remova o componente
> da tela. O campo `mode` é final (definido no construtor, imutável).

## Exemplo completo (copiar, colar e rodar)
```java
package com.exemplo;

import dev.crossfly.ui.*;
import dev.crossfly.ui.layout.*;
import dev.crossfly.ui.graphics.*;

/** Tela principal executável. Aponte o launcher (classname) e rode: gradlew :lwjgl3:run */
public class MainWindow extends Window
{
   @Override
   public void onShow() throws Exception
   {
      super.onShow();
      setLayout(new VerticalLayout());

      // 1) Spinner (ícone girando) — "carregando" genérico
      Progress spinner = new Progress(new MaterialIcon("autorenew", 48));
      add(spinner);

      // 2) Barra determinada (0 a 100) — atualize conforme o progresso real
      Progress barra = new Progress(0f, 100f);
      add(barra);
      // ...conforme o download avança:
      barra.setValue(75f);   // 75% preenchido

      // 3) Indeterminado (loop infinito) — sem fração conhecida
      Progress infinito = new Progress(ProgressType.MATERIAL);
      add(infinito);

      // Variante spinner circular estilo iOS:
      Progress ios = new Progress(ProgressType.IOS);
      add(ios);
   }
}
```

> O trecho abaixo mostra **só o miolo**. Para rodar, coloque-o no esqueleto `MainWindow` acima.

## Trecho mínimo
```java
// 1) Spinner (ícone girando) — "carregando" genérico
Progress spinner = new Progress(new MaterialIcon("autorenew", 48));
add(spinner);

// 2) Barra determinada (0 a 100) — atualize conforme o progresso real
Progress barra = new Progress(0f, 100f);
add(barra);
// ...conforme o download avança:
barra.setValue(75f);   // 75% preenchido

// 3) Indeterminado (loop infinito) — sem fração conhecida
Progress infinito = new Progress(ProgressType.MATERIAL);
add(infinito);

// Variante spinner circular estilo iOS:
Progress ios = new Progress(ProgressType.IOS);
add(ios);
```

> **Nota de verificação (código 2026).** Confirmado na fonte: os três construtores
> `Progress(Icon)`, `Progress(float min, float max)` e `Progress(ProgressType)`, e o
> `enum Progress.Mode { SPINNING_ICON, DETERMINATE_BAR, INDETERMINATE }` derivado deles.
> `setValue` clampa a `[min, max]` e atualiza `progress` (fração 0..1). O `ProgressType`
> fica em `UIConstants` com os valores `IOS, FLUTTER, MATERIAL, STRIPED`. Em ambiente de
> teste (`DeviceConfig.isTesting`) a animação não inicia automaticamente.

## Aprofunde-se
- Página do widget: [Progress](/docs/ui/widgets/progress) · Fonte canônica: Capítulo 14
- Feedback efêmero (mensagens rápidas): [mostrar-um-hint.md](/docs/cookbook/ui/mostrar-um-hint)
