Files
babymonitor/frontend/src/components/stats/SettingsPopover.tsx
T
2026-04-24 08:02:13 +02:00

118 lines
4.2 KiB
TypeScript

import React, { useState, useRef, useEffect } from 'react';
interface SettingsPopoverProps {
dayStart: string;
dayEnd: string;
wakeupRef: string;
bedtimeRef: string;
onSave: (settings: { dayStart: string; dayEnd: string; wakeupRef: string; bedtimeRef: string }) => void;
}
export function SettingsPopover({ dayStart, dayEnd, wakeupRef, bedtimeRef, onSave }: SettingsPopoverProps) {
const [isOpen, setIsOpen] = useState(false);
const [localDayStart, setLocalDayStart] = useState(dayStart);
const [localDayEnd, setLocalDayEnd] = useState(dayEnd);
const [localWakeupRef, setLocalWakeupRef] = useState(wakeupRef);
const [localBedtimeRef, setLocalBedtimeRef] = useState(bedtimeRef);
const popoverRef = useRef<HTMLDivElement>(null);
useEffect(() => {
setLocalDayStart(dayStart);
setLocalDayEnd(dayEnd);
setLocalWakeupRef(wakeupRef);
setLocalBedtimeRef(bedtimeRef);
}, [dayStart, dayEnd, wakeupRef, bedtimeRef]);
useEffect(() => {
const handleClickOutside = (e: MouseEvent) => {
if (popoverRef.current && !popoverRef.current.contains(e.target as Node)) {
setIsOpen(false);
}
};
if (isOpen) {
document.addEventListener('mousedown', handleClickOutside);
}
return () => document.removeEventListener('mousedown', handleClickOutside);
}, [isOpen]);
const handleSave = () => {
onSave({
dayStart: localDayStart,
dayEnd: localDayEnd,
wakeupRef: localWakeupRef,
bedtimeRef: localBedtimeRef,
});
setIsOpen(false);
};
return (
<div className="relative" ref={popoverRef}>
<button
onClick={() => setIsOpen(!isOpen)}
className="p-2 text-gray-500 hover:text-gray-700"
aria-label="Settings"
>
<svg className="w-5 h-5" fill="none" stroke="currentColor" viewBox="0 0 24 24">
<path strokeLinecap="round" strokeLinejoin="round" strokeWidth={2} d="M10.325 4.317c.426-1.756 2.924-1.756 3.35 0a1.724 1.724 0 002.573 1.066c1.543-.94 3.31.826 2.37 2.37a1.724 1.724 0 001.065 2.572c1.756.426 1.756 2.924 0 3.35a1.724 1.724 0 00-1.066 2.573c.94 1.543-.826 3.31-2.37 2.37a1.724 1.724 0 00-2.572 1.065c-.426 1.756-2.924 1.756-3.35 0a1.724 1.724 0 00-2.573-1.066c-1.543.94-3.31-.826-2.37-2.37a1.724 1.724 0 00-1.065-2.572c-1.756-.426-1.756-2.924 0-3.35a1.724 1.724 0 001.066-2.573c-.94-1.543.826-3.31 2.37-2.37.996.608 2.296.07 2.572-1.065z" />
<path strokeLinecap="round" strokeLinejoin="round" strokeWidth={2} d="M15 12a3 3 0 11-6 0 3 3 0 016 0z" />
</svg>
</button>
{isOpen && (
<div className="absolute right-0 top-full mt-2 w-64 bg-white rounded-xl shadow-lg border border-gray-200 p-4 z-50">
<h4 className="font-semibold text-gray-800 mb-4">Settings</h4>
<div className="space-y-3">
<div>
<label htmlFor="day-start" className="block text-xs text-gray-500 mb-1">Day starts (HH:MM)</label>
<input
id="day-start"
type="time"
value={localDayStart}
onChange={(e) => setLocalDayStart(e.target.value)}
className="w-full p-2 border rounded-md text-sm"
/>
</div>
<div>
<label htmlFor="day-end" className="block text-xs text-gray-500 mb-1">Day ends (HH:MM)</label>
<input
id="day-end"
type="time"
value={localDayEnd}
onChange={(e) => setLocalDayEnd(e.target.value)}
className="w-full p-2 border rounded-md text-sm"
/>
</div>
<div>
<label htmlFor="wakeup-ref" className="block text-xs text-gray-500 mb-1">Wakeup ref (HH:MM)</label>
<input
id="wakeup-ref"
type="time"
value={localWakeupRef}
onChange={(e) => setLocalWakeupRef(e.target.value)}
className="w-full p-2 border rounded-md text-sm"
/>
</div>
<div>
<label htmlFor="bedtime-ref" className="block text-xs text-gray-500 mb-1">Bedtime ref (HH:MM)</label>
<input
id="bedtime-ref"
type="time"
value={localBedtimeRef}
onChange={(e) => setLocalBedtimeRef(e.target.value)}
className="w-full p-2 border rounded-md text-sm"
/>
</div>
</div>
<button
onClick={handleSave}
className="w-full mt-4 py-2 bg-blue-600 text-white rounded-md text-sm font-medium hover:bg-blue-700"
>
Save
</button>
</div>
)}
</div>
);
}