3
votes

I'm trying to replicate the App Store search functionality where tapping the Search Tab Bar again, scrolls the search results back to the first.

My case is simpler in that it's a traditional table view so it needs to scroll to top. I have the UITabBarControllerDelegate set and can detect the tab bar selection.

In the didSelectViewController, I've tried:

- (void) tabBarController:(UITabBarController *)tabBarController didSelectViewController:(UIViewController *)viewController {
  if(viewController == tabBarController.selectedViewController) {
    [searchResultsTable setContentOffset:CGPointZero animated:YES];
  }
}

and

[searchResultsTable scrollRectToVisible:tableOrigin animated:YES];

where tableOrigin is the table view frame rect that I set in viewDidLoad.

The first implementation (setContentOffset) scrolls up but stops short of the search bar and cuts off the first row partially. I'm assuming this is related to iOS 7 in how the nav bar works?

The second implementation (scrollRectToVisible) works the first time but gets wonky if I come back to the search tab later on.

Is there a reliable, repeatable view to mimic the "scroll to top" functionality the way it works on tapping the Status Bar programmatically and doesn't cut off any rows or Search Bar in iOS 7?

UPDATE: The SearchBar is part of the UITableView.

3

3 Answers

3
votes

You can try:

[searchResultsTable scrollToRowAtIndexPath:[NSIndexPath indexPathForRow:0 
                                                              inSection:0]
                          atScrollPosition:UITableViewScrollPositionTop
                                  animated:YES];
0
votes

You are doing nothing wrong. Try to run setNeedsUpdateConstraints on the view. If that doesn't fix it, try [self.view updateConstraints].

0
votes

SWIFT 3

Just change collectionView to tableView

First implement the UITabBarControllerDelegate in the class and make sure the delegate is set in viewDidLoad

class DesignStoryStreamVC: UIViewController, UICollectionViewDelegate, UICollectionViewDataSource, UITabBarControllerDelegate {

 @IBOutlet weak var collectionView: UICollectionView!

 override func viewDidLoad() {
        super.viewDidLoad()

        self.tabBarController?.delegate = self

        collectionView.delegate = self
        collectionView.dataSource = self
    }
}

Next, put this delegate function somewhere in your class.

func tabBarController(_ tabBarController: UITabBarController, didSelect viewController: UIViewController) {

    let tabBarIndex = tabBarController.selectedIndex

    print(tabBarIndex)

    if tabBarIndex == 0 {
        self.collectionView.setContentOffset(CGPoint.zero, animated: true)
    }
}

Make sure to select the correct index in the "if" statement. I included the print function so you can double check.