iOS开发效率工具:TZImagePickerController插件开发指南
痛点与解决方案
你是否还在为iOS原生图片选择器功能单一而烦恼?是否需要一个支持多选、原图、视频、预览和裁剪的全能选择器?TZImagePickerController插件正是为解决这些问题而生。本文将带你从环境配置到高级定制,全面掌握这款高效图片选择器的开发技巧。
读完本文你将获得:
- 快速集成TZImagePickerController的完整步骤
- 核心功能的参数配置与使用示例
- 自定义UI样式的实用技巧
- 性能优化与常见问题解决方案
- 高级功能扩展与最佳实践
1. 项目概述与核心优势
TZImagePickerController是一个功能强大的iOS图片选择框架,作为UIImagePickerController的增强替代品,它提供了更丰富的功能和更高的定制性。
核心功能对比表
| 功能 | 原生UIImagePickerController | TZImagePickerController |
|---|---|---|
| 多选支持 | ❌ 不支持 | ✅ 支持,可自定义最大选择数 |
| 原图选择 | ❌ 不支持 | ✅ 支持,可配置开关 |
| 视频选择 | ⚠️ 有限支持 | ✅ 完整支持,可编辑时长 |
| 预览功能 | ⚠️ 基础支持 | ✅ 完整预览,支持缩放 |
| GIF支持 | ❌ 不支持 | ✅ 原生支持GIF预览与选择 |
| 裁剪功能 | ⚠️ 基础裁剪 | ✅ 支持自定义裁剪框与圆形裁剪 |
| UI定制 | ⚠️ 有限定制 | ✅ 全面支持UI样式自定义 |
| 最低系统支持 | iOS 2.0+ | iOS 10.0+ |
框架架构
2. 环境配置与集成步骤
2.1 系统要求
- iOS 10.0 或更高版本
- Xcode 10.0 或更高版本
- ARC 环境
2.2 安装方式
CocoaPods 安装
# 完整版本
pod 'TZImagePickerController'
# 基础版本(无定位功能)
pod 'TZImagePickerController/Basic'
手动安装
- 克隆仓库到本地
git clone https://gitcode.com/gh_mirrors/tz/TZImagePickerController.git
- 将TZImagePickerController文件夹拖拽到Xcode项目中
- 确保勾选"Copy items if needed"
- 添加必要的系统框架:
- Photos.framework
- PhotosUI.framework
2.3 Info.plist 配置
使用TZImagePickerController需要在Info.plist中添加以下权限描述:
<key>NSCameraUsageDescription</key>
<string>需要访问相机以拍摄照片</string>
<key>NSPhotoLibraryUsageDescription</key>
<string>需要访问相册以选择照片</string>
<key>NSMicrophoneUsageDescription</key>
<string>需要访问麦克风以录制视频</string>
<key>NSLocationWhenInUseUsageDescription</key>
<string>需要访问位置以记录照片位置信息</string>
<key>NSPhotoLibraryAddUsageDescription</key>
<string>需要访问相册以保存照片</string>
3. 快速上手:基础功能实现
3.1 基础初始化与调用
#import "TZImagePickerController.h"
// 在需要调用的地方
- (void)showImagePicker {
// 初始化图片选择器,最多选择9张图片
TZImagePickerController *imagePickerVc = [[TZImagePickerController alloc]
initWithMaxImagesCount:9
delegate:self];
// 设置选择完成回调
[imagePickerVc setDidFinishPickingPhotosHandle:^(NSArray<UIImage *> *photos,
NSArray *assets,
BOOL isSelectOriginalPhoto) {
// 处理选择的图片
self.selectedPhotos = photos;
[self.collectionView reloadData];
}];
// 模态弹出选择器
[self presentViewController:imagePickerVc animated:YES completion:nil];
}
// 实现代理方法(可选)
#pragma mark - TZImagePickerControllerDelegate
- (void)imagePickerController:(TZImagePickerController *)picker
didFinishPickingPhotos:(NSArray<UIImage *> *)photos
sourceAssets:(NSArray *)assets
isSelectOriginalPhoto:(BOOL)isSelectOriginalPhoto {
// 处理选择的图片
NSLog(@"选择了%ld张图片,是否原图:%@", photos.count, isSelectOriginalPhoto ? @"是" : @"否");
}
- (void)tz_imagePickerControllerDidCancel:(TZImagePickerController *)picker {
NSLog(@"用户取消了选择");
}
3.2 关键参数配置
基础参数配置
// 创建选择器实例
TZImagePickerController *imagePickerVc = [[TZImagePickerController alloc]
initWithMaxImagesCount:6
delegate:self];
// 配置参数
imagePickerVc.allowPickingOriginalPhoto = YES; // 允许选择原图
imagePickerVc.allowPickingVideo = YES; // 允许选择视频
imagePickerVc.allowPickingGif = YES; // 允许选择GIF
imagePickerVc.allowTakePicture = YES; // 允许拍摄照片
imagePickerVc.allowTakeVideo = YES; // 允许拍摄视频
imagePickerVc.allowCrop = YES; // 允许裁剪(单选模式下)
imagePickerVc.showSelectedIndex = YES; // 显示选择序号
imagePickerVc.needCircleCrop = NO; // 是否需要圆形裁剪
imagePickerVc.cropRect = CGRectMake(0, 100, self.view.width, self.view.width); // 裁剪框尺寸
// 设置语言(可选)
imagePickerVc.preferredLanguage = @"zh-Hans"; // 简体中文
// imagePickerVc.preferredLanguage = @"en"; // 英文
// imagePickerVc.preferredLanguage = @"ja"; // 日文
视频相关配置
// 允许选择视频
imagePickerVc.allowPickingVideo = YES;
// 允许编辑视频
imagePickerVc.allowEditVideo = YES;
// 视频最大拍摄时间(秒)
imagePickerVc.videoMaximumDuration = 60; // 1分钟
// 视频导出质量
imagePickerVc.presetName = AVAssetExportPresetMediumQuality;
// 编辑视频最大时长
imagePickerVc.maxCropVideoDuration = 30; // 30秒
4. 核心功能实现详解
4.1 多选功能
// 初始化选择器,设置最大选择数为9
TZImagePickerController *imagePickerVc = [[TZImagePickerController alloc]
initWithMaxImagesCount:9
delegate:self];
// 允许选择多种类型
imagePickerVc.allowPickingImage = YES; // 允许选择图片
imagePickerVc.allowPickingVideo = YES; // 允许选择视频
imagePickerVc.allowPickingMultipleVideo = YES; // 允许多选视频
// 选择完成回调
imagePickerVc.didFinishPickingPhotosHandle = ^(NSArray<UIImage *> *photos,
NSArray *assets,
BOOL isSelectOriginalPhoto) {
NSLog(@"选择了%ld个媒体文件", photos.count);
// 遍历结果
for (int i = 0; i < assets.count; i++) {
PHAsset *asset = assets[i];
if (asset.mediaType == PHAssetMediaTypeImage) {
NSLog(@"第%d个是图片", i+1);
} else if (asset.mediaType == PHAssetMediaTypeVideo) {
NSLog(@"第%d个是视频,时长%.1f秒", i+1, asset.duration);
}
}
};
[self presentViewController:imagePickerVc animated:YES completion:nil];
4.2 图片预览与裁剪
// 单选并裁剪模式
- (void)showSingleImagePickerWithCrop {
// 初始化选择器,最多选择1张图片
TZImagePickerController *imagePickerVc = [[TZImagePickerController alloc]
initWithMaxImagesCount:1
delegate:self];
// 配置为单选裁剪模式
imagePickerVc.allowCrop = YES; // 允许裁剪
imagePickerVc.showSelectBtn = NO; // 隐藏选择按钮
imagePickerVc.scaleAspectFillCrop = YES; // 等比缩放填充裁剪框
// 设置裁剪框尺寸(正方形)
CGFloat cropWidth = [UIScreen mainScreen].bounds.size.width - 100;
imagePickerVc.cropRect = CGRectMake(50, 150, cropWidth, cropWidth);
// 圆形裁剪(可选)
// imagePickerVc.needCircleCrop = YES;
// imagePickerVc.circleCropRadius = cropWidth / 2;
// 选择完成回调
imagePickerVc.didFinishPickingPhotosHandle = ^(NSArray<UIImage *> *photos,
NSArray *assets,
BOOL isSelectOriginalPhoto) {
if (photos.count > 0) {
UIImage *selectedImage = photos.firstObject;
self.avatarImageView.image = selectedImage;
}
};
[self presentViewController:imagePickerVc animated:YES completion:nil];
}
4.3 视频选择与编辑
// 视频选择与编辑
- (void)showVideoPickerWithEdit {
TZImagePickerController *imagePickerVc = [[TZImagePickerController alloc]
initWithMaxImagesCount:1
delegate:self];
// 配置视频选择
imagePickerVc.allowPickingImage = NO; // 不允许选择图片
imagePickerVc.allowPickingVideo = YES; // 允许选择视频
imagePickerVc.allowEditVideo = YES; // 允许编辑视频
imagePickerVc.videoMaximumDuration = 60; // 最长录制时间60秒
imagePickerVc.maxCropVideoDuration = 30; // 最长编辑时长30秒
// 设置视频编辑完成回调
imagePickerVc.didFinishPickingAndEditingVideoHandle = ^(UIImage *coverImage,
NSString *outputPath,
NSString *errorMsg) {
if (errorMsg) {
NSLog(@"视频编辑失败: %@", errorMsg);
return;
}
NSLog(@"视频编辑成功,输出路径: %@", outputPath);
// 显示视频封面
self.videoCoverImageView.image = coverImage;
// 保存视频路径用于上传或播放
self.videoPath = outputPath;
};
[self presentViewController:imagePickerVc animated:YES completion:nil];
}
5. UI定制与高级配置
5.1 自定义导航栏样式
// 自定义导航栏样式
TZImagePickerController *imagePickerVc = [[TZImagePickerController alloc]
initWithMaxImagesCount:9
delegate:self];
// 导航栏背景色
imagePickerVc.naviBgColor = [UIColor colorWithRed:0.1 green:0.1 blue:0.1 alpha:1.0];
// 导航栏标题颜色
imagePickerVc.naviTitleColor = [UIColor whiteColor];
// 导航栏标题字体
imagePickerVc.naviTitleFont = [UIFont systemFontOfSize:18 weight:UIFontWeightMedium];
// 状态栏样式
imagePickerVc.statusBarStyle = UIStatusBarStyleLightContent;
// 按钮文字颜色
imagePickerVc.barItemTextColor = [UIColor whiteColor];
// 按钮文字字体
imagePickerVc.barItemTextFont = [UIFont systemFontOfSize:16];
5.2 自定义选择器UI
// 自定义底部工具栏
imagePickerVc.photoPickerPageUIConfigBlock = ^(UICollectionView *collectionView,
UIView *bottomToolBar,
UIButton *previewButton,
UIButton *originalPhotoButton,
UILabel *originalPhotoLabel,
UIButton *doneButton,
UIImageView *numberImageView,
UILabel *numberLabel,
UIView *divideLine) {
// 修改底部工具栏背景色
bottomToolBar.backgroundColor = [UIColor colorWithRed:0.1 green:0.1 blue:0.1 alpha:1.0];
// 修改完成按钮样式
doneButton.backgroundColor = [UIColor colorWithRed:0.2 green:0.6 blue:1.0 alpha:1.0];
doneButton.layer.cornerRadius = 22.0;
doneButton.clipsToBounds = YES;
[doneButton setTitleColor:[UIColor whiteColor] forState:UIControlStateNormal];
[doneButton setTitleColor:[UIColor lightGrayColor] forState:UIControlStateDisabled];
// 修改原图按钮文字颜色
originalPhotoLabel.textColor = [UIColor whiteColor];
};
// 自定义选中序号颜色
imagePickerVc.iconThemeColor = [UIColor colorWithRed:0.2 green:0.6 blue:1.0 alpha:1.0];
5.3 自定义单元格样式
// 自定义相册单元格
imagePickerVc.albumCellDidSetModelBlock = ^(TZAlbumCell *cell,
UIImageView *posterImageView,
UILabel *titleLabel) {
// 自定义相册封面
posterImageView.layer.cornerRadius = 8;
posterImageView.clipsToBounds = YES;
posterImageView.contentMode = UIViewContentModeScaleAspectFill;
// 自定义标题
titleLabel.font = [UIFont systemFontOfSize:15 weight:UIFontWeightMedium];
titleLabel.textColor = [UIColor colorWithRed:0.1 green:0.1 blue:0.1 alpha:1.0];
};
// 自定义照片单元格
imagePickerVc.assetCellDidSetModelBlock = ^(TZAssetCell *cell,
UIImageView *imageView,
UIImageView *selectImageView,
UILabel *indexLabel,
UIView *bottomView,
UILabel *timeLength,
UIImageView *videoImgView) {
// 自定义照片显示
imageView.layer.cornerRadius = 4;
imageView.clipsToBounds = YES;
// 自定义选中标记
selectImageView.layer.borderColor = [UIColor colorWithRed:0.2 green:0.6 blue:1.0 alpha:1.0].CGColor;
selectImageView.layer.borderWidth = 2;
// 自定义时长标签
bottomView.backgroundColor = [UIColor colorWithWhite:0 alpha:0.6];
timeLength.textColor = [UIColor whiteColor];
timeLength.font = [UIFont systemFontOfSize:12];
};
5.4 多语言支持
// 设置首选语言
TZImagePickerController *imagePickerVc = [[TZImagePickerController alloc]
initWithMaxImagesCount:9
delegate:self];
// 支持的语言: zh-Hans(简体中文), zh-Hant(繁体中文), en(英文), vi(越南语), ja(日语), ko-KP(韩语), etc.
imagePickerVc.preferredLanguage = @"en"; // 设置为英文
// 自定义语言包(高级用法)
NSBundle *customBundle = [NSBundle bundleWithPath:[[NSBundle mainBundle] pathForResource:@"CustomLanguage" ofType:@"bundle"]];
imagePickerVc.languageBundle = customBundle;
6. 性能优化与最佳实践
6.1 内存优化策略
图片加载优化
// 获取图片时指定合理尺寸,避免加载过大图片
[[TZImageManager sharedManager] getPhotoWithAsset:asset
photoWidth:300 // 指定宽度,高度会按比例计算
completion:^(UIImage *photo, NSDictionary *info, BOOL isDegraded) {
// 使用获取到的图片
cell.imageView.image = photo;
}];
使用NSOperationQueue控制并发
// 创建串行队列处理图片加载,避免并发过高导致内存峰值
NSOperationQueue *imageQueue = [[NSOperationQueue alloc] init];
imageQueue.maxConcurrentOperationCount = 3; // 控制最大并发数
for (PHAsset *asset in assets) {
[imageQueue addOperationWithBlock:^{
[[TZImageManager sharedManager] getPhotoWithAsset:asset
photoWidth:300
completion:^(UIImage *photo, NSDictionary *info, BOOL isDegraded) {
if (!isDegraded) { // 只处理完整加载的图片
dispatch_async(dispatch_get_main_queue(), ^{
// 更新UI显示图片
});
}
}];
}];
}
6.2 常见问题解决方案
问题1: iOS 14+ 照片权限问题
解决方案:
在Info.plist中添加以下权限:
<key>NSPhotoLibraryUsageDescription</key>
<string>需要访问您的相册以选择照片</string>
<key>NSPhotoLibraryAddUsageDescription</key>
<string>需要访问您的相册以保存照片</string>
<key>Prevent limited photos access alert</key>
<true/>
问题2: iCloud照片加载缓慢
解决方案:
// 监听图片加载进度
TZPhotoPreviewCell *cell = [collectionView cellForItemAtIndexPath:indexPath];
cell.imageProgressUpdateBlock = ^(double progress) {
// 显示进度指示器
cell.progressView.progress = progress;
cell.progressView.hidden = (progress >= 1);
};
问题3: 视频导出失败
解决方案:
// 禁用视频转向修正,解决部分安卓视频导出问题
imagePickerVc.needFixComposition = NO;
// 监听视频导出失败
imagePickerVc.didFinishPickingAndEditingVideoHandle = ^(UIImage *coverImage, NSString *outputPath, NSString *errorMsg) {
if (errorMsg) {
NSLog(@"视频导出失败: %@", errorMsg);
// 显示错误提示
UIAlertController *alert = [UIAlertController alertControllerWithTitle:@"导出失败"
message:errorMsg
preferredStyle:UIAlertControllerStyleAlert];
[alert addAction:[UIAlertAction actionWithTitle:@"确定" style:UIAlertActionStyleDefault handler:nil]];
[self presentViewController:alert animated:YES completion:nil];
}
};
6.3 调试与日志
// 启用详细日志(仅调试时使用)
#define TZDebugLog(...) NSLog(__VA_ARGS__)
// 常见调试技巧:
// 1. 检查相册权限状态
PHAuthorizationStatus status = [PHPhotoLibrary authorizationStatus];
NSLog(@"相册权限状态: %ld", (long)status);
// 2. 检查资源类型
PHAsset *asset = ...;
NSLog(@"资源类型: %ld, 时长: %.1f秒",
(long)asset.mediaType, asset.duration);
// 3. 检查图片尺寸
UIImage *image = ...;
NSLog(@"图片尺寸: %@", NSStringFromCGSize(image.size));
7. 版本更新与维护
7.1 版本更新记录
| 版本 | 发布日期 | 主要更新内容 |
|---|---|---|
| 3.8.9 | 2025-05-27 | 优化性能,修复若干bug |
| 3.8.8 | 2024-09-14 | 支持iOS18,修复openURL失效问题 |
| 3.8.5 | 2024-05-20 | 新增隐私清单文件 |
| 3.8.4 | 2024-03-15 | 支持使用不带定位代码的版本 |
| 3.8.1 | 2023-11-08 | iOS14下可添加访问更多照片 |
| 3.7.6 | 2023-01-15 | 修复iOS15.2下初次授权卡顿问题 |
| 3.6.7 | 2021-10-28 | 修复Xcode13&iOS15导航栏颜色异常 |
7.2 长期维护建议
- 关注官方仓库更新
定期查看官方仓库获取最新安全补丁和功能更新:
# 查看远程仓库信息
git remote -v
# 拉取最新代码
git pull origin master
- 定期重构关键代码
随着项目迭代,定期重构使用TZImagePickerController的代码,保持与最新API同步。
- 监控性能指标
使用Xcode Instruments监控内存使用和性能瓶颈:
# 使用Instruments监控应用性能
instruments -t "Allocations" -l 60 myapp.app
8. 总结与展望
TZImagePickerController作为一个功能全面的图片选择框架,为iOS开发者提供了高效、灵活的媒体选择解决方案。通过本文介绍的配置方法和最佳实践,你可以快速集成并定制出符合应用需求的图片选择功能。
8.1 关键知识点回顾
- 核心优势: 多选支持、原图选择、视频处理、UI定制
- 基础配置: 初始化参数、权限设置、回调处理
- 高级功能: 图片裁剪、视频编辑、GIF支持
- 性能优化: 内存管理、并发控制、资源加载
- 问题解决: 权限处理、iCloud同步、视频导出
8.2 未来发展方向
-
Swift重构: 官方正在计划推出Swift版本,提供更好的类型安全和现代Swift特性支持。
-
AI增强: 未来可能集成AI图片识别功能,支持智能分类和搜索。
-
AR支持: 加入AR照片预览和编辑功能,提升用户体验。
-
跨平台兼容: 探索Flutter版本,实现跨平台统一体验。
通过持续关注项目更新和社区动态,你可以及时获取最新功能和最佳实践,为你的应用提供更好的媒体选择体验。
希望本文能帮助你更好地理解和使用TZImagePickerController框架。如有任何问题或建议,欢迎在项目GitHub仓库提交issue或PR,共同推动框架的完善和发展。
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考



