ngx-bootstrap icon indicating copy to clipboard operation
ngx-bootstrap copied to clipboard

Using minDate input for the datepicker fails to fire the bsValueChange after first date clicked in v5.60+

Open charms9 opened this issue 3 years ago • 14 comments

After updating our app to angular 9 and ngx-bootstrap v5.6.1, we encountered an issue with the datepicker where the minDate being set causes the function supplied to (bsValueChange) to not get fired after the first time a date on the calendar is clicked. Removing the minDate attribute allows the function to be called as expected. We downgraded our ngx-bootstrap to v5.5.0 which allowed the minDate attribute to work, although it had to be changed from the output of a function call to a variable/object property.

In version 5.6.0 and up, the event fires the supplied bsValueChange function with the following: <bs-datepicker-inline [bsValue]="displayDate" [bsConfig]="{showWeekNumbers: false}" (bsValueChange)="updateDeadlineDate($event)" [maxDate]="calMaxDate">

...but not with <bs-datepicker-inline [bsValue]="displayDate" [bsConfig]="{showWeekNumbers: false}" (bsValueChange)="updateDeadlineDate($event)" [minDate]="minDate" [maxDate]="calMaxDate">

charms9 avatar Aug 01 '20 01:08 charms9

@charms9 True, I have the same issue while using Angular 9 and ngx-bootstrap version v.5.6.1 where the following code doesn't fire a (bsValueChange) event:

<bs-datepicker-inline
    [bsValue]="value"
    [bsConfig]="{showWeekNumbers: false}"
    [minDate]="minDate"
    [maxDate]="maxDate"
    (bsValueChange)="onDateChange($event)"
></bs-datepicker-inline>

But the (bsValueChange) event is triggered if we remove the [minDate]:

<bs-datepicker-inline
    [bsValue]="value"
    [bsConfig]="{showWeekNumbers: false}"
    [maxDate]="maxDate"
    (bsValueChange)="onDateChange($event)"
></bs-datepicker-inline>

Did you find a solution for it or still waiting for the issue to be fixed?

frezo00 avatar Sep 11 '20 11:09 frezo00

No, the issue was still present as of v6.1. For various reasons we are changing our app to use the Material Design calendar.

charms9 avatar Sep 11 '20 12:09 charms9

Too bad to hear that. For now, on each change detection, we'll try to update the minDate property of bsConfig in the similar way as it is described on the following example: https://valor-software.com/ngx-bootstrap/old/5.6.1/#/datepicker#config-method If we manage to make it work, I'll post a solution here, but this should not be the way to do it, they should fix this asap.

frezo00 avatar Sep 11 '20 13:09 frezo00

@daniloff200 Do you have any knowledge about that? The issue should have been fixed https://github.com/valor-software/ngx-bootstrap/issues/5286

latusdenis avatar Sep 17 '20 15:09 latusdenis

@latusdenis Here is how I solved it in my case.

The template still looks the same, just without [minDate]="minDate" property binding:

<bs-datepicker-inline
    [bsValue]="value"
    [bsConfig]="bsConfig"
    [maxDate]="maxDate"
    (bsValueChange)="onDateChange($event)"
></bs-datepicker-inline>

Inside the component I've just added few lines of code:

