nicklockwood / SwipeView

SwipeView is a class designed to simplify the implementation of horizontal, paged scrolling views on iOS. It is based on a UIScrollView, but adds convenient functionality such as a UITableView-style dataSource/delegate interface for loading views dynamically, and efficient view loading, unloading and recycling.
Other
2.65k stars 413 forks source link

animateWithDuration makes swipeview choppy in indexDidChange. #53

Closed theprojectabot closed 11 years ago

theprojectabot commented 11 years ago

I have utlized a swipeView set as a subview in a viewcontroller, another subview on the viewcontroller is a backgroundImageView. I change the image of the backgroundImageView during the:

This works fine unless I have that image view do a coreanimation animateWithDuration. The scroll then becomes very chop as it finishes itself. I have found that setting the swipeview to: _swipeView.defersItemViewLoading = YES;

mitigates the problem, however now the transition is delayed... Here is my code for that method. Any possibility to make this work much smoother without setting the defer?

- (void)swipeViewCurrentItemIndexDidChange:(SwipeView *)swipeView
{
//update page control page
pageControl.currentPage = swipeView.currentPage;
[pageControl updateCurrentPageDisplay];

  _backgroundImageView.image = [_backgroundImages objectAtIndex:pageControl.currentPage];
[UIView animateWithDuration:0.3
                      delay:0
                    options: UIViewAnimationOptionTransitionCrossDissolve
                 animations:^{
                     //view.alpha = 1;
                     //if([view isKindOfClass:[WDTourItemView class]])
                     _backgroundImageView.image = [_backgroundImages objectAtIndex:pageControl.currentPage];
                 } completion:^(BOOL finished){}];
}
nicklockwood commented 11 years ago

Try doing the transition using core animation like this instead of [UIView animateWithDuration:]

CATransition *transition = [CATransition animation];
transition.type = kCATransitionFade;
transition.duration = 0.3;
[_backgroundImageView.layer addAnimation:transition forKey:nil];

_backgroundImageView.image = [_backgroundImages objectAtIndex:pageControl.currentPage];
theprojectabot commented 11 years ago

Thanks! I found a similar solution but found that the transition flickers... unless I place this infront of the transition:

if ([UIImagePNGRepresentation(self.image) isEqualToData:UIImagePNGRepresentation(image)]) {
    return;
}

but then I end up with the same choppy swipe transition.

theprojectabot commented 11 years ago

I believe the flicker is because the coreanimation is getting interrupted so it auto completes the transition and then starts a new CATransition and so that auto complete sets the imageview's image and a flicker occurs.

theprojectabot commented 11 years ago

This is because of the quasi-completion state that the control is in as I swipe left and right...

theprojectabot commented 11 years ago

I have tried removing all Animations before calling the CATransition just to clear things out but it doesnt aleviate the flicker.

nicklockwood commented 11 years ago

I'm pretty sure getting the UIImagePNGRepresentation is an incredibly slow and expensive operation. Why not just compare the image pointers directly? If you have multiple image objects containing the same image, you should really use some kind of caching to make sure that doesn't happen.