Xcode 12.2中UITableViewCell内嵌UICollectionView无法水平滚动求助
内嵌UICollectionView水平滚动失效的修复方案
直接对应代码逻辑,逐一修复导致问题的配置偏差:
- 代理绑定与实现逻辑错位问题
你在控制器的cellForRowAt方法中将seasonsCollectionView的delegate、dataSource绑定给了SelectedShowVC实例,但所有collectionView的代理方法(数据源、尺寸计算的实现)全部写在NumberOfSeasonsCell的扩展中。这种绑定和实现不匹配的状态,会导致代理方法根本无法被触发,你看到的“数据正常加载”大概率是cell复用残留的视觉假象。
修复方法:直接在NumberOfSeasonsCell内部完成collectionView的代理绑定,删除控制器层的代理赋值代码,保持绑定和实现的对象统一:lazy var seasonsCollectionView: UICollectionView = { let layout = UICollectionViewFlowLayout() layout.scrollDirection = .horizontal layout.minimumLineSpacing = 15 layout.estimatedItemSize = .zero // 关闭iOS12默认开启的自适应估算,避免滚动范围计算异常 let cv = UICollectionView(frame: .zero, collectionViewLayout: layout) cv.backgroundColor = UIColor.clear cv.register(SeasonCell.self, forCellWithReuseIdentifier: "identifierSeasons") cv.showsHorizontalScrollIndicator = false cv.translatesAutoresizingMaskIntoConstraints = false cv.delegate = self cv.dataSource = self return cv }() - 视图层级与AutoLayout约束缺失问题
你声明了seasonsCollectionView的AutoLayout属性,但没有将其添加到cell的contentView上,也没有加四向约束让collectionView撑满整个cell内容区。这种状态下collectionView的实际frame是随机值,触摸事件会直接被外层UITableView拦截,无法触发collectionView自身的滚动。
修复方法:在NumberOfSeasonsCell的初始化方法中完成视图添加和约束配置:override init(style: UITableViewCell.CellStyle, reuseIdentifier: String?) { super.init(style: style, reuseIdentifier: reuseIdentifier) contentView.addSubview(seasonsCollectionView) NSLayoutConstraint.activate([ seasonsCollectionView.topAnchor.constraint(equalTo: contentView.topAnchor), seasonsCollectionView.leadingAnchor.constraint(equalTo: contentView.leadingAnchor), seasonsCollectionView.trailingAnchor.constraint(equalTo: contentView.trailingAnchor), seasonsCollectionView.bottomAnchor.constraint(equalTo: contentView.bottomAnchor) ]) } required init?(coder: NSCoder) { fatalError("init(coder:) has not been implemented") } - 外层滚动事件拦截问题
完成上述配置后如果还是无法响应水平滑动,需要调整UITableView的触摸事件优先级配置,避免垂直方向的手势识别器过早拦截水平滑动的触摸事件:let tableSeasons: UITableView = { let table = UITableView(frame: CGRect.zero) table.register(NumberOfSeasonsCell.self, forCellReuseIdentifier: "seasonsRegister") table.backgroundColor = .clear table.layer.cornerRadius = 0 table.separatorColor = .clear table.translatesAutoresizingMaskIntoConstraints = false table.showsHorizontalScrollIndicator = false table.showsVerticalScrollIndicator = false table.delaysContentTouches = false // 取消触摸延迟,优先响应内嵌视图的滚动 table.canCancelContentTouches = false // 禁止外层随意取消已经交给内嵌视图的触摸事件 return table }()
内容的提问来源于stack exchange,提问作者ZeroCooL
相关产品推荐
相关产品推荐

