SDRefreshView.m 8.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239
  1. //
  2. // SDRefreshView.m
  3. // SDRefreshView
  4. //
  5. // Created by aier on 15-2-22.
  6. // Copyright (c) 2015年 GSD. All rights reserved.
  7. //
  8. /**
  9. *******************************************************
  10. * *
  11. * 感谢您的支持, 如果下载的代码在使用过程中出现BUG或者其他问题 *
  12. * 您可以发邮件到gsdios@126.com 或者 到 *
  13. * https://github.com/gsdios?tab=repositories 提交问题 *
  14. * *
  15. *******************************************************
  16. */
  17. #import "SDRefreshView.h"
  18. #import "UIView+SDExtension.h"
  19. #import "WFCUImage.h"
  20. CGFloat const SDRefreshViewDefaultHeight = 70.0f;
  21. CGFloat const SDActivityIndicatorViewMargin = 50.0f;
  22. CGFloat const SDTextIndicatorMargin = 20.0f;
  23. CGFloat const SDTimeIndicatorMargin = 10.0f;
  24. @implementation SDRefreshView
  25. {
  26. UIImageView *_stateIndicatorView;
  27. UILabel *_textIndicator;
  28. UILabel *_timeIndicator;
  29. NSString *_lastRefreshingTimeString;
  30. BOOL _hasSetOriginalInsets;
  31. }
  32. - (id)initWithFrame:(CGRect)frame
  33. {
  34. self = [super initWithFrame:frame];
  35. if (self) {
  36. UIActivityIndicatorView *activity = [[UIActivityIndicatorView alloc] init];
  37. activity.activityIndicatorViewStyle = UIActivityIndicatorViewStyleGray;
  38. [activity startAnimating];
  39. [self addSubview:activity];
  40. _activityIndicatorView = activity;
  41. // 状态提示图片
  42. UIImageView *stateIndicator = [[UIImageView alloc] init];
  43. stateIndicator.image = [WFCUImage imageNamed:@"sdRefeshView_arrow"];
  44. [self addSubview:stateIndicator];
  45. _stateIndicatorView = stateIndicator;
  46. _stateIndicatorView.bounds = CGRectMake(0, 0, 15, 40);
  47. // 状态提示label
  48. UILabel *textIndicator = [[UILabel alloc] init];
  49. textIndicator.bounds = CGRectMake(0, 0, 300, 30);
  50. textIndicator.textAlignment = NSTextAlignmentCenter;
  51. textIndicator.backgroundColor = [UIColor clearColor];
  52. textIndicator.font = [UIFont systemFontOfSize:14];
  53. textIndicator.textColor = [UIColor lightGrayColor];
  54. [self addSubview:textIndicator];
  55. _textIndicator = textIndicator;
  56. // 更新时间提示label
  57. UILabel *timeIndicator = [[UILabel alloc] init];
  58. timeIndicator.bounds = CGRectMake(0, 0, 160, 16);;
  59. timeIndicator.textAlignment = NSTextAlignmentCenter;
  60. timeIndicator.textColor = [UIColor lightGrayColor];
  61. timeIndicator.font = [UIFont systemFontOfSize:14];
  62. [self addSubview:timeIndicator];
  63. _timeIndicator = timeIndicator;
  64. }
  65. return self;
  66. }
  67. + (instancetype)refreshView
  68. {
  69. return [[self alloc] init];
  70. }
  71. - (void)willMoveToSuperview:(UIView *)newSuperview
  72. {
  73. [super willMoveToSuperview:newSuperview];
  74. if (!newSuperview) {
  75. [self.superview removeObserver:self forKeyPath:SDRefreshViewObservingkeyPath];
  76. }
  77. }
  78. - (void)didMoveToSuperview
  79. {
  80. [super didMoveToSuperview];
  81. self.bounds = CGRectMake(0, 0, self.scrollView.frame.size.width, SDRefreshViewDefaultHeight);
  82. }
  83. - (void)layoutSubviews
  84. {
  85. [super layoutSubviews];
  86. _activityIndicatorView.center = CGPointMake(SDActivityIndicatorViewMargin, self.sd_height * 0.5);
  87. _stateIndicatorView.center = _activityIndicatorView.center;
  88. _textIndicator.center = CGPointMake(self.sd_width * 0.5, _activityIndicatorView.sd_height * 0.5 + SDTextIndicatorMargin);
  89. _timeIndicator.center = CGPointMake(self.sd_width * 0.5, self.sd_height - _timeIndicator.sd_height * 0.5 - SDTimeIndicatorMargin);
  90. }
  91. - (NSString *)lastRefreshingTimeString
  92. {
  93. if (_lastRefreshingTimeString == nil) {
  94. return [self refreshingTimeString];
  95. }
  96. return _lastRefreshingTimeString;
  97. }
  98. - (void)addToScrollView:(UIScrollView *)scrollView
  99. {
  100. _scrollView = scrollView;
  101. [_scrollView addSubview:self];
  102. [_scrollView addObserver:self forKeyPath:SDRefreshViewObservingkeyPath options:NSKeyValueObservingOptionNew context:nil];
  103. // 默认是在NavigationController控制下,否则可以调用addToScrollView:isEffectedByNavigationController:(设值为NO) 即可
  104. _isEffectedByNavigationController = YES;
  105. }
  106. - (void)addToScrollView:(UIScrollView *)scrollView isEffectedByNavigationController:(BOOL)effectedByNavigationController
  107. {
  108. [self addToScrollView:scrollView];
  109. _isEffectedByNavigationController = effectedByNavigationController;
  110. _originalEdgeInsets = scrollView.contentInset;
  111. }
  112. - (void)addTarget:(id)target refreshAction:(SEL)action
  113. {
  114. _beginRefreshingTarget = target;
  115. _beginRefreshingAction = action;
  116. }
  117. // 获得在scrollView的contentInset原来基础上增加一定值之后的新contentInset
  118. - (UIEdgeInsets)syntheticalEdgeInsetsWithEdgeInsets:(UIEdgeInsets)edgeInsets
  119. {
  120. return UIEdgeInsetsMake(_originalEdgeInsets.top + edgeInsets.top, _originalEdgeInsets.left + edgeInsets.left, _originalEdgeInsets.bottom + edgeInsets.bottom, _originalEdgeInsets.right + edgeInsets.right);
  121. }
  122. - (void)setRefreshState:(SDRefreshViewState)refreshState
  123. {
  124. _refreshState = refreshState;
  125. switch (refreshState) {
  126. // 进入刷新状态
  127. case SDRefreshViewStateRefreshing:
  128. {
  129. if (!_hasSetOriginalInsets) {
  130. _originalEdgeInsets = self.scrollView.contentInset;
  131. _hasSetOriginalInsets = YES;
  132. }
  133. _scrollView.contentInset = [self syntheticalEdgeInsetsWithEdgeInsets:self.scrollViewEdgeInsets];
  134. [_activityIndicatorView startAnimating];
  135. _stateIndicatorView.hidden = YES;
  136. _activityIndicatorView.hidden = NO;
  137. _lastRefreshingTimeString = [self refreshingTimeString];
  138. _textIndicator.text = SDRefreshViewRefreshingStateText;
  139. if (self.beginRefreshingOperation) {
  140. self.beginRefreshingOperation();
  141. } else if (self.beginRefreshingTarget) {
  142. if ([self.beginRefreshingTarget respondsToSelector:self.beginRefreshingAction]) {
  143. // 屏蔽performSelector-leak警告
  144. #pragma clang diagnostic push
  145. #pragma clang diagnostic ignored "-Warc-performSelector-leaks"
  146. [self.beginRefreshingTarget performSelector:self.beginRefreshingAction];
  147. }
  148. }
  149. }
  150. break;
  151. case SDRefreshViewStateWillRefresh:
  152. {
  153. _textIndicator.text = SDRefreshViewWillRefreshStateText;
  154. [UIView animateWithDuration:0.5 animations:^{
  155. _stateIndicatorView.transform = CGAffineTransformMakeRotation(self.stateIndicatorViewWillRefreshStateTransformAngle);
  156. }];
  157. }
  158. break;
  159. case SDRefreshViewStateNormal:
  160. {
  161. [UIView animateWithDuration:0.5 animations:^{
  162. _stateIndicatorView.transform = CGAffineTransformMakeRotation(self.stateIndicatorViewNormalTransformAngle);
  163. }];
  164. _textIndicator.text = self.textForNormalState;
  165. _timeIndicator.text = [NSString stringWithFormat:@"最后更新:%@", [self lastRefreshingTimeString]];
  166. _stateIndicatorView.hidden = NO;
  167. [_activityIndicatorView stopAnimating];
  168. _activityIndicatorView.hidden = YES;
  169. }
  170. break;
  171. default:
  172. break;
  173. }
  174. }
  175. - (void)endRefreshing
  176. {
  177. [UIView animateWithDuration:0.6 animations:^{
  178. _scrollView.contentInset = _originalEdgeInsets;
  179. } completion:^(BOOL finished) {
  180. [self setRefreshState:SDRefreshViewStateNormal];
  181. if (self.isManuallyRefreshing) {
  182. self.isManuallyRefreshing = NO;
  183. }
  184. }];
  185. }
  186. // 更新时间
  187. - (NSString *)refreshingTimeString
  188. {
  189. NSDate *date = [NSDate date];
  190. NSDateFormatter *formatter = [[NSDateFormatter alloc] init];
  191. formatter.dateFormat = @"HH:mm";
  192. return [formatter stringFromDate:date];
  193. }
  194. // 保留!
  195. - (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context
  196. {
  197. ;
  198. }
  199. @end