Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/ios/97.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/swift/18.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Ios CollectionViewCell的渐变层';s子视图仅在视图控制器首次进入时存在_Ios_Swift_Uicollectionview_Uicollectionviewcell_Cagradientlayer - Fatal编程技术网

Ios CollectionViewCell的渐变层';s子视图仅在视图控制器首次进入时存在

Ios CollectionViewCell的渐变层';s子视图仅在视图控制器首次进入时存在,ios,swift,uicollectionview,uicollectionviewcell,cagradientlayer,Ios,Swift,Uicollectionview,Uicollectionviewcell,Cagradientlayer,我有一个CollectionViewController,它是从另一个推送过来的。此CollectionViewController的视图有两个子视图:内部带有标签的简单UIView和UICollectionView。当它第一次出现时,一切都很好,梯度显示正确。但是当我弹出这个视图控制器(所以它被解除分配)并从同一个父视图控制器再次推送它时,渐变并没有显示出来 该单元按如下方式退出队列: func collectionView(_ collectionView: UICollectionView

我有一个
CollectionViewController
,它是从另一个推送过来的。此
CollectionViewController
的视图有两个子视图:内部带有标签的简单UIView和
UICollectionView
。当它第一次出现时,一切都很好,梯度显示正确。但是当我弹出这个视图控制器(所以它被解除分配)并从同一个父视图控制器再次推送它时,渐变并没有显示出来

该单元按如下方式退出队列:

func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
    let cell = collectionView.dequeueReusableCell(withReuseIdentifier: PageScrollGeminiCellIdentifier, for: indexPath) as! PageScrollGeminiCell
    let item = viewModel.items[indexPath.item]
    cell.configure(withTitle: item.name, description: item. description, imageURL: item.imageUrl, gradientColor: item.color, theme: theme)
    mainView.geminiView.animateCell(cell)
    return cell
}
下面是我在cell的类方法和细胞生命周期中所做的:

private var gradientColor: UIColor?
private var gradientLayer: CAGradientLayer?
[...]
override init(frame: CGRect) {
    super.init(frame: .zero)
    setupView()
}
required init?(coder aDecoder: NSCoder) {
    return nil
}
override func layoutSubviews() {
    if gradientLayer != nil {
        gradientView.layer.sublayers = nil
    }
    if let color = gradientColor {
        let gradientPoints = (CGPoint(x: 0.0, y: 0.15), CGPoint(x: 0.0, y: 1.0))
        self.gradientLayer = gradientView.applyGradient(with: [color, color.withAlphaComponent(0.08)], gradient: .vertical(gradientPoints))
    }
}
// MARK: Private
private func setupView() {
    clipsToBounds = true
    layer.cornerRadius = 15
    backgroundColor = .clear
    addSubview(containerView)
    containerView.addSubview(backgroundImageView)
    containerView.addSubview(gradientView)
    containerView.addSubview(labelsContainerView)
    labelsContainerView.addSubview(titleLabel)
    labelsContainerView.addSubview(descriptionLabel)
    containerView.snp.makeConstraints { maker in
        maker.edges.equalToSuperview()
    }
    backgroundImageView.snp.makeConstraints { maker in
        maker.edges.equalToSuperview()
    }
    gradientView.snp.makeConstraints { maker in
        maker.leading.trailing.top.bottom.equalToSuperview()
    }
    labelsContainerView.snp.makeConstraints { maker in
        maker.leading.top.equalTo(16)
        maker.trailing.equalTo(-16)
    }
    titleLabel.snp.makeConstraints { maker in
        maker.top.leading.trailing.equalToSuperview()
    }
    descriptionLabel.snp.makeConstraints { maker in
        maker.top.equalTo(titleLabel.snp.bottom).offset(8)
        maker.leading.trailing.bottom.equalToSuperview()
    }
}
// MARK: - Internal
func configure(withTitle title: String?, description: String?, imageURL: String?, gradientColor: UIColor?, theme: Themeable) {
    backgroundImageView.setImage(withString: imageURL)
    titleLabel.text = title
    titleLabel.font = theme.font.h2
    descriptionLabel.text = description
    descriptionLabel.font = theme.font.b1
    self.gradientColor = gradientColor
}
我还想向您展示
applyGradient
func:

func applyGradient(with colours: [UIColor], gradient orientation: GradientOrientation) -> CAGradientLayer {
    layoutSubviews()
    let gradient = CAGradientLayer()
    gradient.frame = self.bounds
    gradient.colors = colours.map { $0.cgColor }
    gradient.startPoint = orientation.startPoint
    gradient.endPoint = orientation.endPoint
    gradient.cornerRadius = layer.cornerRadius
    self.layer.insertSublayer(gradient, at: 0)
    return gradient
}
我发现,当视图控制器第一次出现时,layoutSubviews()方法会被调用两次,但每次下一次,每个单元格只调用一次

现在我不确定我是否在我的手机中插入了超过1个子层,但我确定我正在清除子层数组,所以我认为这不是问题。

不应该调用layoutSubviews(),应用程序会在需要时自行调用这个func(这就是为什么它在开始时被调用了两次) 如Swift开发者网站所述:

您不应该直接调用此方法。如果要强制布局更新,请在下次图形更新之前调用setNeedsLayout()方法。如果要立即更新视图的布局,请调用layoutIfNeeded()方法

尝试避免使用或调用layoutSubviews(),相反,您可以尝试在func中设置gradientLayer变量,并在需要调用时调用它,请在setupView()下面尝试


如果有帮助,请告诉我。

“第一次展示时,一切都很好”-具体展示了什么?你把风投放在哪里?@VadimF。整个问题是关于一个视图控制器(
CollectionViewController
)。我通过按导航栏上的“上一步”按钮来弹出此按钮。编辑了answI。我不调用此方法,我已覆盖它。我想您是在func applyGradient中调用它(使用颜色:[UIColor],渐变方向:GradientOrientation)->CAGradientLayer{layoutSubviews()…}我不是。它由应用程序本身在
gradient.frame=self.bounds
之后调用。