pushtell / react-bootstrap-date-picker

React-Bootstrap based date picker.
MIT License
346 stars 195 forks source link

The selected month resets when the component is rendered #162

Open lstorey opened 6 years ago

lstorey commented 6 years ago

Table of Contents

Expected Behavior

If the date picker is open, the month should not change to the selected month when the component rerenders.

Current Behavior

The month resets when the component is rerendered while the date picker is open.

Possible Solution

Steps to Reproduce (for bugs)

  1. Select a date in November and close the date picker.
  2. Open the date picker and navigate to December.
  3. Date Picker rerenders due to some change in the props somewhere in the parent tree.
  4. The date picker now shows November again. I expect it to still be showing December since it has not been closed and a value has not been selected.

Context

We have data changes that cause a rerender at least once per second. This bug effectively means that you cannot select a date in another month.

As a temporary fix, I created a wrapper which uses componentShouldUpdate to only update the component when value changes. This is not ideal because it prevents the month from resetting to the selected value when the date picker is closed and opened again. It also prevents updates to other props, which is not a problem for my use case.

Your Environment

jasonpastor commented 5 years ago

I think the problem stems from the "makeDateValues" function. When this function is called, it resets the "displayDate" to the "selectedDate". In particular, when the componentWillReceiveProps method is called on the DatePicker, it attempts to check for value changes prior to calling "makeDateValues". However, in my case, the values weren't matching because of the time on the date value. The component sets the time on the internal dates to "12:00:00.000Z". I was able to workaround the issue by manipulating the value string in the same was as the internal component prior to setting the property.

For example:

render() {
  let dateString = this.state.date.toISOString().slice(0,10) + 'T12:00:00.000Z';
  return <DatePicker value={dateString} .../>
}

Perhaps a better fix would be for the "componentWillReceiveProps" function to compare only the date parts of the current and new value.