tableview section Header 中的视差效果抛出 UIView-nil 错误?

Parallax effect in tableview section Header throws a UIView-nil error?

我有一个自定义的 UITableViewHeaderFooterView header.I 对本文进行了扩展 Swift - Parallax Header View - ScrollView overlap cells

import UIKit

class CustomSoccerHeaderView: UITableViewHeaderFooterView {

    var clickBravisso: Soccer?
    @IBOutlet weak var bravoBtn: UIButton!
    @IBOutlet weak var countBravo: UILabel!
   @IBOutlet weak var nameHeader: UILabel!
    @IBOutlet weak var imageHeader: UIImageView!
    override func awakeFromNib() {
        super.awakeFromNib()
        // Initialization code



    }


extension UITableView {

    func addImageHeaderView(headerView: UIView, height: CGFloat) {
        self.contentInset = UIEdgeInsets(top: height, left: 0, bottom: 0, right: 0)
        self.contentOffset = CGPoint(x: 0, y: -height)
        self.tableHeaderView = headerView
        self.tableHeaderView?.frame = CGRect(x: 0, y: 0, width: self.bounds.width, height: height)
    }

    func updateHeaderView(height kTableHeaderHeight: CGFloat) {

        var headerRect = CGRect(x: 0, y: -kTableHeaderHeight , width: self.bounds.width, height: kTableHeaderHeight)
        if self.contentOffset.y < -kTableHeaderHeight {
            headerRect.origin.y = self.contentOffset.y
            headerRect.size.height = -self.contentOffset.y
        }
        self.tableHeaderView?.frame = headerRect
    }

}

在下载数据到cell的方法header.Stalled中实现Parallaxeffect.I的函数中effect.I谁能在这提示并指正me.Experience将不胜感激内容不够,找不到合适的文章。

func tableView(_ tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? {

        let header = tableView.dequeueReusableHeaderFooterView(withIdentifier: "CustomSoccerHeaderView") as! CustomSoccerHeaderView

        header.frame = CGRect(x: 0, y: 0, width: UIScreen.main.bounds.width, height: 350)

        header.clickBravisso = detailSoccer

        header.nameHeader.text = detailSoccer.matchS
        header.countBravo.text = ""


        // header.bravoBtn.addTarget(CustomSoccerHeaderView(), action: #selector(CustomSoccerHeaderView.likeBtn(_:)), for: UIControlEvents.touchUpInside)


        detailSoccer.imagePrS.getDataInBackground { (data, error) in
            header.imageHeader.image = error == nil ? UIImage(data: data!) : nil
        }


        return header
    }

    class DetailSoccerTableViewController: UIViewController,UITableViewDelegate,UITableViewDataSource,UIScrollViewDelegate  {

    @IBOutlet weak var tableView: UITableView!

        var detailSoccer: Soccer!
        var selectedSoccer = [Soccer]()

        var headerView: UIView!

    override func viewDidLoad() {
            super.viewDidLoad()

            let backButton = UIBarButtonItem()
            backButton.title = ""

           self.navigationController?.navigationBar.topItem?.backBarButtonItem = backButton

           // self.navigationItem.rightBarButtonItem = barButton
          //  self.navigationItem.rightBarButtonItem?.tintColor = UIColor.universalColorYellow
            let yourBackImage = UIImage(named: "backItem")
            self.navigationController?.navigationBar.backIndicatorImage = yourBackImage
            self.navigationController?.navigationBar.backIndicatorTransitionMaskImage = yourBackImage
            self.navigationController?.navigationItem.leftItemsSupplementBackButton = true
            self.navigationController?.navigationBar.tintColor = UIColor.universalColorYellow


            //title = detailSoccer.detailTitleS

            let nib: UINib = UINib(nibName: "CustomSoccerHeaderView", bundle: nil)
            tableView.register(nib, forHeaderFooterViewReuseIdentifier: "CustomSoccerHeaderView")


            tableView.tableFooterView = UIView(frame: .zero)

            //tableView.layer.masksToBounds = true
            tableView.estimatedRowHeight = 280
            tableView.rowHeight = UITableView.automaticDimension
            tableView.separatorStyle = .none
            tableView.delegate = self
            tableView.dataSource = self
            tableView.register(UINib(nibName:"FootTableViewCell",bundle:nil), forCellReuseIdentifier: "cellSoc")
            self.view.addSubview(tableView)

            self.edgesForExtendedLayout = UIRectEdge.init(rawValue: 0)
            self.extendedLayoutIncludesOpaqueBars = true

            tableView.addImageHeaderView(headerView: headerView, height: 0)// error 

            tableView.reloadData()
            loadMatchSoccer()

            tableView.rowHeight = UITableView.automaticDimension

        }
 func scrollViewDidScroll(_ scrollView: UIScrollView) {
        tableView.updateHeaderView(height: 200)
    }

        }

这一行报错 - tableView.addImageHeaderView(headerView: headerView, height: 0) headerView = (UIView?) nil

你还没有初始化headerView

在添加此行之前

tableView.addImageHeaderView(headerView: headerView, height: 0)

再添加一行到 init headerView。

headerView = UIView(frame: CGRect(x: 0, y: 0, width: self.bounds.width, height: height))

在 viewDidLoad 中添加您的代码最终将如下所示

headerView = UIView(frame: CGRect(x: 0, y: 0, width: self.bounds.width, height: height))
tableView.addImageHeaderView(headerView: headerView, height: 0)

如果您的自定义视图是在 xib 中定义的,请尝试更改此行:

var headerView: UIView!

为此:

lazy var headerView: CustomSoccerHeaderView = {
    return Bundle.main.loadNibNamed("CustomSoccerHeaderView", owner: nil, options: nil)!.first as! CustomSoccerHeaderView
}()

注意不要混淆这两个概念:

  1. UITableViewHeaderFooterView - 具有特定的子视图,您应该将自定义设置放入其中,理想情况下应该使用标识符进行注册。
  2. tableHeaderView - 只是任何旧的 UIView 子类,不参与单元格重用机制。

如上所述,您需要第二个选项,但您发布的代码似乎正在支持第一个选项。