iOS CollectionView Header 不显示

Posted

技术标签:

【中文标题】iOS CollectionView Header 不显示【英文标题】:iOS CollectionView Header doesn't show 【发布时间】:2016-10-08 19:53:34 【问题描述】:

我正在尝试将分段控件添加到我的标题中,但我在执行此操作时遇到了麻烦。在这个例子中,为了让事情变得更简单,我添加了一个标签,但这也没有显示。有人能告诉我为什么这没有发生吗?

import UIKit

class SessionsViewController: UICollectionViewController , UICollectionViewDelegateFlowLayout 

    override func viewDidLoad() 
        super.viewDidLoad()

        prepareCollectionView()

        view.backgroundColor = UIColor.white
        navigationController?.navigationBar.isTranslucent = true

        navigationItem.leftBarButtonItem = UIBarButtonItem(title: "Log Out", style: .plain, target: self, action: #selector(handleLogout))
        navigationItem.rightBarButtonItem = UIBarButtonItem(image: UIImage(named: "plus") , style: .plain, target: self, action: nil)
        navigationItem.rightBarButtonItem?.tintColor = UIColor.honePalette.accent
    


    func prepareSegmentedControll()->UISegmentedControl
        let items = ["Future Sessions", "Past Sessions"]
        let control = UISegmentedControl(items: items)
        control.selectedSegmentIndex = 0
        control.tintColor = UIColor.honePalette.accent

        let font = UIFont.systemFont(ofSize: 12)
        control.setTitleTextAttributes([NSFontAttributeName: font], for: .normal)
        return control
    

    func prepareCollectionView()
        collectionView?.backgroundColor = UIColor.white
        collectionView?.alwaysBounceVertical = true
        collectionView?.register(sessionsInfo.self, forCellWithReuseIdentifier: "cellId")
    

    // return of the number per item per section
    override func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int 
        return 5
    

    //this is when the collection is clicked
    override func collectionView(_ collectionView: UICollectionView, didSelectItemAt indexPath: IndexPath) 
        let indexPath = collectionView.indexPathsForSelectedItems
        print("this is index path:", indexPath)

    

    // this is the cell of the collection returning initialized with the SessionsInfo
    override func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell 
        let myCell = collectionView.dequeueReusableCell(withReuseIdentifier: "cellId", for: indexPath) as? sessionsInfo
        myCell?.sessionLabel.text = "cell  \(indexPath.row)"
        return myCell!
    
    // this is when the size of the cell returns
    func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize 
        return CGSize(width: view.frame.width - 10, height: 80)
    

    // return supplementary view
    override func collectionView(_ collectionView: UICollectionView, viewForSupplementaryElementOfKind kind: String, at indexPath: IndexPath) -> UICollectionReusableView 



        let headerView = collectionView.dequeueReusableSupplementaryView(ofKind: kind, withReuseIdentifier: "header", for: indexPath)

        let label = UILabel(frame: headerView.bounds)
        label.text = "Top View"
        label.font = UIFont(name: "helvetica", size: 12)
        label.textAlignment = .center
        headerView.addSubview(label)
        //headerView.headerLabel.text = "header"

        return headerView


    


    func handleLogout()
        BaseServices.baseServices.signOut()
        present(LoginViewController(), animated: true, completion: nil)

    



class headerInfo : UICollectionReusableView
    override init(frame: CGRect) 
        super.init(frame: frame)
        setupHeader()
    

    var headerLabel : UILabel = 
        let label = UILabel()
        label.text = "HEADER"
        label.translatesAutoresizingMaskIntoConstraints = false
        return label
    ()


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

    func setupHeader()

        backgroundColor = UIColor.honePalette.raindrops
        addSubview(headerLabel)
        addConstraints(NSLayoutConstraint.constraints( withVisualFormat: "H:|[v0]|", options: NSLayoutFormatOptions(), metrics: nil, views: ["v0":headerLabel]))
        addConstraints(NSLayoutConstraint.constraints( withVisualFormat: "V:|[v0]|", options: NSLayoutFormatOptions(), metrics: nil, views: ["v0":headerLabel]))

    




class sessionsInfo: UICollectionViewCell 

    override init(frame: CGRect) 
        super.init(frame: frame)
        setupSessions()
    

    var sessionLabel : UILabel = 
        let label = UILabel()
        label.text = "sessionView"
        label.translatesAutoresizingMaskIntoConstraints = false
        return label
    ()

    var sessionTimeLabel : UILabel = 
        let label = UILabel()
        label.text = ""
        label.translatesAutoresizingMaskIntoConstraints = false
        return label
    ()

    var sessionLocationLabel : UILabel = 
        let label = UILabel()
        label.text = ""
        label.translatesAutoresizingMaskIntoConstraints = false
        return label
    ()

    func setupSessions()

        backgroundColor = UIColor.honePalette.raindrops
        addSubview(sessionLabel)
        addConstraints(NSLayoutConstraint.constraints( withVisualFormat: "H:|[v0]|", options: NSLayoutFormatOptions(), metrics: nil, views: ["v0":sessionLabel]))
        addConstraints(NSLayoutConstraint.constraints( withVisualFormat: "V:|[v0]|", options: NSLayoutFormatOptions(), metrics: nil, views: ["v0":sessionLabel]))

    

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




【问题讨论】:

【参考方案1】:

我在一个新项目中尝试了您的代码,但您缺少两个关键步骤:注册补充视图和设置标题的大小。

在你的prepareCollectionView函数中,你还需要注册header view:

collectionView?.register(headerInfo.self, forSupplementaryViewOfKind: UICollectionElementKindSectionHeader, withReuseIdentifier: "header")

您还需要实现另一个委托函数,以提供标题视图的大小:

func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, referenceSizeForHeaderInSection section: Int) -> CGSize 
    return CGSize(width: 100, height: 100) // fix to be your intended size

这是它有效的证据。 (我无法访问您的自定义颜色,这就是为什么一切都是橙色和灰色的。)

【讨论】:

有没有办法使标题视图不可滚动,以便它始终保持在顶部并且集合仍然可以滚动? 如果您希望视图保持在顶部,您可以将其设置为与集合视图分开的视图,直接位于其上方。集合视图页眉和页脚的目的是它们随着集合视图的内容滚动。 那么当内容视图移动并且作为标题的日期保持到下一个日期视图标题到来之前,我应该在标题方面使用什么?是 UITableView 吗? 我会在 Stack Overflow 上查看“固定标题”或“粘性标题”。有很多很好的答案可以准确地描述您想要实现的目标。这最常使用 UITableView 完成。

以上是关于iOS CollectionView Header 不显示的主要内容,如果未能解决你的问题,请参考以下文章

CollectionView "Header" 像 instagram 一样滚动时粘在顶部

CollectionView Header And Footer 的使用

如何在 CollectionView iOS Swift 4 中显示不显示单元格的标题?

使用 Xib 在 Tableview Header 中快速重新加载 CollectionView

iOS 11 UI Collection Section Header 裁剪滚动指示器

Xamarin效果第四篇之CollectionView子项右侧布局