React-MUI InputBase自定义搜索组件每次按键失焦问题求助
解决InputBase组件按键输入时失焦的问题
问题根源
你的SearchInput组件中,将MUI styled 创建的Search、SearchIconWrapper、StyledInputBase全部定义在了组件函数内部。每次组件重新渲染(比如输入框值变化触发父组件更新),这些styled组件都会被重新创建,React会将它们识别为全新组件,销毁旧DOM节点并重建,直接导致输入框失去焦点。
解决方案
把所有styled组件的定义移到SearchInput组件函数外部,确保它们仅在模块加载时创建一次,不会随组件渲染重复生成。
修改后的搜索组件代码
import { styled } from "@mui/material/styles"; import { InputBase } from "@mui/material"; import SearchIcon from "@mui/icons-material/Search"; // 移到组件外部的styled定义 const Search = styled("div")(({ theme }) => ({ position: "relative", borderRadius: theme.shape.borderRadius, backgroundColor: "rgba(171, 171, 171, 0.15)", "&:hover": { backgroundColor: "rgba(171, 171, 171, 0.25)", }, marginLeft: 0, width: "100%", height: "46.67px", [theme.breakpoints.up("sm")]: { marginLeft: theme.spacing(1), width: "auto", }, })); const SearchIconWrapper = styled("div")(({ theme }) => ({ padding: theme.spacing(0, 2), height: "100%", position: "absolute", pointerEvents: "none", display: "flex", alignItems: "center", justifyContent: "center", })); const StyledInputBase = styled(InputBase)(({ theme }) => ({ color: "inherit", "& .MuiInputBase-input": { padding: "12px 8px 12px 0px", paddingLeft: `calc(1em + ${theme.spacing(4)})`, transition: theme.transitions.create("width"), width: "100%", [theme.breakpoints.up("sm")]: { width: "12ch", "&:focus": { width: "20ch", }, }, }, })); export const SearchInput = (props) => { return ( <Search> <SearchIconWrapper> <SearchIcon /> </SearchIconWrapper> <StyledInputBase placeholder={props.placeholder} inputProps={{ "aria-label": "search", type: "text" }} onChange={props.onChange} value={props.value} /> </Search> ); };
说明
修改后,styled组件会在模块初始化时就完成创建,每次SearchInput渲染时复用同一个组件实例,DOM节点不会被重复销毁重建,输入框就能稳定保持焦点。之前放在同一文件正常是因为渲染上下文的特殊性,拆分后组件独立渲染,内部重复创建styled组件的问题才会显现。
内容的提问来源于stack exchange,提问作者Sadesh Surendra
相关产品推荐
相关产品推荐

