Device-Bugs icon indicating copy to clipboard operation
Device-Bugs copied to clipboard

-webkit-overflow-scrolling: touch does not "obey" z-index

Open bridgestew opened this issue 13 years ago • 34 comments

Summary:

-webkit-overflow-scrolling: touch does not "obey" z-index.

Platforms:

iOS5, not sure about other platforms

How to reproduce:

  1. Build a content area and a modal overlay above it using HTML/CSS
  2. View on iPad for the example below. When you attempt to scroll the page, the content behind the modal scrolls. I wouldn't expect this, since attempting to click a link behind a z-index div doesn't work...

Reduced Example:

(Hastily thrown together example. No Media queries applied, so ignore the ugly -- just check out the bug.) http://jsfiddle.net/cPHMN/48/embedded/result/

Bug Tracker ticket(s):

Workarounds:

bridgestew avatar Mar 27 '12 15:03 bridgestew

Interesting. This sounds and looks similar to how touch devices vary in their bubbling of scroll events on elements in the page.

Is your scroll region short enough to trigger a scroll? I wonder how it'll behave if it is...

On Mar 27, 2012, at 9:19 PM, bridgestew wrote:

Summary:

-webkit-overflow-scrolling: touch does not "obey" z-index.

Platforms:

iOS5, not sure about other platforms

How to reproduce:

  1. Build a content area and a modal overlay above it using HTML/CSS
  2. View on iPad for the example below. When you attempt to scroll the page, the content behind the modal scrolls. I wouldn't expect this, since attempting to click a link behind a z-index div doesn't work...

Reduced Example:

(Hastily thrown together example. No Media queries applied, so ignore the ugly -- just check out the bug.) http://jsfiddle.net/cPHMN/48/embedded/result/

Bug Tracker ticket(s):

Workarounds:


Reply to this email directly or view it on GitHub: https://github.com/scottjehl/Device-Bugs/issues/14

scottjehl avatar Mar 29 '12 08:03 scottjehl

I don't understand your question about the scroll region being short enough. :)

bridgestew avatar Apr 24 '12 15:04 bridgestew

One workaround is to apply the same overflow: scroll and -webkit-overflow-scrolling: touch on the layer above it to stop the lower one from getting the events.

moll avatar May 06 '12 08:05 moll

I think I ran into the same issue with my custom map component.

I have a large pannable image (with -webkit-overflow-scrolling: touch) and absolutely positioned marker images on top. Sometimes I get one marker to show up, but usually they are hidden no matter what the z-index is.

Any solutions yet for this?

kpuputti avatar May 28 '12 07:05 kpuputti

@kpuputti This bug's problem with z-index is only functional — visually the items are correct. You sure the map you've got has a lower z-index than all the markers?

moll avatar May 28 '12 07:05 moll

@moll Yes, the z-index on the map is lower than on the markers.

I'm using Overthrow ( http://filamentgroup.github.com/Overthrow/ ) and the map works fine on Android 2.3 & 4.0, WP7, iOS 4.2. Of these platforms, at least Android 4.0 supports the native touch scrolling.

This comment is the only info I've found: http://mobile.tutsplus.com/tutorials/mobile-web-apps/ios-5-fixed-positioning-and-content-scrolling/comment-page-1/#comment-17477

kpuputti avatar May 28 '12 07:05 kpuputti

Oh, I found the solution. My problem seemed to be the same as in this issue:

https://github.com/scottjehl/Device-Bugs/issues/8

and the proposed workaround fixed the problem.

kpuputti avatar May 28 '12 08:05 kpuputti

This is not a bug; -webkit-overflow-scrolling: touch induces a stacking context. Just like if you put opacity: 0.9 or a 3d transform on the element.

hober avatar Aug 28 '12 00:08 hober

Thanks for chiming in with this info @hober.

toddparker avatar Aug 28 '12 01:08 toddparker

@hober How is this not a bug? I have my context layered properly and -webkit-overflow-scrolling: touch on the top most layer. Functionally everything works properly, except that the background scrolls instead of my modal, unless I use the scrollbar to scroll the div (which contains an unavoidable iFrame). Has anyone else found a workaround for this?

cstewartgannett avatar Feb 20 '13 16:02 cstewartgannett

Hello all,

I am in the same boat here, unfortunately. But I did find a solution to this. Actually only one, for now.

The solution that I've found is to turn off overflow for the DIV underneath (having lesser z-index) using "overflow:hidden". This seems to trick iOS into capturing the touch events on the top-most DIV (having a higher z-index).

The only downside to this trick, however, is once the DIV having the higher z-index is dismissed (using animation or not), and "overflow:auto" or "overflow:scroll" is reapplied to the DIV underneath, a short "flick" is noticed as if the iOS is redrawing that DIV.

If any of you guys or gals found a better solution, it'd be nice to share.

/Noor

noordawod avatar May 12 '13 15:05 noordawod

@noordawod:

If any of you guys or gals found a better solution, it'd be nice to share.

Well, I consider the workaround I posted a year ago to be a better solution as it doesn't require JavaScript nor changes other elements' styles.

moll avatar May 12 '13 17:05 moll

