If you have an iPhone application that makes use of a long UIWebView, alot of times you’ll want it to stay scrolled to wherever the user has scrolled to, even if they restart the application. This means that you need to find out where the user is scrolled in the document when the application closes, store that information, and then scroll back there when it opens again.

You can use NSUserDefaults to easily store the position, but the harder part is figuring out where the user is and getting it back to that position. In order to do this, you have to use Javascript, with a few semi-obscure functions (at least I had never heard of them).

You can execute Javascript on a UIWebView using stringByEvaluatingJavaScriptFromString. To find out how far down the page the user has scrolled, execute scrollY.

[myWebView stringByEvaluatingJavaScriptFromString: @"scrollY"];

Then, when you want to go back to that point, call the scrollTo (x, y). It’s important that you pass it both x and y parameters, even if x is 0, or it won’t work. So scrollTo(0, 500) would scroll you 500 pixels down the page. And of course, you have to call this after your UIWebView has actually loaded the page, no just when your application starts.

Here’s some sample code for getting the position, saving it, and then reloading it. This code would need to be in the class that is your app delegate, as well as the . Also, make sure you define an NSInteger in your header file, like NSInteger initialScrollPosition;.


// Application is terminating.
- (void)applicationWillTerminate:(UIApplication *)application {
  [[NSUserDefaults standardUserDefaults] setInteger:
    [[myWebView stringByEvaluatingJavaScriptFromString: @"scrollY"]
      intValue] forKey: @"currentScroll"];
}

// Application is loading.
- (void)applicationDidFinishLaunching:(UIApplication *)application {
	initialScrollPosition = [[NSUserDefaults standardUserDefaults]
                                integerForKey: @"currentScroll"];
}

// WebView is finished loading
- (void)webViewDidFinishLoad:(UIWebView *)webView {

  // Check if we need to scroll this somewhere.
  if (initialScrollPosition != 0) {

    // Scroll to the position.
    [passageView stringByEvaluatingJavaScriptFromString:
      [NSString stringWithFormat: @"window.scrollTo(0, %d);",
      self.initialScrollPosition]];

    // Set the initial scroll value to zero so we don't try
    // to scroll to it again if the user navigates to another page.
    self.initialScrollPosition = 0;
  }
}

And that should give you a UIWebView that stays in place even when the user restarts the application.

 

11 Responses to Going back to the last place you were in a UIWebView

  1. Mark says:

    What is passageView? Should that be webView?

    Also if I can’t get this to work (inspecting the string passed to stringByEvaluatingJavaScriptFromString shows that it looks fine: window.scrollTo(0,262); but the UIWebView simply does not scroll) what might be going wrong?

  2. Manjit Bedi says:

    Thanks for that.

    I am trying to figure out how to get the current page of a PDF displayed in a UIWebView. There does not appear to be a class property that can be accessed but this will get me there.

    I think I then need to compare the scroll value to the page size in the PDF and do some math.

  3. alexnking says:

    Mark – that should be webView. Thank you. Not quite sure what’s going wrong with your code though.

    Manjit – sounds like you’re definitely on the right track there.

  4. Milan says:

    i had try below of the code but does not work..

    anyone can help me.?

    Thanks you

  5. Jindal says:

    Thank You,

    It’s working for me.

  6. rahul says:

    Nice post.

    what should i do get end y coordinates of HTML, so that i can directly navigate user to end of HTML file.

  7. RV says:

    alexnking thanks a lot, that was a very helpful.

  8. Pepe says:

    Thanks! You have helped me to understand the UIWebView.

  9. Richie says:

    Hi, could you please upload the xcode project files to see the code working?

    Thanks!

  10. Philip Hansen says:

    Hi,

    When I implement your code I get 2 errors in webViewDidFinishLoading when building:

    error: request for member ‘initialScrollPosition’ in something not a structure or union.

    Do you know why this occurs?

  11. Tommy Herbert says:

    Excellent – thanks very much.

Leave a Reply

Your email address will not be published. Required fields are marked *

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>

Set your Twitter account name in your settings to use the TwitterBar Section.