iOS开发之获取系统相册中的图片与视频(内带url转换)

  • @话不多说,直接上代码

     

    001. #import <AssetsLibrary/AssetsLibrary.h>  // 必须导入
    002.  
    003. // 照片原图路径
    004. #define KOriginalPhotoImagePath  
    005. [[NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES) objectAtIndex:0] stringByAppendingPathComponent:@"OriginalPhotoImages"]
    006.  
    007. // 视频URL路径
    008. #define KVideoUrlPath  
    009. [[NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES) objectAtIndex:0] stringByAppendingPathComponent:@"VideoURL"]
    010.  
    011. // caches路径
    012. #define KCachesPath  
    013. [NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES) objectAtIndex:0]
    014.  
    015. // MainViewController
    016. @interface MTHMainViewController ()
    017.  
    018. @property (nonatomic,strong) MTHNextViewController *nextVC;
    019. @property (nonatomic,strong) NSMutableArray        *groupArrays;
    020. @property (nonatomic,strong) UIImageView           *litimgView;
    021.  
    022. @end
    023.  
    024. @implementation MTHMainViewController
    025.  
    026. - (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
    027. {
    028. self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
    029. if (self) {
    030. // Custom initialization
    031. }
    032. return self;
    033. }
    034.  
    035. - (void)viewDidLoad
    036. {
    037. [super viewDidLoad];
    038. // Do any additional setup after loading the view.
    039. self.navigationItem.title = @"Demo";
    040. self.view.backgroundColor = [UIColor clearColor];
    041.  
    042. // 初始化
    043. self.groupArrays = [NSMutableArray array];
    044.  
    045. // 测试BarItem
    046. self.navigationItem.rightBarButtonItem = [[UIBarButtonItem alloc] initWithTitle:@"测试"style:UIBarButtonItemStylePlain target:self action:@selector(testRun)];
    047.  
    048. // 测试手势
    049. UIPanGestureRecognizer *panRecognizer = [[UIPanGestureRecognizer alloc] initWithTarget:self action:@selector(didClickPanGestureRecognizer:)];
    050. [self.navigationController.view addGestureRecognizer:panRecognizer];
    051.  
    052. // 图片或者视频的缩略图显示
    053. self.litimgView = [[UIImageView alloc] initWithFrame:CGRectMake(100200120120)];
    054. [self.view addSubview:_litimgView];
    055. }
    056.  
    057.  
    058. - (void)testRun
    059. {
    060. __weak MTHMainViewController *weakSelf = self;
    061. dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
    062. ALAssetsLibraryGroupsEnumerationResultsBlock listGroupBlock = ^(ALAssetsGroup *group, BOOL *stop) {
    063. if (group != nil) {
    064. [weakSelf.groupArrays addObject:group];
    065. else {
    066. [weakSelf.groupArrays enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop) {
    067. [obj enumerateAssetsUsingBlock:^(ALAsset *result, NSUInteger index, BOOL *stop) {
    068. if ([result thumbnail] != nil) {
    069. // 照片
    070. if ([[result valueForProperty:ALAssetPropertyType] isEqualToString:ALAssetTypePhoto]){
    071.  
    072. NSDate *date= [result valueForProperty:ALAssetPropertyDate];
    073. UIImage *image = [UIImage imageWithCGImage:[result thumbnail]];
    074. NSString *fileName = [[result defaultRepresentation] filename];
    075. NSURL *url = [[result defaultRepresentation] url];
    076. int64_t fileSize = [[result defaultRepresentation] size];
    077.  
    078. NSLog(@"date = %@",date);
    079. NSLog(@"fileName = %@",fileName);
    080. NSLog(@"url = %@",url);
    081. NSLog(@"fileSize = %lld",fileSize);
    082.  
    083. // UI的更新记得放在主线程,要不然等子线程排队过来都不知道什么年代了,会很慢的
    084. dispatch_async(dispatch_get_main_queue(), ^{
    085. self.litimgView.image = image;
    086. });
    087. }
    088. // 视频
    089. else if ([[result valueForProperty:ALAssetPropertyType] isEqualToString:ALAssetTypeVideo] ){
    090.  
    091. // 和图片方法类似
    092. }
    093. }
    094. }];
    095. }];
    096.  
    097. }
    098. };
    099.  
    100. ALAssetsLibraryAccessFailureBlock failureBlock = ^(NSError *error)
    101. {
    102.  
    103. NSString *errorMessage = nil;
    104.  
    105. switch ([error code]) {
    106. case ALAssetsLibraryAccessUserDeniedError:
    107. case ALAssetsLibraryAccessGloballyDeniedError:
    108. errorMessage = @"用户拒绝访问相册,请在<隐私>中开启";
    109. break;
    110.  
    111. default:
    112. errorMessage = @"Reason unknown.";
    113. break;
    114. }
    115.  
    116. dispatch_async(dispatch_get_main_queue(), ^{
    117. UIAlertView *alertView = [[UIAlertView alloc]initWithTitle:@"错误,无法访问!"
    118. message:errorMessage
    119. delegate:self
    120. cancelButtonTitle:@"确定"
    121. otherButtonTitles:nil, nil];
    122. [alertView show];
    123. });
    124. };
    125.  
    126.  
    127. ALAssetsLibrary *assetsLibrary = [[ALAssetsLibrary alloc]  init];
    128. [assetsLibrary enumerateGroupsWithTypes:ALAssetsGroupAll
    129. usingBlock:listGroupBlock failureBlock:failureBlock];
    130. });
    131. }
    \

     

    @但是:

    按照上面方法直接取出来的路径是无法传输的,必须自己转化成NSData对象重新写入沙盒路径

     

    01. // 将原始图片的URL转化为NSData数据,写入沙盒
    02. - (void)imageWithUrl:(NSURL *)url withFileName:(NSString *)fileName
    03. {
    04. // 进这个方法的时候也应该加判断,如果已经转化了的就不要调用这个方法了
    05. // 如何判断已经转化了,通过是否存在文件路径
    06. ALAssetsLibrary *assetLibrary = [[ALAssetsLibrary alloc] init];
    07. // 创建存放原始图的文件夹--->OriginalPhotoImages
    08. NSFileManager * fileManager = [NSFileManager defaultManager];
    09. if (![fileManager fileExistsAtPath:KOriginalPhotoImagePath]) {
    10. [fileManager createDirectoryAtPath:KOriginalPhotoImagePath withIntermediateDirectories:YES attributes:nil error:nil];
    11. }
    12. dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
    13. if (url) {
    14. // 主要方法
    15. [assetLibrary assetForURL:url resultBlock:^(ALAsset *asset) {
    16. ALAssetRepresentation *rep = [asset defaultRepresentation];
    17. Byte *buffer = (Byte*)malloc((unsigned long)rep.size);
    18. NSUInteger buffered = [rep getBytes:buffer fromOffset:0.0 length:((unsignedlong)rep.size) error:nil];
    19. NSData *data = [NSData dataWithBytesNoCopy:buffer length:buffered freeWhenDone:YES];
    20. NSString * imagePath = [KOriginalPhotoImagePath stringByAppendingPathComponent:fileName];
    21. [data writeToFile:imagePath atomically:YES];
    22. } failureBlock:nil];
    23. }
    24. });
    25. }
    26.  
    27. // 将原始视频的URL转化为NSData数据,写入沙盒
    28. - (void)videoWithUrl:(NSURL *)url withFileName:(NSString *)fileName
    29. {
    30. // 解析一下,为什么视频不像图片一样一次性开辟本身大小的内存写入?
    31. // 想想,如果1个视频有1G多,难道直接开辟1G多的空间大小来写?
    32. ALAssetsLibrary *assetLibrary = [[ALAssetsLibrary alloc] init];
    33. dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
    34. if (url) {
    35. [assetLibrary assetForURL:url resultBlock:^(ALAsset *asset) {
    36. ALAssetRepresentation *rep = [asset defaultRepresentation];
    37. NSString * videoPath = [KCachesPath stringByAppendingPathComponent:fileName];
    38. char const *cvideoPath = [videoPath UTF8String];
    39. FILE *file = fopen(cvideoPath, "a+");
    40. if (file) {
    41. const int bufferSize = 1024 1024;
    42. // 初始化一个1M的buffer
    43. Byte *buffer = (Byte*)malloc(bufferSize);
    44. NSUInteger read = 0, offset = 0, written = 0;
    45. NSError* err = nil;
    46. if (rep.size != 0)
    47. {
    48. do {
    49. read = [rep getBytes:buffer fromOffset:offset length:bufferSize error:&err];
    50. written = fwrite(buffer, sizeof(char), read, file);
    51. offset += read;
    52. while (read != 0 && !err);//没到结尾,没出错,ok继续
    53. }
    54. // 释放缓冲区,关闭文件
    55. free(buffer);
    56. buffer = NULL;
    57. fclose(file);
    58. file = NULL;
    59. }
    60. } failureBlock:nil];
    61. }
    62. });
    63. }

    @转载请标注:转自iOS界@迷糊小书童 谢谢
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值