最近的app项目中遇到了上传视频和图片的问题
上传视频的时候发现一个问题就是 有些视频在相册是方向正确的,但是上传到阿里云之后变得旋转了
就是针对这个问题把压缩和视频旋转一并说下
首先你需要提前获取到PHAsset文件(包含视频的那种)
phAsset; //提前获取
if (phAsset.mediaType == PHAssetMediaTypeVideo || phAsset.mediaSubtypes == PHAssetMediaSubtypePhotoLive) {
PHVideoRequestOptions *options = [[PHVideoRequestOptions alloc] init];
options.version = PHVideoRequestOptionsVersionOriginal;
[[PHImageManager defaultManager] requestAVAssetForVideo:phAsset options:options resultHandler:^(AVAsset *asset, AVAudioMix *audioMix, NSDictionary *info) {
if ([asset isKindOfClass:[AVURLAsset class]]) {
AVURLAsset* urlAsset = (AVURLAsset*)asset;
NSURL *url = urlAsset.URL;
NSData *data = [NSData dataWithContentsOfURL:url];
NSInteger dataSizeNum = data.length /(1024);
NSLog(@"压缩前视频大小是多少::::%ldM", (long)dataSizeNum/1024);
}
NSNumber *number = [NSNumber numberWithInteger:dataSizeNum];
dispatch_async(dispatch_get_main_queue(), ^{
[MBProgressHUD showLoadHUDMsg:@"视频压缩中"];
});
//以下是视频压缩的代码
AVAssetExportSession * session = [[AVAssetExportSession alloc] initWithAsset:asset presetName:AVAssetExportPresetMediumQuality];
//优化网络
session.shouldOptimizeForNetworkUse = YES;
//转换后的格式
//拼接输出文件路径 为了防止同名 可以根据日期拼接名字 或者对名字进行MD5加密
NSString* path = [[NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) lastObject] stringByAppendingPathComponent:@"newVideo.mp4"];
//判断文件是否存在,如果已经存在删除
[[NSFileManager defaultManager] removeItemAtPath:path error:nil];
//设置输出路径
session.outputURL = [NSURL fileURLWithPath:path];
//设置输出类型 这里可以更改输出的类型 具体可以看文档描述
session.outputFileType = AVFileTypeMPEG4;
//判断旋转方向,对于没有旋转的不进行处理了
NSUInteger degrees = [weakSelf degressFromVideoFileWithAsset:asset];
if (degrees != 0) { //需要旋转
session.videoComposition = [weakSelf getVideoComposition:asset];//判断旋转并矫正
}
[session exportAsynchronouslyWithCompletionHandler:^{
//压缩完成
currentData = [NSData dataWithContentsOfURL:session.outputURL];
} else { //压缩失败
// NSLog(@"-------压缩失败%@", session.error)
}];
}]
}
//视频扶正
- (AVMutableVideoComposition *)getVideoComposition:(AVAsset *)asset{
NSArray *tracks = [asset tracksWithMediaType:AVMediaTypeVideo];
AVAssetTrack *videoTrack = [tracks objectAtIndex:0];
CGAffineTransform translateToCenter;
CGAffineTransform mixedTransform;
AVMutableVideoComposition *waterMarkVideoComposition = [AVMutableVideoComposition videoComposition];
waterMarkVideoComposition.frameDuration = CMTimeMake(1, 30);
NSUInteger degrees = [self degressFromVideoFileWithAsset:asset];
if (degrees == 0) { //不需要旋转
} else{
if(degrees == 90){
//顺时针旋转90°
NSLog(@"视频旋转90度,home按键在左");
translateToCenter = CGAffineTransformMakeTranslation(videoTrack.naturalSize.height, 0.0);
mixedTransform = CGAffineTransformRotate(translateToCenter,M_PI_2);
waterMarkVideoComposition.renderSize = CGSizeMake(videoTrack.naturalSize.height,videoTrack.naturalSize.width);
} else if(degrees == 180){
//顺时针旋转180° NSLog(@"视频旋转180度,home按键在上");
translateToCenter = CGAffineTransformMakeTranslation(videoTrack.naturalSize.width, videoTrack.naturalSize.height);
mixedTransform = CGAffineTransformRotate(translateToCenter,M_PI);
waterMarkVideoComposition.renderSize = CGSizeMake(videoTrack.naturalSize.width,videoTrack.naturalSize.height);
} else { //顺时针旋转270° NSLog(@"视频旋转270度,home按键在右");
translateToCenter = CGAffineTransformMakeTranslation(0.0, videoTrack.naturalSize.width);
mixedTransform = CGAffineTransformRotate(translateToCenter,M_PI_2*3.0);
waterMarkVideoComposition.renderSize = CGSizeMake(videoTrack.naturalSize.height,videoTrack.naturalSize.width);
}
AVMutableVideoCompositionInstruction *roateInstruction = [AVMutableVideoCompositionInstruction videoCompositionInstruction];
roateInstruction.timeRange = CMTimeRangeMake(kCMTimeZero, [asset duration]);
AVMutableVideoCompositionLayerInstruction *roateLayerInstruction = [AVMutableVideoCompositionLayerInstruction videoCompositionLayerInstructionWithAssetTrack:videoTrack];
[roateLayerInstruction setTransform:mixedTransform atTime:kCMTimeZero];
roateInstruction.layerInstructions = @[roateLayerInstruction];
//将视频方向旋转加入到视频处理中
waterMarkVideoComposition.instructions = @[roateInstruction];
}
return waterMarkVideoComposition;
}
//以下是判断方向的
-(NSUInteger)degressFromVideoFileWithAsset:(AVAsset*)asset {
NSUInteger degress = 0;
NSArray *tracks = [asset tracksWithMediaType:AVMediaTypeVideo];
if([tracks count] > 0) {
AVAssetTrack *videoTrack = [tracks objectAtIndex:0];
CGAffineTransform t = videoTrack.preferredTransform;
if(t.a == 0 && t.b == 1.0 && t.c == -1.0 && t.d == 0){
// Portrait
degress = 90;
}else if(t.a == 0 && t.b == -1.0 && t.c == 1.0 && t.d == 0){
// PortraitUpsideDown
degress = 270;
}else if(t.a == 1.0 && t.b == 0 && t.c == 0 && t.d == 1.0){
// LandscapeRight
degress = 0;
}else if(t.a == -1.0 && t.b == 0 && t.c == 0 && t.d == -1.0){
// LandscapeLeft
degress = 180;
}
}
return degress;
}
如有不正之处,望各位大神指出。谢谢。