Skip to content

Commit 8c6641f

Browse files
Merge pull request #1465 from flutter-form-builder-ecosystem/feature/#1456-remove-deprecated-code
feat: #1456-remove-deprecated-code
2 parents 7754009 + 8bbfdbf commit 8c6641f

21 files changed

+314
-47
lines changed

.github/workflows/base.yaml

+3-1
Original file line numberDiff line numberDiff line change
@@ -42,11 +42,13 @@ jobs:
4242
- name: Install dependencies
4343
run: flutter pub get
4444
- name: Format code
45-
run: dart format --set-exit-if-changed .
45+
run: dart format --set-exit-if-changed lib/ test/ example/
4646
- name: Analyze static code
4747
run: flutter analyze
4848
- name: Run tests
4949
run: flutter test --coverage
50+
- name: Run fixes tests
51+
run: dart fix --compare-to-golden test_fixes/
5052
- name: Upload coverage to Codecov
5153
uses: codecov/codecov-action@v5
5254
with:

analysis_options.yaml

+4
Original file line numberDiff line numberDiff line change
@@ -1 +1,5 @@
11
include: package:flutter_lints/flutter.yaml
2+
3+
analyzer:
4+
exclude:
5+
- "test_fixes/**"

example/lib/minimal_code_example.dart

