2011-05-13 45 views
15

Tôi đang cố gắng kết hợp video, đến từ máy ảnh với hình ảnh tĩnh (watermarking).Kết hợp video với hình ảnh tĩnh trong CALayer bằng cách sử dụng AVVideoCompositionCoreAnimationTool

Tôi đã kiểm tra các câu hỏi/câu trả lời ở đây và một số ví dụ, bao gồm WWDC AVEditDemo từ Apple và kết thúc bằng mã sau. Thật không may, video đã xuất không chứa lớp có hình ảnh. Bất kỳ ý tưởng nào?

- (void)imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary *)info { 

/// incoming video 
NSURL *videoURL = [info valueForKey:UIImagePickerControllerMediaURL]; 

/// UIImage into CALayer 
UIImage *myImage = [UIImage imageNamed:@"m1h.png"]; 
CALayer *aLayer = [CALayer layer]; 
aLayer.contents = (id)myImage.CGImage; 

AVURLAsset* url = [AVURLAsset URLAssetWithURL:videoURL options:nil]; 
AVMutableComposition *videoComposition = [AVMutableComposition composition]; 
NSError *error; 
NSFileManager *fileManager = [NSFileManager defaultManager]; 

AVMutableCompositionTrack *compositionVideoTrack = [videoComposition addMutableTrackWithMediaType:AVMediaTypeVideo preferredTrackID:kCMPersistentTrackID_Invalid]; 
AVAssetTrack *clipVideoTrack = [[url tracksWithMediaType:AVMediaTypeVideo] objectAtIndex:0]; 
[compositionVideoTrack insertTimeRange:CMTimeRangeMake(kCMTimeZero, [url duration]) ofTrack:clipVideoTrack atTime:kCMTimeZero error:&error]; 

AVMutableVideoComposition* videoComp = [[AVMutableVideoComposition videoComposition] retain]; 
videoComp.renderSize = CGSizeMake(640, 480); 
videoComp.frameDuration = CMTimeMake(1, 30); 
videoComp.animationTool = [AVVideoCompositionCoreAnimationTool videoCompositionCoreAnimationToolWithAdditionalLayer:aLayer asTrackID:2]; 


/// instruction 
AVMutableVideoCompositionInstruction *instruction = [AVMutableVideoCompositionInstruction videoCompositionInstruction]; 
instruction.timeRange = CMTimeRangeMake(kCMTimeZero, CMTimeMakeWithSeconds(60, 30)); 
AVMutableVideoCompositionLayerInstruction* layerInstruction = [AVMutableVideoCompositionLayerInstruction videoCompositionLayerInstructionWithAssetTrack:clipVideoTrack]; 
instruction.layerInstructions = [NSArray arrayWithObject:layerInstruction]; 
videoComp.instructions = [NSArray arrayWithObject: instruction]; 

/// outputs 
NSString *filePath = nil; 
filePath = [NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES) objectAtIndex:0]; 
filePath = [filePath stringByAppendingPathComponent:@"temp.mov"]; 
NSLog(@"exporting to: %@", filePath); 
if ([fileManager fileExistsAtPath:filePath]) 
{ 
     BOOL success = [fileManager removeItemAtPath:filePath error:&error]; 
     if (!success) NSLog(@"FM error: %@", [error localizedDescription]); 
} 

/// exporting 
AVAssetExportSession *exporter; 
exporter = [[AVAssetExportSession alloc] initWithAsset:videoComposition presetName:AVAssetExportPresetHighestQuality] ; 
exporter.videoComposition = videoComp; 
exporter.outputURL=[NSURL fileURLWithPath:filePath]; 
exporter.outputFileType=AVFileTypeQuickTimeMovie; 

[statusLabel setText:@"processing..."]; 

[exporter exportAsynchronouslyWithCompletionHandler:^(void){ 
    switch (exporter.status) { 
     case AVAssetExportSessionStatusFailed: 
      NSLog(@"exporting failed"); 
      break; 
     case AVAssetExportSessionStatusCompleted: 
      NSLog(@"exporting completed"); 
      UISaveVideoAtPathToSavedPhotosAlbum(filePath, self, @selector(video:didFinishSavingWithError:contextInfo:), NULL); 
      break; 
     case AVAssetExportSessionStatusCancelled: 
      NSLog(@"export cancelled"); 
      break; 
    } 
}]; 

}

Trả lời

10

Sau khi chơi xung quanh tôi đã kết thúc với một cái gì đó như thế này trong một bổ sung vào mã ở trên, cũng thay đổi phương pháp sử dụng để videoCompositionCoreAnimationToolWithPostProcessingAsVideoLayer:

CALayer *parentLayer = [CALayer layer]; 
CALayer *videoLayer = [CALayer layer]; 
parentLayer.frame = CGRectMake(0, 0, videoSize.width, videoSize.height); 
videoLayer.frame = CGRectMake(0, 0, videoSize.width, videoSize.height); 
[parentLayer addSublayer:videoLayer]; 
[parentLayer addSublayer:aLayer]; 
videoComp.animationTool = [AVVideoCompositionCoreAnimationTool videoCompositionCoreAnimationToolWithPostProcessingAsVideoLayer:videoLayer inLayer:parentLayer]; 

Hy vọng nó sẽ giúp ai đó.

