This is a follow-up to How to get notified when a tableViewController finishes animating the push onto a nav stack.
In a tableView
I want to deselect a row with animation, but only after the tableView has finished animating the scroll to the selected row. How can I be notified when that happens, or what method gets called the moment that finishes.
This is the order of things:
- Push view controller
- In
viewWillAppear
I select a certain row. - In
viewDidAppear
IscrollToRowAtIndexPath
(to the selected row). - Then when that finishes scrolling I want to
deselectRowAtIndexPath: animated:YES
This way, the user will know why they were scrolled there, but then I can fade away the selection.
Step 4 is the part I haven't figured out yet. If I call it in viewDidAppear
then by the time the tableView scrolls there, the row has been deselected already which is no good.
Implementing this in a Swift extension.
This works for most cases although the TableView delegate is changed during the scroll, which may be undesired in some cases.
You can use the table view delegate's
scrollViewDidEndScrollingAnimation:
method. This is because aUITableView
is a subclass ofUIScrollView
andUITableViewDelegate
conforms toUIScrollViewDelegate
. In other words, a table view is a scroll view, and a table view delegate is also a scroll view delegate.So, create a
scrollViewDidEndScrollingAnimation:
method in your table view delegate and deselect the cell in that method. See the reference documentation forUIScrollViewDelegate
for information on thescrollViewDidEndScrollingAnimation:
method.You can include the
scrollToRowAtIndexPath:
inside a[UIView animateWithDuration:...]
block which will trigger the completion block after all included animations conclude. So, something like this:try this
Don't forget to set animated to NO, the animation of scrollToRow will be overridden by UIView animateWithDuration.
Hope this help !
To address Ben Packard's comment on the accepted answer, you can do this. Test if the tableView can scroll to the new position. If not, execute your method immediately. If it can scroll, wait until the scrolling is finished to execute your method.