const [isOpenList, setIsOpenList] = useState<boolean>(false)
const [autoList, setAutoList] = useState<string[]>([])
const [cursorIdx, setCursorIdx] = useState<number>(-1)
const dropdownRef = useRef<React.LegacyRef<HTMLUListElement> | undefined>()
const onChangeHandler = (e: ChangeEvent<HTMLInputElement>) => {
const { value } = e.target
setCategoryValue({
...categoryValue,
categoryName: value,
})
if (value === '') {
setAutoList([])
} else {
setAutoList(ITEM_CREATE_TITLE_LIST.filter((e) => e.includes(value)))
}
if (autoList.length > 0) {
setIsOpenList(true)
if (e.key === 'ArrowDown' && cursorIdx <= autoList.length - 2) {
setCursorIdx((idx) => idx + 1)
} else if (e.key === 'ArrowUp' && cursorIdx !== -1) {
setCursorIdx((idx) => idx - 1)
} else if (e.key === 'Enter' && cursorIdx !== -1) {
setCategoryValue({
...categoryValue,
categoryName: dropdownRef.current.children[cursorIdx].innerText,
})
setIsOpenList(false)
}
}
}
<div
style={{
display: 'flex',
flexDirection: 'column',
gap: '16px',
position: 'relative',
}}
>
<InputComponent
ph="카테고리명을 입력"
style={inputStyle}
onChange={(e) => onChangeHandler(e)}
type="text"
name="categoryName"
value={categoryName}
onKeyUp={(e) => onChangeHandler(e)}
/>
{isOpenList && (
<Automatic ref={dropdownRef}>
{autoList.map((list, idx) => (
<AutomaticItem
key={list}
onKeyUp={() => autoHandler(list)}
color={idx === cursorIdx}
>
{list}
</AutomaticItem>
))}
</Automatic>
)}
</div>
const Automatic = styled.ul`
position: absolute;
top: 52px;
left: 0;
z-index: 91;
width: 80%;
/* border: 1px solid #c4c4c4; */
background-color: white;
border-radius: 16px;
`
const AutomaticItem = styled.li<{ color: boolean }>`
height: 50px;
padding: 14px 16px 14px 16px;
font-size: 14px;
border-right: 1px solid #c4c4c4;
border-left: 1px solid #c4c4c4;
border-bottom: 1px solid #c4c4c4;
background-color: ${({ color }) => (color ? 'gray' : 'white')};
&:first-child {
border-radius: 16px 16px 0 0;
}
&:last-child {
border-radius: 0 0 16px 16px;
}
&:hover {
background-color: gray;
}
`