2

I have the following test code which is supposed to create a video file of a image file in OSX. However altho running successfully the video file is unplayable....

Can anyone think of what i might of done wrong or missed?

- (void)testVideoWriter { NSImage *someImage = [NSImage imageNamed:@"002"]; CGSize size = CGSizeMake(someImage.size.width, someImage.size.height); CMTime frameLength = CMTimeMake(1, 5); CMTime currentTime = kCMTimeZero; NSError *error = nil; //remember to delete video before re-runnign or you will get fails... AVAssetWriter *videoWriter = [[AVAssetWriter alloc] initWithURL:[NSURL fileURLWithPath:@"/Users/petertribe/Desktop/testvideo.mov"] fileType:AVFileTypeMPEG4 error:&error]; NSDictionary *videoSettings = [NSDictionary dictionaryWithObjectsAndKeys:AVVideoCodecH264, AVVideoCodecKey, [NSNumber numberWithInt:size.width ], AVVideoWidthKey, [NSNumber numberWithInt:size.height ], AVVideoHeightKey, nil]; AVAssetWriterInput *writerInput = [AVAssetWriterInput assetWriterInputWithMediaType:AVMediaTypeVideo outputSettings:videoSettings]; NSDictionary *sourcePixelBufferAttributesDictionary = [NSDictionary dictionaryWithObjectsAndKeys: [NSNumber numberWithInt:k32ARGBPixelFormat], kCVPixelBufferPixelFormatTypeKey, nil]; AVAssetWriterInputPixelBufferAdaptor *adaptor = [AVAssetWriterInputPixelBufferAdaptor assetWriterInputPixelBufferAdaptorWithAssetWriterInput:writerInput sourcePixelBufferAttributes:sourcePixelBufferAttributesDictionary]; [videoWriter addInput:writerInput]; [videoWriter startWriting]; [videoWriter startSessionAtSourceTime:kCMTimeZero]; for (int i = 0; i < 100; i++) { CVPixelBufferRef pixel_buffer = [self fastImageFromNSImage:someImage]; while (adaptor.assetWriterInput.readyForMoreMediaData == FALSE) { NSDate *maxDate = [NSDate dateWithTimeIntervalSinceNow:0.1]; [[NSRunLoop currentRunLoop] runUntilDate:maxDate]; } if(![adaptor appendPixelBuffer:pixel_buffer withPresentationTime:currentTime]) { NSLog(@"FAIL"); } else { NSLog(@"Success:%d", i); currentTime = CMTimeAdd(currentTime, frameLength); } CVPixelBufferRelease(pixel_buffer); } [writerInput markAsFinished]; NSLog(@"Done"); } - (CVPixelBufferRef)fastImageFromNSImage:(NSImage *)image { CVPixelBufferRef buffer = NULL; // config size_t width = [image size].width; size_t height = [image size].height; size_t bitsPerComponent = 8; CGColorSpaceRef cs = CGColorSpaceCreateWithName(kCGColorSpaceGenericRGB); CGBitmapInfo bi = kCGImageAlphaNoneSkipFirst; NSDictionary *d = [NSDictionary dictionaryWithObjectsAndKeys:[NSNumber numberWithBool:YES], kCVPixelBufferCGImageCompatibilityKey, [NSNumber numberWithBool:YES], kCVPixelBufferCGBitmapContextCompatibilityKey, nil]; // create pixel buffer CVPixelBufferCreate(kCFAllocatorDefault, width, height, k32ARGBPixelFormat, (__bridge CFDictionaryRef)d, &buffer); CVPixelBufferLockBaseAddress(buffer, 0); void *rasterData = CVPixelBufferGetBaseAddress(buffer); size_t bytesPerRow = CVPixelBufferGetBytesPerRow(buffer); // context to draw in, set to pixel buffer's address CGContextRef ctxt = CGBitmapContextCreate(rasterData, width, height, bitsPerComponent, bytesPerRow, cs, bi); if(ctxt == NULL){ NSLog(@"could not create context"); return NULL; } // draw NSGraphicsContext *nsctxt = [NSGraphicsContext graphicsContextWithGraphicsPort:ctxt flipped:NO]; [NSGraphicsContext saveGraphicsState]; [NSGraphicsContext setCurrentContext:nsctxt]; [image drawAtPoint:NSMakePoint(0, 0) fromRect:NSMakeRect(0, 0, image.size.width, image.size.height) operation:NSCompositeCopy fraction:1]; [NSGraphicsContext restoreGraphicsState]; CVPixelBufferUnlockBaseAddress(buffer, 0); CFRelease(ctxt); return buffer; } 

1 Answer 1

1

Ok, I must of been having a funny few moments, the fix was simple...

just adding

[videoWriter finishWriting]; 

to the end of the testVideoWriter method, fixed the problem

Sign up to request clarification or add additional context in comments.

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.