iOS打开摄像头录像调用系统的UI界面,也可以自定义UI界面
UIImagePickerController 这个类可以为大家提供照相的功能,以及图片,视频浏览的功能。
#pragma mark - 摄像头和相册相关的公共类
// 判断设备是否有摄像头
- (BOOL) isCameraAvailable{
return [UIImagePickerController isSourceTypeAvailable:UIImagePickerControllerSourceTypeCamera];
}
// 前面的摄像头是否可用
- (BOOL) isFrontCameraAvailable{
return [UIImagePickerControllerisCameraDeviceAvailable:UIImagePickerControllerCameraDeviceFront];
}
// 后面的摄像头是否可用
- (BOOL) isRearCameraAvailable{
return [UIImagePickerControllerisCameraDeviceAvailable:UIImagePickerControllerCameraDeviceRear];
}
// 判断是否支持某种多媒体类型:拍照,视频
- (BOOL) cameraSupportsMedia:(NSString *)paramMediaType sourceType:(UIImagePickerControllerSourceType)paramSourceType{
__block BOOL result = NO;
if ([paramMediaType length] == 0){
NSLog(@"Media type is empty.");
return NO;
}
NSArray *availableMediaTypes =[UIImagePickerControlleravailableMediaTypesForSourceType:paramSourceType];
[availableMediaTypes enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL*stop) {
NSString *mediaType = (NSString *)obj;
if ([mediaTypeisEqualToString:paramMediaType]){
result = YES;
*stop= YES;
}
}];
return result;
}
// 检查摄像头是否支持录像
- (BOOL) doesCameraSupportShootingVideos{
return [self cameraSupportsMedia:( NSString *)kUTTypeMoviesourceType:UIImagePickerControllerSourceTypeCamera];
}
// 检查摄像头是否支持拍照
- (BOOL) doesCameraSupportTakingPhotos{
return [self cameraSupportsMedia:( NSString *)kUTTypeImagesourceType:UIImagePickerControllerSourceTypeCamera];
}
#pragma mark - 相册文件选取相关
// 相册是否可用
- (BOOL) isPhotoLibraryAvailable{
return [UIImagePickerController isSourceTypeAvailable:UIImagePickerControllerSourceTypePhotoLibrary];
}
// 是否可以在相册中选择视频
- (BOOL) canUserPickVideosFromPhotoLibrary{
return [self cameraSupportsMedia:( NSString *)kUTTypeMoviesourceType:UIImagePickerControllerSourceTypePhotoLibrary];
}
// 是否可以在相册中选择视频
- (BOOL) canUserPickPhotosFromPhotoLibrary{
return [self cameraSupportsMedia:( NSString *)kUTTypeImagesourceType:UIImagePickerControllerSourceTypePhotoLibrary];
}
#pragma mark - 拍照按钮事件
- (void)ClickControlAction:(id)sender{
// 判断有摄像头,并且支持拍照功能
if ([self isCameraAvailable] && [self doesCameraSupportTakingPhotos]){
// 初始化图片选择控制器
UIImagePickerController *controller = [[UIImagePickerController alloc] init];
[controller setSourceType:UIImagePickerControllerSourceTypeCamera];// 设置类型
// 设置所支持的类型,设置只能拍照,或则只能录像,或者两者都可以
NSString *requiredMediaType = ( NSString *)kUTTypeImage;
NSString *requiredMediaType1 = ( NSString *)kUTTypeMovie;
NSArray *arrMediaTypes=[NSArray arrayWithObjects:requiredMediaType, requiredMediaType1,nil];
[controller setMediaTypes:arrMediaTypes];
// 设置录制视频的质量
[controller setVideoQuality:UIImagePickerControllerQualityTypeHigh];
//设置最长摄像时间
[controller setVideoMaximumDuration:10.f];
[controller setAllowsEditing:YES];// 设置是否可以管理已经存在的图片或者视频
[controller setDelegate:self];// 设置代理
[self.navigationController presentModalViewController:controller animated:YES];
[controller release];
} else {
NSLog(@"Camera is not available.");
}
}
typedef NS_ENUM(NSInteger, UIImagePickerControllerSourceType) {
UIImagePickerControllerSourceTypePhotoLibrary,
UIImagePickerControllerSourceTypeCamera,
UIImagePickerControllerSourceTypeSavedPhotosAlbum
};
// 设置所支持的类型,设置只能拍照,或则只能录像,或者两者都可以
NSString *requiredMediaType = ( NSString *)kUTTypeImage;
NSString *requiredMediaType1 = ( NSString *)kUTTypeMovie;
NSArray *arrMediaTypes=[NSArray arrayWithObjects:requiredMediaType, requiredMediaType1,nil];
[controller setMediaTypes:arrMediaTypes];
#pragma mark - UIImagePickerControllerDelegate 代理方法
// 保存图片后到相册后,调用的相关方法,查看是否保存成功
- (void) imageWasSavedSuccessfully:(UIImage *)paramImage didFinishSavingWithError:(NSError *)paramError contextInfo:(void *)paramContextInfo{
if (paramError == nil){
NSLog(@"Image was saved successfully.");
} else {
NSLog(@"An error happened while saving the image.");
NSLog(@"Error = %@", paramError);
}
}
// 当得到照片或者视频后,调用该方法
-(void)imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary *)info{
NSLog(@"Picker returned successfully.");
NSLog(@"%@", info);
NSString *mediaType = [info objectForKey:UIImagePickerControllerMediaType];
// 判断获取类型:图片
if ([mediaType isEqualToString:( NSString *)kUTTypeImage]){
UIImage *theImage = nil;
// 判断,图片是否允许修改
if ([picker allowsEditing]){
//获取用户编辑之后的图像
theImage = [info objectForKey:UIImagePickerControllerEditedImage];
} else {
// 照片的元数据参数
theImage = [info objectForKey:UIImagePickerControllerOriginalImage];
}
// 保存图片到相册中
SEL selectorToCall = @selector(imageWasSavedSuccessfully:didFinishSavingWithError:contextInfo:);
UIImageWriteToSavedPhotosAlbum(theImage, self,selectorToCall, NULL);
}else if ([mediaType isEqualToString:(NSString *)kUTTypeMovie]){
// 判断获取类型:视频
//获取视频文件的url
NSURL* mediaURL = [info objectForKey:UIImagePickerControllerMediaURL];
//创建ALAssetsLibrary对象并将视频保存到媒体库
// Assets Library 框架包是提供了在应用程序中操作图片和视频的相关功能。相当于一个桥梁,链接了应用程序和多媒体文件。
ALAssetsLibrary *assetsLibrary = [[ALAssetsLibrary alloc] init];
// 将视频保存到相册中
[assetsLibrary writeVideoAtPathToSavedPhotosAlbum:mediaURL
completionBlock:^(NSURL *assetURL,NSError *error) {
if (!error) {
NSLog(@"captured video saved with no error.");
}else{
NSLog(@"error occured while saving the video:%@", error);
}
}];
[assetsLibrary release];
}
[picker dismissModalViewControllerAnimated:YES];
}
// 当用户取消时,调用该方法
- (void)imagePickerControllerDidCancel:(UIImagePickerController *)picker{
[picker dismissModalViewControllerAnimated:YES];
}
#pragma mark - 相册操作
- (void)ClickShowPhotoAction:(id)sender{
if ([self isPhotoLibraryAvailable]){
UIImagePickerController *controller = [[UIImagePickerController alloc]init];
[controller setSourceType:UIImagePickerControllerSourceTypePhotoLibrary];// 设置类型
NSMutableArray *mediaTypes = [[NSMutableArray alloc] init];
if ([self canUserPickPhotosFromPhotoLibrary]){
[mediaTypes addObject:( NSString *)kUTTypeImage];
}
if ([self canUserPickVideosFromPhotoLibrary]){
[mediaTypes addObject:( NSString *)kUTTypeMovie];
}
[controller setMediaTypes:mediaTypes];
[controller setDelegate:self];// 设置代理
[self.navigationController presentModalViewController:controlleranimated:YES];
[controller release];
[mediaTypes release];
}
}
-(void)imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary *)info方法,中的info值,会根据我们操作的类型不同,而产生了不同的数据信息:
当操作的为图片时::
{
UIImagePickerControllerCropRect = "NSRect: {{0, 405}, {2448, 2449}}";
UIImagePickerControllerEditedImage = "";
UIImagePickerControllerMediaMetadata = {
DPIHeight = 72;
DPIWidth = 72;
Orientation = 6;
"{Exif}" = {
ApertureValue = "2.526068811667588";
BrightnessValue = "-0.0709875088566263";
ColorSpace = 1;
DateTimeDigitized = "2013:04:05 16:43:00";
DateTimeOriginal = "2013:04:05 16:43:00";
ExposureMode = 0;
ExposureProgram = 2;
ExposureTime = "0.05882352941176471";
FNumber = "2.4";
Flash = 24;
FocalLenIn35mmFilm = 35;
FocalLength = "4.28";
ISOSpeedRatings = (
400
);
MeteringMode = 5;
PixelXDimension = 3264;
PixelYDimension = 2448;
SceneType = 1;
SensingMethod = 2;
Sharpness = 0;
ShutterSpeedValue = "4.099543917546131";
SubjectArea = (
1631,
1223,
881,
881
);
WhiteBalance = 0;
};
"{TIFF}" = {
DateTime = "2013:04:05 16:43:00";
Make = Apple;
Model = "iPhone 4S";
Software = "5.1.1";
XResolution = 72;
YResolution = 72;
};
};
UIImagePickerControllerMediaType = "public.image";
UIImagePickerControllerOriginalImage = "";
}
{
UIImagePickerControllerMediaType = "public.movie";
UIImagePickerControllerMediaURL = "file://localhost/private/var/mobile/Applications/22A14825-DD7E-48E1-A1D5-2D85B82095B5/tmp/capture-T0x1363a0.tmp.etXfD4/capturedvideo.MOV";
}
================================
1.调用系统的UI界面
要用UIImagePickerController来拍照或者录制视频通常可以分为如下步骤:
1. 创建UIImagePickerController对象。
2. 指定拾取源,平时选择照片时使用的拾取源是照片库或者相簿,此刻需要指定为摄像头类型。
3. 指定摄像头,前置摄像头或者后置摄像头。
4. 设置媒体类型mediaType,注意如果是录像必须设置,如果是拍照此步骤可以省略,因为mediaType默认包含kUTTypeImage(注意媒体类型定义在MobileCoreServices.framework中)
5. 指定捕获模式,拍照或者录制视频。(视频录制时必须先设置媒体类型再设置捕获模式)
6. 展示UIImagePickerController(通常以模态窗口形式打开)。
7. 拍照和录制视频结束后在代理方法中展示/保存照片或视频。
MyViewController.h
#import "GetFilePath.h"
@interface MyViewController () <UINavigationControllerDelegate, UIImagePickerControllerDelegate>
@end
@implementation MyViewController
//触发事件:拍照
- (void)addCamera
{
UIImagePickerController *picker = [[UIImagePickerController alloc] init];
picker.delegate = self;
picker.allowsEditing = YES; //可编辑
//判断是否可以打开照相机
if ([UIImagePickerController isSourceTypeAvailable:UIImagePickerControllerSourceTypeCamera]) {
//摄像头
//UIImagePickerControllerSourceTypeSavedPhotosAlbum:相机胶卷
picker.sourceType = UIImagePickerControllerSourceTypeCamera;
} else { //否则打开照片库
picker.sourceType = UIImagePickerControllerSourceTypePhotoLibrary;
}
[self presentViewController:picker animated:YES completion:nil];
}
//触发事件:录像
- (void)addVideo
{
UIImagePickerController *picker = [[UIImagePickerController alloc] init];
picker.delegate = self;
picker.allowsEditing = YES;
if ([UIImagePickerController isSourceTypeAvailable:UIImagePickerControllerSourceTypeCamera]) {
picker.sourceType = UIImagePickerControllerSourceTypeCamera;
picker.mediaTypes = [UIImagePickerController availableMediaTypesForSourceType:UIImagePickerControllerSourceTypeCamera];
picker.videoQuality = UIImagePickerControllerQualityTypeMedium; //录像质量
picker.videoMaximumDuration = 600.0f; //录像最长时间
picker.mediaTypes = [NSArray arrayWithObjects:@"public.movie", nil];
} else {
UIAlertView *alert = [[UIAlertView alloc] initWithTitle:@"温馨提示" message:@"当前设备不支持录像功能" delegate:self cancelButtonTitle:@"确定" otherButtonTitles:nil];
[alert show];
}
//跳转到拍摄页面
[self presentViewController:picker animated:YES completion:nil];
}
#pragma mark - UIImagePickerControllerDelegate
//拍摄完成后要执行的代理方法
- (void)imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary *)info
{
NSString *mediaType = [info objectForKey:UIImagePickerControllerMediaType];
BOOL success;
NSFileManager *fileManager = [NSFileManager defaultManager];
if ([mediaType isEqualToString:@"public.image"]) {
//得到照片
UIImage *image = [info objectForKey:UIImagePickerControllerOriginalImage];
if ([UIImagePickerController isSourceTypeAvailable:UIImagePickerControllerSourceTypeCamera]) {
//图片存入相册
UIImageWriteToSavedPhotosAlbum(image, nil, nil, nil);
}
NSString *imagePath = [GetFilePath getSavePathWithFileSuffix:@"png"];
success = [fileManager fileExistsAtPath:imagePath];
if (success) {
[fileManager removeItemAtPath:imagePath error:nil];
}
NSData *imageData = UIImagePNGRepresentation(image);
[imageData writeToFile:imagePath atomically:YES]; //写入本地
success = [fileManager fileExistsAtPath:imagePath];
if (success) {
NSLog(@"图片写入成功,image路径:%@",imagePath);
}
} else if ([mediaType isEqualToString:@"public.movie"]) {
NSString *videoPath = [GetFilePath getSavePathWithFileSuffix:@"mov"];
success = [fileManager fileExistsAtPath:videoPath];
if (success) {
[fileManager removeItemAtPath:videoPath error:nil];
}
NSURL *videoURL = [info objectForKey:UIImagePickerControllerMediaURL];
NSData *videlData = [NSData dataWithContentsOfURL:videoURL];
[videlData writeToFile:videoPath atomically:YES]; //写入本地
//存储数据
success = [fileManager fileExistsAtPath:videoPath];
if (success) {
NSLog(@"media 写入成功,video路径:%@",videoPath);
}
}
[self dismissViewControllerAnimated:YES completion:nil];
}
//进入拍摄页面点击取消按钮
- (void)imagePickerControllerDidCancel:(UIImagePickerController *)picker
{
[self dismissViewControllerAnimated:YES completion:nil];
}
GetFilePath.h
#import <Foundation/Foundation.h>
@interface GetFilePath : NSObject
//获取要保存的本地文件路径
+ (NSString *)getSavePathWithFileSuffix:(NSString *)suffix;
//获取录像的缩略图
+ (UIImage *)getVideoThumbnailWithFilePath:(NSString *)filePath;
+ (UIImage *)getImage:(NSString *)filePath;
@end
.m
#import "GetFilePath.h"
#import <MediaPlayer/MediaPlayer.h>
#import <AVFoundation/AVFoundation.h>
@implementation GetFilePath
+ (NSString *)getSavePathWithFileSuffix:(NSString *)suffix
{
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentPath = [paths objectAtIndex:0];
NSDate *date = [NSDate date];
//获取当前时间
NSDateFormatter *dateFormat = [[NSDateFormatter alloc] init];
[dateFormat setDateFormat:@"yyyyMMddHHmmss"];
NSString *curretDateAndTime = [dateFormat stringFromDate:date];
//获取用户userID
NSDictionary *userDic= [[NSUserDefaults standardUserDefaults] objectForKey:UserInformation];
//命名文件
NSString *fileName = [NSString stringWithFormat:@"%@%@.%@",userDic[@"UserID"],curretDateAndTime,suffix];
//指定文件存储路径
NSString *filePath = [documentPath stringByAppendingPathComponent:fileName];
return filePath;
}
+ (UIImage *)getVideoThumbnailWithFilePath:(NSString *)filePath
{
MPMoviePlayerController *moviePlayer = [[MPMoviePlayerController alloc] initWithContentURL:[NSURL fileURLWithPath:filePath]];
moviePlayer.shouldAutoplay = NO;
UIImage *image = [moviePlayer thumbnailImageAtTime:1.0 timeOption:MPMovieTimeOptionNearestKeyFrame];
return image;
}
+ (UIImage *)getImage:(NSString *)filePath
{
NSDictionary *options = [NSDictionary dictionaryWithObject:[NSNumber numberWithBool:NO] forKey:AVURLAssetPreferPreciseDurationAndTimingKey];
NSURL *url = [NSURL fileURLWithPath:filePath];
AVURLAsset *urlAsset = [[AVURLAsset alloc] initWithURL:url options:options];
AVAssetImageGenerator *generator = [AVAssetImageGenerator assetImageGeneratorWithAsset:urlAsset];
generator.appliesPreferredTrackTransform = YES;
generator.maximumSize = CGSizeMake(60, 60);
CGImageRef imageRef = [generator copyCGImageAtTime:CMTimeMake(10, 10) actualTime:NULL error:nil];
UIImage *image = [UIImage imageWithCGImage:imageRef];
return image;
}