[iOS]从相册获取以及用相机拍摄视频并缓存到沙盒

来源:互联网 发布:logback.xml不打印sql 编辑:程序博客网 时间:2024/05/02 00:32

[iOS]从相册获取以及用相机拍摄视频并缓存到沙盒


Demo:http://download.csdn.net/detail/u012881779/9449227

从标题很容易发现,本文只是为了获取视频数据源,以便后面能方便完成视频上传等操作

需要导入AVFoundation.framework(获取数据源), MediaPlayer.framework(播放视频)

#import "DMSelectVideoViewController.h"#import "ZYQAssetPickerController.h"#import <AVFoundation/AVFoundation.h>#import <MediaPlayer/MediaPlayer.h>// 视频URL路径#define KVideoUrlPath   \[[NSSearchPathForDirectoriesInDomains(NSCachesDirectory, NSUserDomainMask, YES) objectAtIndex:0] stringByAppendingPathComponent:@"VideoURL"]@interface DMSelectVideoViewController ()<UIActionSheetDelegate , ZYQAssetPickerControllerDelegate , UINavigationControllerDelegate ,UITextFieldDelegate , UIImagePickerControllerDelegate>@property (strong, nonatomic) NSMutableArray     *uploadDataArr;   @property (weak, nonatomic) IBOutlet UITextView  *desTextView;@property (weak, nonatomic) IBOutlet UIImageView *imgView;@property (weak, nonatomic) IBOutlet UILabel     *titleLab;@property (weak, nonatomic) IBOutlet UILabel     *typeLab;@property (weak, nonatomic) IBOutlet UILabel     *timeLab;@property (strong, nonatomic) MPMoviePlayerViewController *moviePlayerView;@end@implementation DMSelectVideoViewController@synthesize uploadDataArr = _uploadDataArr;@synthesize moviePlayerView = _moviePlayerView;//播放视频- (IBAction)playVideoAction:(id)sender {    if(_uploadDataArr){        NSDictionary *lastObj = [_uploadDataArr lastObject];        NSString *viPath = [lastObj objectForKey:@"path"];        if(![viPath isEqualToString:@""]){            NSURL *movieURL = [NSURL fileURLWithPath:viPath];            [_moviePlayerView.view removeFromSuperview];            _moviePlayerView = nil;            _moviePlayerView =[[MPMoviePlayerViewController alloc] initWithContentURL:movieURL];            [_moviePlayerView.moviePlayer prepareToPlay];            [self.view addSubview:_moviePlayerView.view];            _moviePlayerView.moviePlayer.shouldAutoplay=YES;            [_moviePlayerView.moviePlayer setControlStyle:MPMovieControlStyleDefault];            [_moviePlayerView.moviePlayer setFullscreen:YES];            [_moviePlayerView.view setFrame:self.view.bounds];                        //播放完后的通知            [[NSNotificationCenter defaultCenter] addObserver:self                                                     selector:@selector(movieFinishedCallback:)                                                         name:MPMoviePlayerPlaybackDidFinishNotification                                                      object:nil];            //离开全屏时通知,因为默认点击Done是退出全屏,要离开播放器就要覆盖掉这个事件            [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(exitFullScreen:) name: MPMoviePlayerDidExitFullscreenNotification object:nil];        }    }}//播放结束后离开播放器,点击上一曲、下一曲也是播放结束-(void)movieFinishedCallback:(NSNotification*)notify {    MPMoviePlayerController* theMovie = [notify object];    [[NSNotificationCenter defaultCenter] removeObserver:self                                                   name:MPMoviePlayerPlaybackDidFinishNotification                                                 object:theMovie];    [theMovie.view removeFromSuperview];}-(void)exitFullScreen:(NSNotification *)notification{    [_moviePlayerView.view removeFromSuperview];}//选择视频- (IBAction)ChioceVideoAction:(id)sender {    [self.view endEditing:YES];    UIActionSheet *actionSheet=[[UIActionSheet alloc] initWithTitle:nil                                                           delegate:self                                                  cancelButtonTitle:@"取消"                                             destructiveButtonTitle:nil                                                  otherButtonTitles:@"从相册选择",@"相机拍摄", nil];    actionSheet.actionSheetStyle = UIActionSheetStyleBlackOpaque;    [actionSheet showInView:self.view];}//投稿- (IBAction)IWantToContributeAction:(id)sender {    [self.view endEditing:YES];}-(void)actionSheet:(UIActionSheet *)actionSheet clickedButtonAtIndex:(NSInteger)buttonIndex{        switch (buttonIndex) {        case 0:            //从相册选择            [self selectFromAlbumAction];            break;                    case 1:            //相机拍摄            [self shootingWithCameraAction];            break;                    default:            break;    }}#pragma mark 从相册选择//从相册选择-(void)selectFromAlbumAction{    ZYQAssetPickerController *picker = [[ZYQAssetPickerController alloc] init];    picker.maximumNumberOfSelection = 1;    picker.assetsFilter = [ALAssetsFilter allVideos];    picker.showEmptyGroups=NO;    picker.delegate=self;        picker.selectionFilter = [NSPredicate predicateWithBlock:^BOOL(id evaluatedObject, NSDictionary *bindings) {        if ([[(ALAsset*)evaluatedObject valueForProperty:ALAssetPropertyType] isEqual:ALAssetTypeVideo]) {            NSTimeInterval duration = [[(ALAsset*)evaluatedObject valueForProperty:ALAssetPropertyDuration] doubleValue];            return duration <= 60;                    } else {            return YES;        }    }];        [self presentViewController:picker animated:YES completion:NULL];}#pragma mark - ZYQAssetPickerController Delegate-(void)assetPickerController:(ZYQAssetPickerController *)picker didFinishPickingAssets:(NSArray *)assets{        if(!_uploadDataArr){        _uploadDataArr = [[NSMutableArray alloc] init];    }    [_uploadDataArr removeAllObjects];    //清空缓存中数据    [self cleanCachesVideo];    //清空UI上数据    [self cleanOnUIData];        for (int i=0; i<assets.count; i++) {        ALAsset *asset=assets[i];        ALAssetRepresentation * representation = asset.defaultRepresentation;                UIImage *tempImg = [UIImage imageWithCGImage:asset.thumbnail];        NSData *data = UIImageJPEGRepresentation(tempImg, 1);        NSString *reName = [self renameWithTimeSp:representation.filename];        [self videoWithUrl:representation.url withFileName:reName];                    int seconds  =[[asset valueForProperty:ALAssetPropertyDuration] intValue];        NSMutableDictionary *objDict = [[NSMutableDictionary alloc] init];        if(data){            [objDict setObject:data forKey:@"header"];        }        [objDict setObject:[NSString stringWithFormat:@"%@/%@",KVideoUrlPath,reName]  forKey:@"path"];        [objDict setObject:[NSString stringWithFormat:@"%.2fM",(representation.size/1024.0)/1024.0] forKey:@"type"];        [objDict setObject:reName  forKey:@"name"];                [objDict setObject:[NSString stringWithFormat:@"%d",seconds]  forKey:@"time"];        [_uploadDataArr addObject:objDict];    }}// 将原始视频的URL转化为NSData数据,写入沙盒- (void)videoWithUrl:(NSURL *)url withFileName:(NSString *)fileName{     NSFileManager * fileManager = [NSFileManager defaultManager];    if (![fileManager fileExistsAtPath:KVideoUrlPath]) {        [fileManager createDirectoryAtPath:KVideoUrlPath withIntermediateDirectories:YES attributes:nil error:nil];    }    ALAssetsLibrary *assetLibrary = [[ALAssetsLibrary alloc] init];    dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{        if (url) {            [assetLibrary assetForURL:url resultBlock:^(ALAsset *asset) {                ALAssetRepresentation *rep = [asset defaultRepresentation];                NSString * videoPath = [KVideoUrlPath stringByAppendingPathComponent:fileName];                const char *cvideoPath = [videoPath UTF8String];                FILE *file = fopen(cvideoPath, "a+");                if (file) {                    const int bufferSize = 11024 * 1024;                    // 初始化一个1M的buffer                    Byte *buffer = (Byte*)malloc(bufferSize);                    NSUInteger read = 0, offset = 0, written = 0;                    NSError* err = nil;                    if (rep.size != 0)                    {                        do {                            read = [rep getBytes:buffer fromOffset:offset length:bufferSize error:&err];                            written = fwrite(buffer, sizeof(char), read, file);                            offset += read;                        } while (read != 0 && !err);                    }                    // 释放缓冲区,关闭文件                    free(buffer);                    buffer = NULL;                    fclose(file);                    file = NULL;                                        // UI的更新放在主线程                    dispatch_async(dispatch_get_main_queue(), ^{                        NSDictionary *firstDict = [_uploadDataArr firstObject];                        if(firstDict){                            _imgView.image = [UIImage imageWithData:[firstDict objectForKey:@"header"]];                            _titleLab.text = [firstDict objectForKey:@"name"];                            _typeLab.text = [firstDict objectForKey:@"type"];                            NSString *timeStr = [firstDict objectForKey:@"time"];                            if([timeStr intValue] > 0){                                _timeLab.text = [NSString stringWithFormat:@"%@S",timeStr];                            }                        }                    });                }            } failureBlock:nil];        }    });}//清空缓存中数据-(void)cleanCachesVideo{    NSFileManager * fileManager = [NSFileManager defaultManager];    if (![fileManager fileExistsAtPath:KVideoUrlPath]) {        [fileManager createDirectoryAtPath:KVideoUrlPath withIntermediateDirectories:YES attributes:nil error:nil];    }    NSArray *contents = [fileManager contentsOfDirectoryAtPath:KVideoUrlPath error:NULL];    NSEnumerator *e = [contents objectEnumerator];    NSString *filename;    while ((filename = [e nextObject])) {          [fileManager removeItemAtPath:[KVideoUrlPath stringByAppendingPathComponent:filename] error:NULL];    }}//用时间戳对文件命名 到毫秒-(NSString *)renameWithTimeSp:(NSString *)fileName{    NSArray *spArr = [fileName componentsSeparatedByString:@"."];    int hs = arc4random() % 100;    NSDate *newDate = [NSDate date];    long int timeSp = (long)[newDate timeIntervalSince1970];    fileName = [NSString stringWithFormat:@"%ld%d.%@",timeSp,hs,[spArr lastObject]];    return fileName;}//清空UI上数据-(void)cleanOnUIData{    _imgView.image = nil;    _titleLab.text = @"";    _typeLab.text = @"";    _timeLab.text = @"";}#pragma mark 相机拍摄//相机拍摄-(void)shootingWithCameraAction{    UIImagePickerController *ipc = [[UIImagePickerController alloc] init];    ipc.sourceType = UIImagePickerControllerSourceTypeCamera;//sourcetype有三种分别是camera,photoLibrary和photoAlbum    NSArray *availableMedia = [UIImagePickerController availableMediaTypesForSourceType:UIImagePickerControllerSourceTypeCamera];//Camera所支持的Media格式都有哪些,共有两个分别是@"public.image",@"public.movie"    ipc.mediaTypes = [NSArray arrayWithObject:availableMedia[1]];//设置媒体类型为public.movie    [self presentViewController:ipc animated:YES completion:nil];    ipc.videoMaximumDuration = 60.0f;//60秒    ipc.delegate = self;//设置委托}//选择完成后响应- (void)imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary *)info{    NSString*sourceURL = [info objectForKey:UIImagePickerControllerMediaURL];    NSLog(@"%@",sourceURL);    NSFileManager * fileManager = [NSFileManager defaultManager];    if (![fileManager fileExistsAtPath:KVideoUrlPath]) {        [fileManager createDirectoryAtPath:KVideoUrlPath withIntermediateDirectories:YES attributes:nil error:nil];    }    //视频长度    float videoLengthTime = [self getVideoLength:(NSURL *)sourceURL];    //视频缩略图    UIImage *videoImgtemp = [self getImage:(NSURL *)sourceURL];        NSData *createData = [NSData dataWithContentsOfFile:sourceURL];    if(createData){        //清空缓存中数据        [self cleanCachesVideo];        //清空UI上数据        [self cleanOnUIData];                NSString *lastName = @"capturedvideo.MOV";        NSString *kvideoPath = [NSString stringWithFormat:@"%@/%@",KVideoUrlPath,[self renameWithTimeSp:lastName]];        BOOL result = [fileManager createFileAtPath:kvideoPath contents:createData attributes:nil];        if(result){            NSString *paiPath = [NSString stringWithFormat:@"%@/tmp", NSHomeDirectory()] ;            NSArray *contents = [fileManager contentsOfDirectoryAtPath:paiPath error:NULL];            NSEnumerator *e = [contents objectEnumerator];            NSString *filename;            while ((filename = [e nextObject])) {                [fileManager removeItemAtPath:[paiPath stringByAppendingPathComponent:filename] error:NULL];            }        }        if (![kvideoPath isEqualToString:@""]) {            if(!_uploadDataArr){                _uploadDataArr = [[NSMutableArray alloc] init];            }            [_uploadDataArr removeAllObjects];                        AVURLAsset *avAsset = [AVURLAsset URLAssetWithURL:[NSURL URLWithString:kvideoPath] options:nil];            NSString *addname = [[kvideoPath componentsSeparatedByString:@"/"] lastObject];            NSMutableDictionary *objDict = [[NSMutableDictionary alloc] init];            NSData *data = UIImageJPEGRepresentation(videoImgtemp, 1);            if(data){                [objDict setObject:data forKey:@"header"];            }            [objDict setObject:kvideoPath  forKey:@"path"];            [objDict setObject:[NSString stringWithFormat:@"%.2fM",[self getFileSize:kvideoPath]] forKey:@"type"];            [objDict setObject:addname forKey:@"name"];            [objDict setObject:[NSString stringWithFormat:@"%.f",videoLengthTime]  forKey:@"time"];            [_uploadDataArr addObject:objDict];                        // UI的更新放在主线程            dispatch_async(dispatch_get_main_queue(), ^{                NSDictionary *firstDict = [_uploadDataArr firstObject];                if(firstDict){                    _imgView.image = [UIImage imageWithData:[firstDict objectForKey:@"header"]];                    _titleLab.text = [firstDict objectForKey:@"name"];                    _typeLab.text = [firstDict objectForKey:@"type"];                    NSString *timeStr = [firstDict objectForKey:@"time"];                    if([timeStr intValue] > 0){                        _timeLab.text = [NSString stringWithFormat:@"%@S",timeStr];                    }                }            });        }    }        [self dismissViewControllerAnimated:YES completion:nil];}//获取视频文件的大小,返回的是单位是M。- (CGFloat)getFileSize:(NSString *)path{    NSFileManager *fileManager = [[NSFileManager alloc] init];    float filesize = -1.0;    if ([fileManager fileExistsAtPath:path]) {        NSDictionary *fileDic = [fileManager attributesOfItemAtPath:path error:nil];//获取文件的属性        unsigned long long size = [[fileDic objectForKey:NSFileSize] longLongValue];        filesize = (1.0*size/1024)/1024.0;            }    return filesize;}//获取视频文件的时长。- (CGFloat)getVideoLength:(NSURL *)URL{    NSDictionary *opts = [NSDictionary dictionaryWithObject:[NSNumber numberWithBool:NO]                                                     forKey:AVURLAssetPreferPreciseDurationAndTimingKey];    AVURLAsset *urlAsset = [AVURLAsset URLAssetWithURL:URL options:opts];    float second = 0;    second = urlAsset.duration.value/urlAsset.duration.timescale;    return second;    }//获取本地视频缩略图,网上说需要添加AVFoundation.framework- (UIImage *)getImage:(NSURL *)URL{        AVURLAsset *asset = [[AVURLAsset alloc] initWithURL:URL options:nil];    AVAssetImageGenerator *gen = [[AVAssetImageGenerator alloc] initWithAsset:asset];    gen.appliesPreferredTrackTransform = YES;    CMTime time = CMTimeMakeWithSeconds(0.0, 600);    NSError *error = nil;    CMTime actualTime;    CGImageRef image = [gen copyCGImageAtTime:time actualTime:&actualTime error:&error];    UIImage *thumb = [[UIImage alloc] initWithCGImage:image];    CGImageRelease(image);        return thumb;}@end 
示意图:






0 0
原创粉丝点击