Web pages on iOS by default have a “momentum” style scrolling where a flick of the finger sends the web page scrolling and it keeps going until eventually slowing down and stopping as if friction is slowing it down. Like if you were to push a hockey puck across the ice or something. You might think that any element with scrolling would have this behavior as well, but it doesn’t. You can add it back with a special property.
.module {
width: 300px;
height: 200px;
overflow-y: scroll; /* has to be scroll, not auto */
-webkit-overflow-scrolling: touch;
}
Check out this Pen!
Hey Chris,
Is there a way to prevent the momentum scrolling on desktop (using a magic mouse or trackpad) as well as on iOS? I have been searching for a long time, but without luck.
Hey David, you can implement a scroll debouncer that can limit to only 1 scroll event being run every few milliseconds. Thing is, it will be far from perfect and in several cases may feel pretty unnatural.
Perhaps I’ll write a simple tutorial for this.
Why would you ever want to do that? That’d be the most annoying thing.
You could check for touch events with modernizr or something like it, and then only apply the rule in certain cases.
Checking for touch events is unreliable. Too many false positives and even at Modernizr they don’t recommend it.
Hey, you could try to use
@media
feature to see the size of your screen and if it is so small then the code works, but if it is bigger than x value it will not work, for example:That will only apply to a screen size max of 768px. That’s the simplest way, and it is how many websites do it
if i use -webkit-overflow-scrolling:touch, when page are scrolling, i tap a button to reset the container of scrollTop = 0 , in ios or android, it can stop scrolling but it can’t go to the top of container
Hi this seemed to work really well until Feb 2019 – when there seems to be some rendering issues – anyone else encountered this?
Chris, momentum scrolling doesn’t seem work inside an iframe. I’ve tried several settings, I’ve also tried to iframe in the demo,
http://playground.johanbrook.com/css/touchtest.html
But it doesn’t produce scrollbars 99% of the time. Looking into a hack.
Chandra, did you find a solution to touch scrolling on iframes? I’m getting mad after the same problem…
Yeah, it doesn’t work on iframes. If you wrap the iframe in a container and put the
-webkit-overflow-scrolling: touch
andoverflow-y: scroll
on that, it should work. See this Codepen.Kristie, thanks for the codepen example – it totally solved our problem!
Thanks this works perfectly!
Do you have anything to resolve the milisecond lag when clicking on a link on a touch device?
I’m currently using webkit-touch-scrolling to increase performance the performance of scrolling in iPad and iPhone web applications. It has significantly increased performance, but just like most applications that use a timeline like environment with images, the iPad runs out of memory when a lot of ’tiles’ have loaded.
Is there any way to track the scroll position when momentum scrolling? Much like the ‘touchmove’ and ‘scroll’ event? So far I have seen lot of no’s.
My current solution would be to set a variable when the user starts scrolling and set a setTimeout() to an X amount of milliseconds to ‘simulate’ the scroll function.
This is just a little side note, the reason you run out of memory is because apple will only allow you to have 10 mb of ram with web applications. Why would they let you create native like applications on the web? If you could, there would be no reason to pay to be in their app store. We need to hold them accountable.
Had the same problem as you, iOS safari crashing. I debugged this for over a day, because I was sure the memory crash was due to hundreds of Angular hg-repeat elements(empty ones, which loads images upon scroll position).
The funny thing is, when debugging this in iOS Simulator, it doesn’t occur! Another funny fact is that I went from a menu with position:fixed, because the menu pops down when a input field is activated(rendering halts upon window resize), but at the same time changing the input field to a select field which doesn’t pull up the keyboard. So all i all, I just implemented a bug which wasn’t even needed, argh!
For others that might search for this, I will include that the browser crashed upon invoking $location.hash(id) and $anchoScroll().
happy
I tested your demo on Windows Phone (IE10) and both divs. scrolled kinetically.
This is only an issue with iOS. Both Android and WP behave properly without the use of ridiculous proprietary styles.
Exactly what I needed, Chris!
And I think you might be from the future, because you always seem to foresee what I’m going to need next. Very appreciated, man!
So incredibly helpful. Thank you!
I was wondering how I managed to accidentally disable the momentum scroll.
Thanks! So relieved CSS fixes this!
Every time I try this style out, some of the content on some of my pages just disappears –– has anyone else had this problem? The elements that disappear still take up space (so it’s not like they’re
display:none;
) I can see the content when I look in Chrome’s inspector window, and the yellow indicator points to where my content is supposed be, and it basically points to these invisible divs that haveheight:0px;
It’s definitely these “momentum scrolling” styles causing this. I’ve tried only deleting those styles, and my content comes back, but then goes poof when I add the them again.
Because I wanted the whole page to have the momentum scrolling, this is how I did my styles:
Any ideas what I might be doing wrong? Any thoughts much appreciated.
Oops – nevermind! Tried adding the style to
html
instead, worked like a charm. DuhYup, you got it right Annie: thanks! It works like a charm. :)
Hey! I sat next to you at the jQuery conference in San Diego! lol
Thank you Annie! I’ve fixed my issue! Change the -webkit-overflow-scrolling to none before to change overflow to hidden so I can prevent the disappearing :)
Thanks buddy!
I noticed that using
overflow-y: auto;
(from Chris’s example) also works. Tested in the native browser and Chrome of a Samsung tablet with Android 4.0.4 and also on iPad with iOS 6, Safari + Chrome.overflow-y: auto; is working on all browser for me but not working on iPad. I am using following Style:
.m-scrollable-filter {
overflow-x: hidden !important;
overflow-y: auto !important;
-webkit-overflow-scrolling: touch !important;
}
pls give me any response.
Thanks
Chris said in the article that
overflow-y
must be set toscroll
for-webkit-overflow-scrolling: touch
to work. So use this code instead (there’s no need for!important
):Anyone have this associated issue and know how to prevent it (or what I’m doing wrong)?…
I have a div within a wrapper div which specifically allows horizontal scrolling but prevents vertical scrolling. Everything is fine except that on ipad it remains possible to vertically lift the entire div, which then bounces back on release. What is more annoying is that this then allows the same div to ‘drag’ diagonally with a diagonal swipe. Here’s the page in progress…
http://raewilkinson.scratchthesky.com/
I fixed this issue with javascript that prevents the default scroll-bounce behaviour in the vertical axis. It works but it’s not ideal. I still have no insight into how the entire div could become ‘dragable’ in every direction.
I had the other case where the content was scrollable in vertical direction. I had this style applied:
Even when there were no need for horisontal scroll, it behaved like if you drag horizontally it moves the content sideways and bounce back. I solved this by doing:
This cause momentum to be used only in y-direction, since momentum is disabled when setting overflow to auto.
You can set it the other way:
overflow-y:auto
to only use momentum in x-direction.If I add this:
overflow-y: scroll; /* has to be scroll, not auto */
to the html, or body, or any major block of my website I get no scroll improvements and I cannot tap on the top bar to scroll to the top. Any idea why?-webkit-overflow-scrolling: touch;
You don’t need to add it to
html
orbody
on your webpages; Apple uses momentum scrolling on all pages automatically.-webkit-overflow-scrolling: touch
is just for scrolling other elements on the page (only being able to scroll, say, ap
). Also,touch
scrolling gives no “scroll improvements” — it just lets you flick your finger to quickly get through something long.Thank you very much for this, exactly what i needed for fixing the scrolling issue on ios.
Hey — Just thought id take a second to say THANK YOU for this … as much as it seems i should have already known about the -webkit property, had i not seen this i may very well have gone down a dark road trying to implement a javascript replacement for overflow-y … THANK YOU SINCERELY
Just a warning for folks out there finding this great feature – if you are using it in a rule that also includes
overflow-x: hidden
– beware. Because the-webkit-overflow-scrolling: touch
property will allow the user to scroll vertically and horizontally, which may reveal hidden divs that are meant to be hidden to the left or right.I am facing this exact problem. I loose the vertical momentum scrolling as soon as I add
overflow-x: hidden
to the html and body tag. Adding-webkit-overflow-scrolling: touch
restores the vertical momentum scrolling but breaks myoverflow-x: hidden
. Is there a way to get away with both? I tried to place the two styles at different places, in the html tag only, in the body tag only, in a wrapper div, always with no luck.I believe that now (Aug 2018) this is not an issue. I have a website that acts like a full-height app, using
position: fixed
for full height content blocks that transition into one another, and one of them hasoverflow-y: auto
for when it overflows. I added the-webkit-overflow-scrolling: touch
property, as well as theoverflow-x: hidden
to this block, and it seems to be fine. It definitely helped the scrolling issue we were experiencing in older IOS phones (iPhone 6), and we don’t notice any other side effects (although I’m not sure if I have any content that overflows the left and right). I’d also like to point out that this is working even withoverflow-y: auto
, despite the code example in this post mentioning it only works on scroll (perhaps now that it’s 2018, IOS has resolved these issues).Does any one know how to add a auto scrolling function to a horizontal scroll bar???I have some images in a table row and i want that row to auto scroll horizontally but not manually..
Please help me
I have customize scroll using CSS3, its working fine in all browser but the overflow-x is not visible in iphone. Here is the code what I have done. http://codepen.io/anon/pen/aLwhq
works great on ipad, thanks for the tip.
Thank you, this fixed a problem I was having and now the iPhone page looks like it should!
Okay, so when I have overflow-y: scroll; and -webkit-overflow-scrolling: touch; it works fine in most cases… except on the DIV I actually need it.
It’s a fixed DIV. When I load the page in landscape, and there is enough content to need overflow it works, but if I then change the device orientation to portrait (where the content doesn’t need overflow) then back to landscape the DIV no longer scrolls at all!
Please reply on this comment to above comment so I get notifications :P (I wish there were a way to edit such preferences on here!)
Hi Charles,
I am also having this same issue, have you got any solution for this?
This was a great find — worked as promised. The only side effect is that child elements with position: fixed now move with the parent’s scrolling, until the momentum stops, and then they snap back into their fixed positions.
Did you ever find a solution to this? I’m having the same issue with a position:fixed navigation header div positioned on the top.
I’m having a similar issue. Fixed child element in container that that has “-webkit-overflow-scroll” moves while scrolling, and in addition, it’s hidden (I think the latter issue is related to z-index being changed when “webkit-overflow-scroll” is applied.
I can confirm that
overflow: auto;
-webkit-overflow-scrolling: touch;
Works if you don’t want to show scroll bars all the time. Thanks for the tip, Chris!
Thanks for the tip Chris;
overflow: auto;
-webkit-overflow-scrolling: touch;
works fine for iPhone media query;
but when I used it within media query for iPad (1,2), it was causing the iOS app that was loading the page through iframe, to crash.
Hello All,
It works great for me. But I have another problem.
While creating custom scroll, I’m unable to get smooth scrolling.
Did I miss something?
Saved my day! However why I would need to add this in the first place is beyond me
Saved my week !!!
Thanks Chris, just made my day too!
Bundle of thanks!
Dear your technique works for me. i was facing problem in scrolling on touch devices, then i give your code to“`
“`
now my website scrolling smooth now.
Wow, that was a life saver.
Why in the world would you disable inertial scrolling by default? Who thought “This developer clearly wants this thing to be scrollable, but he probably wants it to be janky, so let’s make that the default.”?
why overscroll scroll?
Thanks for this, just saved me a few hours. Thanks also to the keywords that got me here.
Crazy how specific some of the controls can be.
Love it! Worked Thanks! :D
I love you
You just saved me hours of futzing around. Again. Thanks!
Thank you verry much!
Keep on going with this good work, great article!
Words cannot express how grateful I am for this. Thank you!
I have a strange problem. I’ve tried looking everywhere and I can’t find any answers.
I’m using this CSS property (
-webkit-overflow-scrolling
) in an iOS app loaded inside a web view.As soon as I open the app, it crashes and closes again. The crash report lead me to this page: http://bit.ly/1GobVK2 which suggests that it is caused by this CSS property. Is that legit? Should I continue to try and fix this based on this theory?
Has anyone else had similar issues with this CSS property?
Hey Chris,
just wanted to say, it actually does work with
overflow: auto;
, I have it set up and working on a few sites.Thank you for this snippet – don’t know why, but I keep forgetting this exact declaration and come back every time I need it again. ;)
Hey Chris,
This is really helpful. I was struggling for this issue and after applying -webkit-overflow-scrolling: touch; all the things stated moving smoothly. Thanks man for this :)
Hi, I’m a real tech dummy, so can you please help me and put it really simply like go to settings, go to x, then x, etc. my iPhone 5s screen keeps scrolling and it’s driving me nuts! The screen is clean, it’s a year old. I’ve tried turning it off and on again, no joy. How do I fix it? If it’s a memory thing should I delete some aps? Thanks! :-)
So yeah, didn’t read that it doesn’t work on “auto” and then tried it… Works on auto for me using Cordova on iOS so it might have changed, just a heads up.
https://developer.mozilla.org/en-US/docs/Web/CSS/-webkit-overflow-scrolling
There seems to be a warning on the page to not use ‘-webkit-overflow-scrolling’ on production facing sites.
Thank you! This worked perfectly!!
What a nice solution, it worked perfectly! Thanks!
Hi – when i use -webkit-overflow-scrolling on a div on ios 9+, cordova app it only activates scroll on 2 finger drag. any ideas on a work around?
I know that this is an old post, but…
“Web pages on iOS by default have a “momentum” style scrolling where a flick of the finger sends the web page scrolling and it keeps going until eventually slowing down and stopping as if friction is slowing it down. Like if you were to push a hockey puck across the ice or something”
…I believe this statement is actually false. Take any web page, including this very website, and scroll it in mobile Safari. It will not have inertia scrolling. Scrolling stops almost immediately when you lift your finger. Inertia scrolling at the page level isn’t a default at all.
Unless of course I am crazy and am the only person getting these results. Tested in iOS 7, 8 and 9, on 3 devices.
My finding is that you actually do have to use webkit-overflow at the document level. And because most sites don’t, they are seriously missing out.
Helped me a lot. I went from scrolling divs to scrolling page, so now it works on iOS. Has worked perfect on android from the beginning.
I love you!! just what I needed. you saved my app.
It seriously makes a world of difference to enable it, since it really isn’t a default. More info here:
https://ferdychristant.com/the-world-s-most-overlooked-web-optimization-for-ios-d88c7517d520#.r6pijsei7
This fix no longer seems to be working.
– Is anybody experiencing the same issue?
– Does anybody know how it could be fixed now?
Seems to be working on my iPhone SE, just not on my desktop Mac.
is there a way to make momentum scrolling work and hide the scrollbar permanently ?
I tried using ::-webkit-scrollbar et all – looks like they are not compatible with
-webkit-overflow-scrolling: touch;
Does anyone know how to get topbar and bottom bar for iphone to hide? In iOS 9 it is standard, but with this scrolling that standard disappears..
You saved me again. Thanks!
Try this it’s working for me
if (window.location == window.parent.location && navigator.userAgent.match(/(iPod|iPhone|iPad)/)) {
$(‘#orderpop’).attr(‘style’, ‘-webkit-overflow-scrolling: touch !important; overflow-y: scroll !important;’);
}
});
What about other prefixes, -moz-, -khtml-, -o-, -ie-, or is this specifically for safari only? Does this need to be done for android too? What other prefixes would be needed for those?
Thid demo and in my project don’t work on iPad(MD329LL/a) with 7.0.4(11B554a)
Thank you for this. I had such a hard time even finding the right thing to call this that I almost gave up on it. Amazing how little it’s actually used in things like responsive menus. I’m even finding paid plugins and whatnot that don’t even use this.
It works fine for scrolling but lazy loading stopped working. After touchmove event the is still scrolling and unable to load the images. How to fix this?
This no longer requires
overflow-y
to bescroll
– it can be set to auto and have the intended effect only once the content goes over the element’s bounds causing a scrollbar.overflow-y: scroll; /* has to be scroll, not auto */
I could be mistaken, but I don’t think this is true? I have
overflow-y: auto
set and momentum scrolling seems to be working fine in iOS.Some things are just that easy. After hours of debugging and searching i found this simple solution… and it even works in cordova/phonegap. Next time i visit this site first. Thank you.
CSS-Tricks 4TW!
Works perfectly, thanks so much!
This worked and is much more pleasant BUT the container that was scrolling horizontally had elements with hover states that would activate when touched on iOS, now they do not respond to touch, so I will probably have to scrap the inertia scroll since the information displayed on hover is more important :(
I want Same scrolling Feature in android devices
Here postcss plugin https://npmjs.com/package/postcss-momentum-scrolling
Just to reiterate the sprinkled comments in here:
THIS BREAKS SCROLL NOTIFICATION
I appreciate the article as it does give inertial scrolling back, but a few developers in here (Jessie, Nishant, Charles) have noted that they no longer receive scroll events when this is turned on. This is imported for our application. We do get one event when inertial scrolling finally stops to exactly 0 but this does not help our use cases. We need events WHILE the scrolling is occuring, as we get when this is not in or as we get on other products with inertial scrolling. Jessie, thanks for the setTimeout and track solution. I will probably simulate it this way until we find another answer.
This fix no longer seems to be working.
– Is anybody experiencing the same issue?
– Does anybody know how it could be fixed now?
According to this it is no longer needed: https://ferdychristant.com/why-ios-11-is-great-news-for-the-web-345c43cc55db
Hi,
Thanks for that tips it’s working really well ! But I have a problem, the scrollbar appear, while I put ‘ ::-webkit-scrollbar { display: none; }.
Can you help me to make it transparent, or customize it ?
Thanks
Hi! Nice post, thx!
There is a problem when using the animation on the page. Content when scrolling begins to “dance”. Has anyone encountered, tried to fix?
Great. This was useful to see. We use this in the credits within our game.
webkit-overflow-scrolling: auto not work on my iPad now.
“webkit-overflow-scrolling” no more works in ios 13 as ios 13 has by default enabled the momentum scrolling in any scrollable container but I do not want that behavior. Anyone have any idea how can I disable momentum scrolling on my webpage?