Unverified Commit 591c5957 authored by 谭真's avatar 谭真 Committed by GitHub

Merge pull request #1338 from shuLeesin/master

图片视频iCloud同步失败的UI提示和交互
parents 63a47e39 68f2dc43
......@@ -168,6 +168,13 @@
}
_bigImageRequestID = [[TZImageManager manager] requestImageDataForAsset:_model.asset completion:^(NSData *imageData, NSString *dataUTI, UIImageOrientation orientation, NSDictionary *info) {
if (!imageData && [info[PHImageResultIsInCloudKey] boolValue]) {
self.model.iCloudFailed = YES;
if (self.didSelectPhotoBlock) {
self.didSelectPhotoBlock(YES);
self.selectImageView.image = self.photoDefImage;
}
}
[self hideProgressView];
} progressHandler:^(double progress, NSError *error, BOOL *stop, NSDictionary *info) {
if (self.model.isSelected) {
......@@ -185,6 +192,19 @@
[self cancelBigImageRequest];
}
}];
if (_model.type == TZAssetCellTypeVideo) {
[[TZImageManager manager] getVideoWithAsset:_model.asset completion:^(AVPlayerItem *playerItem, NSDictionary *info) {
if (!playerItem && [info[PHImageResultIsInCloudKey] boolValue]) {
dispatch_async(dispatch_get_main_queue(), ^{
self->_model.iCloudFailed = YES;
if (self->_didSelectPhotoBlock) {
self->_didSelectPhotoBlock(YES);
self->_selectImageView.image = self.photoDefImage;
}
});
}
}];
}
}
- (void)cancelBigImageRequest {
......
......@@ -24,6 +24,7 @@ typedef enum : NSUInteger {
@property (nonatomic, assign) BOOL isSelected; ///< The select status of a photo, default is No
@property (nonatomic, assign) TZAssetModelMediaType type;
@property (nonatomic, copy) NSString *timeLength;
@property (nonatomic, assign) BOOL iCloudFailed;
/// Init a photo dataModel With a PHAsset
/// 用一个PHAsset实例,初始化一个照片模型
......
......@@ -566,6 +566,11 @@ static CGFloat itemMargin = 5;
[[NSNotificationCenter defaultCenter] postNotificationName:@"TZ_PHOTO_PICKER_RELOAD_NOTIFICATION" object:strongSelf.navigationController];
}
[UIView showOscillatoryAnimationWithLayer:strongLayer type:TZOscillatoryAnimationToSmaller];
if (strongCell.model.iCloudFailed) {
[strongSelf->_models replaceObjectAtIndex:indexPath.item withObject:strongCell.model];
NSString *title = [NSBundle tz_localizedStringForKey:@"iCloud sync failed"];
[tzImagePickerVc showAlertWithTitle:title];
}
} else {
// 2. select:check if over the maxImagesCount / 选择照片,检查是否超过了最大个数的限制
if (tzImagePickerVc.selectedModels.count < tzImagePickerVc.maxImagesCount) {
......
......@@ -38,7 +38,10 @@
@property (nonatomic, strong) UIScrollView *scrollView;
@property (nonatomic, strong) UIView *imageContainerView;
@property (nonatomic, strong) TZProgressView *progressView;
@property (nonatomic, strong) UIView *iCloudErrorView; // iCloud加载失败提示View
@property (nonatomic, strong) UIImageView *iCloudErrorIcon;
@property (nonatomic, strong) UILabel *iCloudErrorLabel;
@property (nonatomic, copy) void (^iCloudSyncFailedHandle)(id asset, BOOL isSyncFailed);
@property (nonatomic, assign) BOOL allowCrop;
@property (nonatomic, assign) CGRect cropRect;
......@@ -61,6 +64,9 @@
@property (strong, nonatomic) UIButton *playButton;
@property (strong, nonatomic) UIImage *cover;
@property (nonatomic, strong) NSURL *videoURL;
@property (nonatomic, strong) UIImageView *iCloudErrorIcon;
@property (nonatomic, strong) UILabel *iCloudErrorLabel;
@property (nonatomic, copy) void (^iCloudSyncFailedHandle)(id asset, BOOL isSyncFailed);
- (void)pausePlayerAndShowNaviBar;
@end
......
......@@ -66,7 +66,7 @@
- (void)setModel:(TZAssetModel *)model {
[super setModel:model];
_previewView.asset = model.asset;
_previewView.model = model;
}
- (void)recoverSubviews {
......@@ -134,19 +134,16 @@
_imageView.clipsToBounds = YES;
[_imageContainerView addSubview:_imageView];
_iCloudErrorView = [[UIView alloc] initWithFrame:CGRectMake(0, [TZCommonTools tz_isIPhoneX] ? 88 : 64, self.tz_width, 28)];
UIImageView *icloud = [[UIImageView alloc] init];
icloud.image = [UIImage tz_imageNamedFromMyBundle:@"iCloudError"];
icloud.frame = CGRectMake(10, 0, 28, 28);
[_iCloudErrorView addSubview:icloud];
UILabel *label = [[UILabel alloc] init];
label.frame = CGRectMake(40, 0, self.tz_width - 50, 28);
label.font = [UIFont systemFontOfSize:10];
label.textColor = [UIColor whiteColor];
label.text = [NSBundle tz_localizedStringForKey:@"iCloud sync failed"];
[_iCloudErrorView addSubview:label];
[self addSubview:_iCloudErrorView];
_iCloudErrorView.hidden = YES;
_iCloudErrorIcon = [[UIImageView alloc] init];
_iCloudErrorIcon.image = [UIImage tz_imageNamedFromMyBundle:@"iCloudError"];
_iCloudErrorIcon.hidden = YES;
[self addSubview:_iCloudErrorIcon];
_iCloudErrorLabel = [[UILabel alloc] init];
_iCloudErrorLabel.font = [UIFont systemFontOfSize:10];
_iCloudErrorLabel.textColor = [UIColor whiteColor];
_iCloudErrorLabel.text = [NSBundle tz_localizedStringForKey:@"iCloud sync failed"];
_iCloudErrorLabel.hidden = YES;
[self addSubview:_iCloudErrorLabel];
UITapGestureRecognizer *tap1 = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(singleTap:)];
[self addGestureRecognizer:tap1];
......@@ -173,12 +170,15 @@
if (model.type == TZAssetModelMediaTypePhotoGif) {
// 先显示缩略图
[[TZImageManager manager] getPhotoWithAsset:model.asset completion:^(UIImage *photo, NSDictionary *info, BOOL isDegraded) {
if (!photo && [info[PHImageResultIsInCloudKey] boolValue]) {
self.iCloudErrorView.hidden = NO;
} else {
self.iCloudErrorView.hidden = YES;
BOOL iCloudSyncFailed = !photo && [info[PHImageResultIsInCloudKey] boolValue];
self.iCloudErrorLabel.hidden = !iCloudSyncFailed;
self.iCloudErrorIcon.hidden = !iCloudSyncFailed;
if (self.iCloudSyncFailedHandle) {
self.iCloudSyncFailedHandle(model.asset, iCloudSyncFailed);
}
if (photo) {
self.imageView.image = photo;
}
[self resizeSubviews];
if (self.isRequestingGIF) {
return;
......@@ -223,13 +223,16 @@
_asset = asset;
self.imageRequestID = [[TZImageManager manager] getPhotoWithAsset:asset completion:^(UIImage *photo, NSDictionary *info, BOOL isDegraded) {
if (![asset isEqual:self->_asset]) return;
if (!photo && [info[PHImageResultIsInCloudKey] boolValue]) {
self.iCloudErrorView.hidden = NO;
} else {
self.iCloudErrorView.hidden = YES;
BOOL iCloudSyncFailed = !photo && [info[PHImageResultIsInCloudKey] boolValue];
self.iCloudErrorLabel.hidden = !iCloudSyncFailed;
self.iCloudErrorIcon.hidden = !iCloudSyncFailed;
if (self.iCloudSyncFailedHandle) {
self.iCloudSyncFailedHandle(asset, iCloudSyncFailed);
}
if (![asset isEqual:self->_asset]) return;
if (photo) {
self.imageView.image = photo;
}
[self resizeSubviews];
if (self.imageView.tz_height && self.allowCrop) {
CGFloat scale = MAX(self.cropRect.size.width / self.imageView.tz_width, self.cropRect.size.height / self.imageView.tz_height);
......@@ -337,8 +340,9 @@
CGFloat progressX = (self.tz_width - progressWH) / 2;
CGFloat progressY = (self.tz_height - progressWH) / 2;
_progressView.frame = CGRectMake(progressX, progressY, progressWH, progressWH);
[self recoverSubviews];
_iCloudErrorIcon.frame = CGRectMake(20, [TZCommonTools tz_isIPhoneX] ? 88 + 10 : 64 + 10, 28, 28);
_iCloudErrorLabel.frame = CGRectMake(53, [TZCommonTools tz_isIPhoneX] ? 88 + 10 : 64 + 10, self.tz_width - 63, 28);
}
#pragma mark - UITapGestureRecognizer Event
......@@ -395,6 +399,14 @@
- (void)configSubviews {
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(appWillResignActiveNotification) name:UIApplicationWillResignActiveNotification object:nil];
_iCloudErrorIcon = [[UIImageView alloc] init];
_iCloudErrorIcon.image = [UIImage tz_imageNamedFromMyBundle:@"iCloudError"];
_iCloudErrorIcon.hidden = YES;
_iCloudErrorLabel = [[UILabel alloc] init];
_iCloudErrorLabel.font = [UIFont systemFontOfSize:10];
_iCloudErrorLabel.textColor = [UIColor whiteColor];
_iCloudErrorLabel.text = [NSBundle tz_localizedStringForKey:@"iCloud sync failed"];
_iCloudErrorLabel.hidden = YES;
}
- (void)configPlayButton {
......@@ -406,6 +418,8 @@
[_playButton setImage:[UIImage tz_imageNamedFromMyBundle:@"MMVideoPreviewPlayHL"] forState:UIControlStateHighlighted];
[_playButton addTarget:self action:@selector(playButtonClick) forControlEvents:UIControlEventTouchUpInside];
[self addSubview:_playButton];
[self addSubview:_iCloudErrorIcon];
[self addSubview:_iCloudErrorLabel];
}
- (void)setModel:(TZAssetModel *)model {
......@@ -428,10 +442,24 @@
if (self.model && self.model.asset) {
[[TZImageManager manager] getPhotoWithAsset:self.model.asset completion:^(UIImage *photo, NSDictionary *info, BOOL isDegraded) {
BOOL iCloudSyncFailed = !photo && [info[PHImageResultIsInCloudKey] boolValue];
self.iCloudErrorLabel.hidden = !iCloudSyncFailed;
self.iCloudErrorIcon.hidden = !iCloudSyncFailed;
if (self.iCloudSyncFailedHandle) {
self.iCloudSyncFailedHandle(self.model.asset, iCloudSyncFailed);
}
if (photo) {
self.cover = photo;
}
}];
[[TZImageManager manager] getVideoWithAsset:self.model.asset completion:^(AVPlayerItem *playerItem, NSDictionary *info) {
dispatch_async(dispatch_get_main_queue(), ^{
BOOL iCloudSyncFailed = !playerItem && [info[PHImageResultIsInCloudKey] boolValue];
self.iCloudErrorLabel.hidden = !iCloudSyncFailed;
self.iCloudErrorIcon.hidden = !iCloudSyncFailed;
if (self.iCloudSyncFailedHandle) {
self.iCloudSyncFailedHandle(self.model.asset, iCloudSyncFailed);
}
[self configPlayerWithItem:playerItem];
});
}];
......@@ -455,6 +483,8 @@
[super layoutSubviews];
_playerLayer.frame = self.bounds;
_playButton.frame = CGRectMake(0, 64, self.tz_width, self.tz_height - 64 - 44);
_iCloudErrorIcon.frame = CGRectMake(20, [TZCommonTools tz_isIPhoneX] ? 88 + 10 : 64 + 10, 28, 28);
_iCloudErrorLabel.frame = CGRectMake(53, [TZCommonTools tz_isIPhoneX] ? 88 + 10 : 64 + 10, self.tz_width - 63, 28);
}
- (void)photoPreviewCollectionViewDidScroll {
......
......@@ -42,6 +42,7 @@
@property (nonatomic, assign) double progress;
@property (strong, nonatomic) UIAlertController *alertView;
@property (nonatomic, strong) UIView *iCloudErrorView;
@end
@implementation TZPhotoPreviewController
......@@ -441,7 +442,6 @@
_currentIndex = currentIndex;
[self refreshNaviBarAndBottomBarState];
}
[[NSNotificationCenter defaultCenter] postNotificationName:@"photoPreviewCollectionViewDidScroll" object:nil];
}
......@@ -459,8 +459,20 @@
__weak typeof(self) weakSelf = self;
if (_tzImagePickerVc.allowPickingMultipleVideo && model.type == TZAssetModelMediaTypeVideo) {
cell = [collectionView dequeueReusableCellWithReuseIdentifier:@"TZVideoPreviewCell" forIndexPath:indexPath];
TZVideoPreviewCell *currentCell = (TZVideoPreviewCell *)cell;
currentCell.iCloudSyncFailedHandle = ^(id asset, BOOL isSyncFailed) {
model.iCloudFailed = isSyncFailed;
[weakSelf didICloudSyncStatusChanged:model];
[weakSelf.models replaceObjectAtIndex:indexPath.item withObject:model];
};
} else if (_tzImagePickerVc.allowPickingMultipleVideo && model.type == TZAssetModelMediaTypePhotoGif && _tzImagePickerVc.allowPickingGif) {
cell = [collectionView dequeueReusableCellWithReuseIdentifier:@"TZGifPreviewCell" forIndexPath:indexPath];
TZGifPreviewCell *currentCell = (TZGifPreviewCell *)cell;
currentCell.previewView.iCloudSyncFailedHandle = ^(id asset, BOOL isSyncFailed) {
model.iCloudFailed = isSyncFailed;
[weakSelf didICloudSyncStatusChanged:model];
[weakSelf.models replaceObjectAtIndex:indexPath.item withObject:model];
};
} else {
cell = [collectionView dequeueReusableCellWithReuseIdentifier:@"TZPhotoPreviewCell" forIndexPath:indexPath];
TZPhotoPreviewCell *photoPreviewCell = (TZPhotoPreviewCell *)cell;
......@@ -485,6 +497,11 @@
}
}
}];
photoPreviewCell.previewView.iCloudSyncFailedHandle = ^(id asset, BOOL isSyncFailed) {
model.iCloudFailed = isSyncFailed;
[weakSelf didICloudSyncStatusChanged:model];
[weakSelf.models replaceObjectAtIndex:indexPath.item withObject:model];
};
}
cell.model = model;
......@@ -492,6 +509,7 @@
__strong typeof(weakSelf) strongSelf = weakSelf;
[strongSelf didTapPreviewCell];
}];
return cell;
}
......@@ -562,7 +580,8 @@
_originalPhotoLabel.hidden = YES;
_doneButton.hidden = YES;
}
// iCloud同步失败的UI刷新
[self didICloudSyncStatusChanged:model];
if (_tzImagePickerVc.photoPreviewPageDidRefreshStateBlock) {
_tzImagePickerVc.photoPreviewPageDidRefreshStateBlock(_collectionView, _naviBar, _backButton, _selectButton, _indexLabel, _toolBar, _originalPhotoButton, _originalPhotoLabel, _doneButton, _numberImageView, _numberLabel);
}
......@@ -578,6 +597,25 @@
});
}
- (void)didICloudSyncStatusChanged:(TZAssetModel *)model{
dispatch_async(dispatch_get_main_queue(), ^{
TZImagePickerController *_tzImagePickerVc = (TZImagePickerController *)self.navigationController;
// onlyReturnAsset为NO时,依赖TZ返回大图,所以需要有iCloud同步失败的提示,并且不能选择,
if (_tzImagePickerVc.onlyReturnAsset) {
return;
}
TZAssetModel *currentModel = self.models[self.currentIndex];
if (_tzImagePickerVc.selectedModels.count <= 0) {
self->_doneButton.enabled = !currentModel.iCloudFailed;
} else {
self->_doneButton.enabled = YES;
}
self->_selectButton.hidden = currentModel.iCloudFailed;
self->_originalPhotoButton.hidden = currentModel.iCloudFailed;
self->_originalPhotoLabel.hidden = currentModel.iCloudFailed;
});
}
- (void)showPhotoBytes {
[[TZImageManager manager] getPhotosBytesWithArray:@[_models[self.currentIndex]] completion:^(NSString *totalBytes) {
self->_originalPhotoLabel.text = [NSString stringWithFormat:@"(%@)",totalBytes];
......
......@@ -224,13 +224,13 @@
#pragma mark - lazy
- (UIView *)iCloudErrorView{
if (!_iCloudErrorView) {
_iCloudErrorView = [[UIView alloc] initWithFrame:CGRectMake(0, [TZCommonTools tz_isIPhoneX] ? 88 : 64, self.view.tz_width, 28)];
_iCloudErrorView = [[UIView alloc] initWithFrame:CGRectMake(0, [TZCommonTools tz_isIPhoneX] ? 88 + 10 : 64 + 10, self.view.tz_width, 28)];
UIImageView *icloud = [[UIImageView alloc] init];
icloud.image = [UIImage tz_imageNamedFromMyBundle:@"iCloudError"];
icloud.frame = CGRectMake(10, 0, 28, 28);
icloud.frame = CGRectMake(20, 0, 28, 28);
[_iCloudErrorView addSubview:icloud];
UILabel *label = [[UILabel alloc] init];
label.frame = CGRectMake(40, 0, self.view.tz_width - 50, 28);
label.frame = CGRectMake(53, 0, self.view.tz_width - 63, 28);
label.font = [UIFont systemFontOfSize:10];
label.textColor = [UIColor whiteColor];
label.text = [NSBundle tz_localizedStringForKey:@"iCloud sync failed"];
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment