diff --git a/example/lib/minimal_code_example.dart b/example/lib/minimal_code_example.dart index 99d06a5c2..1f8ea2cb3 100644 --- a/example/lib/minimal_code_example.dart +++ b/example/lib/minimal_code_example.dart @@ -1,7 +1,5 @@ import 'package:flutter/material.dart'; import 'package:flutter_form_builder/flutter_form_builder.dart'; -import 'package:flutter_localizations/flutter_localizations.dart'; -import 'package:form_builder_validators/form_builder_validators.dart'; void main() => runApp(const MyApp()); @@ -13,12 +11,6 @@ class MyApp extends StatelessWidget { return MaterialApp( title: 'Flutter FormBuilder Example', debugShowCheckedModeBanner: false, - localizationsDelegates: const [ - FormBuilderLocalizations.delegate, - ...GlobalMaterialLocalizations.delegates, - GlobalWidgetsLocalizations.delegate, - ], - supportedLocales: FormBuilderLocalizations.supportedLocales, home: const _ExamplePage(), ); } @@ -37,56 +29,47 @@ class _ExamplePageState extends State<_ExamplePage> { @override Widget build(BuildContext context) { return Scaffold( - appBar: AppBar(title: const Text('Minimal code example')), - body: Padding( - padding: const EdgeInsets.all(16), - child: FormBuilder( - key: _formKey, - child: Column( - children: [ - FormBuilderFilterChips( - decoration: const InputDecoration( - labelText: 'The language of my people', - ), - name: 'languages_filter', - selectedColor: Colors.red, - options: const [ - FormBuilderChipOption( - value: 'Dart', - avatar: CircleAvatar(child: Text('D')), + body: SafeArea( + child: Column( + children: [ + FormBuilder( + key: _formKey, + child: Column( + children: [ + FormBuilderTextField( + name: 'full_name', + decoration: const InputDecoration(labelText: 'Full Name'), + validator: (value) { + if (value == null || value.isEmpty) { + return 'Please enter your full name'; + } + return null; + }, ), - FormBuilderChipOption( - value: 'Kotlin', - avatar: CircleAvatar(child: Text('K')), - ), - FormBuilderChipOption( - value: 'Java', - avatar: CircleAvatar(child: Text('J')), - ), - FormBuilderChipOption( - value: 'Swift', - avatar: CircleAvatar(child: Text('S')), - ), - FormBuilderChipOption( - value: 'Objective-C', - avatar: CircleAvatar(child: Text('O')), + Builder( + builder: (innerContext) { + return Text( + FormBuilder.of(innerContext).isValid + ? 'OK Valid' + : 'X Invalid', + ); + }, ), + const SizedBox(height: 10), + Builder(builder: (innerContext) { + return ElevatedButton( + onPressed: () { + FormBuilder.of(innerContext).saveAndValidate(); + debugPrint( + FormBuilder.of(innerContext).value.toString()); + }, + child: const Text('Print'), + ); + }), ], - validator: FormBuilderValidators.compose([ - FormBuilderValidators.minLength(1), - FormBuilderValidators.maxLength(3), - ]), ), - const SizedBox(height: 10), - ElevatedButton( - onPressed: () { - _formKey.currentState?.saveAndValidate(); - debugPrint(_formKey.currentState?.value.toString()); - }, - child: const Text('Print'), - ) - ], - ), + ), + ], ), ), ); diff --git a/example/pubspec.lock b/example/pubspec.lock index 9ae53bb79..89ff28531 100644 --- a/example/pubspec.lock +++ b/example/pubspec.lock @@ -5,10 +5,10 @@ packages: dependency: transitive description: name: async - sha256: d2872f9c19731c2e5f10444b14686eb7cc85c76274bd6c16e1816bff9a3bab63 + sha256: "758e6d74e971c3e5aceb4110bfd6698efc7f501675bcfe0c775459a8140750eb" url: "https://pub.dev" source: hosted - version: "2.12.0" + version: "2.13.0" boolean_selector: dependency: transitive description: diff --git a/lib/src/form_builder.dart b/lib/src/form_builder.dart index f5ce4239a..dfa2ef9c3 100644 --- a/lib/src/form_builder.dart +++ b/lib/src/form_builder.dart @@ -110,8 +110,35 @@ class FormBuilder extends StatefulWidget { this.canPop, }); - static FormBuilderState? of(BuildContext context) => - context.findAncestorStateOfType(); + static FormBuilderState of(BuildContext context, [bool listen = false]) { + final FormBuilderState? formState = maybeOf(context, listen); + assert(() { + if (formState == null) { + throw FlutterError( + 'FormBuilder.of() was called with a context that does not contain a FormBuilder widget.\n' + 'No FormBuilder widget ancestor could be found starting from the context that ' + 'was passed to FormBuilder.of(). This can happen because you are using a widget ' + 'that looks for a FormBuilder ancestor, but no such ancestor exists.\n' + 'The context used was:\n' + ' $context', + ); + } + return true; + }()); + return formState!; + } + + static FormBuilderState? maybeOf( + BuildContext context, [ + bool listen = false, + ]) { + if (listen) { + return context + .dependOnInheritedWidgetOfExactType<_FormBuilderScope>() + ?._formState; + } + return context.findAncestorStateOfType(); + } @override FormBuilderState createState() => FormBuilderState(); diff --git a/pubspec.lock b/pubspec.lock index 0e6bb7614..09725c745 100644 --- a/pubspec.lock +++ b/pubspec.lock @@ -5,10 +5,10 @@ packages: dependency: transitive description: name: async - sha256: d2872f9c19731c2e5f10444b14686eb7cc85c76274bd6c16e1816bff9a3bab63 + sha256: "758e6d74e971c3e5aceb4110bfd6698efc7f501675bcfe0c775459a8140750eb" url: "https://pub.dev" source: hosted - version: "2.12.0" + version: "2.13.0" boolean_selector: dependency: transitive description: