-
Notifications
You must be signed in to change notification settings - Fork 0
LayrzCheckboxInput
Boolean toggle input with support for checkbox, switch, and dropdown field styles.
DERIVED from layrz_theme. This specification is extracted from the current ThemedCheckboxInput API and awaits team confirmation. Details may change during the M3 inputs review. CRITICAL OPEN QUESTION: Whether this component composes LayrzTextInput at all (see Composition Architecture section below).
| Field | Value |
|---|---|
| Mirrors |
ThemedCheckboxInput from layrz_theme |
| Phase | M3 (Core Inputs) |
| Domain | Inputs |
| Composes | UNCLEAR — may or may not compose LayrzTextInput (see open questions) |
| SDK Primitive |
ToggleableStateMixin (toggleable.dart:37) + ToggleablePainter (toggleable.dart:409) for checkbox/switch rendering; hand-rolled toggleable controls |
LayrzCheckboxInput conditionally conforms to the shared input contract:
-
If
style: .asField(dropdown field style): Conforms fully and may compose LayrzTextInput. -
If
style: .asCheckboxorstyle: .asSwitch(bare checkbox or switch): Does NOT conform to the input contract, as these are not text fields. See Composition Architecture section below.
Only input-specific deltas are documented here.
-
Value type:
bool(three-state toggleable, but often boolean only) - Interaction: Click/tap to toggle
-
Three rendering styles (controlled by
styleparameter):-
asCheckbox: Inline checkbox control (✓ / ☐) -
asSwitch: Inline toggle switch (ON / OFF) -
asField: Dropdown field (renders as "Yes"/"No" selection in a styled text field)
-
The fundamental question: Does LayrzCheckboxInput compose LayrzTextInput at all?
The source shows that ThemedCheckboxInput._buildAsField() composes ThemedSelectInput<bool>, not a text field:
// From layrz_theme source
Widget _buildAsField() {
return ThemedSelectInput<bool>(
labelText: widget.labelText,
label: widget.label,
// ... configured to display Yes/No options
);
}This means:
- The
.asFieldstyle DOES compose another input (a select input), so it inherits the input contract via SelectInput. - The
.asCheckboxand.asSwitchstyles are bare toggleables, NOT text fields.
For layrz_ui, the team must decide:
Option A: LayrzCheckboxInput composes LayrzTextInput ONLY for .asField style
-
.asField→ renders as read-only LayrzTextInput with a dropdown affordance opening a Yes/No picker. -
.asCheckboxand.asSwitch→ separate bare toggleable components, NOT inputs in the family. May be re-homed to aLToggle*family or remain as part of LayrzCheckboxInput for convenience. -
Implication: The input contract applies only to
.asField; checkbox/switch are not contract members.
Option B: LayrzCheckboxInput does NOT compose LayrzTextInput
- All three styles (checkbox, switch, field) are independent control renderings, grouped under one component name for convenience.
- The input contract is NOT inherited; LayrzCheckboxInput has its own minimal contract.
-
Implication: Only the
.asFieldstyle maintains form-field semantics (label, errors, padding); the others are bare controls.
Option C: Split into Multiple Components
-
LayrzCheckboxInput— bare checkbox using SDK primitives, NOT a form input. -
LSwitchInput— bare switch using SDK primitives, NOT a form input. -
LayrzSelectInput<bool>— field-style with Yes/No dropdown (existing as generic select). - Implication: Cleaner architecture (one concern per component), but breaks the layrz_theme API parity.
Assuming LayrzCheckboxInput is retained as a single component with three styles:
-
style(ThemedCheckboxInputStyle, enum) — determines the visual rendering:-
.asCheckbox— Flutter-native checkbox (Material-free using SDK primitives). -
.asSwitch— Material-free toggle switch. -
.asField— yes/no dropdown field (read-only text field with picker). -
.asCheckbox2— alternative checkbox design (use TBD, possibly for future design refresh). Default:.asCheckbox.
-
-
value(bool) — the current boolean state. Default:false. -
onChanged(void Function(bool)?) — invoked when the user toggles the state. -
disabled(bool) — when true, the control is not interactive.
-
labelText(String?) — label text. Applicable to all styles. For.asCheckboxand.asSwitch, may render beside or below the control. -
label(Widget?) — label widget. NOT supported in layrz_ui (labelText only). -
padding(EdgeInsets) — padding around the control. Default:EdgeInsets.all(10). -
hideDetails(bool) — whether to suppress error display. Applicable mainly to.asFieldstyle. -
errors(List<String>) — list of error messages.
For porting purposes, the current layrz_theme implementation exposes (extracted from source):
// Design sketch — parameter names from layrz_theme source
enum ThemedCheckboxInputStyle {
asField, // Dropdown field
asSwitch, // Toggle switch
asFlutterCheckbox, // Standard checkbox
asCheckbox2, // Alternative checkbox
}
class ThemedCheckboxInput extends StatefulWidget {
final String? labelText;
final Widget? label; // NOT supported
final void Function(bool)? onChanged;
final bool value; // Default: false
final bool disabled; // Default: false
final List<String> errors; // Default: []
final bool hideDetails; // Default: false
final EdgeInsets padding; // Default: EdgeInsets.all(10)
final ThemedCheckboxInputStyle style; // Default: .asFlutterCheckbox
}Rendering implementations (from source):
-
.asField→ internally usesThemedSelectInput<bool>with hardcoded Yes/No options. -
.asSwitch→ uses Flutter'sSwitchwidget (Material widget — will need Material-free replacement). -
.asFlutterCheckbox→ uses Flutter'sCheckboxwidget (Material widget — will need Material-free replacement). -
.asCheckbox2→ alternative checkbox design (source shows same logic as.asFlutterCheckboxbut flaggedasNewDesign: true).
Since layrz_ui cannot use Material's Checkbox or Switch widgets, the following SDK primitives are available:
ToggleableStateMixin (flutter/src/material/checkbox.dart, line ~37)
- Provides internal state management for toggleable controls (checked/unchecked/tristate).
- Abstract mixin; must be mixed into a custom State class.
- Handles long-press, keyboard interaction (space/enter), and focus visualization.
ToggleablePainter (flutter/src/material/toggleable.dart, line ~409)
- Abstract painter for rendering toggle controls.
- Provides utilities like
paintRadialReaction()for ripple effects and animations. - Subclass to implement custom checkbox or switch rendering via
CustomPaint.
RawRadio and toggle derivatives
-
RawRadio(raw_radio.dart:44) is design-agnostic and used by both Material and Cupertino. - No equivalent
RawCheckboxorRawSwitchexists in the SDK.
Implement custom toggle controls using ToggleableStateMixin + CustomPaint for rendering, or explore whether the internal Checkbox and Switch implementations can be extracted without Material dependencies. Cupertino's toggle switch may also be Material-free and reusable.
Both Checkbox and Switch from Flutter's Material design are not importable in layrz_ui. Custom Material-free implementations must be provided.
Status: Blocking implementation until resolved.
If .asField style composes LayrzTextInput or LayrzSelectInput, those inputs must be available first.
Status: Conditional on composition architecture decision (see open questions).
- Does LayrzCheckboxInput compose LayrzTextInput? If so, only for which styles?
- Should all three styles (checkbox, switch, field) remain in one component, or split into separate components?
- Refer to the Composition Architecture section for discussion.
- For
.asCheckbox, what is the visual appearance (size, color, animation, disabled state)? - For
.asSwitch, what is the visual appearance (thumb/track colors, animation, disabled state)? - Should animations (check animation, switch sliding) be smooth or instant?
- For
.asCheckboxand.asSwitch, is the label rendered to the right of the control, to the left, or above? - Is the label clickable (clicking the label toggles the control)?
- How are
errorsrendered for.asCheckboxand.asSwitchstyles? Below the control, beside it, or via a tooltip? - For
.asField, errors are inherited from the select input rendering.
- Should checkbox/switch support keyboard toggle (Space or Enter to toggle)?
- Should they support Tab navigation?
- Does the checkbox support indeterminate/tristate (true, false, null), or only boolean (true, false)?
- If tristate, how is the null state visually represented and transitioned between states?
Last updated: 2026-08-13
Related documents: Input Contract, LayrzTextInput, ./l_radio_input.md, Flutter 347 Audit
Made with ❤️ by Golden M, Inc.
- LayrzTextInput
- LayrzSelectableAction
- LayrzSelectionToolbar
- LayrzTextSelectionControls
- LayrzSelectionMagnifier
- LayrzSelectionHandlePainter
- LayrzTextAreaInput
- LayrzComboBoxInput
- LayrzNumberInput
- LayrzPasswordInput
- LayrzCheckboxInput
- LayrzRadioInput
- LayrzSelectInput
- LayrzMultiSelectInput
- LayrzSearchInput
- LayrzDualListInput
- LayrzDurationInput