I am adjusting a detail view controller's state, just before it is pushed on a navigationController
:
[self.detailViewController detailsForObject:someObject];
[self.navigationController pushViewController:self.detailViewController
animated:YES];
In the DetailViewController
a scrollView resides. Which content I resize based on the passed object:
- (void)detailsForObject:(id)someObject {
// set some textView's content here
self.contentView.frame = <rect with new calculated size>;
self.scrollView.contentSize = self.contentView.frame.size;
self.scrollView.contentOffset = CGPointZero;
}
Now, this all works, but the scrollView adjusts it's contentOffset
during the navigationController's slide-in animation. The contentOffset
will be set to the difference between the last contentSize and the new calculated one. This means that the second time you open the detailsView, the details will scroll to some unwanted location. Even though I'm setting the contentOffset
to CGPointZero
explicitly.
I found that resetting the contentOffset
in - viewWillAppear
has no effect. The best I could come up with is resetting the contentOffset in viewDidAppear
, causing a noticeable up and down movement of the content:
- (void)viewDidAppear:(BOOL)animated {
self.scrollView.contentOffset = CGPointZero;
}
Is there a way to prevent a UIScrollView
from adjusting its contentOffset
when its contentSize
is changed?
Here's what worked for me:
In the storyboard, in the Size Inspector for the scrollView, set Content Insets Adjustment Behavior to "Never".
Occurs when pushing a
UIViewController
containing aUIScrollView
using aUINavigationController
.iOS 7
Solution 1 (Code)
Set
@property(nonatomic, assign) BOOL automaticallyAdjustsScrollViewInsets
toNO
.Solution 2 (Storyboard)
Uncheck the
Adjust Scroll View Insets
iOS 6
Solution (Code)
Set the
UIScrollView
's propertycontentOffset
andcontentInset
inviewWillLayoutSubviews
. Sample code:I had the same issue with a UIScrollview, where the problem was caused by not setting the contentSize. After setting the contentSize to the number of items this problem was solved.
Is your scrollView the root view of the DetailViewController? If yes, try wrapping the scrollView in a plain
UIView
and make the latter the root view of DetailViewController. SinceUIView
s don't have acontentOffset
property, they are immune to content offset adjustments made by the navigation controller (due to the navigation bar, etc.).I experienced the problem, and for a specific case - I don't adjust the size - I used the following:
Same would work with y:
anotherPosition + SmallScroll.frame.size.height / 2.0
So if you don't need to resize, this is a quick and painless solution.
I was experiencing a similar problem, where UIKit was setting the contentOffset of my scrollView during push animations.
None of these solutions were working for me, maybe because I was supporting iOS 10 and iOS 11.
I was able to fix my issue by subclassing my scrollview to keep UIKit from changing my offsets after the scrollview had been removed from the window: