Replace native date/time inputs with DatePicker across calendar and todo forms
- EventForm + EventDetailPanel: native <Input type=date|datetime-local> → DatePicker with dynamic mode via all_day toggle - TodoForm + TodoDetailPanel: merge date + time into single datetime DatePicker, remove separate time input, move recurrence select into 2-col grid beside date picker Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
parent
e20c04ac4f
commit
6cd648f3a8
@ -13,6 +13,7 @@ import { formatUpdatedAt } from '@/components/shared/utils';
|
||||
import CopyableField from '@/components/shared/CopyableField';
|
||||
import { Button } from '@/components/ui/button';
|
||||
import { Input } from '@/components/ui/input';
|
||||
import { DatePicker } from '@/components/ui/date-picker';
|
||||
import { Textarea } from '@/components/ui/textarea';
|
||||
import { Select } from '@/components/ui/select';
|
||||
import { Checkbox } from '@/components/ui/checkbox';
|
||||
@ -633,22 +634,24 @@ export default function EventDetailPanel({
|
||||
<div className="grid grid-cols-2 gap-3">
|
||||
<div className="space-y-1">
|
||||
<Label htmlFor="panel-start" required>Start</Label>
|
||||
<Input
|
||||
<DatePicker
|
||||
variant="input"
|
||||
id="panel-start"
|
||||
type={editState.all_day ? 'date' : 'datetime-local'}
|
||||
mode={editState.all_day ? 'date' : 'datetime'}
|
||||
value={editState.start_datetime}
|
||||
onChange={(e) => updateField('start_datetime', e.target.value)}
|
||||
onChange={(v) => updateField('start_datetime', v)}
|
||||
className="text-xs"
|
||||
required
|
||||
/>
|
||||
</div>
|
||||
<div className="space-y-1">
|
||||
<Label htmlFor="panel-end">End</Label>
|
||||
<Input
|
||||
<DatePicker
|
||||
variant="input"
|
||||
id="panel-end"
|
||||
type={editState.all_day ? 'date' : 'datetime-local'}
|
||||
mode={editState.all_day ? 'date' : 'datetime'}
|
||||
value={editState.end_datetime}
|
||||
onChange={(e) => updateField('end_datetime', e.target.value)}
|
||||
onChange={(v) => updateField('end_datetime', v)}
|
||||
className="text-xs"
|
||||
/>
|
||||
</div>
|
||||
|
||||
@ -13,6 +13,7 @@ import {
|
||||
SheetClose,
|
||||
} from '@/components/ui/sheet';
|
||||
import { Input } from '@/components/ui/input';
|
||||
import { DatePicker } from '@/components/ui/date-picker';
|
||||
import { Textarea } from '@/components/ui/textarea';
|
||||
import { Select } from '@/components/ui/select';
|
||||
import { Label } from '@/components/ui/label';
|
||||
@ -281,22 +282,24 @@ export default function EventForm({ event, templateData, templateName, initialSt
|
||||
<div className="grid grid-cols-2 gap-4">
|
||||
<div className="space-y-2">
|
||||
<Label htmlFor="start" required>Start</Label>
|
||||
<Input
|
||||
<DatePicker
|
||||
variant="input"
|
||||
id="start"
|
||||
type={formData.all_day ? 'date' : 'datetime-local'}
|
||||
mode={formData.all_day ? 'date' : 'datetime'}
|
||||
value={formData.start_datetime}
|
||||
onChange={(e) => setFormData({ ...formData, start_datetime: e.target.value })}
|
||||
onChange={(v) => setFormData({ ...formData, start_datetime: v })}
|
||||
required
|
||||
/>
|
||||
</div>
|
||||
|
||||
<div className="space-y-2">
|
||||
<Label htmlFor="end">End</Label>
|
||||
<Input
|
||||
<DatePicker
|
||||
variant="input"
|
||||
id="end"
|
||||
type={formData.all_day ? 'date' : 'datetime-local'}
|
||||
mode={formData.all_day ? 'date' : 'datetime'}
|
||||
value={formData.end_datetime}
|
||||
onChange={(e) => setFormData({ ...formData, end_datetime: e.target.value })}
|
||||
onChange={(v) => setFormData({ ...formData, end_datetime: v })}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@ -389,38 +389,31 @@ export default function TodoDetailPanel({
|
||||
<DatePicker
|
||||
variant="input"
|
||||
id="todo-due-date"
|
||||
value={editState.due_date}
|
||||
onChange={(v) => updateField('due_date', v)}
|
||||
mode="datetime"
|
||||
value={editState.due_date ? (editState.due_date + 'T' + (editState.due_time || '00:00')) : ''}
|
||||
onChange={(v) => {
|
||||
updateField('due_date', v ? v.slice(0, 10) : '');
|
||||
updateField('due_time', v ? v.slice(11, 16) : '');
|
||||
}}
|
||||
className="text-xs"
|
||||
/>
|
||||
</div>
|
||||
<div className="space-y-1">
|
||||
<Label htmlFor="todo-due-time">Due Time</Label>
|
||||
<Input
|
||||
id="todo-due-time"
|
||||
type="time"
|
||||
value={editState.due_time}
|
||||
onChange={(e) => updateField('due_time', e.target.value)}
|
||||
<Label htmlFor="todo-recurrence">Recurrence</Label>
|
||||
<Select
|
||||
id="todo-recurrence"
|
||||
value={editState.recurrence_rule}
|
||||
onChange={(e) => updateField('recurrence_rule', e.target.value)}
|
||||
className="text-xs"
|
||||
/>
|
||||
>
|
||||
<option value="">None</option>
|
||||
<option value="daily">Daily</option>
|
||||
<option value="weekly">Weekly</option>
|
||||
<option value="monthly">Monthly</option>
|
||||
</Select>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="space-y-1">
|
||||
<Label htmlFor="todo-recurrence">Recurrence</Label>
|
||||
<Select
|
||||
id="todo-recurrence"
|
||||
value={editState.recurrence_rule}
|
||||
onChange={(e) => updateField('recurrence_rule', e.target.value)}
|
||||
className="text-xs"
|
||||
>
|
||||
<option value="">None</option>
|
||||
<option value="daily">Daily</option>
|
||||
<option value="weekly">Weekly</option>
|
||||
<option value="monthly">Monthly</option>
|
||||
</Select>
|
||||
</div>
|
||||
|
||||
{/* Save / Cancel at bottom */}
|
||||
<div className="flex items-center justify-end gap-2 pt-2 border-t border-border">
|
||||
<Button variant="outline" size="sm" onClick={handleEditCancel}>
|
||||
|
||||
@ -133,35 +133,30 @@ export default function TodoForm({ todo, onClose }: TodoFormProps) {
|
||||
<DatePicker
|
||||
variant="input"
|
||||
id="due_date"
|
||||
value={formData.due_date}
|
||||
onChange={(v) => setFormData({ ...formData, due_date: v })}
|
||||
mode="datetime"
|
||||
value={formData.due_date ? (formData.due_date + 'T' + (formData.due_time || '00:00')) : ''}
|
||||
onChange={(v) => setFormData({
|
||||
...formData,
|
||||
due_date: v ? v.slice(0, 10) : '',
|
||||
due_time: v ? v.slice(11, 16) : '',
|
||||
})}
|
||||
/>
|
||||
</div>
|
||||
|
||||
<div className="space-y-2">
|
||||
<Label htmlFor="due_time">Due Time</Label>
|
||||
<Input
|
||||
id="due_time"
|
||||
type="time"
|
||||
value={formData.due_time}
|
||||
onChange={(e) => setFormData({ ...formData, due_time: e.target.value })}
|
||||
/>
|
||||
<Label htmlFor="recurrence">Recurrence</Label>
|
||||
<Select
|
||||
id="recurrence"
|
||||
value={formData.recurrence_rule}
|
||||
onChange={(e) => setFormData({ ...formData, recurrence_rule: e.target.value })}
|
||||
>
|
||||
<option value="">None</option>
|
||||
<option value="daily">Daily</option>
|
||||
<option value="weekly">Weekly</option>
|
||||
<option value="monthly">Monthly</option>
|
||||
</Select>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="space-y-2">
|
||||
<Label htmlFor="recurrence">Recurrence</Label>
|
||||
<Select
|
||||
id="recurrence"
|
||||
value={formData.recurrence_rule}
|
||||
onChange={(e) => setFormData({ ...formData, recurrence_rule: e.target.value })}
|
||||
>
|
||||
<option value="">None</option>
|
||||
<option value="daily">Daily</option>
|
||||
<option value="weekly">Weekly</option>
|
||||
<option value="monthly">Monthly</option>
|
||||
</Select>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<SheetFooter>
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user