MUI Autocomplete状态变更时下拉列表上移问题求助
MUI Autocomplete下拉列表展开/折叠时上移问题解决
我用MUI的Autocomplete组件开发了带展开/折叠功能的组件,展开状态存在expandedPortfolios状态中。点击箭头触发handleExpand修改状态时,组件能正常重新渲染,但下拉列表会出现上移的问题。尝试过用shouldComponentUpdate处理,结果导致状态变更后组件无法渲染,引发新问题。
相关代码
handleExpand函数
handleExpand = (portfolioName) => { var portfolio = (this.state.portfoliosAsGroup || []).find(p => p.name == portfolioName); if (portfolio) { let portfolioId = portfolio.id; let current = this.state.expandedPortfolios; let Ids = []; if (current.includes(portfolioId)) { Ids = current.filter((i) => i !== portfolioId); } else { Ids.push(...current, portfolioId); } this.setState({ expandedPortfolios: Ids, expand: !this.state.expand }); } }
renderGroup配置
renderGroup={(params) => ( <> <div style={{ display: "flex", alignItems: "center", height: "20px", marginTop: '15px' }}> {params.group != dropdownGroupTags.all && <IconButton size="small" onClick={() => this.handleExpand(params.group)}> {(!(this.state.expandedPortfolios || []).includes(this.getPortfolioIdByName(params.group)) ? <ExpandLessIcon /> : <ExpandMoreIcon />)} </IconButton>} {params.group != dropdownGroupTags.all ? <WarehouseIcon /> : <AccountBalanceIcon />} <Button onClick={() => params.group != "Unportfolio" && this.handleCompanyChange(this.createCompanyGroupChangeText(params.group), params.group)}> <Typography variant="subtitle1" sx={{ fontWeight: 'bold' }}> {params.group} </Typography> </Button> <div style={{ marginLeft: 'auto', marginRight: '30px' }}> <Typography align="right" variant="subtitle1" sx={{ fontWeight: 'bold' }}> {params.group != dropdownGroupTags.all && `${(params.children || []).length} Unit`} </Typography> </div> </div> <br /> {(this.state.expandedPortfolios || []).includes(this.getPortfolioIdByName(params.group)) ? params.children : []} </> )}
问题示例

解决方法
- 禁用Popper自动位置调整:通过
PopperProps关闭翻转和溢出修正,避免下拉列表因内容变化重新计算位置时偏移:<Autocomplete // 其他原有props PopperProps={{ modifiers: [ { name: 'flip', enabled: false }, { name: 'preventOverflow', enabled: false } ] }} /> - 移除多余状态更新:
handleExpand中的expand: !this.state.expand是冗余状态,仅保留expandedPortfolios更新即可,减少不必要的渲染触发:this.setState({ expandedPortfolios: Ids }); - 保持DOM结构稳定:折叠状态下不要返回空数组,改用空容器占位,避免DOM节点数量突变导致布局计算异常:
{(this.state.expandedPortfolios || []).includes(this.getPortfolioIdByName(params.group)) ? params.children : <div style={{ height: 0, overflow: 'hidden' }} />} - 保持下拉面板挂载状态:设置
keepMounted: true让下拉面板始终挂载(即使隐藏),避免重新挂载时的位置计算错误:<Autocomplete // 其他原有props PopperProps={{ keepMounted: true }} />
内容的提问来源于stack exchange,提问作者alperenoz
相关产品推荐
相关产品推荐

