天天省钱快报

SDBrowserImageView.m 7.3KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240
  1. //
  2. // SDBrowserImageView.m
  3. // SDPhotoBrowser
  4. //
  5. // Created by aier on 15-2-6.
  6. // Copyright (c) 2015年 GSD. All rights reserved.
  7. //
  8. #import "SDBrowserImageView.h"
  9. #import "UIImageView+WebCache.h"
  10. #import "SDPhotoBrowserConfig.h"
  11. @implementation SDBrowserImageView
  12. {
  13. __weak SDWaitingView *_waitingView;
  14. BOOL _didCheckSize;
  15. UIScrollView *_scroll;
  16. UIImageView *_scrollImageView;
  17. UIScrollView *_zoomingScroolView;
  18. UIImageView *_zoomingImageView;
  19. CGFloat _totalScale;
  20. }
  21. - (id)initWithFrame:(CGRect)frame
  22. {
  23. self = [super initWithFrame:frame];
  24. if (self) {
  25. self.userInteractionEnabled = YES;
  26. self.contentMode = UIViewContentModeScaleAspectFit;
  27. _totalScale = 1.0;
  28. // 捏合手势缩放图片
  29. UIPinchGestureRecognizer *pinch = [[UIPinchGestureRecognizer alloc] initWithTarget:self action:@selector(zoomImage:)];
  30. pinch.delegate = self;
  31. [self addGestureRecognizer:pinch];
  32. }
  33. return self;
  34. }
  35. - (BOOL)isScaled
  36. {
  37. return 1.0 != _totalScale;
  38. }
  39. - (void)layoutSubviews
  40. {
  41. [super layoutSubviews];
  42. _waitingView.center = CGPointMake(self.frame.size.width * 0.5, self.frame.size.height * 0.5);
  43. CGSize imageSize = self.image.size;
  44. if (self.bounds.size.width * (imageSize.height / imageSize.width) > self.bounds.size.height) {
  45. if (!_scroll) {
  46. UIScrollView *scroll = [[UIScrollView alloc] init];
  47. scroll.backgroundColor = [UIColor whiteColor];
  48. UIImageView *imageView = [[UIImageView alloc] init];
  49. imageView.image = self.image;
  50. _scrollImageView = imageView;
  51. [scroll addSubview:imageView];
  52. scroll.backgroundColor = SDPhotoBrowserBackgrounColor;
  53. _scroll = scroll;
  54. [self addSubview:scroll];
  55. if (_waitingView) {
  56. [self bringSubviewToFront:_waitingView];
  57. }
  58. }
  59. _scroll.frame = self.bounds;
  60. CGFloat imageViewH = self.bounds.size.width * (imageSize.height / imageSize.width);
  61. _scrollImageView.bounds = CGRectMake(0, 0, _scroll.frame.size.width, imageViewH);
  62. _scrollImageView.center = CGPointMake(_scroll.frame.size.width * 0.5, _scrollImageView.frame.size.height * 0.5);
  63. _scroll.contentSize = CGSizeMake(0, _scrollImageView.bounds.size.height);
  64. } else {
  65. if (_scroll) [_scroll removeFromSuperview]; // 防止旋转时适配的scrollView的影响
  66. }
  67. }
  68. - (void)setProgress:(CGFloat)progress
  69. {
  70. _progress = progress;
  71. _waitingView.progress = progress;
  72. }
  73. - (void)setImageWithURL:(NSURL *)url placeholderImage:(UIImage *)placeholder
  74. {
  75. SDWaitingView *waiting = [[SDWaitingView alloc] init];
  76. waiting.bounds = CGRectMake(0, 0, 100, 100);
  77. waiting.mode = SDWaitingViewProgressMode;
  78. _waitingView = waiting;
  79. [self addSubview:waiting];
  80. __weak SDBrowserImageView *imageViewWeak = self;
  81. [self sd_setImageWithURL:url placeholderImage:placeholder options:SDWebImageRetryFailed progress:^(NSInteger receivedSize, NSInteger expectedSize,NSURL * _Nullable targetUR) {
  82. imageViewWeak.progress = (CGFloat)receivedSize / expectedSize;
  83. } completed:^(UIImage *image, NSError *error, SDImageCacheType cacheType, NSURL *imageURL) {
  84. [imageViewWeak removeWaitingView];
  85. if (error) {
  86. UILabel *label = [[UILabel alloc] init];
  87. label.bounds = CGRectMake(0, 0, 160, 30);
  88. label.center = CGPointMake(imageViewWeak.bounds.size.width * 0.5, imageViewWeak.bounds.size.height * 0.5);
  89. label.text = @"图片加载失败";
  90. label.font = [UIFont systemFontOfSize:16];
  91. label.textColor = [UIColor whiteColor];
  92. label.backgroundColor = [UIColor colorWithRed:0 green:0 blue:0 alpha:0.8];
  93. label.layer.cornerRadius = 5;
  94. label.clipsToBounds = YES;
  95. label.textAlignment = NSTextAlignmentCenter;
  96. [imageViewWeak addSubview:label];
  97. } else {
  98. _scrollImageView.image = image;
  99. [_scrollImageView setNeedsDisplay];
  100. }
  101. }];
  102. }
  103. - (void)zoomImage:(UIPinchGestureRecognizer *)recognizer
  104. {
  105. [self prepareForImageViewScaling];
  106. CGFloat scale = recognizer.scale;
  107. CGFloat temp = _totalScale + (scale - 1);
  108. [self setTotalScale:temp];
  109. recognizer.scale = 1.0;
  110. }
  111. - (void)setTotalScale:(CGFloat)totalScale
  112. {
  113. if ((_totalScale < 0.5 && totalScale < _totalScale) || (_totalScale > 2.0 && totalScale > _totalScale)) return; // 最大缩放 2倍,最小0.5倍
  114. [self zoomWithScale:totalScale];
  115. }
  116. - (void)zoomWithScale:(CGFloat)scale
  117. {
  118. _totalScale = scale;
  119. _zoomingImageView.transform = CGAffineTransformMakeScale(scale, scale);
  120. if (scale > 1) {
  121. CGFloat contentW = _zoomingImageView.frame.size.width;
  122. CGFloat contentH = MAX(_zoomingImageView.frame.size.height, self.frame.size.height);
  123. _zoomingImageView.center = CGPointMake(contentW * 0.5, contentH * 0.5);
  124. _zoomingScroolView.contentSize = CGSizeMake(contentW, contentH);
  125. CGPoint offset = _zoomingScroolView.contentOffset;
  126. offset.x = (contentW - _zoomingScroolView.frame.size.width) * 0.5;
  127. // offset.y = (contentH - _zoomingImageView.frame.size.height) * 0.5;
  128. _zoomingScroolView.contentOffset = offset;
  129. } else {
  130. _zoomingScroolView.contentSize = _zoomingScroolView.frame.size;
  131. _zoomingScroolView.contentInset = UIEdgeInsetsMake(0, 0, 0, 0);
  132. _zoomingImageView.center = _zoomingScroolView.center;
  133. }
  134. }
  135. - (void)doubleTapToZommWithScale:(CGFloat)scale
  136. {
  137. [self prepareForImageViewScaling];
  138. [UIView animateWithDuration:0.5 animations:^{
  139. [self zoomWithScale:scale];
  140. } completion:^(BOOL finished) {
  141. if (scale == 1) {
  142. [self clear];
  143. }
  144. }];
  145. }
  146. - (void)prepareForImageViewScaling
  147. {
  148. if (!_zoomingScroolView) {
  149. _zoomingScroolView = [[UIScrollView alloc] initWithFrame:self.bounds];
  150. _zoomingScroolView.backgroundColor = SDPhotoBrowserBackgrounColor;
  151. _zoomingScroolView.contentSize = self.bounds.size;
  152. UIImageView *zoomingImageView = [[UIImageView alloc] initWithImage:self.image];
  153. CGSize imageSize = zoomingImageView.image.size;
  154. CGFloat imageViewH = self.bounds.size.height;
  155. if (imageSize.width > 0) {
  156. imageViewH = self.bounds.size.width * (imageSize.height / imageSize.width);
  157. }
  158. zoomingImageView.bounds = CGRectMake(0, 0, self.bounds.size.width, imageViewH);
  159. zoomingImageView.center = _zoomingScroolView.center;
  160. zoomingImageView.contentMode = UIViewContentModeScaleAspectFit;
  161. _zoomingImageView = zoomingImageView;
  162. [_zoomingScroolView addSubview:zoomingImageView];
  163. [self addSubview:_zoomingScroolView];
  164. }
  165. }
  166. - (void)scaleImage:(CGFloat)scale
  167. {
  168. [self prepareForImageViewScaling];
  169. [self setTotalScale:scale];
  170. }
  171. // 清除缩放
  172. - (void)eliminateScale
  173. {
  174. [self clear];
  175. _totalScale = 1.0;
  176. }
  177. - (void)clear
  178. {
  179. [_zoomingScroolView removeFromSuperview];
  180. _zoomingScroolView = nil;
  181. _zoomingImageView = nil;
  182. }
  183. - (void)removeWaitingView
  184. {
  185. [_waitingView removeFromSuperview];
  186. }
  187. @end
  188. // 版权属于原作者
  189. // http://code4app.com (cn) http://code4app.net (en)
  190. // 发布代码于最专业的源码分享网站: Code4App.com