如何为 collectionView Cell 的 cellForItemAt 中的子视图着色?

How to color SubViews in a collectionView Cell's cellForItemAt?

我正在尝试建立一个时间轴。我有一个包含 collectionView 的视图控制器。每个 collectionView 单元格代表一个月的数据。在每个单元格中,我都有一个 stackView。这个 stackView 包含 30 个子视图,每个子视图代表一天的数据。

完整的项目在这里,如果你想尝试一下:https://github.com/AlexMarshall12/iOS-timeline

我目前为每个 dayCell 子视图着色的方法是首先在自定义单元格的 awakeFromNib 中创建单元格中的所有子视图。

class MonthCollectionViewCell: UICollectionViewCell {

    @IBOutlet weak var stackView: UIStackView!
    var dayViews: [Int:UIView] = [:]

    override func awakeFromNib() {
        super.awakeFromNib()
        for i in 1...30 {
            let tick = UIView()
            dayViews[i] = tick
            self.stackView?.addArrangedSubview(tick)
        }
    }

}

请注意,我还构建了一个字典,从 1-30 索引单元格中的每个子视图。

然后在我的 viewController 中,在我的 collectionView 的 cellForItemAt 方法中,我使用 "dates" 函数查看该月的数据中有哪些天数。然后我用我之前构建的字典查找这个视图并将其着色为红色。

func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
    let cell = collectionView.dequeueReusableCell(withReuseIdentifier: "MonthCollectionViewCell", for: indexPath) as! MonthCollectionViewCell
    cell.backgroundColor = UIColor.gray
    let dayViews = cell.dayViews
    let firstDate = dates.first
    let index = indexPath.item
    let monthDate = Calendar.current.date(byAdding: .month, value: index, to: firstDate as! Date)
    let monthInt = Calendar.current.component(.month, from: monthDate!)
    let yearInt = Calendar.current.component(.year, from: monthDate!)
    let monthDates = dates(self.dates as! [Date], withinMonth: monthInt, withinYear: yearInt)
    for date in monthDates {
        let dayInt = date.interval(ofComponent: .day, fromDate: (monthDate?.startOfMonth())!)
        let tick = dayViews[dayInt]
        print(tick,"tick")
        tick?.backgroundColor = UIColor.red
        }
    return cell
}

func dates(_ dates: [Date], withinMonth month: Int, withinYear year: Int) -> [Date] {
    let calendar = Calendar.current
    let components: Set<Calendar.Component> = [.month,.year]
    print(components,"components")
    let filtered = dates.filter { (date) -> Bool in
        let monthAndYear = calendar.dateComponents(components, from: date)
        return (monthAndYear.month == month && monthAndYear.year == year)
    }
    return filtered
}

目前,所有内容都显示为可以从右向左滚动的灰色月份单元格。尽管我的控制台告诉我它找到的颜色匹配,但它似乎并没有为它们着色。 approach/implementation 我做错了什么?

当您遇到 "I don't see the view I expect to see" 的情况时,运行 您的应用程序在模拟器中,然后返回 Xcode,启动 View Debugger。

在这种情况下,当你这样做时,你会立即看到你的错误:你所有的 "ticks" 都是不可见的,因为你正在向你的 "Fill distribution" 堆栈视图发送零大小的普通 UIView作为安排的子视图。堆栈视图不知道如何处理这些。所以它们最终没有大小,这使得它们不可见。

在 xib 编辑器中将 "Fill distribution" 更改为 "Fill Equally distribution",再次 运行 应用程序,很快,您将开始看到一些滴答声!