mirror of
https://github.com/Sea-Haven-Industries/shoc-frontend-new.git
synced 2026-09-30 13:53:12 +00:00
fix(work-orders): allow read-only open for canceled board rows
This commit is contained in:
parent
32609659b7
commit
fef7918f6b
2 changed files with 83 additions and 43 deletions
|
|
@ -3,7 +3,7 @@ import { Eye, Pencil } from "lucide-react";
|
|||
type WoTableRowActionsProps = {
|
||||
onView: () => void;
|
||||
|
||||
onEdit: () => void;
|
||||
onEdit?: () => void;
|
||||
};
|
||||
|
||||
export function WoTableRowActions({ onView, onEdit }: WoTableRowActionsProps) {
|
||||
|
|
@ -61,7 +61,7 @@ export function WoTableRowActions({ onView, onEdit }: WoTableRowActionsProps) {
|
|||
<div className="flex items-center justify-end gap-1 opacity-0 transition-opacity group-hover/row:opacity-100">
|
||||
{mk(Eye, "View details", onView, "#e6f4fb", "var(--primary)")}
|
||||
|
||||
{mk(Pencil, "Edit", onEdit, "#e6f4fb", "var(--primary)")}
|
||||
{onEdit ? mk(Pencil, "Edit", onEdit, "#e6f4fb", "var(--primary)") : null}
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -85,23 +85,37 @@ export function WoTableRow({
|
|||
}
|
||||
|
||||
const patchAndMaybeAuto = (patch: Partial<WorkOrderTableRow>) => {
|
||||
if (isCanceled) return;
|
||||
const merged = { ...row, ...patch };
|
||||
const auto = maybeAutoSchedulePatch(merged);
|
||||
handlers.onPatch(row.id, { ...patch, ...auto });
|
||||
};
|
||||
|
||||
const patchRow = (patch: Partial<WorkOrderTableRow>) => {
|
||||
if (isCanceled) return;
|
||||
handlers.onPatch(row.id, patch);
|
||||
};
|
||||
|
||||
/** Block mutation controls on canceled rows while keeping row/View clickable. */
|
||||
const mutationCellStyle = isCanceled ? ({ pointerEvents: "none" } as const) : undefined;
|
||||
|
||||
return (
|
||||
<tr
|
||||
id={`wo-row-${row.id}`}
|
||||
draggable={!isCanceled}
|
||||
title={isCanceled ? "This work order has been cancelled" : undefined}
|
||||
onClick={() => handlers.onRowClick(row)}
|
||||
onDragStart={() => handlers.onDragStart(row.id)}
|
||||
onDragStart={() => {
|
||||
if (isCanceled) return;
|
||||
handlers.onDragStart(row.id);
|
||||
}}
|
||||
onDragOver={(e) => {
|
||||
if (isCanceled) return;
|
||||
e.preventDefault();
|
||||
handlers.onDragOver(row.id);
|
||||
}}
|
||||
onDrop={(e) => {
|
||||
if (isCanceled) return;
|
||||
e.preventDefault();
|
||||
handlers.onDrop();
|
||||
}}
|
||||
|
|
@ -112,7 +126,6 @@ export function WoTableRow({
|
|||
borderBottom: "1px solid var(--border)",
|
||||
borderTop: isDropTarget ? "2px solid var(--color-primary)" : undefined,
|
||||
opacity: isCanceled ? 0.45 : isDragging ? 0.4 : 1,
|
||||
pointerEvents: isCanceled ? "none" : undefined,
|
||||
background: isFlashing || isSelected ? "var(--color-primary-tint)" : "var(--card)",
|
||||
outline: isFlashing ? "2px solid var(--color-primary)" : "none",
|
||||
outlineOffset: isFlashing ? "-2px" : undefined,
|
||||
|
|
@ -131,23 +144,34 @@ export function WoTableRow({
|
|||
}}
|
||||
>
|
||||
<td
|
||||
style={{ padding: "0 0 0 6px", boxShadow: firstCellShadow }}
|
||||
style={{ padding: "0 0 0 6px", boxShadow: firstCellShadow, ...mutationCellStyle }}
|
||||
onClick={(e) => e.stopPropagation()}
|
||||
>
|
||||
<span
|
||||
className="flex items-center justify-center"
|
||||
style={{
|
||||
cursor: isDragging ? "grabbing" : "grab",
|
||||
cursor: isCanceled ? "default" : isDragging ? "grabbing" : "grab",
|
||||
color: "var(--color-text-muted)",
|
||||
}}
|
||||
>
|
||||
<GripVertical size={14} />
|
||||
</span>
|
||||
</td>
|
||||
<td style={{ padding: "0 2px 0 8px" }} onClick={(e) => e.stopPropagation()}>
|
||||
<FlagCell color={flagColor} onChange={(c) => handlers.setFlag(row.id, c)} />
|
||||
<td
|
||||
style={{ padding: "0 2px 0 8px", ...mutationCellStyle }}
|
||||
onClick={(e) => e.stopPropagation()}
|
||||
>
|
||||
<FlagCell
|
||||
color={flagColor}
|
||||
disabled={isCanceled}
|
||||
onChange={(c) => handlers.setFlag(row.id, c)}
|
||||
/>
|
||||
</td>
|
||||
<td className="group/cell" style={{ padding: "0 14px" }} onClick={(e) => e.stopPropagation()}>
|
||||
<td
|
||||
className="group/cell"
|
||||
style={{ padding: "0 14px", ...mutationCellStyle }}
|
||||
onClick={(e) => e.stopPropagation()}
|
||||
>
|
||||
<SiteCell
|
||||
value={row.site}
|
||||
location={row.location}
|
||||
|
|
@ -158,7 +182,7 @@ export function WoTableRow({
|
|||
sites={sites}
|
||||
q={search}
|
||||
onSave={(p) =>
|
||||
handlers.onPatch(row.id, {
|
||||
patchRow({
|
||||
site: p.site,
|
||||
location: p.location,
|
||||
locationId: p.locationId,
|
||||
|
|
@ -169,7 +193,7 @@ export function WoTableRow({
|
|||
}
|
||||
/>
|
||||
</td>
|
||||
<td style={{ padding: "0 14px", whiteSpace: "nowrap" }}>
|
||||
<td style={{ padding: "0 14px", whiteSpace: "nowrap", ...mutationCellStyle }}>
|
||||
<EditableWONumberCell
|
||||
value={row.woNumber}
|
||||
rescheduleCount={row.rescheduleCount}
|
||||
|
|
@ -177,18 +201,22 @@ export function WoTableRow({
|
|||
q={search}
|
||||
currentId={row.id}
|
||||
allOrders={allRows}
|
||||
onSave={(v) => handlers.onPatch(row.id, { woNumber: v })}
|
||||
onSave={(v) => patchRow({ woNumber: v })}
|
||||
onDuplicateFound={handlers.onDuplicateFound}
|
||||
/>
|
||||
</td>
|
||||
<td className="group/cell" style={{ padding: "0 14px" }} onClick={(e) => e.stopPropagation()}>
|
||||
<TypeCell
|
||||
value={row.type}
|
||||
q={search}
|
||||
onSave={(t) => handlers.onPatch(row.id, { type: t })}
|
||||
/>
|
||||
<td
|
||||
className="group/cell"
|
||||
style={{ padding: "0 14px", ...mutationCellStyle }}
|
||||
onClick={(e) => e.stopPropagation()}
|
||||
>
|
||||
<TypeCell value={row.type} q={search} onSave={(t) => patchRow({ type: t })} />
|
||||
</td>
|
||||
<td className="group/cell" style={{ padding: "0 14px" }} onClick={(e) => e.stopPropagation()}>
|
||||
<td
|
||||
className="group/cell"
|
||||
style={{ padding: "0 14px", ...mutationCellStyle }}
|
||||
onClick={(e) => e.stopPropagation()}
|
||||
>
|
||||
<AssignedToCell
|
||||
dispatcherId={row.dispatcherId}
|
||||
users={users}
|
||||
|
|
@ -196,7 +224,11 @@ export function WoTableRow({
|
|||
onSave={(id, name) => patchAndMaybeAuto({ dispatcherId: id, dispatcherName: name })}
|
||||
/>
|
||||
</td>
|
||||
<td className="group/cell" style={{ padding: "0 14px" }} onClick={(e) => e.stopPropagation()}>
|
||||
<td
|
||||
className="group/cell"
|
||||
style={{ padding: "0 14px", ...mutationCellStyle }}
|
||||
onClick={(e) => e.stopPropagation()}
|
||||
>
|
||||
<DateCell
|
||||
value={row.scheduledOn}
|
||||
q={search}
|
||||
|
|
@ -215,22 +247,25 @@ export function WoTableRow({
|
|||
}
|
||||
/>
|
||||
</td>
|
||||
<td className="group/cell" style={{ padding: "0 14px" }} onClick={(e) => e.stopPropagation()}>
|
||||
<DateCell
|
||||
value={row.dueDate}
|
||||
q={search}
|
||||
onSave={(date) => handlers.onPatch(row.id, { dueDate: date })}
|
||||
/>
|
||||
<td
|
||||
className="group/cell"
|
||||
style={{ padding: "0 14px", ...mutationCellStyle }}
|
||||
onClick={(e) => e.stopPropagation()}
|
||||
>
|
||||
<DateCell value={row.dueDate} q={search} onSave={(date) => patchRow({ dueDate: date })} />
|
||||
</td>
|
||||
<td className="group/cell" style={{ padding: "0 14px" }} onClick={(e) => e.stopPropagation()}>
|
||||
<PMTypeCell
|
||||
value={row.pm}
|
||||
pmTypes={pmTypes}
|
||||
q={search}
|
||||
onSave={(pm) => handlers.onPatch(row.id, { pm })}
|
||||
/>
|
||||
<td
|
||||
className="group/cell"
|
||||
style={{ padding: "0 14px", ...mutationCellStyle }}
|
||||
onClick={(e) => e.stopPropagation()}
|
||||
>
|
||||
<PMTypeCell value={row.pm} pmTypes={pmTypes} q={search} onSave={(pm) => patchRow({ pm })} />
|
||||
</td>
|
||||
<td className="group/cell" style={{ padding: "0 14px" }} onClick={(e) => e.stopPropagation()}>
|
||||
<td
|
||||
className="group/cell"
|
||||
style={{ padding: "0 14px", ...mutationCellStyle }}
|
||||
onClick={(e) => e.stopPropagation()}
|
||||
>
|
||||
<VendorCell
|
||||
company={row.company}
|
||||
tech={row.tech}
|
||||
|
|
@ -238,7 +273,7 @@ export function WoTableRow({
|
|||
vendors={vendors}
|
||||
q={search}
|
||||
onSave={(p) =>
|
||||
handlers.onPatch(row.id, {
|
||||
patchRow({
|
||||
company: p.company,
|
||||
tech: p.tech,
|
||||
techPhone: p.techPhone,
|
||||
|
|
@ -246,16 +281,21 @@ export function WoTableRow({
|
|||
}
|
||||
/>
|
||||
</td>
|
||||
<td className="group/cell" style={{ padding: "0 14px" }} onClick={(e) => e.stopPropagation()}>
|
||||
<ApptTimeCell
|
||||
apptTime={row.apptTime}
|
||||
onSave={(v) => handlers.onPatch(row.id, { apptTime: v })}
|
||||
/>
|
||||
<td
|
||||
className="group/cell"
|
||||
style={{ padding: "0 14px", ...mutationCellStyle }}
|
||||
onClick={(e) => e.stopPropagation()}
|
||||
>
|
||||
<ApptTimeCell apptTime={row.apptTime} onSave={(v) => patchRow({ apptTime: v })} />
|
||||
</td>
|
||||
<td className="group/cell" style={{ padding: "0 14px" }} onClick={(e) => e.stopPropagation()}>
|
||||
<td
|
||||
className="group/cell"
|
||||
style={{ padding: "0 14px", ...mutationCellStyle }}
|
||||
onClick={(e) => e.stopPropagation()}
|
||||
>
|
||||
<StatusCell
|
||||
wo={row}
|
||||
onChangeStatus={(status) => handlers.onPatch(row.id, { status })}
|
||||
onChangeStatus={(status) => patchRow({ status })}
|
||||
onOpenSlideOver={() => handlers.onOpenSlideOver(row)}
|
||||
onPastDueAttempt={() => handlers.onPastDueAttempt?.(row.id)}
|
||||
/>
|
||||
|
|
@ -272,7 +312,7 @@ export function WoTableRow({
|
|||
<td style={{ padding: "0 8px" }} onClick={(e) => e.stopPropagation()}>
|
||||
<WoTableRowActions
|
||||
onView={() => handlers.onView(row)}
|
||||
onEdit={() => handlers.onEdit(row)}
|
||||
onEdit={isCanceled ? undefined : () => handlers.onEdit(row)}
|
||||
/>
|
||||
</td>
|
||||
</tr>
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue