Oleksandr Matrosov
Oleksandr Matrosov

Reputation: 27113

UITableView move to cell

I want to make next:

I have an UITableView that have to dispaly words (A-Z).

Currently when view did load I have one cell that displayed (and this is correct). First cell display first word from my array words.

Purpose: I want to move to the cell that must display 10 word from my array, but problem is that the cell with indexPath.row = 10 does not exist (and this correct, because I don't scroll yet).

What is a right wait to make transition from 1 to 10 cell.

I think if I don't use dequeueReusableCellWithIdentifier for creating my cell I can do it and solve my problem, but I mean this problem for device memory.

In other words I need to make scrollToRowAtIndexPath

Thanks!

Upvotes: 42

Views: 34091

Answers (4)

YourMJK
YourMJK

Reputation: 1629

If you're trying to present a ÙITableViewController, calling tableView.reloadData() in viewDidLoad() or viewWillAppear() will cause noticeable UI lag before the presentation animation.

However, you will need to wait for the ÙITableView to have loaded its data and layed out its view, otherwise scrollToRow(at:, at:, animated:) will not work.

Here's the (slightly hacky) solution I came with up with for scrolling in a table view which is currently being presented:

private var needsToScroll = true

override func viewDidLayoutSubviews() {
    super.viewDidLayoutSubviews()
    
    if needsToScroll {
        needsToScroll = false
        DispatchQueue.main.async {
            let indexPath = ...
            tableView.scrollToRow(at: indexPath, at: .top, animated: false)
        }
    }
}

needsToScroll is needed because viewDidLayoutSubviews() will often be called more than once, which is an issue since scrollToRow(at:, at:, animated:) can result in viewDidLayoutSubviews() being called again.

Upvotes: 0

A R
A R

Reputation: 461

//For iOS 7 
[self.TableView reloadData];
NSIndexPath *indexPath = [NSIndexPath indexPathForRow:1 inSection:1];
[TableView scrollToRowAtIndexPath:indexPath atScrollPosition:UITableViewScrollPositionTop animated:YES];

Upvotes: 6

user1751240
user1751240

Reputation:

One can identify the row(in the eg. below it is forRow) that needs to be made visible and reload the row. Upon the completion of that one can scroll to that row.

let moveToIndexPath = NSIndexPath(forRow: forRow, inSection: 0)
self.tableView.reloadRowsAtIndexPaths([moveToIndexPath], withRowAnimation: .None)
self.tableView.scrollToRowAtIndexPath(moveToIndexPath, atScrollPosition: atScrollPosition, animated: true)

Upvotes: 2

andyroberts
andyroberts

Reputation: 3518

You are right to identify the scrollToRowAtIndexPath method. So all you need to do is create a fresh IndexPath with the row you wish to move to, e.g., row index = 10:

[tableView scrollToRowAtIndexPath:[NSIndexPath indexPathForRow:10 inSection:indexPath.section] 
             atScrollPosition:UITableViewScrollPositionMiddle animated:NO];

Upvotes: 87

Related Questions