feature: users with treatment edit permission should now have working hours defined. the appointment grid is now being drawn based on the doctor's working hours.
This commit is contained in:
103
frontend/src/components/staff/StaffWorkingHoursStep.tsx
Normal file
103
frontend/src/components/staff/StaffWorkingHoursStep.tsx
Normal file
@@ -0,0 +1,103 @@
|
||||
'use client';
|
||||
|
||||
import { useEffect, useState } from 'react';
|
||||
import { WorkingHoursEditor } from '@/components/staff/WorkingHoursEditor';
|
||||
import {
|
||||
blocksFromEditorDays,
|
||||
editorDaysFromBlocks,
|
||||
emptyWorkingHoursEditorDays,
|
||||
validateEditorDays,
|
||||
type WorkingHoursEditorDay,
|
||||
} from '@/components/staff/workingHours';
|
||||
|
||||
interface StaffWorkingHoursStepProps {
|
||||
days: WorkingHoursEditorDay[];
|
||||
autoRepeatWeekly: boolean;
|
||||
onDaysChange: (days: WorkingHoursEditorDay[]) => void;
|
||||
onAutoRepeatWeeklyChange: (value: boolean) => void;
|
||||
onValidationChange?: (error: string | null) => void;
|
||||
disabled?: boolean;
|
||||
}
|
||||
|
||||
export function StaffWorkingHoursStep({
|
||||
days,
|
||||
autoRepeatWeekly,
|
||||
onDaysChange,
|
||||
onAutoRepeatWeeklyChange,
|
||||
onValidationChange,
|
||||
disabled,
|
||||
}: StaffWorkingHoursStepProps) {
|
||||
useEffect(() => {
|
||||
onValidationChange?.(validateEditorDays(days));
|
||||
}, [days, onValidationChange]);
|
||||
|
||||
return (
|
||||
<div className="space-y-3">
|
||||
<div className="rounded-[var(--radius-md)] border border-primary/25 bg-primary/5 px-3 py-3">
|
||||
<p className="text-sm text-text-primary font-medium">Working hours recommended</p>
|
||||
<p className="text-sm text-text-secondary mt-1">
|
||||
Staff with treatment edit access appear as provider columns in Appointments. Set their
|
||||
weekly hours so the schedule grid shows the right bookable times.
|
||||
</p>
|
||||
</div>
|
||||
<WorkingHoursEditor
|
||||
days={days}
|
||||
autoRepeatWeekly={autoRepeatWeekly}
|
||||
onDaysChange={onDaysChange}
|
||||
onAutoRepeatWeeklyChange={onAutoRepeatWeeklyChange}
|
||||
disabled={disabled}
|
||||
/>
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
export function createDefaultWorkingHoursState() {
|
||||
return {
|
||||
days: emptyWorkingHoursEditorDays(),
|
||||
autoRepeatWeekly: true,
|
||||
};
|
||||
}
|
||||
|
||||
export function workingHoursPayloadFromState(state: {
|
||||
days: WorkingHoursEditorDay[];
|
||||
autoRepeatWeekly: boolean;
|
||||
}) {
|
||||
return {
|
||||
autoRepeatWeekly: state.autoRepeatWeekly,
|
||||
blocks: blocksFromEditorDays(state.days),
|
||||
};
|
||||
}
|
||||
|
||||
export function workingHoursStateFromApi(data: {
|
||||
autoRepeatWeekly: boolean;
|
||||
blocks: { dayOfWeek: number; startMinute: number; endMinute: number; sortOrder?: number }[];
|
||||
}) {
|
||||
const hasBlocks = data.blocks.length > 0;
|
||||
return {
|
||||
days: hasBlocks ? editorDaysFromBlocks(data.blocks) : emptyWorkingHoursEditorDays(),
|
||||
autoRepeatWeekly: data.autoRepeatWeekly,
|
||||
};
|
||||
}
|
||||
|
||||
export function useWorkingHoursForm(initial?: {
|
||||
days: WorkingHoursEditorDay[];
|
||||
autoRepeatWeekly: boolean;
|
||||
}) {
|
||||
const [days, setDays] = useState(initial?.days ?? emptyWorkingHoursEditorDays());
|
||||
const [autoRepeatWeekly, setAutoRepeatWeekly] = useState(initial?.autoRepeatWeekly ?? true);
|
||||
const [validationError, setValidationError] = useState<string | null>(null);
|
||||
|
||||
return {
|
||||
days,
|
||||
setDays,
|
||||
autoRepeatWeekly,
|
||||
setAutoRepeatWeekly,
|
||||
validationError,
|
||||
setValidationError,
|
||||
reset(next?: { days: WorkingHoursEditorDay[]; autoRepeatWeekly: boolean }) {
|
||||
setDays(next?.days ?? emptyWorkingHoursEditorDays());
|
||||
setAutoRepeatWeekly(next?.autoRepeatWeekly ?? true);
|
||||
setValidationError(null);
|
||||
},
|
||||
};
|
||||
}
|
||||
Reference in New Issue
Block a user