React中修改map渲染的指定div背景色问题求助
问题分析与解决方案
问题根源
你现在所有的Grid组件都共用同一个background状态变量,只要调用setBackground修改这个值,所有绑定了该变量的Grid背景色都会同步变化,这就是点击任意div所有都变色的原因。
解决思路
我们需要跟踪当前被选中的Grid的唯一标识(比如每个supply的id),而不是用一个统一的背景色状态。然后在渲染每个Grid时,判断它的id是否是当前选中的id,再决定背景色。
修改后的代码
状态与事件处理部分
// 把原来的background状态改成记录选中id的状态 const [selectedId, setSelectedId] = useState<number | null>(null); const handleChange = (e: React.ChangeEvent<HTMLInputElement>) => { console.log(e.target.value); }; // 点击时传入当前supply的id,更新选中状态 const changeBackground = (id: number) => { setSelectedId(id); };
JSX部分
<Grid sx={{ display:'flex' }} > { props.supplies.map((supply, id) => { // 判断当前item是否被选中,动态设置背景色 const isSelected = selectedId === id; return( <Grid onClick={() => changeBackground(id)} lg={4} key={id} sx={{ marginRight:"0.8rem", backgroundColor: isSelected ? 'lightblue' : 'white', border:2, borderRadius:2, borderColor:'#ddedf4', padding:'5px 8px 25px 25px' }} > <RadioGroup name={supply.months} onChange={handleChange} value={value} > <FormControlLabel value={ supply.months } control={<Radio size="small"/>} label={ <Typography fontSize='14px'>{supply.months}</Typography> } /> <Typography marginLeft='30px'>{ supply.boxes }</Typography> </RadioGroup> </Grid> ) })} </Grid>
额外说明
- 这里用
id作为每个supply的唯一标识,如果你有更合适的唯一字段(比如supply自身的id),可以替换掉map里的id参数,确保每个item的标识不会重复。 - 这样修改后,点击某个Grid时只有它会变成浅蓝,点击其他Grid时,之前选中的会自动变回白色,新点击的变成浅蓝,符合你的需求。
内容的提问来源于stack exchange,提问作者Dave851
相关产品推荐
相关产品推荐

