提交
This commit is contained in:
227
TUIKit/TUIChat/BaseCellData/Chat/TUIImageMessageCellData.m
Normal file
227
TUIKit/TUIChat/BaseCellData/Chat/TUIImageMessageCellData.m
Normal file
@@ -0,0 +1,227 @@
|
||||
//
|
||||
// TUIImageMessageCellData.m
|
||||
// TXIMSDK_TUIKit_iOS
|
||||
//
|
||||
// Created by annidyfeng on 2019/5/21.
|
||||
// Copyright © 2023 Tencent. All rights reserved.
|
||||
//
|
||||
|
||||
#import "TUIImageMessageCellData.h"
|
||||
#import <TIMCommon/TIMDefine.h>
|
||||
#import <TUICore/NSString+TUIUtil.h>
|
||||
|
||||
@interface TUIImageMessageCellData ()
|
||||
@property(nonatomic, assign) BOOL isDownloading;
|
||||
@property(nonatomic, copy) TUIImageMessageDownloadCallback onFinish;
|
||||
@end
|
||||
|
||||
@implementation TUIImageMessageCellData
|
||||
|
||||
+ (TUIMessageCellData *)getCellData:(V2TIMMessage *)message {
|
||||
V2TIMImageElem *elem = message.imageElem;
|
||||
TUIImageMessageCellData *imageData = [[TUIImageMessageCellData alloc] initWithDirection:(message.isSelf ? MsgDirectionOutgoing : MsgDirectionIncoming)];
|
||||
imageData.path = [elem.path safePathString];
|
||||
imageData.items = [NSMutableArray array];
|
||||
for (V2TIMImage *item in elem.imageList) {
|
||||
TUIImageItem *itemData = [[TUIImageItem alloc] init];
|
||||
itemData.uuid = item.uuid;
|
||||
itemData.size = CGSizeMake(item.width, item.height);
|
||||
// itemData.url = item.url;
|
||||
if (item.type == V2TIM_IMAGE_TYPE_THUMB) {
|
||||
itemData.type = TImage_Type_Thumb;
|
||||
} else if (item.type == V2TIM_IMAGE_TYPE_LARGE) {
|
||||
itemData.type = TImage_Type_Large;
|
||||
} else if (item.type == V2TIM_IMAGE_TYPE_ORIGIN) {
|
||||
itemData.type = TImage_Type_Origin;
|
||||
}
|
||||
[imageData.items addObject:itemData];
|
||||
}
|
||||
imageData.reuseId = TImageMessageCell_ReuseId;
|
||||
return imageData;
|
||||
}
|
||||
|
||||
+ (NSString *)getDisplayString:(V2TIMMessage *)message {
|
||||
return TIMCommonLocalizableString(TUIkitMessageTypeImage); // @"[Image]";
|
||||
}
|
||||
|
||||
- (Class)getReplyQuoteViewDataClass {
|
||||
return NSClassFromString(@"TUIImageReplyQuoteViewData");
|
||||
}
|
||||
|
||||
- (Class)getReplyQuoteViewClass {
|
||||
return NSClassFromString(@"TUIImageReplyQuoteView");
|
||||
}
|
||||
|
||||
- (instancetype)initWithDirection:(TMsgDirection)direction {
|
||||
self = [super initWithDirection:direction];
|
||||
if (self) {
|
||||
_uploadProgress = 100;
|
||||
if (direction == MsgDirectionIncoming) {
|
||||
self.cellLayout = [TUIMessageCellLayout incommingImageMessageLayout];
|
||||
} else {
|
||||
self.cellLayout = [TUIMessageCellLayout outgoingImageMessageLayout];
|
||||
}
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
- (NSString *)getImagePath:(TUIImageType)type isExist:(BOOL *)isExist {
|
||||
NSString *path = nil;
|
||||
BOOL isDir = NO;
|
||||
*isExist = NO;
|
||||
if (self.direction == MsgDirectionOutgoing) {
|
||||
path = [NSString stringWithFormat:@"%@%@", TUIKit_Image_Path, _path.lastPathComponent];
|
||||
if ([[NSFileManager defaultManager] fileExistsAtPath:path isDirectory:&isDir]) {
|
||||
if (!isDir) {
|
||||
*isExist = YES;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!*isExist) {
|
||||
TUIImageItem *tImageItem = [self getTImageItem:type];
|
||||
path = [NSString stringWithFormat:@"%@%@_%ld", TUIKit_Image_Path, tImageItem.uuid, (long)tImageItem.type];
|
||||
if ([[NSFileManager defaultManager] fileExistsAtPath:path isDirectory:&isDir]) {
|
||||
if (!isDir) {
|
||||
*isExist = YES;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return path;
|
||||
}
|
||||
|
||||
- (void)downloadImage:(TUIImageType)type finish:(TUIImageMessageDownloadCallback)finish {
|
||||
self.onFinish = finish;
|
||||
[self downloadImage:type];
|
||||
}
|
||||
|
||||
- (void)downloadImage:(TUIImageType)type {
|
||||
BOOL isExist = NO;
|
||||
NSString *path = [self getImagePath:type isExist:&isExist];
|
||||
if (isExist) {
|
||||
[self decodeImage:type];
|
||||
return;
|
||||
}
|
||||
|
||||
if (self.isDownloading) {
|
||||
return;
|
||||
}
|
||||
self.isDownloading = YES;
|
||||
|
||||
V2TIMImage *imImage = [self getIMImage:type];
|
||||
|
||||
@weakify(self);
|
||||
[imImage downloadImage:path
|
||||
progress:^(NSInteger curSize, NSInteger totalSize) {
|
||||
@strongify(self);
|
||||
NSInteger progress = curSize * 100 / totalSize;
|
||||
[self updateProgress:MIN(progress, 99) withType:type];
|
||||
}
|
||||
succ:^{
|
||||
@strongify(self);
|
||||
self.isDownloading = NO;
|
||||
[self updateProgress:100 withType:type];
|
||||
[self decodeImage:type];
|
||||
}
|
||||
fail:^(int code, NSString *msg) {
|
||||
@strongify(self);
|
||||
self.isDownloading = NO;
|
||||
/**
|
||||
* If the uuid of the picture is the same (the same user sends
|
||||
* the same picture continuously), the same path may trigger multiple download operations. Except for the first time, subsequent downloads will report
|
||||
* an error. At this time, it is necessary to judge whether the local file exists.
|
||||
*/
|
||||
[self decodeImage:type];
|
||||
}];
|
||||
}
|
||||
|
||||
- (void)updateProgress:(NSUInteger)progress withType:(TUIImageType)type {
|
||||
dispatch_async(dispatch_get_main_queue(), ^{
|
||||
if (type == TImage_Type_Thumb) self.thumbProgress = progress;
|
||||
if (type == TImage_Type_Large) self.largeProgress = progress;
|
||||
if (type == TImage_Type_Origin) self.originProgress = progress;
|
||||
});
|
||||
}
|
||||
|
||||
- (void)decodeImage:(TUIImageType)type {
|
||||
BOOL isExist = NO;
|
||||
NSString *path = [self getImagePath:type isExist:&isExist];
|
||||
if (!isExist) {
|
||||
return;
|
||||
}
|
||||
|
||||
__weak typeof(self) weakSelf = self;
|
||||
void (^finishBlock)(UIImage *) = ^(UIImage *image) {
|
||||
if (type == TImage_Type_Thumb) {
|
||||
weakSelf.thumbImage = image;
|
||||
weakSelf.thumbProgress = 100;
|
||||
weakSelf.uploadProgress = 100;
|
||||
}
|
||||
if (type == TImage_Type_Large) {
|
||||
weakSelf.largeImage = image;
|
||||
weakSelf.largeProgress = 100;
|
||||
}
|
||||
if (type == TImage_Type_Origin) {
|
||||
weakSelf.originImage = image;
|
||||
weakSelf.originProgress = 100;
|
||||
}
|
||||
if (weakSelf.onFinish) {
|
||||
weakSelf.onFinish();
|
||||
}
|
||||
};
|
||||
|
||||
NSString *cacheKey = [path substringFromIndex:TUIKit_Image_Path.length];
|
||||
|
||||
UIImage *cacheImage = [[SDImageCache sharedImageCache] imageFromCacheForKey:cacheKey];
|
||||
if (cacheImage) {
|
||||
finishBlock(cacheImage);
|
||||
} else {
|
||||
[TUITool asyncDecodeImage:path
|
||||
complete:^(NSString *path, UIImage *image) {
|
||||
dispatch_async(dispatch_get_main_queue(), ^{
|
||||
NSLog(@"image.sd_imageFormat: %ld path:%@ image.sd_imageData.length :%lu",(long)image.sd_imageFormat,path,(unsigned long)image.sd_imageData.length);
|
||||
if (![path tui_containsString:@".gif"] || (image.sd_imageFormat != SDImageFormatGIF) ) {
|
||||
[[SDImageCache sharedImageCache] storeImageToMemory:image forKey:cacheKey];
|
||||
}
|
||||
else {
|
||||
/**
|
||||
* The gif image is too large to be cached in memory
|
||||
* Only cache images less than 1M
|
||||
*/
|
||||
if (image.sd_imageData.length < 1 * 1024 * 1024) {
|
||||
[[SDImageCache sharedImageCache] storeImageToMemory:image forKey:cacheKey];
|
||||
}
|
||||
}
|
||||
finishBlock(image);
|
||||
});
|
||||
}];
|
||||
}
|
||||
}
|
||||
|
||||
- (TUIImageItem *)getTImageItem:(TUIImageType)type {
|
||||
for (TUIImageItem *item in self.items) {
|
||||
if (item.type == type) {
|
||||
return item;
|
||||
}
|
||||
}
|
||||
return nil;
|
||||
}
|
||||
|
||||
- (V2TIMImage *)getIMImage:(TUIImageType)type {
|
||||
V2TIMMessage *imMsg = self.innerMessage;
|
||||
if (imMsg.elemType == V2TIM_ELEM_TYPE_IMAGE) {
|
||||
for (V2TIMImage *imImage in imMsg.imageElem.imageList) {
|
||||
if (type == TImage_Type_Thumb && imImage.type == V2TIM_IMAGE_TYPE_THUMB) {
|
||||
return imImage;
|
||||
} else if (type == TImage_Type_Origin && imImage.type == V2TIM_IMAGE_TYPE_ORIGIN) {
|
||||
return imImage;
|
||||
} else if (type == TImage_Type_Large && imImage.type == V2TIM_IMAGE_TYPE_LARGE) {
|
||||
return imImage;
|
||||
}
|
||||
}
|
||||
}
|
||||
return nil;
|
||||
}
|
||||
|
||||
@end
|
||||
Reference in New Issue
Block a user