jQuery scrollTop() does not work in scrolling DIV on mobile browsers, alternatives?
Asked Answered
N

14

36

I am trying to scroll to a specific location in a scrolling DIV. Right now I am using a pixel offset with the jQuery scrollTop() function which works great on desktop browsers but it does not work on android mobiles browsers with the exception of Google's Chrome Android browser (do not have an iOS device to test if that works). All the solutions I have found are for page (window) scrolling and not for scrolling in a DIV, anyone have any suggestions on what else I can use to accomplish the same task?

Here is a example:
http://jsfiddle.net/aQpPc/
http://jsfiddle.net/aQpPc/embedded/result/

Other things I have tried that work in desktop browsers:

document.getElementById('ID_of_element_in_a_DIV').scrollIntoView();
document.getElementById('ID_of_DIV').scrollTop = 200;

EDIT 3/11/13:

This is a know android browser issue: https://code.google.com/p/android/issues/detail?id=19625

One user in the bug report suggested a workaround:

because the issue only seems to appear when the overflow property is set to scroll, you can first set it to 'hidden', set the scrollTop property, then reset it back to 'scroll' (or auto). The scrollTop property seems to be honored when the element is re-rendered with scrollbars. It's not clear if this has any unexpected side-effects, but "it works on my machine!"

Naked answered 1/9, 2012 at 6:28 Comment(4)
it does work on IOS in both safari and chromeFlaxen
For those in need to scroll for the whole document (like me), you could use $("body").scrollTop(0), trying it on html or div elements did not workImpart
jsfiddle.net/aQpPc/embedded/result I tried this in the built in browser of my Samsung Galaxy S3 and it works just fine.Lemur
hey, fun to see my workaround quoted here. :) That workaround still seems to be the only way I've found to get it to work in a reasonable way. Doubt that this will be fixed any time soon...Kirk
F
10

This worked for me:

setTimeout( function() {
    $(div).scrollTop(0)
}, 500 );
Fighter answered 27/8, 2014 at 10:14 Comment(0)
K
7

A workaound that worked for me: first, temporarily set the overflow property to 'hidden', then set the scrollTop property, then set the overflow property back to 'scroll' (or auto). The scrollTop value seems to be kept intact and honored when the overflow property is set back to 'scroll'. This was a pretty trivial workaround that worked on all browsers I tested on (desktop and mobile). I didn't test it exhaustively, and I didn't test with transitions in place, so there may be side-effects that I haven't encountered... Your mileage may vary - but it's an easy thing to try.

Kirk answered 20/1, 2013 at 7:4 Comment(1)
does not work on Android 4.0.X browsers - when setting overflow back to 'scroll', whole div just goes to top ...Organicism
D
5

I found the answer here http://blog.jonathanargentiero.com/jquery-scrolltop-not-working-on-mobile-devices-iphone-ipad-android-phones/

Mobile phones doesn't understand $('html,body') so u can do the following for mobile

if(navigator.userAgent.match(/(iPod|iPhone|iPad|Android)/)) {           
    window.scrollTo(0)
} else {
    // default `$('html,body')` code for scrolling
}

OR

simply use $('body') instead of $('html, body').

Dennie answered 10/5, 2016 at 9:23 Comment(2)
Uncaught TypeError: Failed to execute 'scrollTo' on 'Window' after adding window.scrollTo(0);Summon
@VivekVikranth what are you using can you share your snippetDennie
E
4

rather than using the scroll, scrollTo, or scrollTop methods (which give me problems in mobile), I recommend setting an ID on your top DOM element (like #top), and just using:

document.getElementById("top").scrollIntoView();

that works the best for me so far across all devices and browsers.

Eudosia answered 17/4, 2019 at 5:54 Comment(0)
G
2

I have a couple solutions for you to try. You will have to test them yourself, as I have not tried them in a mobile browser before, but here they are:

  1. Use jQuery's .css() method (or .animate() depending on what your eventual goal us) to adjust the top margin (note: you would have to change the overflow to hidden and wrap the text in an inner div, which would be the element whose to margin you are adjusting)
  2. Do the same thing as in the first solution, except set the embedded div's position to relative and adjust it's top attribute.

Let me know if you need help with any if this or have any more questions about this. Good luck! :)


Note that although I have not tested these in mobile before they are based on CSS standards, not jQuery functions, so they should work.

Giblets answered 1/9, 2012 at 13:54 Comment(0)
L
1

Temporarily setting the overflow property to 'hidden', as recommended in @Allan Nienhuis' answer, does not work on Android 4.0.3, for instance (which is, e.g., what the Kindle Fire 2s are running) - when you set overflow back to scroll, the element scrolls back to the top.

Alternatives:

  • Roll your own scrolling via a helper function, as demonstrated here - while this is simple to implement, it is bare-bones in that it doesn't give you inertial scrolling or overscrolling.

  • Use a library such as iScroll, which implements its own, sophisticated scrolling (inertial, overscrolling) based on CSS transformations.

