You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
Document that widgets in the overflow of stack do not respond to gestures #19445
Since overflow is Overflow.visible, MyWidget displays outside of the Stack. However, it doesn't accept gestures in the overflowed area. I have no idea if it's easy, difficult or downright impossible to make this change, but I can think of a gazillion use cases for that, which at the moment must be satisfied by using the much more complex Overlay, or some Stack tricks.
And in case it's impossible to make this change, then at least the documentation should clearly state that overflowed content can't receive gestures.
It is intentional that widgets in the overflow area of a stack do not react to gestures and that's unlikely to change. I recommend that people with this (or similar) problems refactor their app to keep all interactable elements within the bounds of a stack.
I do realize that we are not properly documenting this behavior of the stack widget in the API docs. Let's turn this bug into a documentation issue to improve that and properly document the gesture behavior of stack on the class.
Reacted by Francesco Iapicca, Jesse, Lomash Dubey, Michael Lee, Maksim Hapeyenka and Felix Grabler
Reacted by Pikaway Developers, Gabriel Monier, Anton Bacaj, Joel Hernández, Iman Khoshabi, Gabriel Moreyra, George Javakhidze, thinkreed, Victor , BJ and 75 more
Reacted by Joel Hernández, Victor , Alex Li, Mike Behnke, Raven, Sat Mandir S. Khalsa, bitk0der, David Leibovych, Dark Chocolate, Yashwardhan Pauranik and 4 more
changed the title [-]Overflowed positioned widget inside of Stack should be clickable, or documentation updated.[/-][+]Document that widgets in the overflow of stack do not respond to gestures[/+]on Jan 7, 2019
It is intentional that widgets in the overflow area of a stack do not react to gestures and that's unlikely to change. I recommend that people with this (or similar) problems refactor their app to keep all interactable elements within the bounds of a stack.
I do realize that we are not properly documenting this behavior of the stack widget in the API docs. Let's turn this bug into a documentation issue to improve that and properly document the gesture behavior of stack on the class.
@goderbauer Do you know a way around this? it seems like a bug otherwise how can we have one widget on top of another and the one behind it has a tap detector?
So the answer to this is to formalise the issue by documenting it?
Reacted by Andrew Young, Michael Joseph Rosenthal, Thien Chi Vi, Vamsi Krishna, sctajc, Travis Ziegler, ssantanuberaa, Full Stack Developer, Luke Brenton, Mehmet Yılmaz and 8 more
Reacted by ssantanuberaa, Alexey Lihachev, Tanase Hagi and Shubham Soni
Hi guys, I also hit the same rock with an ongoing redesign in our app.
We used an OverlayEntry to display the elements that were overlapping in the Stack. You need to get the position + size of the element which you want to put the other widgets on top of, with that you can position the OverlayEntry using those coordinates.
Doing this, you can get the same position you were doing with the Stack, but now your elements that are overlapping can handle gestures.
The only problem with this is that the overlay is fixed to those coordinates in the device's viewport. For a scrolling page, the overlay will be floating around, to solve this we used CompositedTransformTarget and CompositedTransformFollower, wrapping the target element with the former and the overlapping widget with the latter, both accept a link: LayerLink property, that lets you linked them, with this your overlay will follow the target widget while you scroll.
Something like this:
final _layerLink =LayerLink();
...
returnCompositedTransformTarget(
link: _layerLink,
child:Text('Overlay target'),
);
...
_overlay =OverlayEntry(builder: (_) {
finalRenderBox renderBoxRed = context.findRenderObject(); // BuildContext of the target elementfinal position = renderBoxRed.localToGlobal(Offset.zero);
final size = renderBoxRed.size;
returnPositioned(
left:16, // Horizontal positioning
right:16,
child:CompositedTransformFollower(
link: _layerLink,
offset:Offset(0, (position.dy + size.height)), // Vertical positioning using the target dimensions
child:Text('Overlay follower...'),
),
);
});
}
Overlay.of(context).insert(_overlay);
Hope it helps, if you want to know more about those widgets and different approaches on how to get a widget's size and position, check out these great articles that guided me to this approach.
Well it works fine on Android, iPhone, ... Except the iPhone XS Max (because of its rounded corners a part of this widget becomes invisible and it becomes unclickable).
It is intentional that widgets in the overflow area of a stack do not react to gestures and that's unlikely to change. I recommend that people with this (or similar) problems refactor their app to keep all interactable elements within the bounds of a stack.
I do realize that we are not properly documenting this behavior of the stack widget in the API docs. Let's turn this bug into a documentation issue to improve that and properly document the gesture behavior of stack on the class.
So what is the way to get the gesture when you have a positioned widget to be out of bounds of a container then?
Agreed, Because you are going to have lots of cases with design where you have a big button sitting at a bottom of a square which is a button and so on. To say you can not because it is instead cuts out a lot of designs.
This seems like something that should be a choice for the developer, not a limitation of the framework. I'm ok if the default is how it works currently, but an option to allow the click to allow for interaction outside of the stack boundaries would give that choice to the developer and allow for more options.
I was trying to implement a TapOutside widget that blocks interaction with other elements on the screen when a TextField is focused, and clears focus when tapped (and then allows interaction again). That's when I ran into this limitation. I don't think I can use a ModalRoute, as I want the user to click on and use a TextField that exists in the current screen (not push them to a new route).
I don't want to get too much more specific on the use case or ask for help (although if there is a "Flutter way" that I'm not seeing, I would potentially withdraw my complaint), just trying to demonstrate that there could be a use case. I've also looked into adding a GestureDetector at the root of the screen, and while that "works" for clicks not on other elements, because it's at the root, clicks on it do not block clicks on other elements on the screen. Maybe something with RawGestureDetector would work, but that seems like an awfully complex solution when putting a transparent barrier over the elements when the widget is focused is very simple. It just doesn't work due to this issue.
Reacted by Adrian, Giraldi Maggio, Nicholas Ray, Michael Joseph Rosenthal, David Beljan, Cleofas Villarin, John Lanz, Ozan Pedersen Benn, Vamsi Krishna, Timur Ganiev and 12 more
I agree that this should be left up to the developer. This is the second time I've come across this issue. My first time around I found a decent enough work around, now, it's incredibly verbose to get what I am aiming at when really this should just be left up to the developer to decide, not necessarily a design limitation of the framework.
Reacted by Nathan Cabasso, Giraldi Maggio, Nicholas Ray, Shawn, Ozan Pedersen Benn, ssantanuberaa, Luke Brenton, Hewa Jalal, Bloction Dapp, Kishan and 1 more
I understand the disappointment. Unfortunately, performing hit-testing outside of the bounds of a stack in the overflow is prohibitively expensive in terms of performance.
I do still believe that you can always restructure your app to not require hit-testing in the overflow of a stack. Maybe, people can post some runnable code examples of where you'd like to do hit testing in the overflow of the stack and we can figure out how to restructure the code to not require that. Those example uses cases would also be good for us to include in the updated docs of overflow.
gesture detector is showing weird behavior... for one Screen it is working outside the stack and and for other screen it is not working.
so i solved this using a container with padding top or bottom and color transparent... this way gesture detector detect tap as it comes inside of stack area and is clickable
I faced the same issue now and resolved it as follows.
This can not apply to every case but some cases would be solved.
In my case, I need to overlap half of the tappable widget to the end of the bigger container.
The key is Make a Stack bigger than you need and locate tappable positioned widget at the end
This thread has been automatically locked since there has not been any recent activity after it was closed. If you are still experiencing a similar issue, please open a new bug, including the output of flutter doctor -v and a minimal reproduction of the issue.
Activity
goderbauer commentedon Jan 7, 2019
It is intentional that widgets in the overflow area of a stack do not react to gestures and that's unlikely to change. I recommend that people with this (or similar) problems refactor their app to keep all interactable elements within the bounds of a stack.
I do realize that we are not properly documenting this behavior of the stack widget in the API docs. Let's turn this bug into a documentation issue to improve that and properly document the gesture behavior of stack on the class.
[-]Overflowed positioned widget inside of Stack should be clickable, or documentation updated.[/-][+]Document that widgets in the overflow of stack do not respond to gestures[/+]abacaj commentedon Mar 8, 2019
Has anyone been able to achieve the same desired effect?
I need a stack where one widget slides up behind another and it has a gesture for pressing on it.
abacaj commentedon Mar 8, 2019
@goderbauer Do you know a way around this? it seems like a bug otherwise how can we have one widget on top of another and the one behind it has a tap detector?
lifenautjoe commentedon Mar 13, 2019
So the answer to this is to formalise the issue by documenting it?
frederickcxa commentedon Mar 20, 2019
Hi guys, I also hit the same rock with an ongoing redesign in our app.
We used an
OverlayEntryto display the elements that were overlapping in theStack. You need to get the position + size of the element which you want to put the other widgets on top of, with that you can position theOverlayEntryusing those coordinates.Doing this, you can get the same position you were doing with the
Stack, but now your elements that are overlapping can handle gestures.The only problem with this is that the overlay is fixed to those coordinates in the device's viewport. For a scrolling page, the overlay will be floating around, to solve this we used
CompositedTransformTargetandCompositedTransformFollower, wrapping the target element with the former and the overlapping widget with the latter, both accept alink: LayerLinkproperty, that lets you linked them, with this your overlay will follow the target widget while you scroll.Something like this:
Hope it helps, if you want to know more about those widgets and different approaches on how to get a widget's size and position, check out these great articles that guided me to this approach.
Flutter: Using Overlay to display floating widgets
Flutter : Widget Size and Position
Skyost commentedon Apr 9, 2019
The problem with all of this is when I want to position an element like this :
Well it works fine on Android, iPhone, ... Except the iPhone XS Max (because of its rounded corners a part of this widget becomes invisible and it becomes unclickable).
genesiscz commentedon May 10, 2019
So what is the way to get the gesture when you have a positioned widget to be out of bounds of a container then?
thenexus00 commentedon May 13, 2019
Agreed, Because you are going to have lots of cases with design where you have a big button sitting at a bottom of a square which is a button and so on. To say you can not because it is instead cuts out a lot of designs.
localpcguy commentedon Jun 6, 2019
This seems like something that should be a choice for the developer, not a limitation of the framework. I'm ok if the default is how it works currently, but an option to allow the click to allow for interaction outside of the stack boundaries would give that choice to the developer and allow for more options.
I was trying to implement a TapOutside widget that blocks interaction with other elements on the screen when a TextField is focused, and clears focus when tapped (and then allows interaction again). That's when I ran into this limitation. I don't think I can use a ModalRoute, as I want the user to click on and use a TextField that exists in the current screen (not push them to a new route).
I don't want to get too much more specific on the use case or ask for help (although if there is a "Flutter way" that I'm not seeing, I would potentially withdraw my complaint), just trying to demonstrate that there could be a use case. I've also looked into adding a GestureDetector at the root of the screen, and while that "works" for clicks not on other elements, because it's at the root, clicks on it do not block clicks on other elements on the screen. Maybe something with RawGestureDetector would work, but that seems like an awfully complex solution when putting a transparent barrier over the elements when the widget is focused is very simple. It just doesn't work due to this issue.
adriancmurray commentedon Jun 12, 2019
I agree that this should be left up to the developer. This is the second time I've come across this issue. My first time around I found a decent enough work around, now, it's incredibly verbose to get what I am aiming at when really this should just be left up to the developer to decide, not necessarily a design limitation of the framework.
goderbauer commentedon Jun 13, 2019
I understand the disappointment. Unfortunately, performing hit-testing outside of the bounds of a stack in the overflow is prohibitively expensive in terms of performance.
I do still believe that you can always restructure your app to not require hit-testing in the overflow of a stack. Maybe, people can post some runnable code examples of where you'd like to do hit testing in the overflow of the stack and we can figure out how to restructure the code to not require that. Those example uses cases would also be good for us to include in the updated docs of overflow.
48 remaining items
Akifcan commentedon Dec 5, 2020
move clickable widget to bottom side like this
IlyaMax commentedon Dec 29, 2020
https://dartpad.dev/2ec6318a6658af7501af8f482b84364f? solution
leegohi04517 commentedon Apr 25, 2021
why closed this issue
snoopdoggy322 commentedon Apr 27, 2021
Please fix this issue 🙏🏻
esDotDev commentedon Apr 27, 2021
This is the best bet for getting a fix for this anytime soon, please share your use cases here:
#75747
yasinarik commentedon May 29, 2021
Why is this issue still considered as "works as expected" or "works as intended"?
Clearly, an undeniable amount of power users of Flutter facing it.
AliYar-Khan commentedon Jun 7, 2021
code example will be appreciated
Hwan-seok commentedon Jul 3, 2021
I faced the same issue now and resolved it as follows.
This can not apply to every case but some cases would be solved.
In my case, I need to overlap half of the tappable widget to the end of the bigger container.
The key is
Make a Stack bigger than you need and locate tappable positioned widget at the endMinimum reproduction codes:
Result UI of mine:

Turn on Widget Inspector:

mitchellsion commentedon Jul 4, 2021
Wrapping
StackwithSizedBoxworked for meadschi commentedon Jul 16, 2021
Any updates on this? Got a production app and really need this feature.
leegohi04517 commentedon Jul 19, 2021
why closed the issue???
marcglasberg commentedon Jul 25, 2021
Hey everyone, this issue was closed because it's now only asking for the documentation to clearly state the limitation.
This documentation change was actually done by #60726
Please note, there are other issues that could solve this, here:
And there is also this package:
However, it really doesn't work well because it can't feel a tap outside of the parent's bound.
github-actions commentedon Aug 9, 2021
This thread has been automatically locked since there has not been any recent activity after it was closed. If you are still experiencing a similar issue, please open a new bug, including the output of
flutter doctor -vand a minimal reproduction of the issue.