Sascha
Sascha

Reputation: 1218

Automatic scroll to top doesn't work in UITableView

usually when tapping the top of the screen the tableview scrolls all the way to the top. For some reason this doesn't work in one of my view controllers.

The hirarchy is as follows:

UIView
-> WebView
-> TableView
----->SearchBar
SearchDisplayController.

I think I have everything hooked up correctly (datasource, delegate, ...). I have a similar view controller where everything works. The only difference seems to be WebView, which is missing in the view controller where the tap-and-scroll-to-top works...

Any ideas?

Best regards, Sascha

Upvotes: 19

Views: 20905

Answers (8)

Gurpartap Singh
Gurpartap Singh

Reputation: 2764

Swift variant of opyh's answer. Upvote him!

func disableScrollsToTopPropertyOnAllSubviewsOf(view: UIView) {
    for subview in view.subviews {
        if let scrollView = subview as? UIScrollView {
            (scrollView as UIScrollView).scrollsToTop = false
        }
        self.disableScrollsToTopPropertyOnAllSubviewsOf(subview as UIView)
    }
}

Upvotes: 3

Oliver Pearmain
Oliver Pearmain

Reputation: 20590

Don't know what Apple were smoking but by design, the behaviour on iPhone is distinctly different from iPad. Apple's documentation does include a "Special Condsideration" note as follows...

On iPhone, the scroll-to-top gesture has no effect if there is more than one scroll view on-screen that has scrollsToTop set to YES.

So on iPhone you have to ensure that there is only ever one UIScrollView (or UITableView/UICollectionView/UIWebView etc) that has its scrollsToTop = YES.

Since scrollsToTop defaults to YES you have to explicitly set scrollsToTop = NO for the UIScrollView's you do not want to scroll when the user taps the status bar.

Upvotes: 4

Dan Clarke
Dan Clarke

Reputation: 11

I just wanted to add to this, if you are using a UITextView, it isn't the subviews that need the scrollsToTop adjusting, it's the actual UITextView, in short you need this code:

[myTextView setScrollsToTop:FALSE];

This should fix the problem (additionally, the 'disableScrollsToTopPropertyOnAllSubviewsOf' function doesn't work on the UITextViews).

Hope this helps someone!

Upvotes: 1

Chris Miles
Chris Miles

Reputation: 7516

Set scrollsToTop = NO on all scroll views in the view, except for the one you want to scroll to top. That helps the system find the correct scroll view.

Upvotes: 0

opyh
opyh

Reputation: 1544

You have probably added some view to your view hierarchy that is a UIScrollView or contains scroll views (e.g. UIWebView or UITextView). When you tap the status bar, iOS searches for the topmost scrollview with scrollsToTop set to YES and scrolls to its top.

Add this to your class:

- (void) disableScrollsToTopPropertyOnAllSubviewsOf:(UIView *)view {
    for (UIView *subview in view.subviews) {
        if ([subview isKindOfClass:[UIScrollView class]]) {
            ((UIScrollView *)subview).scrollsToTop = NO;
        }
        [self disableScrollsToTopPropertyOnAllSubviewsOf:subview];
    }
}

…and call

[self disableScrollsToTopPropertyOnAllSubviewsOf:myAddedSubview];

to solve the problem and let your table view scroll to top again.

Upvotes: 30

Martin Lockett
Martin Lockett

Reputation: 2589

I had this problem with just a tableview in the NIB. Very frustrating until I remembered I was programmatically adding a UITextView as the table view header. scrollsToTop=NO on the UITextView did the trick.

Upvotes: 0

Brian
Brian

Reputation: 15706

You need to disable scrollsToTop on all but one of the scrollable views. Since UITableView is a descendant of UIScrollView, it's easy to do. However, if you want to disable it on the webview, it's a little trickier. This seems to work:

[webView.subviews objectAtIndex:0].scrollsToTop = NO;

But that is a little iffy since it's poking around in undocumented parts of the webview. It may stop working if Apple decides to rearrange the subviews.

Upvotes: 27

Frank Schmitt
Frank Schmitt

Reputation: 25766

Apparently if you have more than one scrolling view (in your case the WebView and TableView) in a view controller, the "tap status bar to scroll to top" is disabled.

http://twitter.com/drance/status/2448035250438144

(Matt Drance is a former iPhoneOS developer evangelist and current iOS development rockstar)

Upvotes: 3

Related Questions