+1-1
Original file line numberDiff line numberDiff line change
@@ -44,7 +44,7 @@ class _ExamplePageState extends State<_ExamplePage> {
4444
key: _formKey,
4545
child: Column(
4646
children: [
47-
FormBuilderFilterChip<String>(
47+
FormBuilderFilterChips<String>(
4848
decoration: const InputDecoration(
4949
labelText: 'The language of my people',
5050
enabled: false,

example/lib/sources/complete_form.dart

+2-2
Original file line numberDiff line numberDiff line change
@@ -252,7 +252,7 @@ class _CompleteFormState extends State<CompleteForm> {
252252
FormBuilderValidators.maxLength(3),
253253
]),
254254
),
255-
FormBuilderFilterChip<String>(
255+
FormBuilderFilterChips<String>(
256256
autovalidateMode: AutovalidateMode.onUserInteraction,
257257
decoration: const InputDecoration(
258258
labelText: 'The language of my people'),
@@ -286,7 +286,7 @@ class _CompleteFormState extends State<CompleteForm> {
286286
FormBuilderValidators.maxLength(3),
287287
]),
288288
),
289-
FormBuilderChoiceChip<String>(
289+
FormBuilderChoiceChips<String>(
290290
autovalidateMode: AutovalidateMode.onUserInteraction,
291291
decoration: const InputDecoration(
292292
labelText:

lib/fix_data.yaml

+45
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
version: 1
2+
transforms:
3+
- title: 'Remove deprecated maxChips property on FormBuilderFilterChip'
4+
date: 2025-01-15
5+
element:
6+
uris: [ 'flutter_form_builder.dart' ]
7+
constructor: ''
8+
inClass: 'FormBuilderFilterChip'
9+
changes:
10+
- kind: 'removeParameter'
11+
name: 'maxChips'
12+
- title: 'Remove deprecated resetIcon property on FormBuilderDateTimePicker'
13+
date: 2025-01-15
14+
element:
15+
uris: [ 'flutter_form_builder.dart' ]
16+
constructor: ''
17+
inClass: 'FormBuilderDateTimePicker'
18+
changes:
19+
- kind: 'removeParameter'
20+
name: 'resetIcon'
21+
- title: 'Remove deprecated onPopInvoked property on FormBuilder'
22+
date: 2025-01-15
23+
element:
24+
uris: [ 'flutter_form_builder.dart' ]
25+
constructor: ''
26+
inClass: 'FormBuilder'
27+
changes:
28+
- kind: 'removeParameter'
29+
name: 'onPopInvoked'
30+
- title: 'Rename FormBuilderChoiceChip to be plural'
31+
date: 2025-01-15
32+
element:
33+
uris: [ 'flutter_form_builder.dart' ]
34+
class: 'FormBuilderChoiceChip'
35+
changes:
36+
- kind: 'rename'
37+
newName: 'FormBuilderChoiceChips'
38+
- title: 'Rename FormBuilderFilterChip to be plural'
39+
date: 2025-01-15
40+
element:
41+
uris: [ 'flutter_form_builder.dart' ]
42+
class: 'FormBuilderFilterChip'
43+
changes:
44+
- kind: 'rename'
45+
newName: 'FormBuilderFilterChips'

lib/src/extensions/generic_validator.dart

+1
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
extension GenericValidator<T> on T? {
2+
/// Check if the value is empty in a generic way
23
bool emptyValidator() {
34
if (this == null) return true;
45
if (this is Iterable) return (this as Iterable).isEmpty;

lib/src/fields/form_builder_choice_chips.dart

+4-4
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ import 'package:flutter/material.dart';
22
import 'package:flutter_form_builder/flutter_form_builder.dart';
33

44
/// A list of `Chip`s that acts like radio buttons
5-
class FormBuilderChoiceChip<T> extends FormBuilderFieldDecoration<T> {
5+
class FormBuilderChoiceChips<T> extends FormBuilderFieldDecoration<T> {
66
/// The list of items the user can select.
77
final List<FormBuilderChipOption<T>> options;
88

@@ -344,7 +344,7 @@ class FormBuilderChoiceChip<T> extends FormBuilderFieldDecoration<T> {
344344
final String? tooltip;
345345

346346
/// Creates a list of `Chip`s that acts like radio buttons
347-
FormBuilderChoiceChip({
347+
FormBuilderChoiceChips({
348348
super.autovalidateMode = AutovalidateMode.disabled,
349349
super.enabled,
350350
super.focusNode,
@@ -457,12 +457,12 @@ class FormBuilderChoiceChip<T> extends FormBuilderFieldDecoration<T> {
457457
});
458458

459459
@override
460-
FormBuilderFieldDecorationState<FormBuilderChoiceChip<T>, T> createState() =>
460+
FormBuilderFieldDecorationState<FormBuilderChoiceChips<T>, T> createState() =>
461461
_FormBuilderChoiceChipState<T>();
462462
}
463463

464464
class _FormBuilderChoiceChipState<T>
465-
extends FormBuilderFieldDecorationState<FormBuilderChoiceChip<T>, T> {
465+
extends FormBuilderFieldDecorationState<FormBuilderChoiceChips<T>, T> {
466466
void handleFocusChange() {
467467
setState(() {});
468468
}

lib/src/fields/form_builder_date_time_picker.dart

-5
Original file line numberDiff line numberDiff line change
@@ -40,10 +40,6 @@ class FormBuilderDateTimePicker extends FormBuilderFieldDecoration<DateTime> {
4040
/// to noon. Explicitly set this to `null` to use the current time.
4141
final TimeOfDay initialTime;
4242

43-
@Deprecated(
44-
'This property is no used anymore. Please use decoration.suffixIcon to set your desired icon')
45-
final Widget? resetIcon;
46-
4743
/// Called when an enclosing form is saved. The value passed will be `null`
4844
/// if [format] fails to parse the text.
4945
// final FormFieldSetter<DateTime> onSaved;
@@ -146,7 +142,6 @@ class FormBuilderDateTimePicker extends FormBuilderFieldDecoration<DateTime> {
146142
this.scrollPadding = const EdgeInsets.all(20.0),
147143
this.cursorWidth = 2.0,
148144
this.enableInteractiveSelection = true,
149-
this.resetIcon = const Icon(Icons.close),
150145
this.initialTime = const TimeOfDay(hour: 12, minute: 0),
151146
this.keyboardType,
152147
this.textAlign = TextAlign.start,

lib/src/fields/form_builder_filter_chips.dart

+5-5
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ import 'package:flutter/material.dart';
33
import 'package:flutter_form_builder/flutter_form_builder.dart';
44

55
/// Field with chips that acts like a list checkboxes.
6-
class FormBuilderFilterChip<T> extends FormBuilderFieldDecoration<List<T>> {
6+
class FormBuilderFilterChips<T> extends FormBuilderFieldDecoration<List<T>> {
77
//TODO: Add documentation
88
final Color? backgroundColor;
99
final Color? disabledColor;
@@ -35,7 +35,7 @@ class FormBuilderFilterChip<T> extends FormBuilderFieldDecoration<List<T>> {
3535
final ShapeBorder avatarBorder;
3636

3737
/// Creates field with chips that acts like a list checkboxes.
38-
FormBuilderFilterChip({
38+
FormBuilderFilterChips({
3939
super.autovalidateMode = AutovalidateMode.disabled,
4040
super.enabled,
4141
super.focusNode,
@@ -59,7 +59,7 @@ class FormBuilderFilterChip<T> extends FormBuilderFieldDecoration<List<T>> {
5959
this.labelPadding,
6060
this.labelStyle,
6161
this.materialTapTargetSize,
62-
this.maxChips,
62+
@Deprecated('Useless property. Please remove it.') this.maxChips,
6363
this.padding,
6464
this.pressElevation,
6565
this.runAlignment = WrapAlignment.start,
@@ -143,9 +143,9 @@ class FormBuilderFilterChip<T> extends FormBuilderFieldDecoration<List<T>> {
143143
);
144144

145145
@override
146-
FormBuilderFieldDecorationState<FormBuilderFilterChip<T>, List<T>>
146+
FormBuilderFieldDecorationState<FormBuilderFilterChips<T>, List<T>>
147147
createState() => _FormBuilderFilterChipState<T>();
148148
}
149149

150150
class _FormBuilderFilterChipState<T> extends FormBuilderFieldDecorationState<
151-
FormBuilderFilterChip<T>, List<T>> {}
151+
FormBuilderFilterChips<T>, List<T>> {}

lib/src/fields/form_builder_text_field.dart

+5
Original file line numberDiff line numberDiff line change
@@ -424,6 +424,11 @@ class FormBuilderTextField extends FormBuilderFieldDecoration<String> {
424424
this.contentInsertionConfiguration,
425425
this.spellCheckConfiguration,
426426
this.clipBehavior = Clip.hardEdge,
427+
@Deprecated(
428+
'This property will be removed in the next Flutter stable versions. '
429+
'Use FocusNode.canRequestFocus instead. '
430+
'Ref: https://docs.flutter.dev/release/breaking-changes/can-request-focus',
431+
)
427432
this.canRequestFocus = true,
428433
this.cursorErrorColor,
429434
this.cursorOpacityAnimates,

lib/src/form_builder.dart

+8-21
Original file line numberDiff line numberDiff line change
@@ -10,9 +10,6 @@ class FormBuilder extends StatefulWidget {
1010
/// will rebuild.
1111
final VoidCallback? onChanged;
1212

13-
/// DEPRECATED: Use [onPopInvokedWithResult] instead.
14-
final void Function(bool)? onPopInvoked;
15-
1613
/// {@macro flutter.widgets.navigator.onPopInvokedWithResult}
1714
///
1815
/// {@tool dartpad}
@@ -105,11 +102,6 @@ class FormBuilder extends StatefulWidget {
105102
required this.child,
106103
this.onChanged,
107104
this.autovalidateMode,
108-
@Deprecated(
109-
'Use onPopInvokedWithResult instead. '
110-
'This feature was deprecated after v3.22.0-12.0.pre.',
111-
)
112-
this.onPopInvoked,
113105
this.onPopInvokedWithResult,
114106
this.initialValue = const <String, dynamic>{},
115107
this.skipDisabled = false,
@@ -143,6 +135,7 @@ class FormBuilderState extends State<FormBuilder> {
143135
/// Only used to internal logic
144136
bool get focusOnInvalid => _focusOnInvalid;
145137

138+
/// Get if form is enabled
146139
bool get enabled => widget.enabled;
147140

148141
/// Verify if all fields on form are valid.
@@ -171,6 +164,7 @@ class FormBuilderState extends State<FormBuilder> {
171164
/// Get all fields of form.
172165
FormBuilderFields get fields => _fields;
173166

167+
/// Get all fields values of form.
174168
Map<String, dynamic> get instantValue => Map<String, dynamic>.unmodifiable(
175169
_instantValue.map(
176170
(key, value) => MapEntry(
@@ -204,15 +198,18 @@ class FormBuilderState extends State<FormBuilder> {
204198
initialValue[name];
205199
}
206200

201+
/// Get a field value by name
207202
void setInternalFieldValue<T>(String name, T? value) {
208203
_instantValue[name] = value;
209204
widget.onChanged?.call();
210205
}
211206

207+
/// Remove a field value by name
212208
void removeInternalFieldValue(String name) {
213209
_instantValue.remove(name);
214210
}
215211

212+
/// Register a field on form
216213
void registerField(String name, FormBuilderFieldState field) {
217214
// Each field must have a unique name. Ideally we could simply:
218215
// assert(!_fields.containsKey(name));
@@ -242,6 +239,7 @@ class FormBuilderState extends State<FormBuilder> {
242239
);
243240
}
244241

242+
/// Unregister a field on form
245243
void unregisterField(String name, FormBuilderFieldState field) {
246244
assert(
247245
_fields.containsKey(name),
@@ -270,23 +268,14 @@ class FormBuilderState extends State<FormBuilder> {
270268
}
271269
}
272270

271+
/// Save form values
273272
void save() {
274273
_formKey.currentState!.save();
275274
// Copy values from instant to saved
276275
_savedValue.clear();
277276
_savedValue.addAll(_instantValue);
278277
}
279278

280-
@Deprecated(
281-
'Will be remove to avoid redundancy. Use fields[name]?.invalidate(errorText) instead')
282-
void invalidateField({required String name, String? errorText}) =>
283-
fields[name]?.invalidate(errorText ?? '');
284-
285-
@Deprecated(
286-
'Will be remove to avoid redundancy. Use fields.first.invalidate(errorText) instead')
287-
void invalidateFirstField({required String errorText}) =>
288-
fields.values.first.invalidate(errorText);
289-
290279
/// Validate all fields of form
291280
///
292281
/// Focus to first invalid field when has field invalid, if [focusOnInvalid] is `true`.
@@ -343,7 +332,7 @@ class FormBuilderState extends State<FormBuilder> {
343332
);
344333
}
345334

346-
/// Reset form to `initialValue`
335+
/// Reset form to `initialValue` set on FormBuilder or on each field.
347336
void reset() {
348337
_formKey.currentState?.reset();
349338
}
@@ -376,8 +365,6 @@ class FormBuilderState extends State<FormBuilder> {
376365
key: _formKey,
377366
autovalidateMode: widget.autovalidateMode,
378367
onPopInvokedWithResult: widget.onPopInvokedWithResult,
379-
// ignore: deprecated_member_use
380-
onPopInvoked: widget.onPopInvoked,
381368
canPop: widget.canPop,
382369
// `onChanged` is called during setInternalFieldValue else will be called early
383370
child: _FormBuilderScope(

lib/src/form_builder_field.dart

+26
Original file line numberDiff line numberDiff line change
@@ -71,12 +71,17 @@ class FormBuilderFieldState<F extends FormBuilderField<T>, T>
7171
FormBuilderState? _formBuilderState;
7272
bool _touched = false;
7373
bool _dirty = false;
74+
75+
/// The focus node that is used to focus this field.
7476
late FocusNode effectiveFocusNode;
77+
78+
/// The focus attachment for the [effectiveFocusNode].
7579
FocusAttachment? focusAttachment;
7680

7781
@override
7882
F get widget => super.widget as F;
7983

84+
/// Returns the parent [FormBuilderState] if it exists.
8085
FormBuilderState? get formState => _formBuilderState;
8186

8287
/// Returns the initial value, which may be declared at the field, or by the
@@ -91,18 +96,33 @@ class FormBuilderFieldState<F extends FormBuilderField<T>, T>
9196
widget.valueTransformer == null ? value : widget.valueTransformer!(value);
9297

9398
@override
99+
100+
/// Returns the current error text,
101+
/// which may be a validation error or a custom error text.
94102
String? get errorText => super.errorText ?? _customErrorText;
95103

96104
@override
105+
106+
/// Returns `true` if the field has an error or has a custom error text.
97107
bool get hasError => super.hasError || errorText != null;
98108

99109
@override
110+
111+
/// Returns `true` if the field is valid and has no custom error text.
100112
bool get isValid => super.isValid && _customErrorText == null;
101113

114+
/// Returns `true` if the field is valid.
102115
bool get valueIsValid => super.isValid;
116+
117+
/// Returns `true` if the field has an error.
103118
bool get valueHasError => super.hasError;
104119

120+
/// Returns `true` if the field is enabled and the parent FormBuilder is enabled.
105121
bool get enabled => widget.enabled && (_formBuilderState?.enabled ?? true);
122+
123+
/// Returns `true` if the field is read only.
124+
///
125+
/// See [FormBuilder.skipDisabled] for more information.
106126
bool get readOnly => !(_formBuilderState?.widget.skipDisabled ?? false);
107127

108128
/// Will be true if the field is dirty
@@ -199,6 +219,10 @@ class FormBuilderFieldState<F extends FormBuilderField<T>, T>
199219
}
200220

201221
@override
222+
223+
/// Reset field value to initial value
224+
///
225+
/// Also reset custom error text if exists, and set [isDirty] to `false`.
202226
void reset() {
203227
super.reset();
204228
didChange(initialValue);
@@ -276,10 +300,12 @@ class FormBuilderFieldState<F extends FormBuilderField<T>, T>
276300
);
277301
}
278302

303+
/// Focus field
279304
void focus() {
280305
FocusScope.of(context).requestFocus(effectiveFocusNode);
281306
}
282307

308+
/// Scroll to show field
283309
void ensureScrollableVisibility() {
284310
Scrollable.ensureVisible(context);
285311
}

lib/src/form_builder_field_decoration.dart

+1
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,7 @@ class FormBuilderFieldDecorationState<F extends FormBuilderFieldDecoration<T>,
4040
@override
4141
F get widget => super.widget as F;
4242

43+
/// Get the decoration with the current state
4344
InputDecoration get decoration => widget.decoration.copyWith(
4445
// Read only allow show error to support property skipDisabled
4546
errorText: widget.enabled || readOnly

0 commit comments

Comments
 (0)