Пользовательская форма регистрирует касания за пределами нарисованного контура
Я создал пользовательскую форму в SwiftUI, но когда я добавляю к ней модификатор, он регистрирует касания за пределами области, которую я нарисовал для (он регистрирует касания в любом месте в пределах используемого для рисования). Как сделать так, чтобы касания регистрировались только в пределах нарисованного пути, а не на всем
rect
?
Вот фигура, которую я нарисовал:
struct Arc: Shape {
let angle: Angle
let thickness: CGFloat
let clockwise: Bool
func path(in rect: CGRect) -> Path {
var path = Path()
let innerArcEndPoint = CGPoint(x: rect.maxX - thickness, y: 0)
let innerArcStartPoint = CGPoint(
x: innerArcEndPoint.x * cos(CGFloat(angle.radians)),
y: innerArcEndPoint.x * sin(CGFloat(angle.radians)))
path.move(to: innerArcStartPoint)
path.addArc(center: rect.origin, radius: innerArcEndPoint.x, startAngle: angle, endAngle: Angle.zero, clockwise: !clockwise)
path.addLine(to: CGPoint(x: rect.maxX, y: 0))
path.addArc(center: rect.origin, radius: rect.maxX, startAngle: Angle.zero, endAngle: angle, clockwise: clockwise)
path.closeSubpath()
return path
}
}
Вот я использую
Arc
с
onTapGesture
модификатор:
struct TestTappingArc: View {
var body: some View {
Arc(angle: Angle(degrees: 45), thickness: 20, clockwise: false)
.foregroundColor(.blue) // The only area I want to be tappable
.background(Color.orange) // The area I DON'T want to be tappable (but currently is tappable)
.frame(width: 100, height: 100)
.onTapGesture {
print("hello")
}
}
}
А вот как это выглядит на экране:
2 ответа
Вам нужно использовать
contentShape
с той же формой, чтобы ограничить область проверки попадания (потому что вид всегда прямоугольный), например
Arc(angle: Angle(degrees: 45), thickness: 20, clockwise: false)
.foregroundColor(.blue)
.contentShape(Arc(angle: Angle(degrees: 45), thickness: 20, clockwise: false))
.onTapGesture { // << here !!
print("hello")
}
.background(Color.orange)
.frame(width: 100, height: 100)
Спасибо, Аспери, за этот ответ - это решает проблему. Тем не менее, я понял , еще более простое решение , это просто переместить фон , чтобы после того, какonTapGesture
модификатор, например:
Arc(angle: Angle(degrees: 45), thickness: 20, clockwise: false)
.foregroundColor(.blue)
.frame(width: 100, height: 100)
.onTapGesture {
print("hello")
}
.background(Color.orange)