我正在我的应用程序中开发一项新功能,我希望用户拥有一张图像,然后能够在该图像的顶部扫过collectionView,并添加“过滤器”。我遇到的问题是我希望用户仍然能够与图像进行交互,但是它位于collectionView的后面。如果将collectionViews inUsersInteractionEnabled设置为false,那么我当然就不能使用collectionView。我打算使用与Snapchat的“滚动筛选器”功能类似的功能。任何帮助将不胜感激。感谢大伙们。代码如下:
import UIKit
class FirstCell: UICollectionViewCell {
override init(frame: CGRect) {
super.init(frame: frame)
setupViews()
}
func setupViews() {
backgroundColor = .clear
}
required init?(coder aDecoder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}
}
class SecondCell: UICollectionViewCell {
override init(frame: CGRect) {
super.init(frame: frame)
setupViews()
}
let cellView: UIView = {
let view = UIView()
view.backgroundColor = .red
view.alpha = 0.25
return view
}()
func setupViews() {
backgroundColor = .clear
addSubview(cellView)
cellView.frame = CGRect(x: 0, y: 0, width: self.frame.width, height: self.frame.height)
}
required init?(coder aDecoder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}
}
class SecondController: UIViewController, UICollectionViewDataSource, UICollectionViewDelegate, UICollectionViewDelegateFlowLayout {
lazy var collectionView: UICollectionView = {
let layout = UICollectionViewFlowLayout()
layout.minimumLineSpacing = 0
layout.minimumInteritemSpacing = 0
layout.scrollDirection = .horizontal
let cv = UICollectionView(frame: .zero, collectionViewLayout: layout)
cv.backgroundColor = .clear
cv.dataSource = self
cv.delegate = self
cv.translatesAutoresizingMaskIntoConstraints = false
cv.isPagingEnabled = true
return cv
}()
override func viewDidLoad() {
super.viewDidLoad()
collectionView.register(FirstCell.self, forCellWithReuseIdentifier: "firstCell")
collectionView.register(SecondCell.self, forCellWithReuseIdentifier: "secondCell")
view.backgroundColor = .white
setupViews()
}
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize {
return CGSize(width: view.frame.width, height: view.frame.height)
}
func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int {
return 2
}
func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
if indexPath.item == 0 {
let cell = collectionView.dequeueReusableCell(withReuseIdentifier: "firstCell", for: indexPath) as! FirstCell
return cell
} else {
let cell = collectionView.dequeueReusableCell(withReuseIdentifier: "secondCell", for: indexPath) as! SecondCell
return cell
}
}
lazy var imageView: UIImageView = {
let iv = UIImageView()
let image = UIImage(named: "img")
iv.image = image
iv.contentMode = .scaleAspectFill
iv.translatesAutoresizingMaskIntoConstraints = false
iv.isUserInteractionEnabled = true
iv.addGestureRecognizer(UITapGestureRecognizer(target: self, action: #selector(handleTap)))
return iv
}()
func handleTap() {
print(123)
}
func setupViews() {
view.addSubview(imageView)
view.addSubview(collectionView)
imageView.topAnchor.constraint(equalTo: view.topAnchor).isActive = true
imageView.rightAnchor.constraint(equalTo: view.rightAnchor).isActive = true
imageView.bottomAnchor.constraint(equalTo: view.bottomAnchor).isActive = true
imageView.leftAnchor.constraint(equalTo: view.leftAnchor).isActive = true
collectionView.topAnchor.constraint(equalTo: view.topAnchor).isActive = true
collectionView.rightAnchor.constraint(equalTo: view.rightAnchor).isActive = true
collectionView.bottomAnchor.constraint(equalTo: view.bottomAnchor).isActive = true
collectionView.leftAnchor.constraint(equalTo: view.leftAnchor).isActive = true
}
}
最佳答案
在任何hitTest(_::)
子类中都有一个可以覆盖的UIView
方法,您可以在自定义UICollectionView
子类中实现该方法,并将拍子从该子类转发到任何其他视图(在您的情况下,集合视图后面的图像)。
override func hitTest(_ point: CGPoint,
with event: UIEvent?) -> UIView? {
let hitView = super.hitTest(point, with: event)
if self.parentViewController.forwardTapToImageIfNeeded(point) {
return nil
}
return hitView
}
其中
parentViewController
是对您的SecondController
实例的引用,该实例应具有forwardTapToImageIfNeeded(_)
功能,以检查用户的点击是否在图像框的顶部,如果是,则自动向其传递点击事件。func forwardTapToImageIfNeeded(_ p: CGPoint) -> Bool {
/* Convert point to local coordinates */
let pointInSuperView = self.convert(p, from: collectionView)
/* Check if tap is on top of the image frame */
if imageBehindCollection.frame.contains(pointInSuperView) {
// Forward tap to the image `imageBehindCollection`
return true
}
return false
}
注意:我没有亲自测试此特定代码,因此可能需要在Xcode中进行一些修复。
关于swift - Swift 3:是否可以在collectionViewCell后面点击 View ?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/43117645/