# CLAUDE.md

This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.

## Commands

```bash
# Build the entire workspace
cargo build

# Run a specific example (all live in lib/ruin_app/example/)
cargo run --example 00_bootstrap_and_counter -p ruin_app
cargo run --example 01_async_data_and_effects -p ruin_app
cargo run --example 03_fine_grained_list -p ruin_app

# Run tests
cargo test

# Run tests for a specific crate
cargo test -p ruin_reactivity
```

## Architecture

RUIN is a layered, single-threaded reactive UI framework targeting Linux/Wayland. The layers build on each other strictly from bottom to top:

### Layer Stack

**`ruin-runtime`** (`lib/runtime/`) — Linux x86_64 async runtime. io_uring-backed I/O, single-threaded event loop with JavaScript-style microtask/macrotask scheduling. Entry points are `#[ruin_runtime::async_main]` and `#[ruin_runtime::main]` macros. Provides `fs::*`, `net::*`, `time::*`, `channel::*` (mpsc, oneshot).

**`ruin_reactivity`** (`lib/reactivity/`) — Fine-grained reactive graph. Key primitives: `Cell` (root signal), `Thunk`/`Memo` (derived values), `Effect` (side-effects), `Event` (subscriptions). The reactor is single-threaded and schedules deferred jobs via the runtime's microtask queue. No async inside the reactive graph — async work feeds results in via state updates at the edges.

**`ruin_ui`** (`lib/ui/`) — Platform/renderer-agnostic UI substrate. Intentionally uses explicit Rust construction (no proc-macros at this layer). Key modules: `layout.rs` (flexbox-style layout engine), `text.rs` (cosmic-text integration), `scene.rs` (display list/scene graph), `interaction.rs` (pointer/keyboard routing), `platform.rs` (platform abstraction traits), `tree.rs` (element tree and styling).

**`ruin_ui_platform_wayland`** (`lib/ui_platform_wayland/`) — Wayland backend. Entry point: `start_wayland_ui()`. Handles window creation, input events, clipboard via wayland-client + wgpu renderer.

**`ruin_ui_renderer_wgpu`** (`lib/ui_renderer_wgpu/`) — GPU rendering via wgpu. Text rasterization with cosmic-text.

**`ruin_app`** (`lib/ruin_app/`) — High-level app/runtime glue. This is the crate most application code targets. Exports `App`, `Window`, `Mountable`, and the proc-macros `#[component]`, `view!`, `#[context_provider]`. **Intentionally low-level** — it is the expansion target for proc-macros, not the final ergonomic API.

**`ruin_app_proc_macros`** (`lib/ruin_app_proc_macros/`) — Procedural macros: `#[component]` wraps component functions, `view!` is the DSL for UI tree construction, `#[context_provider]` injects context values.

### Application Model

A typical app entry point:

```rust
#[ruin_runtime::async_main]
async fn main() -> ruin_app::Result<()> {
    App::new()
        .window(Window::new().title("My App").app_id("dev.ruin.myapp").size(960.0, 640.0))
        .mount(view! { MyRootComponent() {} })
        .run()
        .await
}
```

Components use `#[component]` and return `impl IntoView`. Reactive state uses `use_signal`, `use_memo`, `use_effect`. Layout uses `view!` with primitives like `column`, `row`, `block`, `text`, `button`.

### The `aspirational_examples/` Directory

These files (`00_` through `07_`) define the **desired future API** — a cleaner `ruin::prelude::*` surface with shorter syntax like `use_signal` instead of `use_signal(|| ...)`. They are **not wired into the build**. The corresponding **ported implementations** live in `lib/ruin_app/example/` and represent the current actual API. When porting an aspirational example, the goal is to make the example/ version match the aspirational design as closely as the current framework allows.

### Key Design Constraints

- The reactive graph is strictly single-threaded — never share reactive values across threads.
- `Signal<T>` must be `.clone()`d before being moved into closures (it's `Rc`-based, not `Arc`).
- All float layout values are `f32` (e.g., `gap = 8.0`, not `gap = 8`).
- `ruin_app` is the integration target; avoid bypassing it to call `ruin_ui` or `ruin_reactivity` directly in application code unless writing low-level infrastructure.
