Mac Catalyst中UITableViewCell内嵌列表组件显示异常问题
修复macOS 12.5 Catalyst环境下嵌套列表单元格内容缺失问题
针对你在Catalyst环境中遇到的嵌套UITableView/UICollectionView单元格内容缺失问题(点击有效、鼠标悬停才显示,iOS端正常),提供以下修复思路和代码调整方案:
1. 延迟更新高度约束,确保内部列表布局完成
当前代码在reloadData后立即获取contentSize的时机过早,macOS 12.5的Catalyst可能存在布局延迟,导致高度计算不准确。修改updateWithType方法,延迟到下一个RunLoop周期更新高度:
func updateWithType(type: SettingType) { _type = type contentTable.reloadData() // 延迟执行,确保内部列表完成单元格布局 DispatchQueue.main.async { [weak self] in guard let self = self else { return } self.contentTable.layoutIfNeeded() self.contentTableHeightConstraint.constant = self.contentTable.contentSize.height // 触发父级TableView重新布局 self.superview?.superview?.layoutIfNeeded() } }
同时删除awakeFromNib中无效的高度设置(此时无数据,contentSize不准确):
override func awakeFromNib() { super.awakeFromNib() contentTable.delegate = self contentTable.dataSource = self contentTable.isScrollEnabled = false contentTable.register(UINib(nibName: "SettingsRowCell", bundle: nil), forCellReuseIdentifier: "SettingsRowCell") contentTable.estimatedRowHeight = 45.0 contentTable.rowHeight = UITableView.automaticDimension // 移除以下两行无效代码 // layoutIfNeeded() // contentTableHeightConstraint.constant = contentTable.contentSize.height }
2. 强制触发图层重绘
macOS 12.5的Catalyst渲染优化可能导致嵌套列表内容未被正确绘制,可在布局更新后强制重绘:
在updateWithType的异步回调中添加:
self.contentTable.setNeedsDisplay() self.contentTable.layer.setNeedsDisplay()
或者在内部列表的cellForRowAt方法中,给单元格的contentView强制触发重绘:
func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell { let cell = tableView.dequeueReusableCell(withIdentifier: "SettingsRowCell", for: indexPath) as! SettingsRowCell // 你的单元格配置逻辑... cell.contentView.setNeedsDisplay() return cell }
3. 优化父TableView的布局更新
当嵌套单元格高度变化时,强制父TableView重新计算布局,避免布局错位:
在父TableView的cellForRowAt方法中,更新完嵌套单元格后调用:
parentTableView.beginUpdates() parentTableView.endUpdates()
4. 调整嵌套列表的视图属性
尝试修改嵌套contentTable的背景色和裁剪属性,避免Catalyst渲染引擎跳过透明图层:
// 在awakeFromNib中添加 contentTable.clipsToBounds = true contentTable.backgroundColor = .systemBackground // 与单元格背景色保持一致
5. 替换嵌套列表为UIStackView(可选)
如果内部列表结构简单(固定高度行),用UIStackView替代嵌套UITableView能彻底避免滚动视图嵌套的渲染问题:
- 将每个
SettingsRowCell作为StackView的子视图动态添加 - 通过StackView的
intrinsicContentSize自动计算总高度,无需手动维护约束
内容的提问来源于stack exchange,提问作者fphelp
相关产品推荐
相关产品推荐

