feat(timeline): add inline allocation editor on double-click
Double-clicking an allocation bar opens an inline editor overlay with start date, end date, and hours/day fields. Saves via trpc.allocation.update, closes on Escape or click outside. Only visible to users with manage permissions. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -39,6 +39,7 @@ import type { TimelineVisualOverrides } from "./allocationVisualState.js";
|
||||
import { SuccessToast } from "~/components/ui/SuccessToast.js";
|
||||
import { useTimelineKeyboard } from "~/hooks/useTimelineKeyboard.js";
|
||||
import { KeyboardShortcutOverlay } from "./KeyboardShortcutOverlay.js";
|
||||
import { InlineAllocationEditor } from "./InlineAllocationEditor.js";
|
||||
|
||||
// ─── Entry point ────────────────────────────────────────────────────────────
|
||||
// Two-layer mount: the outer shell creates drag state + project context,
|
||||
@@ -397,6 +398,14 @@ function TimelineViewContent({
|
||||
},
|
||||
});
|
||||
|
||||
const [inlineEditTarget, setInlineEditTarget] = useState<{
|
||||
allocationId: string;
|
||||
startDate: Date;
|
||||
endDate: Date;
|
||||
hoursPerDay: number;
|
||||
barRect: DOMRect;
|
||||
} | null>(null);
|
||||
|
||||
const hasActivePointerOverlay =
|
||||
dragState.isDragging || allocDragState.isActive || rangeState.isSelecting || multiSelectState.isMultiDragging;
|
||||
|
||||
@@ -799,6 +808,7 @@ function TimelineViewContent({
|
||||
multiSelectState={multiSelectState}
|
||||
optimisticAllocations={optimisticAllocations}
|
||||
suppressHoverInteractions={hasActivePointerOverlay}
|
||||
{...(!isSelfServiceTimeline ? { onInlineEdit: (id: string, vals: { startDate: Date; endDate: Date; hoursPerDay: number }, rect: DOMRect) => setInlineEditTarget({ allocationId: id, ...vals, barRect: rect }) } : {})}
|
||||
CELL_WIDTH={CELL_WIDTH}
|
||||
dates={dates}
|
||||
totalCanvasWidth={totalCanvasWidth}
|
||||
@@ -1096,6 +1106,19 @@ function TimelineViewContent({
|
||||
/>
|
||||
)}
|
||||
|
||||
{/* Inline allocation editor */}
|
||||
{inlineEditTarget && (
|
||||
<InlineAllocationEditor
|
||||
allocationId={inlineEditTarget.allocationId}
|
||||
initialStartDate={inlineEditTarget.startDate}
|
||||
initialEndDate={inlineEditTarget.endDate}
|
||||
initialHoursPerDay={inlineEditTarget.hoursPerDay}
|
||||
barRect={inlineEditTarget.barRect}
|
||||
onClose={() => setInlineEditTarget(null)}
|
||||
onSaved={() => setInlineEditTarget(null)}
|
||||
/>
|
||||
)}
|
||||
|
||||
{/* Keyboard shortcut overlay */}
|
||||
{showShortcuts && <KeyboardShortcutOverlay onClose={() => setShowShortcuts(false)} />}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user