React中基于map函数实现点击仅打开单个弹窗的方法
问题解决:点击单张电影卡片时仅显示对应弹窗
你的问题出在共用了一个布尔类型的modal状态——所有电影的弹窗都绑定同一个modal变量,只要它变为true,所有弹窗都会同时显示。下面是具体的修复方案:
核心修改思路
- 把状态从单纯的布尔值,改成存储当前激活的电影ID(初始值设为
null) - 弹窗的显示条件改为「当前激活ID等于该电影ID」,确保只有点击的那一个弹窗会显示
修改后的完整代码
function Watchlist() { const { watchlist } = useContext(GlobalContext); // 用activeMovieId存储当前点击的电影ID,初始为null表示无弹窗激活 const [activeMovieId, setActiveMovieId] = useState(null); // 切换弹窗:传入电影ID,点击时设置/清除激活ID const toggleModal = (movieId) => { setActiveMovieId(prevId => prevId === movieId ? null : movieId); } return ( <div className='watchlist'> <h1 className='title'>your watchlist</h1> {watchlist.length > 0 ? ( <div className="movies"> {watchlist.map((movie, index) => { // 抽离margin逻辑,减少重复代码 const margin = index % 3 === 1 ? 30 : 0; return ( <div className="movie-wrapper" key={movie.id}> <button name={movie.id} className="open-modal" onClick={() => toggleModal(movie.id)} > <Card img={`https://image.tmdb.org/t/p/w200${movie.poster_path}`} margin={margin}/> </button> {/* 只有当activeMovieId等于当前电影ID时,才显示弹窗 */} {activeMovieId === movie.id && ( <div className="movie-details"> <div className="modal-content"> <ResultCard movie={movie}/> <button className="close-modal" onClick={() => toggleModal(movie.id)}>X</button> </div> </div> )} </div> ) })} </div> ) : ( <h2 className="no-movies">Add some movies!</h2> )} </div> ) }
额外优化点
- 去掉了重复的map分支逻辑,把margin的判断抽出来,代码更简洁
- 移除了重复的
key属性(只需在最外层的movie-wrapper上设置key即可) - 点击关闭按钮时,同样传入当前电影ID,确保能精准关闭对应弹窗
内容的提问来源于stack exchange,提问作者Jordan
相关产品推荐
相关产品推荐

