wojtekmaj / react-calendar

Ultimate calendar for your React app.
https://projects.wojtekmaj.pl/react-calendar
MIT License
3.46k stars 497 forks source link

multiple select end date wrong? #930

Closed MichaelLiss closed 3 months ago

MichaelLiss commented 3 months ago

Before you start - checklist

Description

here is my code react code

import React from 'react';
import { useState } from 'react';

import './Availability.css';

import Calendar from 'react-calendar';
import { differenceInCalendarDays } from 'date-fns';

import { useAppContext } from '../context/appContextProvider';

const Availability = () => {
  const { isLoggedIn } = useAppContext();
  const [selectedDates, setSelectedDates] = useState(new Date());

  const bookingAvailable = (date) => {
    return true; // for demo.. just return it for every day
  };

  function addMonthsToDate(inputDate, months) {
    // Clone the input date to avoid modifying the original object
    var newDate = new Date(inputDate);

    // Get the current month and year
    var currentMonth = newDate.getMonth();
    var currentYear = newDate.getFullYear();

    // Calculate the new month and year after adding months
    var newMonth = (currentMonth + months) % 12;
    var newYear = currentYear + Math.floor((currentMonth + months) / 12);

    // Set the new month and year to the date object
    newDate.setMonth(newMonth);
    newDate.setFullYear(newYear);

    return newDate;
  }

  let now = new Date();
  let maxDate= addMonthsToDate(now, 12);

  const disabledDates = ['3-22-2024'];

  function tileDisabled({ date, view }) {
    // Disable tiles in month view only
    if (view === 'month') {
      // Check if a date React-Calendar wants to check is on the list of disabled dates
      return disabledDates.find((dDate) => isSameDay(dDate, date));
    }
  }

  function isSameDay(a, b) {
    return differenceInCalendarDays(a, b) === 0;
  }

  console.log('value', JSON.stringify(selectedDates));

  return (
    <div>
      <div>
        <h2>Availability</h2>
        {isLoggedIn && <p>Prices</p>}
      </div>
      <div>{JSON.stringify(selectedDates)}</div>
      <div className="fill-window">
        <Calendar
          onChange={setSelectedDates}
          calendarType="gregory"
          hover
          minDate={now}
          maxDate={maxDate}
          value={selectedDates}
          tileDisabled={tileDisabled}
          selectRange={true}
          tileContent={({ activeStartDate, date, view }) => {
            if (1) {
              if (bookingAvailable(date)) {
                return (
                  <div className="container">
                    <div>Available</div>
                    <div>1</div>
                  </div>
                );
              } else {
                return null;
              }
            }
          }}
        />
      </div>
    </div>
  );
};

export default Availability;

Steps to reproduce

I clicked on 1 Apr 2024 and then extended selection to 3 Apr 2024 and clicked on 3 Apr 2024

Expected behavior

I would expect the selected dates to be 1 Apr 2024 to 3 Apr 2024

Actual behavior

const [selectedDates, setSelectedDates] = useState(new Date());

selectedDates is 1 Apr 2024 to 4 Apr 2024

Additional information

image

Environment

wojtekmaj commented 3 months ago

Dates in JavaScript, upon stringification, are represented as ISO timestamps. 2024-04-04 5:59 in London is 2024-04-03 23:59 your time.

MichaelLiss commented 3 months ago

Dates in JavaScript, upon stringification, are represented as ISO timestamps. 2024-04-04 5:59 in London is 2024-04-03 23:59 your time.

Hi...

I think that if there is a calendar control that deals with dates .. .the hours - minutes - seconds should not matter.

The control does not have a "time" specified of the day you wish to start... it merely gives dates - I am selecting a date range from 1 Apr 2024 to 3 Apr 2024 - the date range returned should be 1 Apr 2024 to 3 Apr 2024.

The 'disabled' dates do not suggest an hours/minutes/seconds: const disabledDates = ['3-22-2024'];

additionally, the function that sets the 'range of valid dates' ( in my example code addMonthsToDate ) does not take into account hours/minutes/seconds

so I am confused the control deals with years/months/days in some aspects and hours/minutes/seconds in others