#ios #swift #uiview #ontouchlistener #event-bubbling
#iOS #swift #uiview #ontouchlistener #событие-пузырящийся
Вопрос:
У меня есть дочерний вид, наложенный на родительский вид. К обоим подключены touchUpInside
прослушиватели. Когда пользователь нажимал дочернее, я хочу, чтобы и дочернее, и родительское представление реагировали на это событие касания. Когда пользователь нажимает только родительский, я хочу, чтобы запускался только родительский прослушиватель.
Как мне это сделать?
Я попытался переопределить следующий метод в моем дочернем представлении, но возврат false здесь полностью игнорирует событие для дочернего устройства. И наоборот, если я обрабатываю событие касания в дочернем, оно игнорируется для родительского.
override func point(inside point: CGPoint, with event: UIEvent?) -> Bool {
return false
}
Ответ №1:
Если у вас есть подклассы для обоих представлений, вы можете переопределить метод UIView touchesBegan. Если вы вызываете метод super touchesBegan
, то это должно привести к результату, который вам нужен, когда событие перемещается вверх по цепочке ответчиков. (т. Е. Если пользователь нажимает на дочернее представление, событие касания как для дочернего, так и для родительского будет реагировать)
override func touchesBegan(_ touches: Set<UITouch>, with event: UIEvent?) {
super.touchesBegan(touches, with: event)
print("TOUCHED")
}
Ответ №2:
Краткий пример…
Коснитесь «innerView», и вы увидите два отладочных отпечатка «касания начались». Коснитесь «outerView», и вы увидите только одно.
class TouchView: UIView {
override func touchesBegan(_ touches: Set<UITouch>, with event: UIEvent?) {
super.touchesBegan(touches, with: event)
print("touches began in (self)")
}
}
class TouchTestViewController: UIViewController {
let innerView: TouchView = {
let v = TouchView()
v.translatesAutoresizingMaskIntoConstraints = false
v.backgroundColor = .red
return v
}()
let outerView: TouchView = {
let v = TouchView()
v.translatesAutoresizingMaskIntoConstraints = false
v.backgroundColor = .cyan
return v
}()
override func viewDidLoad() {
super.viewDidLoad()
view.addSubview(outerView)
outerView.addSubview(innerView)
NSLayoutConstraint.activate([
outerView.widthAnchor.constraint(equalToConstant: 300),
outerView.heightAnchor.constraint(equalToConstant: 300),
outerView.centerXAnchor.constraint(equalTo: view.centerXAnchor),
outerView.centerYAnchor.constraint(equalTo: view.centerYAnchor),
innerView.widthAnchor.constraint(equalToConstant: 150),
innerView.heightAnchor.constraint(equalToConstant: 150),
innerView.centerXAnchor.constraint(equalTo: outerView.centerXAnchor),
innerView.centerYAnchor.constraint(equalTo: outerView.centerYAnchor),
])
}
}