动态单元格大小uitableview

时间:2018-03-01 09:43:03

标签: ios swift uitableview

我得到一个不同文本的json对象。我使用以下函数addText(content: number.content!, bottomAnchor: anchor!)逐个排列获得的作品:

func addText(content: String, bottomAnchor: NSLayoutYAxisAnchor) -> NSLayoutYAxisAnchor {

    let shortContentPost: UILabel = {
        let label = UILabel()
        label.text = content
        label.numberOfLines = 0
        label.sizeToFit()
        label.font = UIFont.systemFont(ofSize: 16, weight: UIFont.Weight.regular)

        let attributedString = NSMutableAttributedString(string: label.text!)
        let paragraphStyle = NSMutableParagraphStyle()
        paragraphStyle.lineSpacing = 10
        attributedString.addAttribute(NSAttributedStringKey.paragraphStyle, value:paragraphStyle, range:NSMakeRange(0, attributedString.length))
        label.attributedText = attributedString;

        return label
    }()
    contentView.addSubview(shortContentPost)
    shortContentPost.anchor(bottomAnchor, left: self.leftAnchor, bottom: nil, right: self.rightAnchor, topConstant: 15, leftConstant: 15, bottomConstant: 0, rightConstant: 15, widthConstant: 0, heightConstant: 100)

    return shortContentPost.bottomAnchor
}

所有内容都在UITableViewCell中输出,但无法以任何方式调整自动高度。

选择这样一个奇怪的输出路线是为了获得这样的网格。并且类似的结论用于在一个单元格中组合文本,图片,链接等。

以前,我通过UICollectionView实现了所有这些并手动计算了高度。方式有效,但是高度计算不准确,他不得不拒绝。

func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
    return 3
}

internal func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat {
    return UITableViewAutomaticDimension
}

func tableView(_ tableView: UITableView, estimatedHeightForRowAt indexPath: IndexPath) -> CGFloat {
    return 50.0
}

func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
    if(indexPath.item == 0){
        let cell = tableView.dequeueReusableCell(withIdentifier: "postId", for: indexPath) as! PostViewTableCell
        cell.contentArray = contentArray
        cell.homeController = self.navigationController
        return cell
    }
    let cell = tableView.dequeueReusableCell(withIdentifier: "cellId", for: indexPath)
    return cell
}

这些是tableView函数

TableViewCell:

import UIKit

