From 49fa8b61eb0e4196713230f67fbb487f5be40255 Mon Sep 17 00:00:00 2001 From: Ricky Stretch Date: Sun, 29 Mar 2026 14:04:20 -0400 Subject: [PATCH] bug fix clean-up --- frontend/src/components/MobileEventForm.jsx | 25 ++++++++------------- frontend/src/components/SchedulePage.jsx | 20 +++-------------- frontend/src/index.css | 23 ------------------- 3 files changed, 12 insertions(+), 56 deletions(-) diff --git a/frontend/src/components/MobileEventForm.jsx b/frontend/src/components/MobileEventForm.jsx index 6948aea..e2eb0cb 100644 --- a/frontend/src/components/MobileEventForm.jsx +++ b/frontend/src/components/MobileEventForm.jsx @@ -74,26 +74,22 @@ function TimeInputMobile({ value, onChange }) { const [inputVal, setInputVal] = useState(fmt12(value)); const wrapRef = useRef(null); const listRef = useRef(null); - const inputRef = useRef(null); useEffect(() => { setInputVal(fmt12(value)); }, [value]); - // Programmatically disable autocomplete after mount - useEffect(() => { - if (inputRef.current) { - inputRef.current.setAttribute('autocomplete', 'off'); - inputRef.current.setAttribute('autocorrect', 'off'); - inputRef.current.setAttribute('autocapitalize', 'off'); - inputRef.current.setAttribute('spellcheck', 'false'); - } - }, []); - useEffect(() => { if (!open || !listRef.current) return; const idx = TIME_SLOTS.findIndex(s => s.value === value); if (idx >= 0) listRef.current.scrollTop = idx * 40 - 40; }, [open, value]); + useEffect(() => { + if (!open) return; + const h = e => { if (wrapRef.current && !wrapRef.current.contains(e.target)) setOpen(false); }; + document.addEventListener('mousedown', h); + return () => document.removeEventListener('mousedown', h); + }, [open]); + const commit = (raw) => { const parsed = parseTypedTime(raw); if (parsed) { onChange(parsed); setInputVal(fmt12(parsed)); } @@ -104,16 +100,13 @@ function TimeInputMobile({ value, onChange }) { return (
setInputVal(e.target.value)} onFocus={() => setOpen(true)} onBlur={e => setTimeout(() => commit(e.target.value), 150)} onKeyDown={e => { if (e.key === 'Enter') { e.preventDefault(); commit(inputVal); } if (e.key === 'Escape') { setInputVal(fmt12(value)); setOpen(false); } }} - autoComplete="nope" - data-autocomplete="off" - inputMode="none" + autoComplete="off" style={{ fontSize: 15, color: 'var(--primary)', fontWeight: 600, background: 'transparent', border: 'none', outline: 'none', cursor: 'text', width: 90 }} /> {open && ( @@ -492,7 +485,7 @@ export default function MobileEventForm({ event, eventTypes, userGroups, selecte {/* form wrapper suppresses Chrome Android's autofill chip bar; autoComplete="new-password" on individual inputs is ignored by Chrome but respected on the form element */} -
e.preventDefault()} style={{ flex:1,overflowY:'auto' }}> + e.preventDefault()} style={{ flex:1,overflowY:'auto' }}> {/* Title */}
setTitle(e.target.value)} autoComplete="new-password" placeholder="Add title" autoCorrect="off" autoCapitalize="sentences" spellCheck={false} style={{ width:'100%',border:'none',background:'transparent',fontSize:22,fontWeight:700,color:'var(--text-primary)',outline:'none' }}/> diff --git a/frontend/src/components/SchedulePage.jsx b/frontend/src/components/SchedulePage.jsx index eb1d6a7..3e8a715 100644 --- a/frontend/src/components/SchedulePage.jsx +++ b/frontend/src/components/SchedulePage.jsx @@ -149,22 +149,11 @@ function TimeInput({ value, onChange, style }) { const [inputVal, setInputVal] = useState(fmt12(value)); const wrapRef = useRef(null); const listRef = useRef(null); - const inputRef = useRef(null); // Keep display in sync when value changes externally useEffect(() => { setInputVal(fmt12(value)); }, [value]); - // Programmatically disable autocomplete after mount - useEffect(() => { - if (inputRef.current) { - inputRef.current.setAttribute('autocomplete', 'off'); - inputRef.current.setAttribute('autocorrect', 'off'); - inputRef.current.setAttribute('autocapitalize', 'off'); - inputRef.current.setAttribute('spellcheck', 'false'); - } - }, []); - - // Scroll the dropdown so the selected slot is near the top + // Scroll the dropdown so that selected slot is near the top useEffect(() => { if (!open || !listRef.current) return; const idx = TIME_SLOTS.findIndex(s => s.value === value); @@ -196,7 +185,6 @@ function TimeInput({ value, onChange, style }) { return (
{ if (e.key === 'Enter') { e.preventDefault(); commit(inputVal); } if (e.key === 'Escape') { setInputVal(fmt12(value)); setOpen(false); } }} style={{ width: '100%', cursor: 'text' }} - autoComplete="nope" - data-autocomplete="off" - inputMode="none" + autoComplete="off" placeholder="9:00 AM" /> {open && ( @@ -680,7 +666,7 @@ function EventForm({ event, userGroups, eventTypes, selectedDate, onSave, onCanc
{/* form wrapper suppresses Chrome Android's autofill chip bar; autoComplete="new-password" on individual inputs is ignored by Chrome but respected on the form element */} - e.preventDefault()}> + e.preventDefault()}>
{if(e.key==='Enter'&&e.target.tagName!=='TEXTAREA') e.preventDefault();}}> {/* Title */}
diff --git a/frontend/src/index.css b/frontend/src/index.css index c0dd2da..6ad822e 100644 --- a/frontend/src/index.css +++ b/frontend/src/index.css @@ -38,29 +38,6 @@ html { font-size: 100%; /* inherits system font size — allows Android accessibility font scaling */ } -/* Aggressively disable Chrome autocomplete on Android */ -input:-webkit-autofill, -input:-webkit-autofill:hover, -input:-webkit-autofill:focus, -textarea:-webkit-autofill, -textarea:-webkit-autofill:hover, -textarea:-webkit-autofill:focus { - -webkit-box-shadow: 0 0 0 1000px white inset !important; - background-color: white !important; - background-image: none !important; - transition: background-color 5000s ease-in-out 0s !important; -} - -/* Disable autocomplete dropdown/panel */ -input::-webkit-credentials-auto-fill-button, -input::-webkit-contacts-auto-fill-button { - display: none !important; - visibility: hidden !important; - pointer-events: none !important; - position: absolute !important; - right: 0 !important; -} - button { font-family: var(--font); cursor: pointer; border: none; background: none; } input, textarea { font-family: var(--font); } a { color: inherit; text-decoration: none; }