您的位置:首页 > 移动开发 > IOS开发

iOS8开发之 PHAsset 保存图片到相册(相机胶卷) 详解一

2016-01-11 18:34 447 查看
http://segmentfault.com/a/1190000003950935

平时开发APP时难免会遇到保存图片到相册的相关操作,具体我么可以直接保存到系统的相机胶卷,

也可以自定义相册保存图片,下面我们就一起来看一看.


保存图片到系统相册

先看看比较简单的直接保存图片到系统相册操作
- (IBAction)save {
// 存储图片到"相机胶卷"
UIImageWriteToSavedPhotosAlbum(self.imageView.image, self, @selector(image:didFinishSavingWithError:contextInfo:), nil);
}

// 成功保存图片到相册中, 必须调用此方法, 否则会报参数越界错误
- (void)image:(UIImage *)image didFinishSavingWithError:(NSError *)error contextInfo:(void *)contextInfo{
if (error) {
[SVProgressHUD showErrorWithStatus:@"保存失败"];
[SVProgressHUD showSuccessWithStatus:@"保存成功"];
}
}


保存图片到自定义相册

以前我们利用 AssetsLibrary框架 来进行相册的相关操作,但是AssetsLibrary坑太多,一不小心就是各种警告错误,这人非常难受,苹果似乎也意识到了问题的严重性,所以从iOS8开始搞了个 Photos框架 来给我们用.

iOS已经更新到了9.0, AssetsLibrary 被完全弃用,下面我们就用 Photos 来做保存图片到自定义相册的操作

#import <AssetsLibrary/AssetsLibrary.h> // iOS9.0彻底弃用,用下面这个吧,拿出来只是提醒你一下
#import <Photos/Photos.h> // iOS8.0开始,我们最好用这个咯

- (IBAction)save {
// 0.判断状态
PHAuthorizationStatus status = [PHPhotoLibrary authorizationStatus];
if (status == PHAuthorizationStatusDenied) {
BSLog(@"用户拒绝当前应用访问相册,我们需要提醒用户打开访问开关");
}else if (status == PHAuthorizationStatusRestricted){
BSLog(@"家长控制,不允许访问");
}else if (status == PHAuthorizationStatusNotDetermined){
BSLog(@"用户还没有做出选择");
[self saveImage];
}else if (status == PHAuthorizationStatusAuthorized){
BSLog(@"用户允许当前应用访问相册");
[self saveImage];
}
}

/**
*  返回相册
*/
- (PHAssetCollection *)collection{
// 先获得之前创建过的相册
PHFetchResult<PHAssetCollection *> *collectionResult = [PHAssetCollection fetchAssetCollectionsWithType:PHAssetCollectionTypeAlbum subtype:PHAssetCollectionSubtypeAlbumRegular options:nil];
for (PHAssetCollection *collection in collectionResult) {
if ([collection.localizedTitle isEqualToString:BSCollectionName]) {
return collection;
}
}

// 如果相册不存在,就创建新的相册(文件夹)
__block NSString *collectionId = nil; // __block修改block外部的变量的值
// 这个方法会在相册创建完毕后才会返回
[[PHPhotoLibrary sharedPhotoLibrary] performChangesAndWait:^{
// 新建一个PHAssertCollectionChangeRequest对象, 用来创建一个新的相册
collectionId = [PHAssetCollectionChangeRequest creationRequestForAssetCollectionWithTitle:BSCollectionName].placeholderForCreatedAssetCollection.localIdentifier;
} error:nil];

return [PHAssetCollection fetchAssetCollectionsWithLocalIdentifiers:@[collectionId] options:nil].firstObject;
}

/**
*  返回相册,避免重复创建相册引起不必要的错误
*/
- (void)saveImage{
/*
PHAsset : 一个PHAsset对象就代表一个资源文件,比如一张图片
PHAssetCollection : 一个PHAssetCollection对象就代表一个相册
*/

__block NSString *assetId = nil;
// 1. 存储图片到"相机胶卷"
[[PHPhotoLibrary sharedPhotoLibrary] performChanges:^{ // 这个block里保存一些"修改"性质的代码
// 新建一个PHAssetCreationRequest对象, 保存图片到"相机胶卷"
// 返回PHAsset(图片)的字符串标识
assetId = [PHAssetCreationRequest creationRequestForAssetFromImage:self.imageView.image].placeholderForCreatedAsset.localIdentifier;
} completionHandler:^(BOOL success, NSError * _Nullable error) {
if (error) {
BSLog(@"保存图片到相机胶卷中失败");
return;
}

BSLog(@"成功保存图片到相机胶卷中");

// 2. 获得相册对象
PHAssetCollection *collection = [self collection];

// 3. 将“相机胶卷”中的图片添加到新的相册
[[PHPhotoLibrary sharedPhotoLibrary] performChanges:^{
PHAssetCollectionChangeRequest *request = [PHAssetCollectionChangeRequest changeRequestForAssetCollection:collection];

// 根据唯一标示获得相片对象
PHAsset *asset = [PHAsset fetchAssetsWithLocalIdentifiers:@[assetId] options:nil].firstObject;
// 添加图片到相册中
[request addAssets:@[asset]];
} completionHandler:^(BOOL success, NSError * _Nullable error) {
if (error) {
BSLog(@"添加图片到相册中失败");
return;
}

BSLog(@"成功添加图片到相册中");
[[NSOperationQueue mainQueue] addOperationWithBlock:^{
[SVProgressHUD showSuccessWithStatus:@"保存成功"];
}];
}];
}];
}


代码比较琐碎,其实在开发的时候直接将上面代码拷进项目稍微改一改就可以了,所以记得收藏哦!!
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: