From 7b02207537d35bfa1714bf8beafc921f717d100a Mon Sep 17 00:00:00 2001 From: 单军华 Date: Wed, 11 Jul 2018 10:47:42 +0800 Subject: [PATCH] 首次上传 --- screendisplay/Pods/TZImagePickerController/TZImagePickerController/TZImagePickerController/TZPhotoPickerController.m | 1002 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 files changed, 1,002 insertions(+), 0 deletions(-) diff --git a/screendisplay/Pods/TZImagePickerController/TZImagePickerController/TZImagePickerController/TZPhotoPickerController.m b/screendisplay/Pods/TZImagePickerController/TZImagePickerController/TZImagePickerController/TZPhotoPickerController.m new file mode 100755 index 0000000..49b1f4f --- /dev/null +++ b/screendisplay/Pods/TZImagePickerController/TZImagePickerController/TZImagePickerController/TZPhotoPickerController.m @@ -0,0 +1,1002 @@ +// +// TZPhotoPickerController.m +// TZImagePickerController +// +// Created by ������ on 15/12/24. +// Copyright �� 2015��� ������. All rights reserved. +// + +#import "TZPhotoPickerController.h" +#import "TZImagePickerController.h" +#import "TZPhotoPreviewController.h" +#import "TZAssetCell.h" +#import "TZAssetModel.h" +#import "UIView+Layout.h" +#import "TZImageManager.h" +#import "TZVideoPlayerController.h" +#import "TZGifPhotoPreviewController.h" +#import "TZLocationManager.h" +#import <MobileCoreServices/MobileCoreServices.h> + +@interface TZPhotoPickerController ()<UICollectionViewDataSource,UICollectionViewDelegate,UIImagePickerControllerDelegate,UINavigationControllerDelegate,UIAlertViewDelegate> { + NSMutableArray *_models; + + UIView *_bottomToolBar; + UIButton *_previewButton; + UIButton *_doneButton; + UIImageView *_numberImageView; + UILabel *_numberLabel; + UIButton *_originalPhotoButton; + UILabel *_originalPhotoLabel; + UIView *_divideLine; + + BOOL _shouldScrollToBottom; + BOOL _showTakePhotoBtn; + + CGFloat _offsetItemCount; +} +@property CGRect previousPreheatRect; +@property (nonatomic, assign) BOOL isSelectOriginalPhoto; +@property (nonatomic, strong) TZCollectionView *collectionView; +@property (strong, nonatomic) UICollectionViewFlowLayout *layout; +@property (nonatomic, strong) UIImagePickerController *imagePickerVc; +@property (strong, nonatomic) CLLocation *location; +@property (assign, nonatomic) BOOL useCachedImage; +@end + +static CGSize AssetGridThumbnailSize; +static CGFloat itemMargin = 5; + +@implementation TZPhotoPickerController + +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wdeprecated-declarations" +- (UIImagePickerController *)imagePickerVc { + if (_imagePickerVc == nil) { + _imagePickerVc = [[UIImagePickerController alloc] init]; + _imagePickerVc.delegate = self; + // set appearance / ��������������������������������������� + if (iOS7Later) { + _imagePickerVc.navigationBar.barTintColor = self.navigationController.navigationBar.barTintColor; + } + _imagePickerVc.navigationBar.tintColor = self.navigationController.navigationBar.tintColor; + UIBarButtonItem *tzBarItem, *BarItem; + if (iOS9Later) { + tzBarItem = [UIBarButtonItem appearanceWhenContainedInInstancesOfClasses:@[[TZImagePickerController class]]]; + BarItem = [UIBarButtonItem appearanceWhenContainedInInstancesOfClasses:@[[UIImagePickerController class]]]; + } else { + tzBarItem = [UIBarButtonItem appearanceWhenContainedIn:[TZImagePickerController class], nil]; + BarItem = [UIBarButtonItem appearanceWhenContainedIn:[UIImagePickerController class], nil]; + } + NSDictionary *titleTextAttributes = [tzBarItem titleTextAttributesForState:UIControlStateNormal]; + [BarItem setTitleTextAttributes:titleTextAttributes forState:UIControlStateNormal]; + } + return _imagePickerVc; +} + +- (void)viewDidLoad { + [super viewDidLoad]; + self.isFirstAppear = YES; + TZImagePickerController *tzImagePickerVc = (TZImagePickerController *)self.navigationController; + _isSelectOriginalPhoto = tzImagePickerVc.isSelectOriginalPhoto; + _shouldScrollToBottom = YES; + self.view.backgroundColor = [UIColor whiteColor]; + self.navigationItem.title = _model.name; + self.navigationItem.rightBarButtonItem = [[UIBarButtonItem alloc] initWithTitle:tzImagePickerVc.cancelBtnTitleStr style:UIBarButtonItemStylePlain target:tzImagePickerVc action:@selector(cancelButtonClick)]; + if (tzImagePickerVc.navLeftBarButtonSettingBlock) { + UIButton *leftButton = [UIButton buttonWithType:UIButtonTypeCustom]; + leftButton.frame = CGRectMake(0, 0, 44, 44); + [leftButton addTarget:self action:@selector(navLeftBarButtonClick) forControlEvents:UIControlEventTouchUpInside]; + tzImagePickerVc.navLeftBarButtonSettingBlock(leftButton); + self.navigationItem.leftBarButtonItem = [[UIBarButtonItem alloc] initWithCustomView:leftButton]; + } + _showTakePhotoBtn = _model.isCameraRoll && ((tzImagePickerVc.allowTakePicture && tzImagePickerVc.allowPickingImage) || (tzImagePickerVc.allowTakeVideo && tzImagePickerVc.allowPickingVideo)); + // [self resetCachedAssets]; + [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(didChangeStatusBarOrientationNotification:) name:UIApplicationDidChangeStatusBarOrientationNotification object:nil]; +} + +- (void)fetchAssetModels { + TZImagePickerController *tzImagePickerVc = (TZImagePickerController *)self.navigationController; + if (_isFirstAppear && !_model.models.count) { + [tzImagePickerVc showProgressHUD]; + } + dispatch_async(dispatch_get_global_queue(0, 0), ^{ + if (!tzImagePickerVc.sortAscendingByModificationDate && self->_isFirstAppear && iOS8Later && self->_model.isCameraRoll) { + [[TZImageManager manager] getCameraRollAlbum:tzImagePickerVc.allowPickingVideo allowPickingImage:tzImagePickerVc.allowPickingImage needFetchAssets:YES completion:^(TZAlbumModel *model) { + self->_model = model; + self->_models = [NSMutableArray arrayWithArray:self->_model.models]; + [self initSubviews]; + }]; + } else { + if (self->_showTakePhotoBtn || !iOS8Later || self->_isFirstAppear) { + [[TZImageManager manager] getAssetsFromFetchResult:self->_model.result completion:^(NSArray<TZAssetModel *> *models) { + self->_models = [NSMutableArray arrayWithArray:models]; + [self initSubviews]; + }]; + } else { + self->_models = [NSMutableArray arrayWithArray:self->_model.models]; + [self initSubviews]; + } + } + }); +} + +- (void)initSubviews { + dispatch_async(dispatch_get_main_queue(), ^{ + TZImagePickerController *tzImagePickerVc = (TZImagePickerController *)self.navigationController; + [tzImagePickerVc hideProgressHUD]; + + [self checkSelectedModels]; + [self configCollectionView]; + self->_collectionView.hidden = YES; + [self configBottomToolBar]; + + [self scrollCollectionViewToBottom]; + }); +} + +- (void)viewWillDisappear:(BOOL)animated { + [super viewWillDisappear:animated]; + TZImagePickerController *tzImagePickerVc = (TZImagePickerController *)self.navigationController; + tzImagePickerVc.isSelectOriginalPhoto = _isSelectOriginalPhoto; +} + +- (BOOL)prefersStatusBarHidden { + return NO; +} + +- (void)configCollectionView { + _layout = [[UICollectionViewFlowLayout alloc] init]; + _collectionView = [[TZCollectionView alloc] initWithFrame:CGRectZero collectionViewLayout:_layout]; + _collectionView.backgroundColor = [UIColor whiteColor]; + _collectionView.dataSource = self; + _collectionView.delegate = self; + _collectionView.alwaysBounceHorizontal = NO; + _collectionView.contentInset = UIEdgeInsetsMake(itemMargin, itemMargin, itemMargin, itemMargin); + + if (_showTakePhotoBtn) { + _collectionView.contentSize = CGSizeMake(self.view.tz_width, ((_model.count + self.columnNumber) / self.columnNumber) * self.view.tz_width); + } else { + _collectionView.contentSize = CGSizeMake(self.view.tz_width, ((_model.count + self.columnNumber - 1) / self.columnNumber) * self.view.tz_width); + } + [self.view addSubview:_collectionView]; + [_collectionView registerClass:[TZAssetCell class] forCellWithReuseIdentifier:@"TZAssetCell"]; + [_collectionView registerClass:[TZAssetCameraCell class] forCellWithReuseIdentifier:@"TZAssetCameraCell"]; +} + +- (void)viewWillAppear:(BOOL)animated { + [super viewWillAppear:animated]; + // Determine the size of the thumbnails to request from the PHCachingImageManager + CGFloat scale = 2.0; + if ([UIScreen mainScreen].bounds.size.width > 600) { + scale = 1.0; + } + CGSize cellSize = ((UICollectionViewFlowLayout *)_collectionView.collectionViewLayout).itemSize; + AssetGridThumbnailSize = CGSizeMake(cellSize.width * scale, cellSize.height * scale); + + if (!_models) { + [self fetchAssetModels]; + } +} + +- (void)viewDidAppear:(BOOL)animated { + [super viewDidAppear:animated]; + if (iOS8Later) { + // [self updateCachedAssets]; + } +} + +- (void)configBottomToolBar { + TZImagePickerController *tzImagePickerVc = (TZImagePickerController *)self.navigationController; + if (!tzImagePickerVc.showSelectBtn) return; + + _bottomToolBar = [[UIView alloc] initWithFrame:CGRectZero]; + CGFloat rgb = 253 / 255.0; + _bottomToolBar.backgroundColor = [UIColor colorWithRed:rgb green:rgb blue:rgb alpha:1.0]; + + _previewButton = [UIButton buttonWithType:UIButtonTypeCustom]; + [_previewButton addTarget:self action:@selector(previewButtonClick) forControlEvents:UIControlEventTouchUpInside]; + _previewButton.titleLabel.font = [UIFont systemFontOfSize:16]; + [_previewButton setTitle:tzImagePickerVc.previewBtnTitleStr forState:UIControlStateNormal]; + [_previewButton setTitle:tzImagePickerVc.previewBtnTitleStr forState:UIControlStateDisabled]; + [_previewButton setTitleColor:[UIColor blackColor] forState:UIControlStateNormal]; + [_previewButton setTitleColor:[UIColor lightGrayColor] forState:UIControlStateDisabled]; + _previewButton.enabled = tzImagePickerVc.selectedModels.count; + + if (tzImagePickerVc.allowPickingOriginalPhoto) { + _originalPhotoButton = [UIButton buttonWithType:UIButtonTypeCustom]; + _originalPhotoButton.imageEdgeInsets = UIEdgeInsetsMake(0, -10, 0, 0); + [_originalPhotoButton addTarget:self action:@selector(originalPhotoButtonClick) forControlEvents:UIControlEventTouchUpInside]; + _originalPhotoButton.titleLabel.font = [UIFont systemFontOfSize:16]; + [_originalPhotoButton setTitle:tzImagePickerVc.fullImageBtnTitleStr forState:UIControlStateNormal]; + [_originalPhotoButton setTitle:tzImagePickerVc.fullImageBtnTitleStr forState:UIControlStateSelected]; + [_originalPhotoButton setTitleColor:[UIColor lightGrayColor] forState:UIControlStateNormal]; + [_originalPhotoButton setTitleColor:[UIColor blackColor] forState:UIControlStateSelected]; + [_originalPhotoButton setImage:tzImagePickerVc.photoOriginDefImage forState:UIControlStateNormal]; + [_originalPhotoButton setImage:tzImagePickerVc.photoOriginSelImage forState:UIControlStateSelected]; + _originalPhotoButton.imageView.clipsToBounds = YES; + _originalPhotoButton.imageView.contentMode = UIViewContentModeScaleAspectFit; + _originalPhotoButton.selected = _isSelectOriginalPhoto; + _originalPhotoButton.enabled = tzImagePickerVc.selectedModels.count > 0; + + _originalPhotoLabel = [[UILabel alloc] init]; + _originalPhotoLabel.textAlignment = NSTextAlignmentLeft; + _originalPhotoLabel.font = [UIFont systemFontOfSize:16]; + _originalPhotoLabel.textColor = [UIColor blackColor]; + if (_isSelectOriginalPhoto) [self getSelectedPhotoBytes]; + } + + _doneButton = [UIButton buttonWithType:UIButtonTypeCustom]; + _doneButton.titleLabel.font = [UIFont systemFontOfSize:16]; + [_doneButton addTarget:self action:@selector(doneButtonClick) forControlEvents:UIControlEventTouchUpInside]; + [_doneButton setTitle:tzImagePickerVc.doneBtnTitleStr forState:UIControlStateNormal]; + [_doneButton setTitle:tzImagePickerVc.doneBtnTitleStr forState:UIControlStateDisabled]; + [_doneButton setTitleColor:tzImagePickerVc.oKButtonTitleColorNormal forState:UIControlStateNormal]; + [_doneButton setTitleColor:tzImagePickerVc.oKButtonTitleColorDisabled forState:UIControlStateDisabled]; + _doneButton.enabled = tzImagePickerVc.selectedModels.count || tzImagePickerVc.alwaysEnableDoneBtn; + + _numberImageView = [[UIImageView alloc] initWithImage:tzImagePickerVc.photoNumberIconImage]; + _numberImageView.hidden = tzImagePickerVc.selectedModels.count <= 0; + _numberImageView.clipsToBounds = YES; + _numberImageView.contentMode = UIViewContentModeScaleAspectFit; + _numberImageView.backgroundColor = [UIColor clearColor]; + + _numberLabel = [[UILabel alloc] init]; + _numberLabel.font = [UIFont systemFontOfSize:15]; + _numberLabel.textColor = [UIColor whiteColor]; + _numberLabel.textAlignment = NSTextAlignmentCenter; + _numberLabel.text = [NSString stringWithFormat:@"%zd",tzImagePickerVc.selectedModels.count]; + _numberLabel.hidden = tzImagePickerVc.selectedModels.count <= 0; + _numberLabel.backgroundColor = [UIColor clearColor]; + + _divideLine = [[UIView alloc] init]; + CGFloat rgb2 = 222 / 255.0; + _divideLine.backgroundColor = [UIColor colorWithRed:rgb2 green:rgb2 blue:rgb2 alpha:1.0]; + + [_bottomToolBar addSubview:_divideLine]; + [_bottomToolBar addSubview:_previewButton]; + [_bottomToolBar addSubview:_doneButton]; + [_bottomToolBar addSubview:_numberImageView]; + [_bottomToolBar addSubview:_numberLabel]; + [_bottomToolBar addSubview:_originalPhotoButton]; + [self.view addSubview:_bottomToolBar]; + [_originalPhotoButton addSubview:_originalPhotoLabel]; + + if (tzImagePickerVc.photoPickerPageUIConfigBlock) { + tzImagePickerVc.photoPickerPageUIConfigBlock(_collectionView, _bottomToolBar, _previewButton, _originalPhotoButton, _originalPhotoLabel, _doneButton, _numberImageView, _numberLabel, _divideLine); + } +} + +#pragma mark - Layout + +- (void)viewDidLayoutSubviews { + [super viewDidLayoutSubviews]; + + TZImagePickerController *tzImagePickerVc = (TZImagePickerController *)self.navigationController; + + CGFloat top = 0; + CGFloat collectionViewHeight = 0; + CGFloat naviBarHeight = self.navigationController.navigationBar.tz_height; + BOOL isStatusBarHidden = [UIApplication sharedApplication].isStatusBarHidden; + CGFloat toolBarHeight = [TZCommonTools tz_isIPhoneX] ? 50 + (83 - 49) : 50; + if (self.navigationController.navigationBar.isTranslucent) { + top = naviBarHeight; + if (iOS7Later && !isStatusBarHidden) top += [TZCommonTools tz_statusBarHeight]; + collectionViewHeight = tzImagePickerVc.showSelectBtn ? self.view.tz_height - toolBarHeight - top : self.view.tz_height - top;; + } else { + collectionViewHeight = tzImagePickerVc.showSelectBtn ? self.view.tz_height - toolBarHeight : self.view.tz_height; + } + _collectionView.frame = CGRectMake(0, top, self.view.tz_width, collectionViewHeight); + CGFloat itemWH = (self.view.tz_width - (self.columnNumber + 1) * itemMargin) / self.columnNumber; + _layout.itemSize = CGSizeMake(itemWH, itemWH); + _layout.minimumInteritemSpacing = itemMargin; + _layout.minimumLineSpacing = itemMargin; + [_collectionView setCollectionViewLayout:_layout]; + if (_offsetItemCount > 0) { + CGFloat offsetY = _offsetItemCount * (_layout.itemSize.height + _layout.minimumLineSpacing); + [_collectionView setContentOffset:CGPointMake(0, offsetY)]; + } + + CGFloat toolBarTop = 0; + if (!self.navigationController.navigationBar.isHidden) { + toolBarTop = self.view.tz_height - toolBarHeight; + } else { + CGFloat navigationHeight = naviBarHeight; + if (iOS7Later) navigationHeight += [TZCommonTools tz_statusBarHeight]; + toolBarTop = self.view.tz_height - toolBarHeight - navigationHeight; + } + _bottomToolBar.frame = CGRectMake(0, toolBarTop, self.view.tz_width, toolBarHeight); + CGFloat previewWidth = [tzImagePickerVc.previewBtnTitleStr tz_calculateSizeWithAttributes:@{NSFontAttributeName:[UIFont systemFontOfSize:16]} maxSize:CGSizeMake(CGFLOAT_MAX, CGFLOAT_MAX)].width + 2; + if (!tzImagePickerVc.allowPreview) { + previewWidth = 0.0; + } + _previewButton.frame = CGRectMake(10, 3, previewWidth, 44); + _previewButton.tz_width = !tzImagePickerVc.showSelectBtn ? 0 : previewWidth; + if (tzImagePickerVc.allowPickingOriginalPhoto) { + CGFloat fullImageWidth = [tzImagePickerVc.fullImageBtnTitleStr tz_calculateSizeWithAttributes:@{NSFontAttributeName:[UIFont systemFontOfSize:13]} maxSize:CGSizeMake(CGFLOAT_MAX, CGFLOAT_MAX)].width; + _originalPhotoButton.frame = CGRectMake(CGRectGetMaxX(_previewButton.frame), 0, fullImageWidth + 56, 50); + _originalPhotoLabel.frame = CGRectMake(fullImageWidth + 46, 0, 80, 50); + } + [_doneButton sizeToFit]; + _doneButton.frame = CGRectMake(self.view.tz_width - _doneButton.tz_width - 12, 0, _doneButton.tz_width, 50); + _numberImageView.frame = CGRectMake(_doneButton.tz_left - 24 - 5, 13, 24, 24); + _numberLabel.frame = _numberImageView.frame; + _divideLine.frame = CGRectMake(0, 0, self.view.tz_width, 1); + + [TZImageManager manager].columnNumber = [TZImageManager manager].columnNumber; + [self.collectionView reloadData]; + + if (tzImagePickerVc.photoPickerPageDidLayoutSubviewsBlock) { + tzImagePickerVc.photoPickerPageDidLayoutSubviewsBlock(_collectionView, _bottomToolBar, _previewButton, _originalPhotoButton, _originalPhotoLabel, _doneButton, _numberImageView, _numberLabel, _divideLine); + } +} + +#pragma mark - Notification + +- (void)didChangeStatusBarOrientationNotification:(NSNotification *)noti { + _offsetItemCount = _collectionView.contentOffset.y / (_layout.itemSize.height + _layout.minimumLineSpacing); +} + +#pragma mark - Click Event +- (void)navLeftBarButtonClick{ + [self.navigationController popViewControllerAnimated:YES]; +} +- (void)previewButtonClick { + TZPhotoPreviewController *photoPreviewVc = [[TZPhotoPreviewController alloc] init]; + [self pushPhotoPrevireViewController:photoPreviewVc needCheckSelectedModels:YES]; +} + +- (void)originalPhotoButtonClick { + _originalPhotoButton.selected = !_originalPhotoButton.isSelected; + _isSelectOriginalPhoto = _originalPhotoButton.isSelected; + _originalPhotoLabel.hidden = !_originalPhotoButton.isSelected; + if (_isSelectOriginalPhoto) { + [self getSelectedPhotoBytes]; + } +} + +- (void)doneButtonClick { + TZImagePickerController *tzImagePickerVc = (TZImagePickerController *)self.navigationController; + // 1.6.8 ��������������������������������������������� + if (tzImagePickerVc.minImagesCount && tzImagePickerVc.selectedModels.count < tzImagePickerVc.minImagesCount) { + NSString *title = [NSString stringWithFormat:[NSBundle tz_localizedStringForKey:@"Select a minimum of %zd photos"], tzImagePickerVc.minImagesCount]; + [tzImagePickerVc showAlertWithTitle:title]; + return; + } + + [tzImagePickerVc showProgressHUD]; + NSMutableArray *assets = [NSMutableArray array]; + NSMutableArray *photos; + NSMutableArray *infoArr; + if (tzImagePickerVc.onlyReturnAsset) { // not fetch image + for (NSInteger i = 0; i < tzImagePickerVc.selectedModels.count; i++) { + TZAssetModel *model = tzImagePickerVc.selectedModels[i]; + [assets addObject:model.asset]; + } + } else { // fetch image + photos = [NSMutableArray array]; + infoArr = [NSMutableArray array]; + for (NSInteger i = 0; i < tzImagePickerVc.selectedModels.count; i++) { [photos addObject:@1];[assets addObject:@1];[infoArr addObject:@1]; } + + __block BOOL havenotShowAlert = YES; + [TZImageManager manager].shouldFixOrientation = YES; + __block id alertView; + for (NSInteger i = 0; i < tzImagePickerVc.selectedModels.count; i++) { + TZAssetModel *model = tzImagePickerVc.selectedModels[i]; + [[TZImageManager manager] getPhotoWithAsset:model.asset completion:^(UIImage *photo, NSDictionary *info, BOOL isDegraded) { + if (isDegraded) return; + if (photo) { + photo = [[TZImageManager manager] scaleImage:photo toSize:CGSizeMake(tzImagePickerVc.photoWidth, (int)(tzImagePickerVc.photoWidth * photo.size.height / photo.size.width))]; + [photos replaceObjectAtIndex:i withObject:photo]; + } + if (info) [infoArr replaceObjectAtIndex:i withObject:info]; + [assets replaceObjectAtIndex:i withObject:model.asset]; + + for (id item in photos) { if ([item isKindOfClass:[NSNumber class]]) return; } + + if (havenotShowAlert) { + [tzImagePickerVc hideAlertView:alertView]; + [self didGetAllPhotos:photos assets:assets infoArr:infoArr]; + } + } progressHandler:^(double progress, NSError *error, BOOL *stop, NSDictionary *info) { + // ���������������������iCloud���������,������������ + if (progress < 1 && havenotShowAlert && !alertView) { + [tzImagePickerVc hideProgressHUD]; + alertView = [tzImagePickerVc showAlertWithTitle:[NSBundle tz_localizedStringForKey:@"Synchronizing photos from iCloud"]]; + havenotShowAlert = NO; + return; + } + if (progress >= 1) { + havenotShowAlert = YES; + } + } networkAccessAllowed:YES]; + } + } + if (tzImagePickerVc.selectedModels.count <= 0 || tzImagePickerVc.onlyReturnAsset) { + [self didGetAllPhotos:photos assets:assets infoArr:infoArr]; + } +} + +- (void)didGetAllPhotos:(NSArray *)photos assets:(NSArray *)assets infoArr:(NSArray *)infoArr { + TZImagePickerController *tzImagePickerVc = (TZImagePickerController *)self.navigationController; + [tzImagePickerVc hideProgressHUD]; + + if (tzImagePickerVc.autoDismiss) { + [self.navigationController dismissViewControllerAnimated:YES completion:^{ + [self callDelegateMethodWithPhotos:photos assets:assets infoArr:infoArr]; + }]; + } else { + [self callDelegateMethodWithPhotos:photos assets:assets infoArr:infoArr]; + } +} + +- (void)callDelegateMethodWithPhotos:(NSArray *)photos assets:(NSArray *)assets infoArr:(NSArray *)infoArr { + TZImagePickerController *tzImagePickerVc = (TZImagePickerController *)self.navigationController; + if (!tzImagePickerVc.allowPickingImage && tzImagePickerVc.allowPickingVideo && tzImagePickerVc.maxImagesCount == 1) { + if ([tzImagePickerVc.pickerDelegate respondsToSelector:@selector(imagePickerController:didFinishPickingVideo:sourceAssets:)]) { + [tzImagePickerVc.pickerDelegate imagePickerController:tzImagePickerVc didFinishPickingVideo:[photos firstObject] sourceAssets:[assets firstObject]]; + } + if (tzImagePickerVc.didFinishPickingVideoHandle) { + tzImagePickerVc.didFinishPickingVideoHandle([photos firstObject], [assets firstObject]); + } + return; + } + + if ([tzImagePickerVc.pickerDelegate respondsToSelector:@selector(imagePickerController:didFinishPickingPhotos:sourceAssets:isSelectOriginalPhoto:)]) { + [tzImagePickerVc.pickerDelegate imagePickerController:tzImagePickerVc didFinishPickingPhotos:photos sourceAssets:assets isSelectOriginalPhoto:_isSelectOriginalPhoto]; + } + if ([tzImagePickerVc.pickerDelegate respondsToSelector:@selector(imagePickerController:didFinishPickingPhotos:sourceAssets:isSelectOriginalPhoto:infos:)]) { + [tzImagePickerVc.pickerDelegate imagePickerController:tzImagePickerVc didFinishPickingPhotos:photos sourceAssets:assets isSelectOriginalPhoto:_isSelectOriginalPhoto infos:infoArr]; + } + if (tzImagePickerVc.didFinishPickingPhotosHandle) { + tzImagePickerVc.didFinishPickingPhotosHandle(photos,assets,_isSelectOriginalPhoto); + } + if (tzImagePickerVc.didFinishPickingPhotosWithInfosHandle) { + tzImagePickerVc.didFinishPickingPhotosWithInfosHandle(photos,assets,_isSelectOriginalPhoto,infoArr); + } +} + +#pragma mark - UICollectionViewDataSource && Delegate + +- (NSInteger)collectionView:(UICollectionView *)collectionView numberOfItemsInSection:(NSInteger)section { + if (_showTakePhotoBtn) { + return _models.count + 1; + } + return _models.count; +} + +- (UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath { + // the cell lead to take a picture / ������������cell + TZImagePickerController *tzImagePickerVc = (TZImagePickerController *)self.navigationController; + if (((tzImagePickerVc.sortAscendingByModificationDate && indexPath.item >= _models.count) || (!tzImagePickerVc.sortAscendingByModificationDate && indexPath.item == 0)) && _showTakePhotoBtn) { + TZAssetCameraCell *cell = [collectionView dequeueReusableCellWithReuseIdentifier:@"TZAssetCameraCell" forIndexPath:indexPath]; + cell.imageView.image = tzImagePickerVc.takePictureImage; + if ([tzImagePickerVc.takePictureImageName isEqualToString:@"takePicture80"]) { + cell.imageView.contentMode = UIViewContentModeCenter; + CGFloat rgb = 223 / 255.0; + cell.imageView.backgroundColor = [UIColor colorWithRed:rgb green:rgb blue:rgb alpha:1.0]; + } else { + cell.imageView.backgroundColor = [UIColor colorWithWhite:1.000 alpha:0.500]; + } + return cell; + } + // the cell dipaly photo or video / ������������������������cell + TZAssetCell *cell = [collectionView dequeueReusableCellWithReuseIdentifier:@"TZAssetCell" forIndexPath:indexPath]; + cell.allowPickingMultipleVideo = tzImagePickerVc.allowPickingMultipleVideo; + cell.photoDefImage = tzImagePickerVc.photoDefImage; + cell.photoSelImage = tzImagePickerVc.photoSelImage; + cell.useCachedImage = self.useCachedImage; + cell.assetCellDidSetModelBlock = tzImagePickerVc.assetCellDidSetModelBlock; + cell.assetCellDidLayoutSubviewsBlock = tzImagePickerVc.assetCellDidLayoutSubviewsBlock; + TZAssetModel *model; + if (tzImagePickerVc.sortAscendingByModificationDate || !_showTakePhotoBtn) { + model = _models[indexPath.item]; + } else { + model = _models[indexPath.item - 1]; + } + cell.allowPickingGif = tzImagePickerVc.allowPickingGif; + cell.model = model; + if (model.isSelected && tzImagePickerVc.showSelectedIndex) { + NSString *assetId = [[TZImageManager manager] getAssetIdentifier:model.asset]; + cell.index = [tzImagePickerVc.selectedAssetIds indexOfObject:assetId] + 1; + } + cell.showSelectBtn = tzImagePickerVc.showSelectBtn; + cell.allowPreview = tzImagePickerVc.allowPreview; + + if (tzImagePickerVc.selectedModels.count >= tzImagePickerVc.maxImagesCount && tzImagePickerVc.showPhotoCannotSelectLayer && !model.isSelected) { + cell.cannotSelectLayerButton.backgroundColor = tzImagePickerVc.cannotSelectLayerColor; + cell.cannotSelectLayerButton.hidden = NO; + } else { + cell.cannotSelectLayerButton.hidden = YES; + } + + __weak typeof(cell) weakCell = cell; + __weak typeof(self) weakSelf = self; + __weak typeof(_numberImageView.layer) weakLayer = _numberImageView.layer; + cell.didSelectPhotoBlock = ^(BOOL isSelected) { + __strong typeof(weakCell) strongCell = weakCell; + __strong typeof(weakSelf) strongSelf = weakSelf; + __strong typeof(weakLayer) strongLayer = weakLayer; + TZImagePickerController *tzImagePickerVc = (TZImagePickerController *)strongSelf.navigationController; + // 1. cancel select / ������������ + if (isSelected) { + strongCell.selectPhotoButton.selected = NO; + model.isSelected = NO; + NSArray *selectedModels = [NSArray arrayWithArray:tzImagePickerVc.selectedModels]; + for (TZAssetModel *model_item in selectedModels) { + if ([[[TZImageManager manager] getAssetIdentifier:model.asset] isEqualToString:[[TZImageManager manager] getAssetIdentifier:model_item.asset]]) { + [tzImagePickerVc removeSelectedModel:model_item]; + break; + } + } + [strongSelf refreshBottomToolBarStatus]; + if (tzImagePickerVc.showSelectedIndex || tzImagePickerVc.showPhotoCannotSelectLayer) { + [strongSelf setUseCachedImageAndReloadData]; + } + [UIView showOscillatoryAnimationWithLayer:strongLayer type:TZOscillatoryAnimationToSmaller]; + } else { + // 2. select:check if over the maxImagesCount / ������������,������������������������������������������ + if (tzImagePickerVc.selectedModels.count < tzImagePickerVc.maxImagesCount) { + strongCell.selectPhotoButton.selected = YES; + model.isSelected = YES; + if (tzImagePickerVc.showSelectedIndex || tzImagePickerVc.showPhotoCannotSelectLayer) { + model.needOscillatoryAnimation = YES; + [strongSelf setUseCachedImageAndReloadData]; + } + [tzImagePickerVc addSelectedModel:model]; + [strongSelf refreshBottomToolBarStatus]; + [UIView showOscillatoryAnimationWithLayer:strongLayer type:TZOscillatoryAnimationToSmaller]; + } else { + NSString *title = [NSString stringWithFormat:[NSBundle tz_localizedStringForKey:@"Select a maximum of %zd photos"], tzImagePickerVc.maxImagesCount]; + [tzImagePickerVc showAlertWithTitle:title]; + } + } + }; + return cell; +} + +- (void)collectionView:(UICollectionView *)collectionView didSelectItemAtIndexPath:(NSIndexPath *)indexPath { + // take a photo / ��������� + TZImagePickerController *tzImagePickerVc = (TZImagePickerController *)self.navigationController; + if (((tzImagePickerVc.sortAscendingByModificationDate && indexPath.item >= _models.count) || (!tzImagePickerVc.sortAscendingByModificationDate && indexPath.item == 0)) && _showTakePhotoBtn) { + [self takePhoto]; return; + } + // preview phote or video / ��������������������� + NSInteger index = indexPath.item; + if (!tzImagePickerVc.sortAscendingByModificationDate && _showTakePhotoBtn) { + index = indexPath.item - 1; + } + TZAssetModel *model = _models[index]; + if (model.type == TZAssetModelMediaTypeVideo && !tzImagePickerVc.allowPickingMultipleVideo) { + if (tzImagePickerVc.selectedModels.count > 0) { + TZImagePickerController *imagePickerVc = (TZImagePickerController *)self.navigationController; + [imagePickerVc showAlertWithTitle:[NSBundle tz_localizedStringForKey:@"Can not choose both video and photo"]]; + } else { + TZVideoPlayerController *videoPlayerVc = [[TZVideoPlayerController alloc] init]; + videoPlayerVc.model = model; + [self.navigationController pushViewController:videoPlayerVc animated:YES]; + } + } else if (model.type == TZAssetModelMediaTypePhotoGif && tzImagePickerVc.allowPickingGif && !tzImagePickerVc.allowPickingMultipleVideo) { + if (tzImagePickerVc.selectedModels.count > 0) { + TZImagePickerController *imagePickerVc = (TZImagePickerController *)self.navigationController; + [imagePickerVc showAlertWithTitle:[NSBundle tz_localizedStringForKey:@"Can not choose both photo and GIF"]]; + } else { + TZGifPhotoPreviewController *gifPreviewVc = [[TZGifPhotoPreviewController alloc] init]; + gifPreviewVc.model = model; + [self.navigationController pushViewController:gifPreviewVc animated:YES]; + } + } else { + TZPhotoPreviewController *photoPreviewVc = [[TZPhotoPreviewController alloc] init]; + photoPreviewVc.currentIndex = index; + photoPreviewVc.models = _models; + [self pushPhotoPrevireViewController:photoPreviewVc]; + } +} + +#pragma mark - UIScrollViewDelegate + +- (void)scrollViewDidScroll:(UIScrollView *)scrollView { + if (iOS8Later) { + // [self updateCachedAssets]; + } +} + +#pragma mark - Private Method + +- (void)setUseCachedImageAndReloadData { + self.useCachedImage = YES; + [self.collectionView reloadData]; + dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(0.1 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{ + self.useCachedImage = NO; + }); +} + +/// ������������������������ +- (void)takePhoto { + AVAuthorizationStatus authStatus = [AVCaptureDevice authorizationStatusForMediaType:AVMediaTypeVideo]; + if ((authStatus == AVAuthorizationStatusRestricted || authStatus ==AVAuthorizationStatusDenied) && iOS7Later) { + + NSDictionary *infoDict = [TZCommonTools tz_getInfoDictionary]; + // ��������� ������������������������ + NSString *appName = [infoDict valueForKey:@"CFBundleDisplayName"]; + if (!appName) appName = [infoDict valueForKey:@"CFBundleName"]; + + NSString *message = [NSString stringWithFormat:[NSBundle tz_localizedStringForKey:@"Please allow %@ to access your camera in \"Settings -> Privacy -> Camera\""],appName]; + if (iOS8Later) { + UIAlertView *alert = [[UIAlertView alloc] initWithTitle:[NSBundle tz_localizedStringForKey:@"Can not use camera"] message:message delegate:self cancelButtonTitle:[NSBundle tz_localizedStringForKey:@"Cancel"] otherButtonTitles:[NSBundle tz_localizedStringForKey:@"Setting"], nil]; + [alert show]; + } else { + UIAlertView *alert = [[UIAlertView alloc] initWithTitle:[NSBundle tz_localizedStringForKey:@"Can not use camera"] message:message delegate:self cancelButtonTitle:[NSBundle tz_localizedStringForKey:@"OK"] otherButtonTitles:nil]; + [alert show]; + } + } else if (authStatus == AVAuthorizationStatusNotDetermined) { + // fix issue 466, ������������������������������������������������������ + if (iOS7Later) { + [AVCaptureDevice requestAccessForMediaType:AVMediaTypeVideo completionHandler:^(BOOL granted) { + if (granted) { + dispatch_async(dispatch_get_main_queue(), ^{ + [self pushImagePickerController]; + }); + } + }]; + } else { + [self pushImagePickerController]; + } + } else { + [self pushImagePickerController]; + } +} + +// ������������ +- (void)pushImagePickerController { + // ������������ + TZImagePickerController *tzImagePickerVc = (TZImagePickerController *)self.navigationController; + if (tzImagePickerVc.allowCameraLocation) { + __weak typeof(self) weakSelf = self; + [[TZLocationManager manager] startLocationWithSuccessBlock:^(NSArray<CLLocation *> *locations) { + __strong typeof(weakSelf) strongSelf = weakSelf; + strongSelf.location = [locations firstObject]; + } failureBlock:^(NSError *error) { + __strong typeof(weakSelf) strongSelf = weakSelf; + strongSelf.location = nil; + }]; + } + + UIImagePickerControllerSourceType sourceType = UIImagePickerControllerSourceTypeCamera; + if ([UIImagePickerController isSourceTypeAvailable: sourceType]) { + self.imagePickerVc.sourceType = sourceType; + NSMutableArray *mediaTypes = [NSMutableArray array]; + if (tzImagePickerVc.allowTakePicture) { + [mediaTypes addObject:(NSString *)kUTTypeImage]; + } + if (tzImagePickerVc.allowTakeVideo) { + [mediaTypes addObject:(NSString *)kUTTypeMovie]; + self.imagePickerVc.videoMaximumDuration = tzImagePickerVc.videoMaximumDuration; + } + self.imagePickerVc.mediaTypes= mediaTypes; + if (iOS8Later) { + _imagePickerVc.modalPresentationStyle = UIModalPresentationOverCurrentContext; + } + if (tzImagePickerVc.uiImagePickerControllerSettingBlock) { + tzImagePickerVc.uiImagePickerControllerSettingBlock(_imagePickerVc); + } + [self presentViewController:_imagePickerVc animated:YES completion:nil]; + } else { + NSLog(@"���������������������������������,���������������������"); + } +} + +- (void)refreshBottomToolBarStatus { + TZImagePickerController *tzImagePickerVc = (TZImagePickerController *)self.navigationController; + + _previewButton.enabled = tzImagePickerVc.selectedModels.count > 0; + _doneButton.enabled = tzImagePickerVc.selectedModels.count > 0 || tzImagePickerVc.alwaysEnableDoneBtn; + + _numberImageView.hidden = tzImagePickerVc.selectedModels.count <= 0; + _numberLabel.hidden = tzImagePickerVc.selectedModels.count <= 0; + _numberLabel.text = [NSString stringWithFormat:@"%zd",tzImagePickerVc.selectedModels.count]; + + _originalPhotoButton.enabled = tzImagePickerVc.selectedModels.count > 0; + _originalPhotoButton.selected = (_isSelectOriginalPhoto && _originalPhotoButton.enabled); + _originalPhotoLabel.hidden = (!_originalPhotoButton.isSelected); + if (_isSelectOriginalPhoto) [self getSelectedPhotoBytes]; +} + +- (void)pushPhotoPrevireViewController:(TZPhotoPreviewController *)photoPreviewVc { + [self pushPhotoPrevireViewController:photoPreviewVc needCheckSelectedModels:NO]; +} + +- (void)pushPhotoPrevireViewController:(TZPhotoPreviewController *)photoPreviewVc needCheckSelectedModels:(BOOL)needCheckSelectedModels { + __weak typeof(self) weakSelf = self; + photoPreviewVc.isSelectOriginalPhoto = _isSelectOriginalPhoto; + [photoPreviewVc setBackButtonClickBlock:^(BOOL isSelectOriginalPhoto) { + __strong typeof(weakSelf) strongSelf = weakSelf; + strongSelf.isSelectOriginalPhoto = isSelectOriginalPhoto; + if (needCheckSelectedModels) { + [strongSelf checkSelectedModels]; + } + [strongSelf.collectionView reloadData]; + [strongSelf refreshBottomToolBarStatus]; + }]; + [photoPreviewVc setDoneButtonClickBlock:^(BOOL isSelectOriginalPhoto) { + __strong typeof(weakSelf) strongSelf = weakSelf; + strongSelf.isSelectOriginalPhoto = isSelectOriginalPhoto; + [strongSelf doneButtonClick]; + }]; + [photoPreviewVc setDoneButtonClickBlockCropMode:^(UIImage *cropedImage, id asset) { + __strong typeof(weakSelf) strongSelf = weakSelf; + [strongSelf didGetAllPhotos:@[cropedImage] assets:@[asset] infoArr:nil]; + }]; + [self.navigationController pushViewController:photoPreviewVc animated:YES]; +} + +- (void)getSelectedPhotoBytes { + // ��������� && 5��������������������������������������������� + if ([[TZImagePickerConfig sharedInstance].preferredLanguage isEqualToString:@"vi"] && self.view.tz_width <= 320) { + return; + } + TZImagePickerController *imagePickerVc = (TZImagePickerController *)self.navigationController; + [[TZImageManager manager] getPhotosBytesWithArray:imagePickerVc.selectedModels completion:^(NSString *totalBytes) { + self->_originalPhotoLabel.text = [NSString stringWithFormat:@"(%@)",totalBytes]; + }]; +} + +- (void)scrollCollectionViewToBottom { + TZImagePickerController *tzImagePickerVc = (TZImagePickerController *)self.navigationController; + if (_shouldScrollToBottom && _models.count > 0) { + NSInteger item = 0; + if (tzImagePickerVc.sortAscendingByModificationDate) { + item = _models.count - 1; + if (_showTakePhotoBtn) { + item += 1; + } + } + dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(0.01 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{ + [self->_collectionView scrollToItemAtIndexPath:[NSIndexPath indexPathForItem:item inSection:0] atScrollPosition:UICollectionViewScrollPositionBottom animated:NO]; + self->_shouldScrollToBottom = NO; + self->_collectionView.hidden = NO; + }); + } else { + _collectionView.hidden = NO; + } +} + +- (void)checkSelectedModels { + NSMutableArray *selectedAssets = [NSMutableArray array]; + TZImagePickerController *tzImagePickerVc = (TZImagePickerController *)self.navigationController; + for (TZAssetModel *model in tzImagePickerVc.selectedModels) { + [selectedAssets addObject:model.asset]; + } + for (TZAssetModel *model in _models) { + model.isSelected = NO; + if ([[TZImageManager manager] isAssetsArray:selectedAssets containAsset:model.asset]) { + model.isSelected = YES; + } + } +} + +#pragma mark - UIAlertViewDelegate + +- (void)alertView:(UIAlertView *)alertView clickedButtonAtIndex:(NSInteger)buttonIndex { + if (buttonIndex == 1) { // ������������������������������������������ + if (iOS8Later) { + [[UIApplication sharedApplication] openURL:[NSURL URLWithString:UIApplicationOpenSettingsURLString]]; + } + } +} + +#pragma mark - UIImagePickerControllerDelegate + +- (void)imagePickerController:(UIImagePickerController*)picker didFinishPickingMediaWithInfo:(NSDictionary *)info { + [picker dismissViewControllerAnimated:YES completion:nil]; + NSString *type = [info objectForKey:UIImagePickerControllerMediaType]; + if ([type isEqualToString:@"public.image"]) { + TZImagePickerController *imagePickerVc = (TZImagePickerController *)self.navigationController; + [imagePickerVc showProgressHUD]; + UIImage *photo = [info objectForKey:UIImagePickerControllerOriginalImage]; + if (photo) { + [[TZImageManager manager] savePhotoWithImage:photo location:self.location completion:^(NSError *error){ + if (!error) { + [self reloadPhotoArrayWithMediaType:type]; + } + }]; + self.location = nil; + } + } else if ([type isEqualToString:@"public.movie"]) { + TZImagePickerController *imagePickerVc = (TZImagePickerController *)self.navigationController; + [imagePickerVc showProgressHUD]; + NSURL *videoUrl = [info objectForKey:UIImagePickerControllerMediaURL]; + if (videoUrl) { + [[TZImageManager manager] saveVideoWithUrl:videoUrl location:self.location completion:^(NSError *error) { + if (!error) { + [self reloadPhotoArrayWithMediaType:type]; + } + }]; + self.location = nil; + } + } +} + +- (void)reloadPhotoArrayWithMediaType:(NSString *)mediaType { + TZImagePickerController *tzImagePickerVc = (TZImagePickerController *)self.navigationController; + [[TZImageManager manager] getCameraRollAlbum:tzImagePickerVc.allowPickingVideo allowPickingImage:tzImagePickerVc.allowPickingImage needFetchAssets:NO completion:^(TZAlbumModel *model) { + self->_model = model; + [[TZImageManager manager] getAssetsFromFetchResult:self->_model.result completion:^(NSArray<TZAssetModel *> *models) { + [tzImagePickerVc hideProgressHUD]; + + TZAssetModel *assetModel; + if (tzImagePickerVc.sortAscendingByModificationDate) { + assetModel = [models lastObject]; + [self->_models addObject:assetModel]; + } else { + assetModel = [models firstObject]; + [self->_models insertObject:assetModel atIndex:0]; + } + + if (tzImagePickerVc.maxImagesCount <= 1) { + if (tzImagePickerVc.allowCrop) { + TZPhotoPreviewController *photoPreviewVc = [[TZPhotoPreviewController alloc] init]; + if (tzImagePickerVc.sortAscendingByModificationDate) { + photoPreviewVc.currentIndex = self->_models.count - 1; + } else { + photoPreviewVc.currentIndex = 0; + } + photoPreviewVc.models = self->_models; + [self pushPhotoPrevireViewController:photoPreviewVc]; + } else { + [tzImagePickerVc addSelectedModel:assetModel]; + [self doneButtonClick]; + } + return; + } + + if (tzImagePickerVc.selectedModels.count < tzImagePickerVc.maxImagesCount) { + if ([mediaType isEqualToString:@"public.movie"] && !tzImagePickerVc.allowPickingMultipleVideo) { + // ��������������������������������������������������������� + } else { + assetModel.isSelected = YES; + [tzImagePickerVc addSelectedModel:assetModel]; + [self refreshBottomToolBarStatus]; + } + } + self->_collectionView.hidden = YES; + [self->_collectionView reloadData]; + + self->_shouldScrollToBottom = YES; + [self scrollCollectionViewToBottom]; + }]; + }]; +} + +- (void)imagePickerControllerDidCancel:(UIImagePickerController *)picker { + [picker dismissViewControllerAnimated:YES completion:nil]; +} + +- (void)dealloc { + // NSLog(@"%@ dealloc",NSStringFromClass(self.class)); +} + +#pragma mark - Asset Caching + +- (void)resetCachedAssets { + [[TZImageManager manager].cachingImageManager stopCachingImagesForAllAssets]; + self.previousPreheatRect = CGRectZero; +} + +- (void)updateCachedAssets { + BOOL isViewVisible = [self isViewLoaded] && [[self view] window] != nil; + if (!isViewVisible) { return; } + + // The preheat window is twice the height of the visible rect. + CGRect preheatRect = _collectionView.bounds; + preheatRect = CGRectInset(preheatRect, 0.0f, -0.5f * CGRectGetHeight(preheatRect)); + + /* + Check if the collection view is showing an area that is significantly + different to the last preheated area. + */ + CGFloat delta = ABS(CGRectGetMidY(preheatRect) - CGRectGetMidY(self.previousPreheatRect)); + if (delta > CGRectGetHeight(_collectionView.bounds) / 3.0f) { + + // Compute the assets to start caching and to stop caching. + NSMutableArray *addedIndexPaths = [NSMutableArray array]; + NSMutableArray *removedIndexPaths = [NSMutableArray array]; + + [self computeDifferenceBetweenRect:self.previousPreheatRect andRect:preheatRect removedHandler:^(CGRect removedRect) { + NSArray *indexPaths = [self aapl_indexPathsForElementsInRect:removedRect]; + [removedIndexPaths addObjectsFromArray:indexPaths]; + } addedHandler:^(CGRect addedRect) { + NSArray *indexPaths = [self aapl_indexPathsForElementsInRect:addedRect]; + [addedIndexPaths addObjectsFromArray:indexPaths]; + }]; + + NSArray *assetsToStartCaching = [self assetsAtIndexPaths:addedIndexPaths]; + NSArray *assetsToStopCaching = [self assetsAtIndexPaths:removedIndexPaths]; + + // Update the assets the PHCachingImageManager is caching. + [[TZImageManager manager].cachingImageManager startCachingImagesForAssets:assetsToStartCaching + targetSize:AssetGridThumbnailSize + contentMode:PHImageContentModeAspectFill + options:nil]; + [[TZImageManager manager].cachingImageManager stopCachingImagesForAssets:assetsToStopCaching + targetSize:AssetGridThumbnailSize + contentMode:PHImageContentModeAspectFill + options:nil]; + + // Store the preheat rect to compare against in the future. + self.previousPreheatRect = preheatRect; + } +} + +- (void)computeDifferenceBetweenRect:(CGRect)oldRect andRect:(CGRect)newRect removedHandler:(void (^)(CGRect removedRect))removedHandler addedHandler:(void (^)(CGRect addedRect))addedHandler { + if (CGRectIntersectsRect(newRect, oldRect)) { + CGFloat oldMaxY = CGRectGetMaxY(oldRect); + CGFloat oldMinY = CGRectGetMinY(oldRect); + CGFloat newMaxY = CGRectGetMaxY(newRect); + CGFloat newMinY = CGRectGetMinY(newRect); + + if (newMaxY > oldMaxY) { + CGRect rectToAdd = CGRectMake(newRect.origin.x, oldMaxY, newRect.size.width, (newMaxY - oldMaxY)); + addedHandler(rectToAdd); + } + + if (oldMinY > newMinY) { + CGRect rectToAdd = CGRectMake(newRect.origin.x, newMinY, newRect.size.width, (oldMinY - newMinY)); + addedHandler(rectToAdd); + } + + if (newMaxY < oldMaxY) { + CGRect rectToRemove = CGRectMake(newRect.origin.x, newMaxY, newRect.size.width, (oldMaxY - newMaxY)); + removedHandler(rectToRemove); + } + + if (oldMinY < newMinY) { + CGRect rectToRemove = CGRectMake(newRect.origin.x, oldMinY, newRect.size.width, (newMinY - oldMinY)); + removedHandler(rectToRemove); + } + } else { + addedHandler(newRect); + removedHandler(oldRect); + } +} + +- (NSArray *)assetsAtIndexPaths:(NSArray *)indexPaths { + if (indexPaths.count == 0) { return nil; } + + NSMutableArray *assets = [NSMutableArray arrayWithCapacity:indexPaths.count]; + for (NSIndexPath *indexPath in indexPaths) { + if (indexPath.item < _models.count) { + TZAssetModel *model = _models[indexPath.item]; + [assets addObject:model.asset]; + } + } + + return assets; +} + +- (NSArray *)aapl_indexPathsForElementsInRect:(CGRect)rect { + NSArray *allLayoutAttributes = [_collectionView.collectionViewLayout layoutAttributesForElementsInRect:rect]; + if (allLayoutAttributes.count == 0) { return nil; } + NSMutableArray *indexPaths = [NSMutableArray arrayWithCapacity:allLayoutAttributes.count]; + for (UICollectionViewLayoutAttributes *layoutAttributes in allLayoutAttributes) { + NSIndexPath *indexPath = layoutAttributes.indexPath; + [indexPaths addObject:indexPath]; + } + return indexPaths; +} +#pragma clang diagnostic pop + +@end + + + +@implementation TZCollectionView + +- (BOOL)touchesShouldCancelInContentView:(UIView *)view { + if ([view isKindOfClass:[UIControl class]]) { + return YES; + } + return [super touchesShouldCancelInContentView:view]; +} + +@end -- Gitblit v1.8.0