+2

Tôi gặp một vấn đề tương tự (xem [ở đây] (http://stackoverflow.com/questions/6749216/how- để đúng-xuất-cal-on-top-of-avmutablecomposition-với-avassetexports)) nhưng một cái gì đó đi sai. Bạn có nghĩ rằng bạn có thể giúp tôi? –

2

tôi đã làm việc này! heres mã! tôi không viết nhiều nhất, tôi chỉ chỉnh sửa một số, nhưng vấn đề duy nhất là bản thân video được xoay cho cảnh quan ở chế độ dọc? và sau đó trong cảnh quay video chân dung của nó, nhưng hình ảnh là bên phải lên!

CALayer *aLayer = [CALayer layer]; 
    aLayer.frame = CGRectMake(5, 0, 320, 480); 
    aLayer.bounds = CGRectMake(5, 0, 320, 480); 
    aLayer.contents = (id) [UIImage imageNamed:@"image.png"].CGImage; 
    aLayer.opacity = 0.5; 
    aLayer.backgroundColor = [UIColor clearColor].CGColor; 
    NSURL *url = [NSURL fileURLWithPath:[urlsOfVideos objectAtIndex:self.pageControl.currentPage]]; 
    AVURLAsset *asset = [AVURLAsset URLAssetWithURL:url options:nil]; 
    cmp = [AVMutableComposition composition]; 

    AVMutableCompositionTrack *trackA = [cmp addMutableTrackWithMediaType:AVMediaTypeVideo preferredTrackID:kCMPersistentTrackID_Invalid]; 
    AVAssetTrack *sourceVideoTrack = [[asset tracksWithMediaType:AVMediaTypeVideo] objectAtIndex:0]; 
    [trackA insertTimeRange:CMTimeRangeMake(kCMTimeZero, [asset duration]) ofTrack:sourceVideoTrack atTime:kCMTimeZero error:nil] ; 

    animComp = [AVMutableVideoComposition videoComposition]; 
    animComp.renderSize = CGSizeMake(320, 480); 
    animComp.frameDuration = CMTimeMake(1,30); 
    CALayer *parentLayer = [CALayer layer]; 
    CALayer *videoLayer = [CALayer layer]; 
    parentLayer.frame = CGRectMake(0, 0, 320, 480); 
    videoLayer.frame = CGRectMake(0, 0, 320, 480); 
    [parentLayer addSublayer:videoLayer]; 
    [parentLayer addSublayer:aLayer]; 
    animComp.animationTool = [AVVideoCompositionCoreAnimationTool videoCompositionCoreAnimationToolWithPostProcessingAsVideoLayer:videoLayer inLayer:parentLayer]; 
    AVMutableVideoCompositionInstruction *instruction = [AVMutableVideoCompositionInstruction videoCompositionInstruction]; 
    instruction.timeRange = CMTimeRangeMake(kCMTimeZero, [asset duration]); 
    AVMutableVideoCompositionLayerInstruction *layerInstruction = [AVMutableVideoCompositionLayerInstruction videoCompositionLayerInstructionWithAssetTrack:trackA]; 
    //[layerInstruction setTrackID:2]; 
    [layerInstruction setOpacity:1.0 atTime:kCMTimeZero]; 
    instruction.layerInstructions = [NSArray arrayWithObject:layerInstruction] ; 
    animComp.instructions = [NSArray arrayWithObject:instruction]; 
    [self exportMovie:self]; 

và đây là mã xuất khẩu

-(IBAction) exportMovie:(id)sender{ 
NSArray *docPaths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES); 
NSString *tempPath = [docPaths objectAtIndex:0]; 
NSLog(@"Temp Path: %@",tempPath); 

NSString *fileName = [NSString stringWithFormat:@"%@/output-anot.MOV",tempPath]; 
NSFileManager *fileManager = [NSFileManager defaultManager] ; 
if([fileManager fileExistsAtPath:fileName ]){ 
    //NSError *ferror = nil ; 
    //BOOL success = [fileManager removeItemAtPath:fileName error:&ferror]; 
} 

NSURL *exportURL = [NSURL fileURLWithPath:fileName]; 

AVAssetExportSession *exporter = [[AVAssetExportSession alloc] initWithAsset:cmp presetName:AVAssetExportPresetHighestQuality] ; 
exporter.outputURL = exportURL; 
exporter.videoComposition = animComp; 
exporter.outputFileType= AVFileTypeQuickTimeMovie; 
[exporter exportAsynchronouslyWithCompletionHandler:^(void){ 
    switch (exporter.status) { 
     case AVAssetExportSessionStatusFailed:{ 
      NSLog(@"Fail"); 
      break; 
     } 
     case AVAssetExportSessionStatusCompleted:{ 
      NSLog(@"Success"); 
      break; 
     } 

     default: 
      break; 
    } 
}]; 

}

+9

không nên hình ảnh của bạn là tits.png? –

+1

@NicolasManzini no, trong tài liệu táo nó nói boobs.png – NSGodMode

+0

LMFAO. Lỗi của tôi. Mã này đã được sử dụng trong một dự án tôi đã làm việc cho một công ty và tôi chỉ sao chép/dán nó mà không kiểm tra nội dung. Ôi trơi. – Maximilian

Các vấn đề liên quan