如何在 scrollview 和 stackview 下以编程方式为 tableview 使用自动高度?

问题描述 投票:0回答:0

我的项目使用 SnapKit 设置约束,并在滚动视图内的堆栈视图中使用表视图。

首先我设置了一个scrollview用于滚动页面,然后在scrollview中添加一个stackview用于定位其他视图。

其次,我在第一个视图的堆栈视图中设置了表视图,并将声明的表视图中的“view.rowHeight = UITableView.automaticDimension”和“view.estimatedRowHeight = 80”设置为自动表视图高度。

三 我用Snap Kit设置位置,不知道怎么设置table view高度的约束?

我的程序如下:

import UIKit
import SnapKit

class ViewController: UIViewController {
    
    let rows: [[String: String]] = [
        ["avatar": "noavatar", "name": "Mary", "date": "2022-12-02 15:10"],
        ["avatar": "noavatar", "name": "Joe", "date": "2022-11-02 10:10"],
        ["avatar": "noavatar", "name": "Michael", "date": "2022-10-02 15:10"],
        ["avatar": "noavatar", "name": "John", "date": "2022-03-02 15:10"],
        ["avatar": "noavatar", "name": "Annie", "date": "2022-09-02 15:10"],
    ]
    
    var scrollView: UIScrollView = {
        let view = UIScrollView()
        
        return view
    }()
    
    let stackView: UIStackView = {
        let view = UIStackView()
        view.axis = .vertical
        view.spacing = 12
        view.alignment = .top
        return view
    }()
    
    let tableView: UITableView = {
        let view = UITableView()
        view.isScrollEnabled = false
        view.backgroundColor = UIColor.clear
        
        view.rowHeight = UITableView.automaticDimension
        view.estimatedRowHeight = 80
        
        view.register(MyCell.self, forCellReuseIdentifier: "MyCell")
                
        return view
    }()

    override func viewDidLoad() {
        super.viewDidLoad()
        
        initScrollView()
        
        tableView.delegate = self
        tableView.dataSource = self
    }

    private func initScrollView() {
        
        self.view.addSubview(scrollView)
        scrollView.snp.makeConstraints { make in
            make.top.equalToSuperview().offset(200)
            make.left.equalToSuperview().offset(20)
            make.right.equalToSuperview().offset(-20)
            make.bottom.equalToSuperview()
        }
        
        scrollView.addSubview(stackView)
        stackView.snp.makeConstraints { make in
            make.top.bottom.equalToSuperview()
            make.width.equalToSuperview()
        }

        stackView.addArrangedSubview(tableView)
        tableView.snp.makeConstraints { make in
            make.left.right.equalToSuperview()
            **make.height.equalTo(200)**
        }
    }
}

extension ViewController: UITableViewDelegate, UITableViewDataSource {
    
    func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
        
        return rows.count
    }

    func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {

        let cell: MyCell = tableView.dequeueReusableCell(withIdentifier: "MyCell", for: indexPath) as! MyCell
        
        let row: [String: String] = rows[indexPath.row]
        cell.update(row: row, no: indexPath.row + 1)
        
        return cell
    }
}

class MyCell: UITableViewCell {
        
    let noLbl: UILabel = {
        let view = UILabel()
        return view
    }()
    
    let avatarIV: UIImageView = {
        let view = UIImageView()
        return view
    }()
    
    let dataContainer: UIView = UIView()
    
    let nameLbl: UILabel = {
        let view = UILabel()
        return view
    }()
    
    let createdAtLbl: UILabel = {
        let view = UILabel()
        view.textColor = UIColor.black
        return view
    }()
    
    let separator: UIView = {
        let view = UIView()
        view.backgroundColor = UIColor.black
        return view
    }()
    
    override init(style: UITableViewCell.CellStyle, reuseIdentifier: String?) {
        super.init(style: style, reuseIdentifier: reuseIdentifier)
        setupView()
    }
    
    required init?(coder: NSCoder) {
        super.init(coder: coder)
        self.setupView()
    }

    override func awakeFromNib() {
        super.awakeFromNib()
        setupView()
    }
    
    private func setupView() {
        backgroundColor = UIColor.clear
        setAnchor()
    }
    
    func setAnchor() {
        
        self.contentView.addSubview(noLbl)
        noLbl.snp.makeConstraints { make in
            make.top.equalToSuperview().offset(12)
            make.left.equalToSuperview()
            make.height.equalTo(48)
        }
        
        self.contentView.addSubview(avatarIV)
        avatarIV.snp.makeConstraints { make in
            make.top.equalToSuperview().offset(12)
            make.left.equalTo(noLbl.snp.right).offset(12)
            make.width.height.equalTo(48)
            make.centerY.equalToSuperview()
        }

        self.contentView.addSubview(dataContainer)
        dataContainer.snp.makeConstraints { make in
            make.top.equalToSuperview().offset(15)
            make.left.equalTo(avatarIV.snp.right).offset(18)
            make.right.equalToSuperview()

            make.height.equalTo(42)
        }

            self.dataContainer.addSubview(nameLbl)
            nameLbl.snp.makeConstraints { make in
                make.top.equalTo(avatarIV.snp.top).offset(4)
                make.left.equalToSuperview()
            }

            self.dataContainer.addSubview(createdAtLbl)
            createdAtLbl.snp.makeConstraints { make in
                make.left.equalToSuperview()
                make.bottom.equalTo(avatarIV.snp.bottom).offset(-4)
            }

        self.contentView.addSubview(separator)
        separator.snp.makeConstraints { make in
            make.left.right.equalToSuperview()
            make.height.equalTo(1)
            make.top.equalTo(avatarIV.snp.bottom).offset(12)
        }
    }
    
    func update(row: [String: String], no: Int) {

        self.noLbl.text = "\(no)."

        self.avatarIV.image = UIImage(named: row["avatar"]!)

        self.nameLbl.text = row["name"]!
        self.createdAtLbl.text = row["date"]!
    }
}

结果如下:

enter image description here

可以看到表格高度只有200,是为了展示3行数据,不是展示完整的数据, 但是如果我取消高度限制设置如下:

tableView.snp.makeConstraints { make in
   make.left.right.equalToSuperview()
   //make.height.equalTo(200)
}

它在屏幕上什么都不显示:

enter image description here

请问我如何设置 tableview 可以在 scrollview 和 stackview 中使用自动高度?

多次遇到auto height tableview,没有一个完整或简单的解决方案吗?

tableview scrollview programmatically stackview
© www.soinside.com 2019 - 2024. All rights reserved.