* esm * wip * wip * wip * wip * wip * wip * subscription notice * wip * wip * wip * fix envs * fix: update docker build * fix * esm/types * delete dashboard :D * add patches to dockerfiles * update packages + catalogs + ts * wip * remove native libs * ts * improvements * fix redirects and fetching session * try fix favicon * fixes * fix * order and resize reportds within a dashboard * improvements * wip * added userjot to dashboard * fix * add op * wip * different cache key * improve date picker * fix table * event details loading * redo onboarding completely * fix login * fix * fix * extend session, billing and improve bars * fix * reduce price on 10M
89 lines
2.3 KiB
TypeScript
89 lines
2.3 KiB
TypeScript
import { pushModal } from '@/modals';
|
|
import { format, isValid, parseISO } from 'date-fns';
|
|
import { CalendarIcon } from 'lucide-react';
|
|
import { type InputHTMLAttributes, useEffect, useState } from 'react';
|
|
import { WithLabel } from '../forms/input-with-label';
|
|
import { Input } from './input';
|
|
|
|
export function InputDateTime({
|
|
value,
|
|
onChange,
|
|
placeholder = 'Select date and time',
|
|
label,
|
|
...props
|
|
}: {
|
|
value: string | undefined;
|
|
onChange: (value: string) => void;
|
|
label: string;
|
|
} & InputHTMLAttributes<HTMLInputElement>) {
|
|
const [internalValue, setInternalValue] = useState(value ?? '');
|
|
|
|
useEffect(() => {
|
|
if (value !== internalValue) {
|
|
setInternalValue(value ?? '');
|
|
}
|
|
}, [value]);
|
|
|
|
// Convert string to Date for modal
|
|
const getDateFromValue = (dateString: string): Date => {
|
|
if (!dateString) return new Date();
|
|
|
|
try {
|
|
const date = parseISO(dateString);
|
|
return isValid(date) ? date : new Date();
|
|
} catch {
|
|
return new Date();
|
|
}
|
|
};
|
|
|
|
// Format date for display
|
|
const getDisplayValue = (dateString: string): string => {
|
|
if (!dateString) return '';
|
|
|
|
try {
|
|
const date = parseISO(dateString);
|
|
return isValid(date) ? format(date, 'MM/dd/yyyy HH:mm') : dateString;
|
|
} catch {
|
|
return dateString;
|
|
}
|
|
};
|
|
|
|
const handleDateTimeSelect = () => {
|
|
pushModal('DateTimePicker', {
|
|
initialDate: getDateFromValue(value || ''),
|
|
title: 'Select Date & Time',
|
|
onChange: (selectedDate: Date) => {
|
|
const isoString = selectedDate.toISOString();
|
|
setInternalValue(isoString);
|
|
onChange(isoString);
|
|
},
|
|
});
|
|
};
|
|
|
|
return (
|
|
<WithLabel label={label}>
|
|
<div
|
|
className="relative w-full cursor-pointer"
|
|
onClick={handleDateTimeSelect}
|
|
onKeyDown={(e) => {
|
|
if (e.key === 'Enter' || e.key === ' ') {
|
|
handleDateTimeSelect();
|
|
}
|
|
}}
|
|
>
|
|
<Input
|
|
{...props}
|
|
value={getDisplayValue(value || '')}
|
|
placeholder={placeholder}
|
|
readOnly
|
|
className="cursor-pointer pr-10"
|
|
size="default"
|
|
/>
|
|
<div className="absolute right-4 top-1/2 -translate-y-1/2 pointer-events-none">
|
|
<CalendarIcon className="h-4 w-4 text-muted-foreground" />
|
|
</div>
|
|
</div>
|
|
</WithLabel>
|
|
);
|
|
}
|