class PostViewTableCell: UITableViewCell {
var anchor: NSLayoutYAxisAnchor?
var contentArray: [PostContentModel]?{
    didSet{
        anchor = datePublishPost.bottomAnchor
        for number in contentArray! {
            if(number.switcher == 1) {
                anchor = addTextContent(content: number.content!, bottomAnchor: anchor!)
            }
            if(number.switcher == 2){
                anchor = addImageContent(content: number.content!, bottomAnchor: anchor!)
            }
            if(number.switcher == 3){
                anchor = addCaptionFirst(content: number.content!, bottomAnchor: anchor!)
            }
            if(number.switcher == 4){
                anchor = addButtonLink(content: number.content!, link: number.link!, bottomAnchor: anchor!)
            }
        }
    }
}

let authorImage: CustomImageView = {
    let image = CustomImageView()
    image.backgroundColor = .white
    image.image = UIImage(named: "authorImage")
    image.layer.masksToBounds = false
    image.layer.cornerRadius = 15
    image.clipsToBounds = true

    return image
}()

let authorNameLabel: UILabel = {
    let label = UILabel()
    label.font = UIFont.systemFont(ofSize: 14)
    label.textColor = UIColor(red: 0.51, green: 0.51, blue: 0.51, alpha: 1)

    return label
}()

let titlePost: UILabel = {
    let label = UILabel()
    label.font = UIFont.systemFont(ofSize: 24, weight: UIFont.Weight.semibold)
    label.numberOfLines = 0
    return label
}()

let categoryPost: UILabel = {
    let label = UILabel()
    label.textColor = UIColor(red: 0.31, green: 0.31, blue: 0.31, alpha: 1)
    label.font = UIFont.systemFont(ofSize: 12, weight: UIFont.Weight.semibold)
    return label
}()

let datePublishPost: UILabel = {
    let label = UILabel ()
    label.font = UIFont.systemFont(ofSize: 12, weight: UIFont.Weight.regular)
    label.textColor = UIColor(red: 0.52, green: 0.52, blue: 0.52, alpha: 1)
    return label
}()

var homeController: UINavigationController?
override init(style: UITableViewCellStyle, reuseIdentifier: String?) {
    super.init(style: style, reuseIdentifier: reuseIdentifier)
    setupView()
}

override func prepareForReuse() {
    super.prepareForReuse()
    let subviews = self.subviews
    for subview in subviews {
        subview.removeFromSuperview()
    }
}

func setupView(){
    addSubview(authorImage)
    addSubview(authorNameLabel)
    addSubview(titlePost)
    addSubview(categoryPost)
    addSubview(datePublishPost)
    authorImage.anchor(self.topAnchor, left: self.leftAnchor, bottom: nil, right: nil, topConstant: 20, leftConstant: 15, bottomConstant: 0, rightConstant: 0, widthConstant: 30, heightConstant: 30)
    authorNameLabel.anchor(authorImage.topAnchor, left: authorImage.rightAnchor, bottom: nil, right: nil, topConstant: 5, leftConstant: 10, bottomConstant: 0, rightConstant: 0, widthConstant: 0, heightConstant: 0)
    titlePost.anchor(authorNameLabel.bottomAnchor, left: self.leftAnchor, bottom: nil, right: self.rightAnchor, topConstant: 13, leftConstant: 15, bottomConstant: 0, rightConstant: 15, widthConstant: 0, heightConstant: 0)
    categoryPost.anchor(titlePost.bottomAnchor, left: self.leftAnchor, bottom: nil, right: nil, topConstant: 7, leftConstant: 15, bottomConstant: 0, rightConstant: 0, widthConstant: 0, heightConstant: 0)
    datePublishPost.anchor(categoryPost.topAnchor, left: categoryPost.rightAnchor, bottom: nil, right: nil, topConstant: 0, leftConstant: 15, bottomConstant: 0, rightConstant: 0, widthConstant: 0, heightConstant: 0)
}

func addTextContent(content: String, bottomAnchor: NSLayoutYAxisAnchor) -> NSLayoutYAxisAnchor{

    let shortContentPost: UILabel = {
        let label = UILabel()
        label.text = content
        label.numberOfLines = 0
        label.font = UIFont.systemFont(ofSize: 16, weight: UIFont.Weight.regular)

        let attributedString = NSMutableAttributedString(string: label.text!)
        let paragraphStyle = NSMutableParagraphStyle()
        paragraphStyle.lineSpacing = 10
        attributedString.addAttribute(NSAttributedStringKey.paragraphStyle, value:paragraphStyle, range:NSMakeRange(0, attributedString.length))
        label.attributedText = attributedString;

        return label
    }()

    contentView.addSubview(shortContentPost)
    shortContentPost.anchor(bottomAnchor, left: self.leftAnchor, bottom: nil, right: self.rightAnchor, topConstant: 15, leftConstant: 15, bottomConstant: 0, rightConstant: 15, widthConstant: 0, heightConstant: 0)

    return shortContentPost.bottomAnchor
}

func addImageContent(content: String, bottomAnchor: NSLayoutYAxisAnchor) -> NSLayoutYAxisAnchor {
    let image: CustomImageView = {
        let image = CustomImageView()
        image.image = UIImage(named: content)
        image.contentMode = .scaleAspectFill
        image.clipsToBounds = true

        return image
    }()


    let imageURL = "https://brodude.ru/wp-content/uploads/" + content.addingPercentEncoding(withAllowedCharacters: .urlHostAllowed)!
    image.loadImageUsingUrlString(urlString: imageURL)

    contentView.addSubview(image)
    image.anchor(bottomAnchor, left: self.leftAnchor, bottom: nil, right: self.rightAnchor, topConstant: 15, leftConstant: 0, bottomConstant: 0, rightConstant: 0, widthConstant: 0, heightConstant: 250)

    return image.bottomAnchor
}

func addCaptionFirst(content: String, bottomAnchor: NSLayoutYAxisAnchor) -> NSLayoutYAxisAnchor {
    let Caption: UILabel = {
        let lb = UILabel()
        lb.text = content
        lb.numberOfLines = 0
        lb.font = UIFont.systemFont(ofSize: 20, weight: UIFont.Weight.semibold)
        return lb
    }()

    contentView.addSubview(Caption)
    Caption.anchor(bottomAnchor, left: self.leftAnchor, bottom: nil, right: self.rightAnchor, topConstant: 30, leftConstant: 15, bottomConstant: 0, rightConstant: 15, widthConstant: 0, heightConstant: 0)
    return Caption.bottomAnchor
}

func addButtonLink(content: String, link: String, bottomAnchor: NSLayoutYAxisAnchor) -> NSLayoutYAxisAnchor {
    let button: LinkButton = {
        let bt = LinkButton()
        bt.LinkString = link
        bt.titleLabel?.font = UIFont.systemFont(ofSize: 18, weight: UIFont.Weight.semibold)
        bt.setTitle(content, for: UIControlState.normal)
        bt.titleLabel?.numberOfLines = 0
        bt.contentHorizontalAlignment = .left
        bt.setTitleColor(UIColor(red: 0.07, green: 0.32, blue: 0.89, alpha: 1.0), for: UIControlState.normal)
        bt.addTarget(self, action: #selector(linkOut), for: .touchUpInside)
        return bt
    }()
    button.sizeToFit()
    contentView.addSubview(button)
    button.anchor(bottomAnchor, left: self.leftAnchor, bottom: nil, right: self.rightAnchor, topConstant: 20, leftConstant: 15, bottomConstant: 0, rightConstant: 15, widthConstant: 0, heightConstant: 0)
    return button.bottomAnchor
}

@objc func linkOut(sender: LinkButton!){
    let viewController: WebViewController = {
        let pv = WebViewController()
        pv.LinkString = sender.LinkString
        return pv
    }()
    homeController?.navigationController?.pushViewController(viewController, animated: true)
}

required init?(coder aDecoder: NSCoder) {
    fatalError("init(coder:) has not been implemented")
}

}

2 个答案:

答案 0 :(得分:1)

如果你只有3个静态单元格,我不认为tableView实际上是有用的。如果有许多单元可以重复使用,那么UITableView在性能方面非常有用 - 那么UI不必一直创建和保存整个UI,而只需要tableView的可见部分。

在您的情况下,由于所有内容都被推送到一个单元格,我建议您只使用UIScrollView

或者(在大内容的情况下)使用tableView每个段落有一个单元格。

答案 1 :(得分:0)

//您必须提供估计的最小细胞高度。 即

func tableView(_ tableView: UITableView, estimatedHeightForRowAt indexPath: IndexPath) -> CGFloat {
    return 50.0
}

单元格可以调整大小超过此值。