Skip to main content
Firstlight / NativePHP

Firstlight / Docs

Native controls, familiar Blade, and the implementation details in between.

View source
Stepper

Stepper

Stepper moves a numeric model by one bounded step at a time. PHP remains the accepted source of truth: a tap proposes the adjacent value and the native control continues showing the accepted value until PHP publishes again.

<firstlight:stepper
    native:model="quantity"
    :min="0"
    :max="10"
    :step="1"
    label="Quantity"
    helper="Adjust one item at a time"
/>

Use Blade's : binding for numbers. Literal HTML attributes such as min="0" are strings and are rejected deliberately.

Props

API Accepted type Purpose
value / native:model finite `int float`
min finite `int float`
max finite `int float`
step finite positive `int float`
label string Visible field label and accessible-name fallback.
helper string Supporting guidance below the control.
error string Validation feedback that replaces helper text.
disabled bool Prevents decrement and increment proposals.
a11y-label string Explicit accessible name when no visible label is appropriate.
a11y-hint string Additional VoiceOver and TalkBack guidance.
class string External EDGE layout for the complete field.

min must be less than max. The accepted value must be within the inclusive bounds, and both it and max must lie on the step grid originating at min. Numeric strings, booleans, null, non-finite values, native Float overflow, off-grid values, and grids larger than the signed 32-bit interval limit are rejected. Values are never clamped or coerced.

Exact PHP number types

Stepper preserves intentional PHP number kinds. If value, min, max, and step are all integers, proposals are integers. If any one is a float, all numeric tree props and proposals are floats, even an integral value such as 5.0. An omitted step defaults to integer 1 for an otherwise integer model.

public int $quantity = 5;
public float $dose = 5.0;

Decimal grid comparisons tolerate only normal binary floating-point noise such as 0.1 + 0.2; the public value still has to be on the authored grid.

Events and server authority

Use @change, plain native:model, or native:model.live. A decrement or increment sends one adjacent precomputed value through the standard callback. Blur and debounce modes are rejected because a step is already an immediate, discrete action.

After a proposal, another tap is ignored until the server publishes the node again. This prevents stale rapid taps from calculating against an old accepted value. The control does not change optimistically and performs no arithmetic on the device.

NativePHP Mobile 4.0.1 still needs verified publication notification when PHP rejects a proposal and republishes an identical accepted value. Stepper remains release-blocked on that upstream behavior; accepted changes already reconcile normally.

Accessibility and platform behavior

Provide a visible label or an explicit a11y-label. VoiceOver and TalkBack receive the accepted value, hint, helper or error, disabled state, and named decrease/increase actions. At a boundary, only the unavailable direction is disabled.

iOS uses the genuine SwiftUI Stepper. Android uses Material 3 icon buttons in the idiomatic minus/value/plus arrangement. Stepper deliberately has no custom icons, formatter, min/max captions, wraparound, orientation, long-press acceleration, required state, size, variant, colour, or style escape props.

Screenshots

Platform Light Dark
iOS Stepper on iOS in light mode Stepper on iOS in dark mode
Android Stepper on Android in light mode Stepper on Android in dark mode

Served from firstlightui/nativephp and cached for a fast first read.