(committing very old stuff) Generates video
This commit is contained in:
parent
6873b949c5
commit
419d7b68c3
2 changed files with 108 additions and 10 deletions
|
@ -152,6 +152,7 @@
|
|||
ALWAYS_SEARCH_USER_PATHS = NO;
|
||||
CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x";
|
||||
CLANG_CXX_LIBRARY = "libc++";
|
||||
CLANG_ENABLE_MODULES = YES;
|
||||
CLANG_ENABLE_OBJC_ARC = YES;
|
||||
CLANG_WARN_BOOL_CONVERSION = YES;
|
||||
CLANG_WARN_CONSTANT_CONVERSION = YES;
|
||||
|
@ -189,6 +190,7 @@
|
|||
ALWAYS_SEARCH_USER_PATHS = NO;
|
||||
CLANG_CXX_LANGUAGE_STANDARD = "gnu++0x";
|
||||
CLANG_CXX_LIBRARY = "libc++";
|
||||
CLANG_ENABLE_MODULES = YES;
|
||||
CLANG_ENABLE_OBJC_ARC = YES;
|
||||
CLANG_WARN_BOOL_CONVERSION = YES;
|
||||
CLANG_WARN_CONSTANT_CONVERSION = YES;
|
||||
|
|
|
@ -6,16 +6,112 @@
|
|||
// Copyright (c) 2014 Joshua Moerman. All rights reserved.
|
||||
//
|
||||
|
||||
#import <Foundation/Foundation.h>
|
||||
@import Foundation;
|
||||
@import AVFoundation;
|
||||
@import CoreGraphics;
|
||||
#import <complex.h>
|
||||
|
||||
int main(int argc, const char * argv[])
|
||||
{
|
||||
static const size_t w = 1280;
|
||||
static const size_t h = 800;
|
||||
|
||||
double length(double x, double y){
|
||||
return sqrt(x*x + y*y);
|
||||
}
|
||||
|
||||
@interface Generator : NSObject{
|
||||
double* values;
|
||||
}
|
||||
- (void)fillBuffer:(CVPixelBufferRef)buffer;
|
||||
@end
|
||||
|
||||
@implementation Generator
|
||||
|
||||
- (id)init{
|
||||
if(self = [super init]){
|
||||
values = calloc(3*w*h, sizeof(double));
|
||||
for(size_t y = 0; y < h; ++y){
|
||||
for(size_t x = 0; x < w; ++x){
|
||||
values[3*(x + y*w) + 0] = x / (double)(w-1);
|
||||
values[3*(x + y*w) + 1] = y / (double)(h-1);
|
||||
values[3*(x + y*w) + 2] = 0.5;
|
||||
}
|
||||
}
|
||||
}
|
||||
return self;
|
||||
}
|
||||
|
||||
- (void)dealloc{
|
||||
free(values);
|
||||
}
|
||||
|
||||
- (void)fillBuffer:(CVPixelBufferRef)image{
|
||||
for(size_t y = 0; y < h; ++y){
|
||||
for(size_t x = 0; x < w; ++x){
|
||||
for(size_t c = 0; c < 3; ++c){
|
||||
double r = 4.0 - 0.1*length(x - 0.5*w, y - 0.5*h) / length(0.5*w, 0.5*h);
|
||||
double v = values[3*(x + y*w) + c];
|
||||
values[c + 3*(x + y*w)] = r*v*(1.0 - v);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
CVPixelBufferLockBaseAddress(image, 0);
|
||||
UInt32* data = CVPixelBufferGetBaseAddress(image);
|
||||
assert(data);
|
||||
for(size_t y = 0; y < h; ++y){
|
||||
for(size_t x = 0; x < w; ++x){
|
||||
uint8_t bb = 255*values[3*(x + y*w) + 0];
|
||||
uint8_t gb = 255*values[3*(x + y*w) + 1];
|
||||
uint8_t rb = 255*values[3*(x + y*w) + 2];
|
||||
uint8_t ab = 255;
|
||||
data[x + y*1280] = ab | (rb << 8) | (gb << 16) | (bb << 24);
|
||||
}
|
||||
}
|
||||
CVPixelBufferUnlockBaseAddress(image, 0);
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
static void do_it(){
|
||||
[[NSFileManager defaultManager] removeItemAtURL:[NSURL fileURLWithPath:@"test.mov"] error:nil];
|
||||
|
||||
AVAssetWriter* asset = [AVAssetWriter assetWriterWithURL:[NSURL fileURLWithPath:@"test.mov"] fileType:AVFileTypeQuickTimeMovie error:nil];
|
||||
AVAssetWriterInput* assetInput = [AVAssetWriterInput assetWriterInputWithMediaType:AVMediaTypeVideo outputSettings:@{AVVideoCodecKey: AVVideoCodecH264, AVVideoWidthKey: @1280, AVVideoHeightKey: @800}];
|
||||
NSDictionary *sourcePixelBufferAttributesDictionary = [NSDictionary dictionaryWithObjectsAndKeys: [NSNumber numberWithInt:kCVPixelFormatType_32ARGB], kCVPixelBufferPixelFormatTypeKey, nil];
|
||||
AVAssetWriterInputPixelBufferAdaptor* adaptor = [AVAssetWriterInputPixelBufferAdaptor assetWriterInputPixelBufferAdaptorWithAssetWriterInput:assetInput sourcePixelBufferAttributes:sourcePixelBufferAttributesDictionary];
|
||||
assert(asset && assetInput && adaptor && [asset canAddInput:assetInput]);
|
||||
|
||||
[asset addInput:assetInput];
|
||||
[asset startWriting];
|
||||
[asset startSessionAtSourceTime:kCMTimeZero];
|
||||
assert(adaptor.pixelBufferPool);
|
||||
|
||||
Generator* gen = [[Generator alloc] init];
|
||||
|
||||
CMTime duration = CMTimeMake(1, 30);
|
||||
CMTime current = CMTimeMake(0, 30);
|
||||
for(int i = 0; i < 300; ++i){
|
||||
while(!assetInput.readyForMoreMediaData) [NSThread sleepForTimeInterval:0.005];
|
||||
|
||||
CVPixelBufferRef image = nil;
|
||||
CVReturn ret = CVPixelBufferPoolCreatePixelBuffer(kCFAllocatorDefault, adaptor.pixelBufferPool, &image);
|
||||
assert(ret == kCVReturnSuccess && image);
|
||||
|
||||
[gen fillBuffer:image];
|
||||
[adaptor appendPixelBuffer:image withPresentationTime:current];
|
||||
|
||||
CVPixelBufferRelease(image);
|
||||
|
||||
current = CMTimeAdd(current, duration);
|
||||
}
|
||||
|
||||
[assetInput markAsFinished];
|
||||
[asset finishWriting];
|
||||
}
|
||||
|
||||
int main(int argc, const char * argv[]){
|
||||
@autoreleasepool {
|
||||
|
||||
// insert code here...
|
||||
NSLog(@"Hello, World!");
|
||||
|
||||
do_it();
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
|
Reference in a new issue