angular / components

Component infrastructure and Material Design components for Angular
https://material.angular.io
MIT License
24.21k stars 6.69k forks source link

help(mat-date-range-picker): Getting date range values from Reactive FormGroup #22158

Open aplus01 opened 3 years ago

aplus01 commented 3 years ago

What are you trying to do?

I would like to use the date range picker in a reactive form and emit an event when the FormGroup's value changes.

I'm subscribing to the valueChanges Observable on the FormGroup and emitting an event when a value changes.

What troubleshooting steps have you tried?

I am seeing many events being emitted when the FormGroup is initialized (4x). And when the form control's value is modified at runtime via button click there are even more events emitted.

Is a way to filter down the valueChange events coming from the FormGroup? I realize I could filter the values coming through the valueChange Observable but I'm not sure how to know which value is the one I'm after.

Reproduction

https://stackblitz.com/edit/date-time-picker-reactive-form?file=src/app/date-range-picker.ts

Environment

aplus01 commented 3 years ago

I found what looks to be a bug against the valueChange observable on a FormGroup which seems to be behind the bulk of the chatter (https://github.com/angular/angular/issues/18350).

I got close to what I'm trying to accomplish. I tried the suggested workaround which was to use distinctUntilChanged() to only emit when the values are different. Then I used skip(1) to not emit the change caused by initializing the FormGroup.

This resulted in me only seeing things emitted by valueChange when either the start or end changed. Its still problematic to try and determine whether selection is complete if I'm only listening to the FormGroup.

In the end I decided to back away from using the FormGroup and instead listen to the mat-date-range-picker closed event and emit the selected values and when a date range preset button is clicked emit those values.

If its possible to us a FormGroup with this component I think I'd prefer that but I'm going to move forward with the solution I have in this stackblitz: https://stackblitz.com/edit/date-time-picker-reactive-form-workaround

jelbourn commented 3 years ago

@AndrewKushnir is this behavior expected from the forms module?

AndrewKushnir commented 3 years ago

Hi @aplus01, thanks for providing Stackblitz repros. However I'm still a bit puzzled which events are you observing in the valueChanges subscription callback and based on that which ones are expected and which ones are not. The ticket that you refer to (angular/angular#18350) is marked as resolved, so I'm curious if you're still seeing that problem or it's something different. Thank you.

aplus01 commented 3 years ago

Hi @AndrewKushnir, I probably should have forked my reproduction so it would be clear what I was seeing prior to experimenting and implementing the workaround I mentioned above. Sorry for any confusion that created.

I've reverted my changes to repro (https://stackblitz.com/edit/date-time-picker-reactive-form) so it should be clearer what I was referring to when I was describing the "extra" events. For anyone interested here is a link to the reproduction that has the workaround: https://stackblitz.com/edit/date-time-picker-reactive-form-workaround

The behavior I was seeing is that initialization of the FormGroup would generate 4 events from valueChanges. I could maybe account for 2 of the events given that there are 2 controls in the form group being initialized the other 2 appear to be duplicates.

Using the preset buttons to apply dates would result in a total of 6 events. And using the UI to choose a start and end date on the calendar results in a total of 8 events. Ideally both of these methods of setting a date range (preset & calendar) would be way less chatty and consistent in the number of events emitted with one anther so I could handle them in one subscription.

I'm unsure if the fix for (angular/angular#18350) is in the version of angular in the reproduction (10.2.4) but I think it does not include it.

AndrewKushnir commented 3 years ago

@aplus01 thanks for additional information.

I've performed additional investigation and it looks like the logic in Material Components invokes Forms API that triggers these valueChanges events. @jelbourn let's may be sync up to investigate it further?

aplus01 commented 3 years ago

@AndrewKushnir If I can help with anything else let me know. Thanks for digging into this.

jelbourn commented 3 years ago

Marking this as triaged as a confirmed bug