onDateChange(newValue: Date) {
    const newMinDate = new Date(2020, 0, 1); // Set your new "minDate" value
    this.bsConfig = { ...this.bsConfig, minDate: newMinDate }; // Update the "bsConfig" property

    // ... do whatever else you want, as with the line above the "minDate" for Date picker 
    // should work the same as if you've set:  [minDate]="minDate" inside the template

I hope this helps, but if you have any specific problem that is not solved with my example, feel free to message me and I'll try to help.

And also I hope this will be fixed asap, so that we don't need to do this workaround anymore 😉

frezo00 avatar Sep 20 '20 16:09 frezo00

@frezo00 The proposed solution seems to not be working for me. The config gets updated however the new min date does not get applied on the picker. Using version 5.6.1. Any updates on this ?

adrianmanduc avatar Sep 23 '20 15:09 adrianmanduc

@adrianmanduc Have you tried experimenting with the ChangeDetectorRef to manually trigger change detection in the Angular which may help you with minDate config getting applied? Try adding it as a Dependency Injection:

constructor(private _cdRef: ChangeDetectorRef) {}`

And inside the method (where you change configs) try adding:

onDateChange(newValue: Date) {
    const newMinDate = new Date(2020, 0, 1); // Set your new "minDate" value
    this.bsConfig = { ...this.bsConfig, minDate: newMinDate }; // Update the "bsConfig" property
    
    // ...do other stuff if needed

    this._cdRef.datectChanges(); // or try: this.cdRef.markForCheck()
}

I hope this helps 😄

frezo00 avatar Oct 06 '20 08:10 frezo00

Hi! I'm facing the same issue, any idea when this will be fixed? Thanks!

Symro avatar Dec 15 '20 14:12 Symro

Hello! I'm also facing the same issue and the solution proposed by @frezo00 doesn't work for me. I downgraded to 5.5.0 to get my work done, but you have any idea when this will be fixed? Thx!

gabtoschi avatar May 28 '21 13:05 gabtoschi

Hi, I'm stuck with similar case... Any update for this issue? Thx! ;)

ghost avatar Jun 26 '21 20:06 ghost

Hey, we've just run into the same issue using the inline datepicker and ended up finding a possible fix for this.

The problem seems to be the setConfig method inside the date picker directive.

This happens every time you change any input except bsConfig, so the Problem does not only apply to minDate.

After the config gets updated, this code in BsDatepickerInlineDirective:

    this._datepickerRef = this._datepicker
      .provide({ provide: BsDatepickerConfig, useValue: this._config })
      .attach(BsDatepickerInlineContainerComponent)
      .to(this._elementRef)
      .show();

Creates a new this._datepickerRef.instance and the subscriptions that are setup in ngOnInit are no longer subscribing to the value changes of the current datepicker instance.

We had to build our own datepicker directive and manually resubscribe to the _datepickerRef.instance.valueChange Observable:

    this._datepickerRef = this._datepicker
      .provide({ provide: BsDatepickerConfig, useValue: this._config })
      .attach(BsDatepickerInlineContainerComponent)
      .to(this._elementRef)
      .show();

    // Creates possible memory leaks if previous subscriptions are not cleaned up!
    if (this._datepickerRef.instance) {
      this._subs.push(
        this._datepickerRef.instance.valueChange.subscribe((value: Date) => {
          this.bsValue = value;
        }),
      );
    }

This is not a perfect solution though.

I opened up a PR with a more complete fix to this.

JoschuaSchneider avatar Jul 08 '21 15:07 JoschuaSchneider

@JoschuaSchneider do you have any update on the state of this fix? I'm currently stuck in my project because your PR hasn't been approved yet. From what I see it failed some of the tests.

rfrcarvalho avatar Oct 06 '21 10:10 rfrcarvalho

I don't have an update on this yet.

A few people asked already and there has been some progress on it as they are working through the open PRs.

We shipped a patch of this locally and will remove it once this gets merged.

The failing tests do not indicate the progress of the PR though because the PR is created from the development branch.

JoschuaSchneider avatar Oct 06 '21 11:10 JoschuaSchneider

Any update on this fix yet? Instances where we have start date and end date with interdependent min and max dates are again one of the use cases where this gap is prevalent.

i-Chan93 avatar Apr 19 '22 10:04 i-Chan93

any update? Facing issue with ngx-bootrap 7.1.2 <bs-daterangepicker-inline [datesEnabled]="availableDates" [bsConfig]="{ showWeekNumbers: false }" (bsValueChange)="selectedRange($event)" [bsValue]="bsInlineRangeValue"

Mangesh5668 avatar Nov 09 '22 17:11 Mangesh5668

Solved this after upgrading to V8.0.0

Mangesh5668 avatar Nov 09 '22 17:11 Mangesh5668