I've got a List view and each row of the list contains an HStack with some text view('s) and an image, like so:
HStack{
Text(group.name)
Spacer()
if (groupModel.required) { Text("Required").color(Color.gray) }
Image("ic_collapse").renderingMode(.template).rotationEffect(Angle(degrees: 90)).foregroundColor(Color.gray)
}.tapAction { self.groupSelected(self.group) }
This seems to work great, except when I tap in the empty section between my text and the image (where the Spacer()
is) the tap action is not registered. The tap action will only occur when I tap on the text or on the image.
Has anyone else faced this issue / knows a workaround?
The VStack allows you to stack views vertically, from top to bottom. You can further customize the view by adding alignment or spacing to the VStack.
A view that arranges its subviews in a vertical line.
As I've recently learned there is also:
HStack {
...
}
.contentShape(Rectangle())
.onTapGesture { ... }
Works well for me.
Why not just use a Button
?
Button(action: { self.groupSelected(self.group) }) {
HStack {
Text(group.name)
Spacer()
if (groupModel.required) { Text("Required").color(Color.gray) }
Image("ic_collapse").renderingMode(.template).rotationEffect(Angle(degrees: 90)).foregroundColor(Color.gray)
}
}.foregroundColor(.primary)
If you don't want the button to apply the accent color to the Text(group.name)
, you have to set the foregroundColor
as I did in my example.
works like magic on every view:
extension View {
func onTapGestureForced(count: Int = 1, perform action: @escaping () -> Void) -> some View {
self
.contentShape(Rectangle())
.onTapGesture(count:count, perform:action)
}
}
The best approach in my opinion for accessibility reasons is to wrap the HStack inside of a Button label, and in order to solve the issue with Spacer can't be tap, you can add a .contentShape(Rectangle())
to the HStack.
So based on your code will be:
Button {
self.groupSelected(self.group)
} label: {
HStack {
Text(group.name)
Spacer()
if (groupModel.required) { Text("Required").color(Color.gray) }
Image("ic_collapse").renderingMode(.template).rotationEffect(Angle(degrees: 90)).foregroundColor(Color.gray)
}
.contentShape(Rectangle())
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With