【问题标题】:UICollectionView in UITableView Freezing while ScrollingUITableView中的UICollectionView在滚动时冻结
【发布时间】:2018-12-24 17:24:37
【问题描述】:

我创建了 1 个演示项目,例如 Gaana 应用程序,为此我在多个 UITableViewCell 中添加了 UICollectionView,它工作正常,但是当我滚动 UITableView 时,UITableView 滚动不顺畅。

你们能帮我解决这个问题吗?下面是我的代码。

override func viewDidLoad() {
        super.viewDidLoad()

        self.tblVW.tableFooterView = UIView(frame: CGRect.zero)
        self.tblVW.separatorColor = UIColor.clear

        let trendingNib = UINib(nibName: "TrendingCell", bundle: nil)
        self.tblVW.register(trendingNib, forCellReuseIdentifier: "TrendingCell")

        let topChartNib = UINib(nibName: "TopChartCell", bundle: nil)
        self.tblVW.register(topChartNib, forCellReuseIdentifier: "TopChartCell")

        let madeForYouNib = UINib(nibName: "MadeForYouCell", bundle: nil)
        self.tblVW.register(madeForYouNib, forCellReuseIdentifier: "MadeForYouCell")

        let newReleaseNib = UINib(nibName: "NewReleaseCell", bundle: nil)
        self.tblVW.register(newReleaseNib, forCellReuseIdentifier: "NewReleaseCell")

        let featuredArtistNib = UINib(nibName: "FeaturedArtistCell", bundle: nil)
        self.tblVW.register(featuredArtistNib, forCellReuseIdentifier: "FeaturedArtistCell")

        let discoverNib = UINib(nibName: "DiscoverCell", bundle: nil)
        self.tblVW.register(discoverNib, forCellReuseIdentifier: "DiscoverCell")

        let editorsPickNib = UINib(nibName: "EditorsPickCell", bundle: nil)
        self.tblVW.register(editorsPickNib, forCellReuseIdentifier: "EditorsPickCell")

        let gaanaSpecialNib = UINib(nibName: "GaanaSpecialCell", bundle: nil)
        self.tblVW.register(gaanaSpecialNib, forCellReuseIdentifier: "GaanaSpecialCell")
    }

func numberOfSections(in tableView: UITableView) -> Int {
        return 8
    }

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

    func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
        if indexPath.section == 0 {
            let cell:TrendingCell = self.tblVW.dequeueReusableCell(withIdentifier: "TrendingCell", for: indexPath) as! TrendingCell

            cell.selectionStyle = UITableViewCellSelectionStyle.none

            cell.layoutSubviews()
            return cell
        }
        else if indexPath.section == 1 {
            let cell:TopChartCell = self.tblVW.dequeueReusableCell(withIdentifier: "TopChartCell", for: indexPath) as! TopChartCell

            cell.selectionStyle = UITableViewCellSelectionStyle.none

            cell.layoutSubviews()
            return cell
        }
        else if indexPath.section == 2 {
            let cell:MadeForYouCell = self.tblVW.dequeueReusableCell(withIdentifier: "MadeForYouCell", for: indexPath) as! MadeForYouCell

            cell.selectionStyle = UITableViewCellSelectionStyle.none

            cell.layoutSubviews()
            return cell
        }
        else if indexPath.section == 3 {
            let cell:NewReleaseCell = self.tblVW.dequeueReusableCell(withIdentifier: "NewReleaseCell", for: indexPath) as! NewReleaseCell

            cell.selectionStyle = UITableViewCellSelectionStyle.none

            cell.layoutSubviews()
            return cell
        }
        else if indexPath.section == 4 {
            let cell:FeaturedArtistCell = self.tblVW.dequeueReusableCell(withIdentifier: "FeaturedArtistCell", for: indexPath) as! FeaturedArtistCell

            cell.selectionStyle = UITableViewCellSelectionStyle.none

            cell.layoutSubviews()
            return cell
        }
        else if indexPath.section == 5 {
            let cell:DiscoverCell = self.tblVW.dequeueReusableCell(withIdentifier: "DiscoverCell", for: indexPath) as! DiscoverCell

            cell.selectionStyle = UITableViewCellSelectionStyle.none

            cell.layoutSubviews()
            return cell
        }
        else if indexPath.section == 6 {
            let cell:EditorsPickCell = self.tblVW.dequeueReusableCell(withIdentifier: "EditorsPickCell", for: indexPath) as! EditorsPickCell

            cell.selectionStyle = UITableViewCellSelectionStyle.none

            cell.layoutSubviews()
            return cell
        }
        else {
            let cell:GaanaSpecialCell = self.tblVW.dequeueReusableCell(withIdentifier: "GaanaSpecialCell", for: indexPath) as! GaanaSpecialCell

            cell.selectionStyle = UITableViewCellSelectionStyle.none

            cell.layoutSubviews()
            return cell
        }
    }

