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
| Axis | Contract |
|---|---|
| Value collection | values 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 fields | A field with enabled: false is left out of TRFormValues. A field with readOnly: true still contributes its value. |
| Validation | validate() 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 timing | autovalidateMode defaults to null, so errors appear only when validation runs. Pass AutovalidateMode.onUserInteraction to validate while the reader types. |
| Change and reset | onChanged 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_uiimport '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
| Prop | Type / default | Purpose |
|---|---|---|
child | Widget (required) | The subtree that holds the form fields. |
autovalidateMode | AutovalidateMode? | Chooses when the native form revalidates. Null validates only on an explicit call. |
onChanged | ValueChanged<TRFormValues>? | Called with a fresh snapshot after any field change and after reset(). |
canPop | bool? | Forwarded to the native Form to guard route pops while the form holds unsaved input. |
onPopInvokedWithResult | PopInvokedWithResultCallback<Object?>? | Forwarded to the native Form and called after a pop attempt. |
TRFormState members
| Prop | Type / default | Purpose |
|---|---|---|
values | TRFormValues | A snapshot of the enabled named fields, taken without running save(). |
save() | TRFormValues | Runs FormState.save() and returns the resulting snapshot. |
validate() | bool | Runs every field validator and returns whether all of them passed. |
validateGranularly() | bool | Validates through the native granular API and returns true when no field reports an error. |
reset() | void | Restores the native field values and fires onChanged with the new snapshot. |
TRForm.maybeOf | TRFormState? Function(BuildContext) | Finds the enclosing form state from a descendant, or returns null outside a TRForm. |
TRFormValues members
| Prop | Type / default | Purpose |
|---|---|---|
operator [] | Object? Function(String name) | Reads one field value by name, or null when the name is absent. |
contains | bool Function(String name) | Reports whether the snapshot holds the name. A disabled field is absent even when it is mounted. |
entries | Iterable<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. |