Using iScroll requires a bit of setup, though: you need a wrapper div with fixed height and style overflow: hidden and the element to scroll should have no overflow style. This jsFiddle demo shows how it's done.

Levania answered 27/8, 2013 at 21:34 Comment(1)
iScroll works on 4.1 and it activates an anchor links! Thanks!Quadrennium
I
1

The only way i could achieve scrolling to the top of the page on a Galaxy Tab was hiding the page body for 100ms while scrolling. Using jQuery:

$("body").hide();
window.scrollTo(0, 0);
setTimeout(function(){ $("body").show() }, 100);
Intonate answered 14/7, 2017 at 13:10 Comment(0)
S
0

Try using jQuery's .animate method:

$('.div').animate({ scrollTo: x; });

Where x is equal to the position of the div you want to scroll to the top of.

Sacroiliac answered 21/1, 2013 at 12:11 Comment(2)
Tried this also initially but this does not work. I think jQuery (don't hold me to it) is using the underling javascript .scrollTop method but just stepping through positions to animate the scroll.Naked
Actually, it's this: $('.div').animate({ scrollTop: x });Homeward
H
0

Did you try this ?

$("html").scrollTop(0);
Harrar answered 20/3, 2013 at 6:6 Comment(1)
Yup, that is the method used in the fiddle and discussed in the description of the first post.Naked
A
0
jQuery(document).ready(function($) {

$(".scroll").click(function(event){     
    event.preventDefault();
    $('html,body').animate({scrollTop:$(this.hash).offset().top}, 1500);
});
});

<a href="#top" class="scroll"></a>
Azotize answered 3/7, 2013 at 5:41 Comment(0)
R
0

Use the following code:

$("body").animate( { scrollTop: 50,  },  800,  function(){
    $("body").clearQueue();
} );
Rotterdam answered 26/7, 2014 at 14:37 Comment(0)
K
0

These solutions did not work for me. I know someone mentioned mobile detection but their approach did not work for me. It finally dawned on me to use mobile detection to deliver two different CSS styles for each case. Maybe not ideal but it for sure works. Temporarily changing the styles with js also suggested above did not work for me.

I had a two column layout with independently scrolling divs, each set to overflow:scroll and the body had to be set to overflow:hidden. I need to use scrollTop on one of the columns and no solutions worked.

I used wp_is_mobile() (Wordpress function) and if mobile true, overflow: hidden is removed from body and the divs with overflow:scroll have that css removed. Finally, scrollTop worked on mobile.

Kiel answered 28/4, 2019 at 5:13 Comment(0)
P
0

  
$(document).ready(function (){
  $(window).scroll(function(){
        if($(this).scrollTop() > 100){
            $('.scrollup').fadeIn();
        } 
        else{
            $('.scrollup').fadeOut();
        }
    });
  
  $('.scrollup').click(function(){
    if (navigator.userAgent.match(/(iPod|iPhone|iPad|Android)/)) {           
      window.scrollTo(0,0);
    }
    else{
      $('html,body').animate({
        scrollTop: 0
        }, 500, function(){
        $('html,body').clearQueue();
      });
    }
  });              
});
body{
  height: 1500px;
}

.scrollup {
    bottom: 135px;
    height: 40px;
    width: 40px;
    display: none;
    background: #000;
    border: 2px solid #fff;
    border-radius: 100%;
    box-shadow: 1px 3px 5px #000;
    text-align: center;
    font-size: 25px;
    color: #fff;
    cursor: pointer;
    position: fixed;
    right: 12px;
    line-height: 36px;
    z-index: 25;
}

svg{
  fill: #fff;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div class="scrollup">
    <svg height="35" viewBox="0 0 512 512" width="30">
        <polygon points="396.6,352 416,331.3 256,160 96,331.3 115.3,352 256,201.5 "/>
    </svg>
</div>
Palatine answered 21/9, 2021 at 15:29 Comment(2)
While this code may solve the question, including an explanation of how and why this solves the problem would really help to improve the quality of your post, and probably result in more up-votes. Remember that you are answering the question for readers in the future, not just the person asking now. Please edit your answer to add explanations.Vassily
Your answer could be improved with additional supporting information. Please edit to add further details, such as citations or documentation, so that others can confirm that your answer is correct. You can find more information on how to write good answers in the help center.Alixaliza
F
-2

I had the same problem and solved it by using jquery .offset() instead.

http://api.jquery.com/offset/

$('#yourFineElement').offset({ top: X, left Y)});
Freezedry answered 25/4, 2013 at 4:9 Comment(1)
That would kill the entire layout as it positions the scrolling DIV itself across the screen (not affecting its scroll position).Afb

© 2022 - 2025 — McMap. All rights reserved.