【问题标题】:navigate on click of collectionview cell inside tableview点击tableview内的collectionview单元格导航
【发布时间】:2017-07-11 09:04:58
【问题描述】:

我有一个 tableview 单元格,我在其中添加了 collectionview 单元格(用于水平滚动)。

现在我想在按下水平集合视图的任何单元格时推送到其他导航控制器。怎么做 ?或者我如何定义单元格按下的委托方法。

代码:

ViewController.swift :

class ViewController: UIViewController {
    var categories = ["Action", "Drama", "Science Fiction", "Kids", "Horror"]
}

extension ViewController : UITableViewDelegate { }

extension ViewController : UITableViewDataSource {

    func tableView(_ tableView: UITableView, titleForHeaderInSection section: Int) -> String? {
        return categories[section]
    }

    func numberOfSections(in tableView: UITableView) -> Int {
        return categories.count
    }

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

    func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
        let cell = tableView.dequeueReusableCell(withIdentifier: "cell") as! CategoryRow
        return cell
    }

}

CategoryRow.swift

class CategoryRow : UITableViewCell {
    @IBOutlet weak var collectionView: UICollectionView!
}

extension CategoryRow : UICollectionViewDataSource {

    func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int {
        return 12
    }

    func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
        let cell = collectionView.dequeueReusableCell(withReuseIdentifier: "videoCell", for: indexPath) as! VideoCell
        return cell
    }

}

extension CategoryRow : UICollectionViewDelegateFlowLayout {

    func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize {
        let itemsPerRow:CGFloat = 4
        let hardCodedPadding:CGFloat = 5
        let itemWidth = (collectionView.bounds.width / itemsPerRow) - hardCodedPadding
        let itemHeight = collectionView.bounds.height - (2 * hardCodedPadding)
        return CGSize(width: itemWidth, height: itemHeight)
    }

}

VideoCell.swift

class VideoCell : UICollectionViewCell {

    @IBOutlet weak var imageView: UIImageView!
}

【问题讨论】:

    标签: ios swift uitableview uicollectionview


    【解决方案1】:

    在这里,您将在 CategoryRow 类上的委托方法 didSelectItemAtIndexPath 上单击单元格,然后您可以从那里触发委托以在 ViewController 内调用 ViewController.swift

        func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
                let cell = tableView.dequeueReusableCell(withIdentifier: "cell") as! CategoryRow
                cell.delegate = self
                return cell
            }
    

    VideoCell.swift

        protocol CategoryRowDelegate:class {
        func cellTapped()
        }
    

    CategoryRow.swift

        class CategoryRow : UITableViewCell {
             weak var delegate:CategoryRowDelegate?
            @IBOutlet weak var collectionView: UICollectionView!
        }
    
         func collectionView(_ collectionView: UICollectionView, didSelectItemAt indexPath: IndexPath) {
        if delegate!= nil {
        delegate?.cellTapped()
        }
        }
    

    ViewController内添加委托函数

    func cellTapped(){
    //code for navigation
    }
    

    【讨论】:

    • 听起来不错:)
    【解决方案2】:

    首先从 CategoryRow.swift 创建委托协议,如下代码

    protocol CollectionViewSelectionDelegate: class {
        func didSelectedCollectionViewItem(selectedObject: AnyObject)
    }
    

    现在在 VideoCell.swift 上创建委托对象,如下所示

    weak var delegate:CollectionViewSelectionDelegate? 
    

    在返回单元格之前更改 ViewController.swift 代码

    cell?.delegate = self
    

    在 ViewController.swift 中重写 delegate 的方法,并从 UICollectionView Delegate 方法调用 VideoCell.swift 中的类似方法。

    【讨论】:

      【解决方案3】:

      我认为在这种情况下使用通知会更好。

      在集合视图的didSelectItem 中发布通知

      NSNotificationCenter.defaultCenter().postNotificationName(notificationIdentifier, object: nil)
      

      并在viewControllerviewDidLoad中添加一个观察者如下

      NSNotificationCenter.defaultCenter().addObserver(self, selector: #selector(pushToNew(_:)), name: notificationIdentifier, object: nil)
      

      在新的pushToNew 函数中,执行你的转场

      func pushToNew(notification: Notification) {
          // perform your segue here. Navigate to next view controller
      }
      

      【讨论】:

      • 另一种解决方案。
      • 如果可能的话,告诉我哪个更有效?使用通知或委托?
      • 我们不能说哪个更有效。两者都在您的情况下执行功能。与委托相比,它更易于使用通知。检查这个答案。它有更多关于通知和代表的详细信息stackoverflow.com/a/5325496/7456236
      【解决方案4】:

      制定协议

      protocol collectionViewCellClicked{
          func cellClicked()
      }
      
      • 在主视图控制器中实现这个协议你的视图控制器看起来像这样

        class ViewController: UITableViewController, collectionViewCellClicked{ func cellClicked(){ // Your Code  }}
        
      • 您的 cellForRowAt 代表如下所示

        override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell indexPath: IndexPath) -> UITableViewCell { let cell = tableView.dequeueReusableCell(withIdentifier: <#T##String#>, for: <#T##IndexPath#>) cell.delegate = self return cell }

      • 在您的表格视图单元格中创建一个 collectionViewCellClicked 类型的变量 var delegate: collectionViewCellClicked?

        在您的 didSelectItemAt 委托中

        func collectionView(_ collectionView: UICollectionView, didSelectItemAt indexPath: IndexPath) { delegate.cellClicked() }

      【讨论】:

        猜你喜欢
        • 2019-05-23
        • 2022-01-08
        • 2019-04-25
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2020-04-02
        • 1970-01-01
        相关资源
        最近更新 更多