下面的代码是UITableViewCell代码的一次。

    class TrendingCell: UITableViewCell {

    @IBOutlet weak var trendingCollectionVW: UICollectionView!
    var arrData = [String]()
    override func awakeFromNib() {
        super.awakeFromNib()

        trendingCollectionVW.dataSource = self
        trendingCollectionVW.delegate   = self

        let trendingSongsNib = UINib(nibName: "TrendingSongCollectionCell", bundle: nil)
        trendingCollectionVW.register(trendingSongsNib, forCellWithReuseIdentifier: "TrendingSongCollectionCell")

    }

    override func setSelected(_ selected: Bool, animated: Bool) {
        super.setSelected(selected, animated: animated)

        // Configure the view for the selected state
    }

//    override func layoutSubviews() {
//        super.layoutSubviews()
//        
//        self.layer.shouldRasterize = true
//        self.layer.rasterizationScale = UIScreen.main.scale
//    }
}

//MARK: - UICollectionView Delegate & DataSource
extension TrendingCell: UICollectionViewDelegate, UICollectionViewDataSource, UICollectionViewDelegateFlowLayout {
    func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int {
        return 10
    }

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

        cell.lblTItle.text = String.init(format: "Indexpath %d", indexPath.item)
        cell.imgVW.image = UIImage.init(named: String.init(format: "trendingSong%d", indexPath.item+1))
        //cell.layoutSubviews()
        return cell
    }

    func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize {
        return CGSize(width: (UIScreen.main.bounds.size.width - 15) / 2.9, height: 175)
    }

    func collectionView(_ collectionView: UICollectionView, didSelectItemAt indexPath: IndexPath) {
        print("You selected cell #\(indexPath.item)!")
    }

    func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, insetForSectionAt section: Int) -> UIEdgeInsets {
        return UIEdgeInsetsMake(0, 5, 5, 5)
    }

    func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, minimumInteritemSpacingForSectionAt section: Int) -> CGFloat {
        return 5
    }

    func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, minimumLineSpacingForSectionAt section: Int) -> CGFloat {
        return 5
    }
}

当我在UITableViewCell 中滚动任何UICollectionView 时,内存突然增加了15 到20 MB。

编辑 这里是演示项目链接: https://www.dropbox.com/s/k1vpdqn9moli9nw/Gaana.zip?dl=0 任何帮助将不胜感激。 谢谢

【问题讨论】:

  • 它是因为当你的 TrendingCell 这个单元格在那个时候你的collectionview 单元格也创建了所以你的内存增加了
  • @HimanshuMoradiya,感谢您的评论。因此,与其在cellForRowAt 内注册UICollectionViewCell,我可以这样做,这样内存就不会增加,UITableView 滚动顺畅。
  • 只是实现分页不要同时加载到很多单元格。
  • @ShauketSheikh 我没明白你的意思,你能给我举个例子吗?

标签: ios swift uitableview scroll uicollectionview


【解决方案1】:

您每次都在创建已经可以重复使用的笔尖,并且在 cellfor 方法中调用 layoutSubviews() 会产生这个问题

您可以对代码进行以下更改

let trendingSongsNib = UINib(nibName: "TrendingSongCollectionCell", bundle: nil)
cell.trendingCollectionVW.register(trendingSongsNib, forCellWithReuseIdentifier: "TrendingSongCollectionCell")

将此行放入您单元格的awakeFromNib()

所以它会在创建 tableviewcell 时注册单元格

并停止拨打cell.layoutSubviews()

【讨论】:

    【解决方案2】:

    这是你做错的几件事。

    问题:

    每次都创建笔尖

        let trendingSongsNib = UINib(nibName: "TrendingSongCollectionCell", bundle: nil)
    

    在错误的地方注册笔尖

        cell.trendingCollectionVW.register(trendingSongsNib, forCellWithReuseIdentifier: "TrendingSongCollectionCell")
    

    即使在注册后您尝试使用不同的重用标识符退出队列

        let cell:TrendingCell = self.tblVW.dequeueReusableCell(withIdentifier: "TrendingCell", for: indexPath) as! TrendingCell
    

    即使您成功地使单元格出列,您也会在每次调用中一次又一次地创建笔尖

        let trendingSongsNib = UINib(nibName: "TrendingSongCollectionCell", bundle: nil)
    

    每次创建集合视图时,它都会加载数据

        // whole architecture is responsible for this, no particular code.
    

    解决方案

    1. 您可以注册单元格的@viewDidLoad 或在界面构建器中

    2. 不要动态加载 nib,dequeue 会自动加载。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-09-28
      • 2018-11-02
      • 2020-09-17
      • 2016-08-05
      相关资源
      最近更新 更多