In the example below we have a tappable red container inside a green container.
Problem: when tapping the red container, BOTH the Listener and GestureDetector receive events, which is a mistake. (Only the topmost widget should get a tap event, when tapped. And only the green widget should get an event when tapped). If both wrapped with GestureDetector, only the topmost widget gets the event.

import 'package:flutter/material.dart';
void main() => runApp(MyApp());
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Welcome to Flutter',
home: Scaffold(
appBar: AppBar(
title: Text('Welcome to Flutter'),
),
body: Center(
child: Column(children: [
// Parent-child -- two events when red is tapped
GestureDetector(
onTap: () {
print("Green");
},
child: Container(
color: Colors.green,
width: 100.0,
height: 100.0,
child: Center(
child: Listener(
behavior: HitTestBehavior.opaque,
onPointerDown: (_) {
print("Red");
},
child: Container(
color: Colors.red,
width: 50.0,
height: 50.0,
),
),
),
),
),
])),
),
);
}
}
as an option wrap Listener with GestureDetector to prevent event bubbling
import 'package:flutter/material.dart';
void main() => runApp(MyApp());
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Welcome to Flutter',
home: Scaffold(
appBar: AppBar(
title: Text('Welcome to Flutter'),
),
body: Center(
child: Column(children: [
// Parent-child -- two events when red is tapped
GestureDetector(
onTap: () {
print("Green");
},
child: Container(
color: Colors.green,
width: 100.0,
height: 100.0,
child: Center(
child: GestureDetector(
behavior: HitTestBehavior.opaque,
onTap: (){},
child: Listener(
behavior: HitTestBehavior.opaque,
onPointerDown: (_) {
print("Red");
},
child: Container(
color: Colors.red,
width: 50.0,
height: 50.0,
),
),
),
),
),
),
])),
),
);
}
}
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