适合图片个数有限的情况,如果是很多或无限个不停加载建议使用UICollectionView实现。
1.主要实现原理是根据UIImageView的中心点距离UIScrollView中心的距离进行放大缩小。距离中心点UIImageView的size大小时越近则放的比例越大,越远则放大比例越小,最远距离则为size的宽,当超出这个距离则按原尺寸显示。
CGPoint point_s = [self convertPoint:self.scrollView.center toView:self];
CGPoint point_i = [self convertPoint:imageView.center toView:self];
CGPoint point_relate = CGPointMake(point_i.x-self.scrollView.contentOffset.x+self.imageWidth, point_i.y);
CGFloat distance = point_s.x - point_relate.x;
if (ABS(distance) < self.imageWidth) {
CGFloat normalizedDistance = distance / self.imageWidth;
CGFloat zoom = 1 + A * (1 - ABS(normalizedDistance));
imageView.transform = CGAffineTransformMakeScale(zoom, zoom);
imageView.transform = CGAffineTransformTranslate(imageView.transform, 1, -transformY*(1 - ABS(normalizedDistance)));
}
① self.imageWidth为UIImageView的宽度。
② distance为计算出图片imageView与scrollView的中心点距离,最大为self.imageWidth 最小为0。。、
③ zoom 缩放比例 当距离小于self.imageWidth时normalizedDistance小于1 ,zoom则大于1放大,normalizedDistance越小zoom越大最大为1+A,当距离为self.imageWidth则normalizedDistance为1,此时zoom为1,imageView显示原尺寸。
④ imageView.transform = CGAffineTransformMakeScale(zoom, zoom);比例缩放。
⑤ imageView.transform = CGAffineTransformTranslate(imageView.transform, 1, -transformY*(1 - ABS(normalizedDistance)));平移,可以先不做考虑。
2.还有值得注意一点是需要将距离中心最近的UIImageView放置到屏幕的最前面。
if (ABS(distance) < self.imageWidth*0.5) {
UIImageView * current_imageView = imageView;
NSInteger current_index = imageView.tag-200;
UIImageView * before_imageView = self.imageViewArray[current_index==0?self.imageViewArray.count-1:current_index-1];
UIImageView * behand_imageView = self.imageViewArray[current_index==self.imageViewArray.count-1?0:current_index+1];
[self.scrollView bringSubviewToFront:before_imageView];
[self.scrollView bringSubviewToFront:behand_imageView];
[self.scrollView bringSubviewToFront:current_imageView];
}
① 这里当imageView的中心点距离scrollview的中心点小于self.imageWidth*0.5即当做是离中心点最近的ImageView。
② 再分别取出前一个 和 后一个放到第二层位置保证从屏幕外进来的图片上下顺序也是正确的。
以上的处理全都放在scrollViewDidScroll代理方法里面来实现
- (void)scrollViewDidScroll:(UIScrollView *)scrollView{
CGRect visibleRect;
visibleRect.origin = scrollView.contentOffset;
visibleRect.size = scrollView.bounds.size;
for (UIImageView * imageView in self.imageViewArray) {
if (CGRectIntersectsRect(visibleRect, imageView.frame)) {
CGPoint point_s = [self convertPoint:self.scrollView.center toView:self];
CGPoint point_i = [self convertPoint:imageView.center toView:self];
CGPoint point_relate = CGPointMake(point_i.x-self.scrollView.contentOffset.x+self.imageWidth, point_i.y);
CGFloat distance = point_s.x - point_relate.x;
if (ABS(distance) < self.imageWidth) {
CGFloat normalizedDistance = distance / self.imageWidth;
CGFloat zoom = 1 + A * (1 - ABS(normalizedDistance));
imageView.transform = CGAffineTransformMakeScale(zoom, zoom);
imageView.transform = CGAffineTransformTranslate(imageView.transform, 1, -transformY*(1 - ABS(normalizedDistance)));
}
if (ABS(distance) < self.imageWidth*0.5) {
UIImageView * current_imageView = imageView;
NSInteger current_index = imageView.tag-200;
UIImageView * before_imageView = self.imageViewArray[current_index==0?self.imageViewArray.count-1:current_index-1];
UIImageView * behand_imageView = self.imageViewArray[current_index==self.imageViewArray.count-1?0:current_index+1];
[self.scrollView bringSubviewToFront:before_imageView];
[self.scrollView bringSubviewToFront:behand_imageView];
[self.scrollView bringSubviewToFront:current_imageView];
}
}else{
imageView.transform = CGAffineTransformIdentity;
}
}
}
demo地址请查看资源链接