This commit is contained in:
2025-12-04 13:37:11 +08:00
parent f770f8055e
commit b216ddaa61
11 changed files with 377 additions and 10 deletions

View File

@@ -10,6 +10,7 @@
#import "UICollectionViewLeftAlignedLayout.h"
#import "KBMyKeyboardCell.h"
#import "KBAlert.h"
#import "KBMyVM.h"
///
static NSString * const kKBMyKeyboardCellId = @"kKBMyKeyboardCellId";
@@ -29,6 +30,7 @@ static NSString * const kKBMyKeyboardCellId = @"kKBMyKeyboardCellId";
//
@property (nonatomic, strong) NSMutableArray<NSMutableArray<NSDictionary *> *> *dataSourceArray; // {emoji,title}
@property (nonatomic, strong) KBMyVM *viewModel; // VM
@end
@@ -40,6 +42,7 @@ static NSString * const kKBMyKeyboardCellId = @"kKBMyKeyboardCellId";
- (void)viewDidLoad {
[super viewDidLoad];
self.viewModel = [[KBMyVM alloc] init];
self.view.backgroundColor = [UIColor colorWithHex:0xF6F8F9];
self.kb_navView.backgroundColor = [UIColor clearColor];
self.kb_titleLabel.text = @"My KeyBoard";
@@ -71,7 +74,11 @@ static NSString * const kKBMyKeyboardCellId = @"kKBMyKeyboardCellId";
}];
//
[self buildDefaultData];
// [self buildDefaultData];
__weak typeof(self) weakSelf = self;
[self.viewModel fetchCharacterListByUserWithCompletion:^(NSArray<KBCharacter *> * _Nonnull characterArray, NSError * _Nullable error) {
}];
}
- (void)viewWillAppear:(BOOL)animated {

View File

@@ -326,17 +326,26 @@
- (void)picker:(PHPickerViewController *)picker didFinishPicking:(NSArray<PHPickerResult *> *)results API_AVAILABLE(ios(14.0)) {
[picker dismissViewControllerAnimated:YES completion:nil];
PHPickerResult *first = results.firstObject; if (!first) return;
PHPickerResult *first = results.firstObject;
if (!first) return;
NSItemProvider *p = first.itemProvider;
if ([p canLoadObjectOfClass:UIImage.class]) {
__weak typeof(self) weakSelf = self;
[p loadObjectOfClass:UIImage.class completionHandler:^(__kindof id<NSItemProviderReading> _Nullable object, NSError * _Nullable error) {
UIImage *img = ([object isKindOfClass:UIImage.class] ? (UIImage *)object : nil);
if (!img) return;
// 线 UI
// 100KB
NSUInteger targetKB = 50;
NSData *compressedData = [weakSelf kb_compressImage:img targetKB:targetKB];
if (!compressedData) return;
UIImage *compressedImage = [UIImage imageWithData:compressedData];
dispatch_async(dispatch_get_main_queue(), ^{
UIImage *compressed = [weakSelf kb_compressImage:img maxPixel:512 quality:0.85];
weakSelf.avatarView.image = compressed;
weakSelf.avatarJPEGData = UIImageJPEGRepresentation(compressed, 0.85);
});
}];
}
@@ -378,6 +387,95 @@
UIImage *result = [UIImage imageWithData:jpeg] ?: scaled ?: image;
return result;
}
/// KB
/// 1. JPEG
/// 2.
- (nullable NSData *)kb_compressImage:(UIImage *)image targetKB:(NSUInteger)targetKB {
if (!image || targetKB == 0) { return nil; }
NSUInteger maxBytes = targetKB * 1024;
//
CGFloat compression = 0.9f;
CGFloat minCompression = 0.1f; //
NSData *data = UIImageJPEGRepresentation(image, compression);
if (!data) return nil;
//
if (data.length <= maxBytes) {
return data;
}
// 1)
while (data.length > maxBytes && compression > minCompression + 0.01f) {
compression -= 0.1f;
data = UIImageJPEGRepresentation(image, compression);
if (!data) return nil;
}
if (data.length <= maxBytes) {
return data;
}
// 2) ->
UIImage *currentImage = image;
//
NSInteger maxResizeCount = 6;
NSInteger resizeCount = 0;
while (data.length > maxBytes && resizeCount < maxResizeCount) {
resizeCount++;
// (maxBytes / ) *
CGFloat ratio = (CGFloat)maxBytes / (CGFloat)data.length;
// 0.8
ratio *= 0.8f;
if (ratio <= 0.0f) {
ratio = 0.5f; //
}
CGFloat scale = sqrt(ratio);
if (scale >= 1.0f) {
scale = 0.5f; //
}
CGSize newSize = CGSizeMake(currentImage.size.width * scale,
currentImage.size.height * scale);
if (newSize.width < 10 || newSize.height < 10) {
// break
break;
}
//
UIGraphicsBeginImageContextWithOptions(newSize, NO, currentImage.scale);
[currentImage drawInRect:CGRectMake(0, 0, newSize.width, newSize.height)];
UIImage *resizedImage = UIGraphicsGetImageFromCurrentImageContext();
UIGraphicsEndImageContext();
if (!resizedImage) {
break;
}
currentImage = resizedImage;
//
compression = 0.9f;
data = UIImageJPEGRepresentation(currentImage, compression);
if (!data) return nil;
//
while (data.length > maxBytes && compression > minCompression + 0.01f) {
compression -= 0.1f;
data = UIImageJPEGRepresentation(currentImage, compression);
if (!data) return nil;
}
}
//
return data;
}
- (KBMyVM *)myVM{
if (!_myVM) {