Last active
April 7, 2016 12:18
-
-
Save thoretton-edwin/2eaa6584edeba6290d47 to your computer and use it in GitHub Desktop.
Gallery with zoom & snap
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
View Hierarchy : | |
Collection | |
> ViewCell for landscape mode | |
>ScrollView | |
> ViewCell for portrait mode | |
>ScrollView | |
Constraints : | |
ScrollView : | |
- Align Center X & Y to ViewCell | |
- Equals W & H | |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
//////////////////////////////////////////////////////////////////////////////////////////////////// | |
- (void)viewDidLoad { | |
[super viewDidLoad]; | |
//get asset of images | |
//_arrayOfAsset = data with images | |
UICollectionSnapFlowLayout* flowLayout = (UICollectionSnapFlowLayout*)self.collection.collectionViewLayout; | |
[flowLayout setScrollDirection:UICollectionViewScrollDirectionHorizontal]; | |
flowLayout.sectionInset = UIEdgeInsetsMake(0, 0, 0, 0); | |
flowLayout.minimumLineSpacing = 0; | |
flowLayout.minimumInteritemSpacing = 0; | |
//auto play | |
[self play:nil]; | |
} | |
-(NSInteger)collectionView:(UICollectionView *)collectionView numberOfItemsInSection:(NSInteger)section{ | |
return _arrayOfAsset.count; | |
} | |
-(NSInteger)numberOfSectionsInCollectionView:(UICollectionView *)collectionView{ | |
return 1; | |
} | |
//////////////////////////////////////////////////////////////////////////////////////////////////// | |
-(UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath{ | |
//UI | |
StopAudioViewCell *cell = nil; | |
if(UIDeviceOrientationIsLandscape([[UIDevice currentDevice] orientation])){ | |
cell = [collectionView dequeueReusableCellWithReuseIdentifier:@"LandscapeScrollCellID" forIndexPath:indexPath]; | |
} | |
else{ | |
cell = [collectionView dequeueReusableCellWithReuseIdentifier:@"PortraitScrollCellID" forIndexPath:indexPath]; | |
} | |
UIImage *orginalImg = //your image | |
if(cell.imageView){ | |
[cell.imageView removeFromSuperview]; | |
} | |
cell.scrollView.contentInset = UIEdgeInsetsZero; | |
cell.imageView = [[UIImageView alloc] initWithImage:orginalImg]; | |
cell.imageView.contentMode = UIViewContentModeCenter; | |
cell.scrollView.contentSize = orginalImg.size; | |
float widthScale = cell.frame.size.width/ orginalImg.size.width; | |
float heightScale = cell.frame.size.height/ orginalImg.size.height; | |
CGFloat minimumZoomScale = MIN(widthScale,heightScale); | |
cell.scrollView.minimumZoomScale= minimumZoomScale; | |
cell.scrollView.maximumZoomScale=minimumZoomScale + 10; | |
cell.scrollView.delegate=cell; | |
cell.scrollView.zoomScale= minimumZoomScale; | |
cell.scrollView.bounds = cell.bounds; | |
cell.scrollView.contentInset = UIEdgeInsetsZero; | |
//We center the contentSize with UIEdgeInset when contentSize < CellSize | |
CGFloat top = 0, left = 0; | |
if(cell.bounds.size.width > cell.scrollView.contentSize.width){ | |
left = (cell.bounds.size.width - cell.scrollView.contentSize.width)/2; | |
} | |
cell.scrollView.contentInset = UIEdgeInsetsMake(top, left, top, left); | |
if(cell.bounds.size.height > cell.scrollView.contentSize.height){ | |
top = (cell.bounds.size.height - cell.scrollView.contentSize.height)/2; | |
} | |
cell.scrollView.contentInset = UIEdgeInsetsMake(top, left, top, left); | |
[cell.scrollView addSubview:cell.imageView]; | |
return cell; | |
} | |
//////////////////////////////////////////////////////////////////////////////////////////////////// | |
- (void)didRotateFromInterfaceOrientation:(UIInterfaceOrientation)fromInterfaceOrientation | |
{ | |
[self.collection reloadData]; | |
[self.collection.collectionViewLayout invalidateLayout]; | |
} | |
//////////////////////////////////////////////////////////////////////////////////////////////////// | |
-(CGSize)collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout *)collectionViewLayout sizeForItemAtIndexPath:(NSIndexPath *)indexPath{ | |
return self.collection.frame.size; | |
} | |
-(UIEdgeInsets) collectionView:(UICollectionView *)collectionView layout:(UICollectionViewLayout *)collectionViewLayout insetForSectionAtIndex:(NSInteger)section{ | |
return UIEdgeInsetsMake(0,0,0,0); | |
} | |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
@interface GalleryImageViewCell : UICollectionViewCell <UIScrollViewDelegate> | |
@property (weak, nonatomic) IBOutlet UIScrollView *scrollContainer; | |
@property (weak, nonatomic) IBOutlet UIImageView *imageView; | |
@property (weak, nonatomic) IBOutlet NSLayoutConstraint *scrollHeightLayoutConstraint; | |
@property (weak, nonatomic) IBOutlet NSLayoutConstraint *scrollWidthLayoutConstraint; | |
@end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#import "GalleryImageViewCell.h" | |
@implementation GalleryImageViewCell | |
- (UIView *)viewForZoomingInScrollView:(UIScrollView *)scrollView | |
{ | |
return self.imageView; | |
} | |
-(void)scrollViewDidEndZooming:(UIScrollView *)scrollView withView:(UIView *)view atScale:(CGFloat)scale{ | |
self.scrollView.contentInset = UIEdgeInsetsZero; | |
CGFloat top = 0, left = 0; | |
if(self.bounds.size.height > self.scrollView.contentSize.height){ | |
top = (self.bounds.size.height - self.scrollView.contentSize.height)/2; | |
} | |
if(self.bounds.size.width > self.scrollView.contentSize.width){ | |
left = (self.bounds.size.width - self.scrollView.contentSize.width)/2; | |
} | |
self.scrollView.contentInset = UIEdgeInsetsMake(top, left, top, left); | |
} | |
@end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#import "UICollectionSnapFlowLayout.h" | |
@implementation UICollectionSnapFlowLayout | |
-(CGPoint) targetContentOffsetForProposedContentOffset:(CGPoint)proposedContentOffset withScrollingVelocity:(CGPoint)velocity | |
{ | |
CGSize collectionViewSize = self.collectionView.bounds.size; | |
CGFloat proposedContentOffsetCenterX = proposedContentOffset.x + self.collectionView.bounds.size.width * 0.5f; | |
CGRect proposedRect = self.collectionView.bounds; | |
// Comment out if you want the collectionview simply stop at the center of an item while scrolling freely | |
// proposedRect = CGRectMake(proposedContentOffset.x, 0.0, collectionViewSize.width, collectionViewSize.height); | |
UICollectionViewLayoutAttributes* candidateAttributes; | |
for (UICollectionViewLayoutAttributes* attributes in [self layoutAttributesForElementsInRect:proposedRect]) | |
{ | |
// == Skip comparison with non-cell items (headers and footers) == // | |
if (attributes.representedElementCategory != UICollectionElementCategoryCell) | |
{ | |
continue; | |
} | |
// == First time in the loop == // | |
if(!candidateAttributes) | |
{ | |
candidateAttributes = attributes; | |
continue; | |
} | |
if (fabsf(attributes.center.x - proposedContentOffsetCenterX) < fabsf(candidateAttributes.center.x - proposedContentOffsetCenterX)) | |
{ | |
candidateAttributes = attributes; | |
} | |
} | |
return CGPointMake(candidateAttributes.center.x - self.collectionView.bounds.size.width * 0.5f, proposedContentOffset.y); | |
} | |
@end |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment