Tinyrack

Form

Validate Flutter form fields and collect enabled named Tinyrack values in one snapshot.

Validate Flutter form fields and collect enabled named Tinyrack values in one snapshot.

Contract

AxisContract
Value collectionvalues returns an immutable TRFormValues snapshot of the named fields; save() runs the native FormState.save() first and then returns the same snapshot.
Disabled and read-only fieldsA field with enabled: false is left out of TRFormValues. A field with readOnly: true still contributes its value.
Validationvalidate() returns whether every field validator passed. validateGranularly() runs the native granular validation and returns true when the error set is empty; the set itself is not exposed. Both report true when the form has no FormState yet.
Validation timingautovalidateMode defaults to null, so errors appear only when validation runs. Pass AutovalidateMode.onUserInteraction to validate while the reader types.
Change and resetonChanged fires with a fresh snapshot whenever a field changes. reset() restores the native field values and then fires onChanged again; application state such as a submitted result must be cleared separately.

Reach TRFormState through a GlobalKey<TRFormState> you hold, or through TRForm.maybeOf(context) from a descendant. Only fields that declare a name appear in TRFormValues.

Install

Add the package, then import its public library.

flutter pub add tinyrack_ui
import 'package:tinyrack_ui/tinyrack_ui.dart';

Playground

Usage

import 'package:material_ui/material_ui.dart';
import 'package:tinyrack_ui/tinyrack_ui.dart';

class RackForm extends StatefulWidget {
  const RackForm({super.key});

  @override
  State<RackForm> createState() => _RackFormState();
}

class _RackFormState extends State<RackForm> {
  final GlobalKey<TRFormState> formKey = GlobalKey<TRFormState>();
  String submitted = '';

  @override
  Widget build(BuildContext context) => TRForm(
    key: formKey,
    child: Column(
      mainAxisSize: MainAxisSize.min,
      spacing: TRSpacing.medium,
      children: [
        TRTextField(
          name: 'rack',
          label: 'Rack name',
          validator: (value) =>
              (value ?? '').trim().isEmpty ? 'Enter a rack name.' : null,
        ),
        TRButton(
          onPressed: () {
            final state = formKey.currentState!;
            if (!state.validate()) return;
            final values = state.save();
            setState(() => submitted = values['rack']?.toString() ?? '');
          },
          child: const Text('Save'),
        ),
        if (submitted.isNotEmpty)
          TRText(submitted, variant: TRTextVariant.bodySm),
      ],
    ),
  );
}

Examples

Collect values and reset permalink

Submit reads the named field through `save()`. Reset restores the initial value, and the application clears its own submitted result.

Required submission and recovery permalink

Submit while the field is empty to see the validator message, then enter a rack name and submit again. `validate()` gates the read of `save()`.

Server error and recovery permalink

A rejected name arrives back as `errorText` instead of a validator. `onChanged` clears the error while the reader edits, and `reset()` restores the field while the application clears its own result.

Live snapshot and granular validation permalink

Type to watch `onChanged` report the snapshot. The disabled region field stays out of `TRFormValues`, and `validateGranularly()` validates without synthesizing a submit.

API

TRForm properties

PropType / defaultPurpose
childWidget (required)The subtree that holds the form fields.
autovalidateModeAutovalidateMode?Chooses when the native form revalidates. Null validates only on an explicit call.
onChangedValueChanged<TRFormValues>?Called with a fresh snapshot after any field change and after reset().
canPopbool?Forwarded to the native Form to guard route pops while the form holds unsaved input.
onPopInvokedWithResultPopInvokedWithResultCallback<Object?>?Forwarded to the native Form and called after a pop attempt.

TRFormState members

PropType / defaultPurpose
valuesTRFormValuesA snapshot of the enabled named fields, taken without running save().
save()TRFormValuesRuns FormState.save() and returns the resulting snapshot.
validate()boolRuns every field validator and returns whether all of them passed.
validateGranularly()boolValidates through the native granular API and returns true when no field reports an error.
reset()voidRestores the native field values and fires onChanged with the new snapshot.
TRForm.maybeOfTRFormState? Function(BuildContext)Finds the enclosing form state from a descendant, or returns null outside a TRForm.

TRFormValues members

PropType / defaultPurpose
operator []Object? Function(String name)Reads one field value by name, or null when the name is absent.
containsbool Function(String name)Reports whether the snapshot holds the name. A disabled field is absent even when it is mounted.
entriesIterable<MapEntry<String, Object?>>Iterates the collected name and value pairs.
toMap()Map<String, Object?>Copies the snapshot into a plain map for encoding or transport.