# Plushie Examples

Example apps demonstrating Plushie's features from minimal to complex.
Run any example with:

```sh
mix plushie.gui <Name>
```

With hot reload enabled (`--watch` flag or `config :plushie,
code_reloader: true`), you can edit an example while the GUI is
running and the window updates instantly.

## DSL styles

The examples deliberately use different DSL styles so you can compare:

- **Keyword opts on the call line** - `column(spacing: 8, padding: 16, children: [...])`
  Used by: Counter, Clock, Shortcuts, AsyncFetch, and most widget calls.
- **Container inline props** - options declared inside the do-block, mixed with children.
  Used by: Todo, Notes, Catalog (Layout tab), RatePlushie.
- **Nested struct do-blocks** - `border do width 1; rounded 8 end` for complex options.
  Used by: RatePlushie, ColorPicker app.
- **Canvas widget modules** - reusable canvas components in `widgets/`.
  Used by: ColorPicker (ColorPickerWidget), RatePlushie (StarRating, ThemeToggle).

All styles are interchangeable. Pick whichever reads best for your use case.

## Examples

### Counter

**File:** `counter.ex`

Minimal Elm-architecture example. Two buttons increment and decrement a count.
Start here to understand `init/1`, `update/2`, and `view/1`.

```sh
mix plushie.gui Counter
```

### Todo

**File:** `todo.ex`

Todo list with text input, checkboxes, filtering (all/active/completed), and
delete. Demonstrates `text_input` with `on_submit`, `checkbox` with dynamic
IDs, `scrollable` layout, and pattern matching on parameterized event IDs
like `"todo:#{id}"`.

```sh
mix plushie.gui Todo
```

### Notes

**File:** `notes.ex`

Notes app combining all five state helpers: `Plushie.State` (change tracking),
`Plushie.Undo` (undo/redo for title and body editing), `Plushie.Selection`
(multi-select in list view), `Plushie.Route` (stack-based `/list` and `/edit`
navigation), and `Plushie.Data` (search/query across note fields). Shows how
to compose multiple state helpers in a single model.

```sh
mix plushie.gui Notes
```

### Clock

**File:** `clock.ex`

Displays the current UTC time, updated every second. Demonstrates
`Plushie.Subscription.every/2` for timer-based subscriptions. The `subscribe/1`
callback returns a timer that delivers `{:tick, timestamp}` events.

```sh
mix plushie.gui Clock
```

### Shortcuts

**File:** `shortcuts.ex`

Logs keyboard events to a scrollable list. Demonstrates
`Plushie.Subscription.on_key_press/0` for global keyboard handling. Shows
modifier key detection (Ctrl, Alt, Shift, Super) and the `Plushie.Event.KeyEvent`
struct.

```sh
mix plushie.gui Shortcuts
```

### AsyncFetch

**File:** `async_fetch.ex`

Button that triggers simulated background work. Demonstrates
`Plushie.Command.task/2` for running expensive operations off the main update
loop. Shows the `{model, command}` return form from `update/2` and how async
results are delivered back as events.

```sh
mix plushie.gui AsyncFetch
```

### ColorPicker

**Files:** `color_picker.ex`, `widgets/color_picker.ex`

HSV color picker using a custom canvas widget. A hue ring surrounds a
saturation/value square with drag interaction. The canvas drawing is
extracted into a reusable widget module (`widgets/color_picker.ex`), showing the
widget composition pattern. Demonstrates canvas layers with the do-block
DSL, path commands, linear gradients with alpha, layer caching, and
coordinate-based canvas events (press/move/release for continuous drag).

```sh
mix plushie.gui ColorPicker
```

### Gallery

**File:** `gallery.ex`

Interactive widget gallery demonstrating common widget types: buttons
(default, primary, danger, text styles), text input (with on_submit),
checkbox, toggler, slider, pick list, radio buttons, progress bar, and
styled text. A good starting point for exploring what widgets are
available and what events they produce.

```sh
mix plushie.gui Gallery
```

### Catalog

**File:** `catalog.ex`

Comprehensive widget catalog exercising every widget type across four
tabbed sections:

- **Layout:** column, row, container, scrollable, stack, grid, pin, float,
  responsive, keyed_column, themer, space
- **Input:** button, text_input, checkbox, toggler, radio, slider,
  vertical_slider, pick_list, combo_box, text_editor
- **Display:** text, rule, progress_bar, tooltip, image, svg, markdown,
  rich_text, canvas
- **Composite:** pointer_area, sensor, pane_grid, table, simulated tabs,
  modal, collapsible panel

Use this as a reference for widget props and event patterns.

```sh
mix plushie.gui Catalog
```

### RatePlushie

**Files:** `rate_plushie.ex`, `widgets/star_rating.ex`, `widgets/theme_toggle.ex`

App rating page with custom canvas-drawn widgets composed into a styled UI.
Features a 5-star rating built from path-drawn star geometry and an animated
emoji theme toggle: a smiley that slides, rotates upside down, and becomes
a smiling imp when "Dark humor" is enabled. The entire page theme flips at
the animation midpoint.

Demonstrates: custom canvas widgets as reusable modules, the interactive
shape directive, canvas transforms for rotation, timer-based animation via
subscriptions, container inline props with nested do-blocks (border, padding),
theme-aware rendering, keyboard interaction (arrow keys adjust rating).

```sh
mix plushie.gui RatePlushie
```

## Multi-file demos

The [plushie-demos](https://github.com/plushie-ui/plushie-demos/tree/main/elixir)
repo has larger self-contained projects with their own mix.exs, tests,
and build configuration:

- [**gauge-demo**](https://github.com/plushie-ui/plushie-demos/tree/main/elixir/gauge-demo)
  - native Rust widget with commands, widget events, and
  optimistic updates (Tier C)
- [**sparkline-dashboard**](https://github.com/plushie-ui/plushie-demos/tree/main/elixir/sparkline-dashboard)
  - render-only Rust canvas widget with timer subscriptions and
  multiple widget instances (Tier A)
- [**notes**](https://github.com/plushie-ui/plushie-demos/tree/main/elixir/notes)
  - pure Elixir widgets + state helpers (Route, Selection, Undo, Data)
  with keyboard shortcuts; no Rust required
- [**collab**](https://github.com/plushie-ui/plushie-demos/tree/main/elixir/collab)
  - collaborative scratchpad over native, WebSocket, and SSH transports
