In my Flutter app I am using package date_time_picker (DateTimePicker) to allow users to pick a date. It is initialized with a date in the future.
I have a reset button that when pressed resets all the fields on the page. That does work for all my other fields and the values on the controller get reset (I am using GetX - though that should have little bearing on the issue).
Similarly, I have a checkbox used to shortcut the date selection to the current date.
When I select a date from DateTimePicker, then do a reset, the displayed selection does not reset date, though, as stated above, the displayed date remains as the last selected value.
Again, similarly, when I use the shortcut, the displayed value remains as the last selected value, not the current date.
My unit tests show that controller does behave as expected.
Here is the relevant widget code:
Padding(
padding: const EdgeInsets.fromLTRB(96, 8, 96, 8),
child: DateTimePicker(
firstDate: controller.firstDate,
lastDate: controller.lastDate,
decoration: InputDecoration(
enabledBorder:
Theme.of(context).inputDecorationTheme.enabledBorder,
focusedBorder:
Theme.of(context).inputDecorationTheme.focusedBorder,
),
onChanged: (val) {
controller.selectedDate.value = DateTime.parse(val);
logger
.d('Set selectedDate to ${controller.selectedDate.value}');
},
controller: controller.dateController,
style: Theme.of(context).textTheme.bodyText2,
),
),
Padding(
padding: const EdgeInsets.fromLTRB(70, 0, 0, 0),
child: Obx(
() => CheckboxListTile(
title: const Text('Check available now?'),
selected: controller.availableNow.value,
value: controller.availableNow.value,
dense: true,
controlAffinity: ListTileControlAffinity.leading,
onChanged: (bool? value) {
controller.availableNow.value = value!;
controller.selectedDate.value = controller.firstDate;
controller.dateController.value = TextEditingValue(
text:
DateFormat('MMM d, y').format(controller.firstDate));
logger.d('Set selectedDate to ${controller.selectedDate}');
},
),
),
),
Here is the logic in my controller:
void resetFilter() {
logger.d(
'resetting selectedDate: ${selectedDate.value}, dateText: ${dateController.text}, availableNow: ${availableNow.value}');
selectedDate.value = _defaultInitialDate;
dateController.text = DateFormat('MMM d, y').format(_defaultInitialDate);
availableNow.value = false;
logger.d(
'reset to selectedDate: ${selectedDate.value}, dateText: ${dateController.text}, availableNow: ${availableNow.value}');
}
I had hoped that setting the value and/or the controller text would update the displayed field.
I tried wrapping the DateTimePicker in an Obx (GetX observable) would solve the problem. Alas, there seems to be a problem with that which I do not understand. Below is definition for the date and the checkbox value - clearly showing they are both observable (the checkbox reverts just fine when I reset):
Rx<DateTime> selectedDate = _defaultInitialDate.obs;
RxBool availableNow = false.obs;
And, the DateTimePicker is wrapped as follows:
child: Obx(
() => DateTimePicker(
// child: DateTimePicker(
firstDate: controller.firstDate,
lastDate: controller.lastDate,
decoration: InputDecoration(
enabledBorder:
Theme.of(context).inputDecorationTheme.enabledBorder,
focusedBorder:
Theme.of(context).inputDecorationTheme.focusedBorder,
),
onChanged: (val) {
controller.selectedDate.value = DateTime.parse(val);
logger.d(
'Set selectedDate to ${controller.selectedDate.value}');
},
controller: controller.dateController,
style: Theme.of(context).textTheme.bodyText2,
),
),
Which gives me the error below when run the app:
[Get] the improper use of a GetX has been detected.
You should only use GetX or Obx for the specific widget that will be updated.
If you are seeing this error, you probably did not insert any observable variables into GetX/Obx
or insert them outside the scope that GetX considers suitable for an update
(example: GetX => HeavyWidget => variableObservable).
Here is the log output of the reset action, which shows I am updating things:
/flutter (26068): ┌───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
I/flutter (26068): │ #0 AvailabilitySelectorController.resetFilter (package:the_shuk/property_search/external/page/controllers/selectors/availability_selector_controller.dart:68:12)
I/flutter (26068): │ #1 FiltersController.resetFilters (package:the_shuk/property_search/external/page/controllers/filters_controller.dart:45:36)
I/flutter (26068): ├┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄
I/flutter (26068): │ 15:43:13.779 (+0:43:13.686580)
I/flutter (26068): ├┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄
I/flutter (26068): │ resetting selectedDate: 2022-04-02 00:00:00.000, dateText: 2022-04-02, availableNow: false
I/flutter (26068): └───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
I/flutter (26068): ┌───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
I/flutter (26068): │ #0 AvailabilitySelectorController.resetFilter (package:the_shuk/property_search/external/page/controllers/selectors/availability_selector_controller.dart:73:12)
I/flutter (26068): │ #1 FiltersController.resetFilters (package:the_shuk/property_search/external/page/controllers/filters_controller.dart:45:36)
I/flutter (26068): ├┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄
I/flutter (26068): │ 15:43:13.780 (+0:43:13.688362)
I/flutter (26068): ├┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄
I/flutter (26068): │ reset to selectedDate: 2022-04-30 00:00:00.000, dateText: Apr 30, 2022, availableNow: false
I/flutter (26068): └───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
I would hope there is a way to achieve what it is I wish to do. If not, the DateTimePicker is missing what I feel is a fundamental capability. If that is the case, suggestions from the community regarding other widgets I could employ that would help me achieve my end goal will be considered acceptable.