I see different behavior between UIPageViewControllerusing transitions Scrollcompared to PageCurl. PageCurl works as I expect, but when using scroll sometimes I see additional (meaningless) calls viewControllerBeforeViewController:and viewControllerAfterViewController:
Does anyone know this scheme of additional calls to the data source?
I am showing a series of images and I can start anywhere in sequence. When using the Scroll transition, but not PageCurl, after the start page is displayed, if I go to the "correct" one, I get 3 calls to DataSource instead of the only one I expect. For the example below, I started with my index value 3. When I sit down to go to the "next" image, I expect to get one call viewControllerAfterViewController:at index 3 to go to index 4. If I run the test I will get two additional calls : one for index 3 (i.e. 2) and one for index after 4 (i.e. 5). Output:
2013-04-19 12:37:33.964 Clouds[496:907] Page 3 - viewControllerAfterViewController called on this index
2013-04-19 12:37:33.988 Clouds[496:907] Page 3 - viewControllerBeforeViewController called on this index
2013-04-19 12:37:34.010 Clouds[496:907] willTransitionToViewControllers to indices
2013-04-19 12:37:34.014 Clouds[496:907] Page 4
2013-04-19 12:37:34.461 Clouds[496:907] Page 4 - viewControllerAfterViewController called on this index
The view that displays after all this is really a view for index 4. After this first transition, the UIPageViewController seems to behave as I expect. When I use the PageCurl transition, it always behaves as I expect, and I do not receive any of these extraneous calls.
The code that actually generated the output:
- (void)viewDidLoad
{
[super viewDidLoad];
self.pageViewController = [[UIPageViewController alloc] initWithTransitionStyle:UIPageViewControllerTransitionStyleScroll navigationOrientation:UIPageViewControllerNavigationOrientationHorizontal options:nil];
self.pageViewController.delegate = self;
self.pageViewController.dataSource = self;
CloudImageVC *startingViewController = [self viewControllerAtIndex:self.currentPage storyboard:self.storyboard];
NSArray *viewControllers = @[startingViewController];
[self.pageViewController setViewControllers:viewControllers direction:UIPageViewControllerNavigationDirectionForward animated:NO completion:NULL];
[self addChildViewController:self.pageViewController];
[self.view addSubview:self.pageViewController.view];
CGRect pageViewRect = self.view.bounds;
self.pageViewController.view.frame = pageViewRect;
[self.pageViewController didMoveToParentViewController:self];
self.view.gestureRecognizers = self.pageViewController.gestureRecognizers;
}
- (CloudImageVC *)viewControllerAtIndex:(NSUInteger)index storyboard:(UIStoryboard *)storyboard {
if (index >= [self.imageNames count]) {
return nil;
}
self.dataViewController = [self makeDataViewControllerAtIndex:index storyboard:storyboard];
return self.dataViewController;
}
- (CloudImageVC *) makeDataViewControllerAtIndex:(NSUInteger)index storyboard:(UIStoryboard *)storyboard {
if (index >= [self.imageNames count]) {
return nil;
}
self.dataViewController = [storyboard instantiateViewControllerWithIdentifier:@"CloudImageVC"];
self.dataViewController.imageIndex = index;
return self.dataViewController;
}
- (NSUInteger)indexOfViewController:(CloudImageVC *)viewController
{
return viewController.imageIndex;
}
#pragma mark - Page View Controller Data Source
- (UIViewController *)pageViewController:(UIPageViewController *)pageViewController viewControllerBeforeViewController:(UIViewController *)viewController {
NSUInteger index = [self indexOfViewController:(CloudImageVC *)viewController];
NSLog(@"Page %d - viewControllerBeforeViewController called on this index", index);
if ((index == 0) || (index == NSNotFound)) {
return nil;
}
index--;
return [self viewControllerAtIndex:index storyboard:viewController.storyboard];
}
- (UIViewController *)pageViewController:(UIPageViewController *)pageViewController viewControllerAfterViewController:(UIViewController *)viewController {
NSUInteger index = [self indexOfViewController:(CloudImageVC *)viewController];
NSLog(@"Page %d - viewControllerAfterViewController called on this index", index);
if (index == NSNotFound) {
return nil;
}
index++;
if (index == self.imageNames.count) {
return nil;
}
return [self viewControllerAtIndex:index storyboard:viewController.storyboard];
}
#pragma mark - Protocol UI PageViewController Delegate
- (void) pageViewController:(UIPageViewController *)pageViewController willTransitionToViewControllers:(NSArray *)pendingViewControllers {
NSLog(@"willTransitionToViewControllers to indices");
for (CloudImageVC *vc in pendingViewControllers) {
NSLog(@"Page %d",vc.imageIndex);
}
}
source
share