@moll

I've seen and checked your proposed solution before. Surely, I had these CSS rules in place since I wanted the top DIV to have a scrollbar, even before I saw your post (it only made sense to me.)

Now, the interesting thing is that although this works when the DIV is displayed without any animation, the solution doesn't work when animating the DIV (for example, making it appear by sliding it from the bottom of the screen to the top, like Safari's Bookmarks panel on the iPhone.)

This must be a bug in iOS's transformations, I am guessing. Not opacity, as @hober suggested, since when I show the DIV instantly without an animation, and set its opacity to 0.9, scrolling still works.

So we're back to the first post by @bridgestew since it doesn't work when the DIV is animated, sadly.

/Noor

noordawod avatar May 12 '13 20:05 noordawod

And like I mentioned before, only setting overflow to hidden on the lower DIV makes the top DIV respond to touch scrolling (when the top DIV has been animated to its position.)

noordawod avatar May 12 '13 20:05 noordawod

Here's more information about a stacking context, introduced by @hober : http://daneden.me/2012/04/css-transforms-and-z-index/

noordawod avatar May 12 '13 20:05 noordawod

@moll your trick works. Thanks!

thztti avatar Sep 02 '13 15:09 thztti

I stumbled onto this conversation because I have a similar issue that I have now fixed. I have a menu panel that is absolutely positioned above the main page. I hide/show this panel using an opacity transition. Both this panel and the main page use -webkit-overflow-scrolling:touch. My problem was that when showing the menu the scrolling would not work and instead the main page behind it would scroll. To fix this, I simply removed the -webkit-overflow-scrolling:touch from the menu when hidden and add it back when shown. It seems that the order in which this value is added is very important here. I was surprised to see that there is no flicker when you do this.

Cheers

tymcdowell avatar Oct 02 '13 18:10 tymcdowell

@moll seems not working on ios7

sofish avatar May 24 '14 18:05 sofish

This bug appears to be gone in iOS8.

joeybaker avatar Aug 27 '14 14:08 joeybaker

Still present on iOS 8.1.

iclanzan avatar Dec 30 '14 23:12 iclanzan

Like @iclanzan, I can confirm it is still present in iOS 8.1 Here's what I think is the relevant bug report on Webkit Bugzilla

Edit: nope.

~~My workaround:~~

.modal {
    overflow-y: scroll;
    -webkit-overflow-scrolling: touch;
}
.content-behind-modal {
    overflow: hidden;
    -webkit-overflow-scrolling: auto;
}

janson avatar Jan 19 '15 15:01 janson

@moll your trick did indeed work like a charm, until iOS8 was released. i could change the -webkit-overflow-scroll: auto; (as mentioned by @jason) but that adds a flicker that I'm not willing to live with.

shi-sergiom avatar May 01 '15 00:05 shi-sergiom

@noordawod calling the css as part of the animation queue solved the problem for me. ("div").css("webkit-overflow-scrolling" , "touch");

robinscholz avatar Aug 25 '15 10:08 robinscholz

Just target IOS device with media query and put overflow:touch; instead of -webkit-overflow-scrolling: touch; that works for me :-)

manoj30dec avatar Oct 08 '15 13:10 manoj30dec

Is there any working workaround for this issue? (The workaround from @moll does not work in my case, the one from @noordawod does, however while the short flicker is still acceptable, the repaint causes heavy performance problems which are far from acceptable)

Two things I've noticed (testing with iPhone 5+6 on iOS 9.1 and 9.3.2): • it only occurs when launching the page/app from the homescreen (pinned app) • changing the device orientation (portrait -> landscape) after page load fixes the problem and everything works as expected

PS: why are the default bullet points bold and enormously large?

Edit: I was able to reduce my project source to a rather comprehensible MCVE (check out this pen). To see the described behaviour you have to load the full-screen version (full) on a iOS device, save it to your home screen and call it from there. Then touch the yellow bar and try to scroll the list below.

ScallyGames avatar Jun 06 '16 15:06 ScallyGames

It seems that this issue (at least in some cases) does not occur when removing

html, body
{
    width: 100%;
    height: 100%;
}

from the CSS.

This is not a suitable solution however, since those declarations are essential for percentage scale values to work.

ScallyGames avatar Jun 08 '16 06:06 ScallyGames

-webkit-overflow-scrolling: touch; overcomes z-index . and if we remove it then the scroll flickers. Is there any good solution of it?

gauravksoni avatar Apr 03 '17 16:04 gauravksoni

Yeah, do like I did years ago: ditch hybrid and go native.

noordawod avatar Apr 07 '17 08:04 noordawod

@gauravksoni Well. I choose to change some html structure to meet the demand.Becase of the mechanism of z-index.

CommanderXL avatar Sep 13 '17 07:09 CommanderXL

Wow, 5 years topic.

I haven't been to this since yesterday, surprisingly its weird not to face with it.

3 hours of research i come up with, overflow:hidden to outer most div-element. (i can say body) this works with the position:fixed inner element situations.

You should care all your segmented elements stack context transform - z-index properties.

kaankucukx avatar Jan 29 '18 11:01 kaankucukx