# `Athanor.Fields`
[🔗](https://github.com/Arsenalist/athanor/blob/v0.1.0-beta.7/lib/athanor/fields.ex#L1)

Auto-renders a component's editable inputs from its `fields/0` schema.

Used by `Athanor.AutoEditorForm` to fill the Component tab of the
configure panel. Stateless function component — the LC machinery
(state, phx-change routing, custom-field on_change plumbing) lives in
`Athanor.AutoEditorForm`.

## Built-in types

- `:text`     — `<input type="text">`
- `:textarea` — `<textarea>`
- `:number`   — `<input type="number">` with optional `min`/`max`
- `:select`   — `<select>` driven by `options:` keyword
- `:radio`    — radio-button group driven by the same `options:` keyword as
                `:select` (static `[{label, value}, …]` list or arity-1 `Ctx`
                function). Inline single-choice for small option sets; inputs
                share the field `name`.
- `:color`    — HTML5 `<input type="color">` (no JS dep)
- `:checkbox` — `<input type="checkbox">` with hidden false-input so
                unchecked submits as `"false"`
- `:asset`    — host-agnostic uploaded-asset picker (image/pdf/video/…).
                Renders neutral chrome (preview/chips + a choose/add
                control) and a paste-a-URL fallback. Emits a fixed
                `"athanor_asset_request"` event (no `phx-target`, so it
                bubbles to the editor LiveView) — it never uploads or
                browses itself. Opts: `accept:` (opaque hint forwarded to
                the host), `multiple:` (gallery/multi-file), `min:`/`max:`
                (forwarded, host-enforced). Value is an asset descriptor
                map `%{"url" => ..., "name" => ..., "content_type" => ...}`
                (single) or a list of them (`multiple: true`); opaque extra
                keys are preserved. See `Athanor.Editor.AssetRequest` and
                `c:Athanor.Editor.handle_asset_request/2`.
- `:custom`   — mounts `<.live_component module={opts[:module]}>`
                matching `Athanor.Field` behaviour

## Conditional fields

Any field opts list may include `if: fn props -> boolean end`. When the
function returns false against the current props, the field is omitted
from the render. Re-evaluated each render, so a sibling field that
changes via `update_props` immediately shows/hides dependents.

## Form layout

Built-in inputs live inside ONE `<.form phx-change="update_props"
phx-target={@myself}>` so a single phx-change submits all fields'
current values as form params. Custom fields render OUTSIDE the form
(they have their own state and `on_change` callback).

# `render`

## Attributes

* `module` (`:atom`) (required) - component module whose fields/0 to render.
* `props` (`:map`) - current node props. Defaults to `%{}`.
* `ctx` (`Athanor.Ctx`) (required)
* `myself` (`:any`) (required) - phx-target for the auto-form's parent LC.
* `component_id` (`:string`) - owning node id — namespaces custom field LC ids so multiple instances of the same component type don't collide on switch. Defaults to `"default"`.
* `on_custom_change` (`:any`) (required) - fn (key, value) -> any -- invoked by custom field LCs.

---

*Consult [api-reference.md](api-reference.md) for complete listing*
