sendou.ink/app/components/DateInput.tsx
William Lam 09851faf83
New Date entry on the new Calendar page is now based off the previous one (#1070)
* Issue 858: On the new calendar page adding a new Date entry with the "Add" button will now insert a new date with an offset of +24 hours of the previous row's date value.

* Added comment to ignore the TSLint "object can be null" error

* Changed `var` to `const`

* Fixed Prettier checks in CI pipeline

* Fixed Typecheck CI pipeline error

* Moved getDateWithHoursOffset() function to app/utils/dates.ts

* Added new line at end of file

* Added getValidNewDateIfInvalid() function. This retrieves a valid date. If invalid, get a new Date object.
- So now, if we intentionally/accidentally delete the data in the Calendar's DateInput element, it will be reset to the current Date/Time

* Refactored DateInput component's update state mechanism to be handled by an onChange() function defined in the parent component that is passed to the child

* Prettier formatting so that the new CI pipeline won't output errors at me

* Removed unused imported types

* Removed the datesCount React Hook & refactored accordingly

* Removed unused loader-related variables

* DateInput onChange prop is now optional

* Instead of generating a new Array, iterate over DateInput's inputState's array instead

* Fix potential undefined error

* DatesInputState: refactored to remove index & access the index during iteration with map() 2nd arg

* Properly initialized state for pre-existing events =)
- Also added TODO comments for improving date input handling (1082)

* Prettier formatting

* Uncommented console.warn()

* Touched up comment
2022-10-31 03:59:51 +01:00

65 lines
1.6 KiB
TypeScript

import { useIsMounted } from "~/hooks/useIsMounted";
import { dateToYearMonthDayHourMinuteString, isValidDate } from "~/utils/dates";
import * as React from "react";
export function DateInput({
id,
name,
defaultValue,
min,
max,
required,
onChange,
}: {
id?: string;
name?: string;
defaultValue?: Date;
min?: Date;
max?: Date;
required?: boolean;
onChange?: (newDate: Date) => void;
}) {
const [date, setDate] = React.useState(defaultValue ?? new Date());
const isMounted = useIsMounted();
if (!isMounted) {
return (
<input
id={id}
type="datetime-local"
name={name}
required={required}
disabled
/>
);
}
return (
<>
{date && <input name={name} type="hidden" value={date.getTime()} />}
<input
id={id}
type="datetime-local"
value={dateToYearMonthDayHourMinuteString(date)}
min={min ? dateToYearMonthDayHourMinuteString(min) : undefined}
max={max ? dateToYearMonthDayHourMinuteString(max) : undefined}
onChange={(e) => {
//TODO: fix invalid Date Input handling: https://github.com/Sendouc/sendou.ink/issues/1082
const updatedDate = new Date(e.target.value);
if (!isValidDate(updatedDate)) {
console.warn("Invalid date");
// throw new RangeError("Invalid Date");
}
setDate(updatedDate);
// Update the correct entry in the React hook from the parent via the passed on callback function
if (typeof onChange !== "undefined") {
onChange(updatedDate);
}
}}
required={required}
/>
</>
);
}