利用AVFoundation實現Blink拍照和錄像的功能

jopen 9年前發布 | 3K 次閱讀 Objective-C IOS

github代碼

前幾天偶然發現一個app叫Blink,閑來無事,純當練手,于是就嘗試下自己實現它的功能.
頁面都挺簡單的

1.打開相機

- (void)openCamera:(AVCaptureDevicePosition)cameraPostion {
    BOOL hasCamera = ([[AVCaptureDevice devices] count] > );
    if (hasCamera) {
        AVCaptureSession *session = [[AVCaptureSession alloc] init];
        session.sessionPreset = AVCaptureSessionPresetHigh;
       
        AVCaptureVideoPreviewLayer *captureVideoPreviewLayer = [[AVCaptureVideoPreviewLayer alloc] initWithSession:session];
        [captureVideoPreviewLayer setVideoGravity:AVLayerVideoGravityResizeAspectFill];
        [captureVideoPreviewLayer setFrame:self.cameraImageView.bounds];
        [self.cameraImageView.layer addSublayer:captureVideoPreviewLayer];
       
        AVCaptureDevice *device = [self getCamera:cameraPostion];
        NSError *error = nil;
       
        AVCaptureDeviceInput *input = [AVCaptureDeviceInput deviceInputWithDevice:device error:&error];
        [session addInput:input];
       
        stillImageOutput = [[AVCaptureStillImageOutput alloc] init];
        NSDictionary *outputSettings = @{ AVVideoCodecKey : AVVideoCodecJPEG};
        [stillImageOutput setOutputSettings:outputSettings];
        [session addOutput:stillImageOutput];
       
        movieOutput = [[AVCaptureMovieFileOutput alloc] init];
        [session addOutput:movieOutput];
       
        [session startRunning];
    }
}

- (AVCaptureDevice *)getCamera:(AVCaptureDevicePosition)cameraPostion {
    NSArray *cameras = [AVCaptureDevice devicesWithMediaType:AVMediaTypeVideo];
    for (AVCaptureDevice *device in cameras) {
        if (device.position == cameraPostion)
            return device;
    }
    return [AVCaptureDevice defaultDeviceWithMediaType:AVMediaTypeVideo];
}

2.獲取靜態圖片

- (void)captureNow {
    AVCaptureConnection *videoConnection = nil;
    for (AVCaptureConnection *connection in stillImageOutput.connections) {
        for (AVCaptureInputPort *port in [connection inputPorts]) {
            if ([[port mediaType] isEqual:AVMediaTypeVideo] ) {
                videoConnection = connection;
                break;
            }
        }
        if (videoConnection) { break; }
    }
    // 取靜態圖片
    [stillImageOutput captureStillImageAsynchronouslyFromConnection:videoConnection
              completionHandler: ^(CMSampleBufferRef imageSampleBuffer, NSError *error) {
                  NSData *imageData = [AVCaptureStillImageOutput jpegStillImageNSDataRepresentation:imageSampleBuffer];
                  NSData *compressedData = [imageData gzippedDataWithCompressionLevel:1.0];
                  NSData *outputData = [compressedData gunzippedData];
                  UIImage *imageT = [[UIImage alloc] initWithData:outputData];
                  _testImageView.image = imageT;
                  _testImageView.hidden = NO;
                  NSFileManager *fileManager = [NSFileManager defaultManager];
                  NSString *filePath = [[NSString alloc] initWithFormat:@"%@%@", NSTemporaryDirectory(),@"main.png"];
                  [fileManager createFileAtPath:filePath contents:imageData attributes:nil];
                 
                  NSString *zipFile = [[NSString alloc] initWithFormat:@"%@%@", NSTemporaryDirectory(),@"main.zip"];
                  ZipArchive *za = [[ZipArchive alloc] init];
                  [za CreateZipFile2:zipFile];
                  [za addFileToZip:filePath newname:@"main.png"];
              }];
}

3.錄像和播放錄像

- (IBAction)beginRecord:(id)sender {
    [movieOutput startRecordingToOutputFileURL:[self fileURLWithName:@"main.mp4"] recordingDelegate:self];
}

- (void)stopRecord {
    [movieOutput stopRecording];
}

- (void)captureOutput:(AVCaptureFileOutput *)captureOutput
        didFinishRecordingToOutputFileAtURL:(NSURL *)outputFileURL
              fromConnections:(NSArray *)connections
                        error:(NSError *)error {
    BOOL recordedSuccessfully = YES;
    if (error == nil) {
        [self playVideo:outputFileURL];
    }
    if ([error code] != noErr) {
        id value = [[error userInfo] objectForKey:AVErrorRecordingSuccessfullyFinishedKey];
        if (value) {
            recordedSuccessfully = [value boolValue];
           
        }
    }
}

- (void)playVideo:(NSURL *)url {
    AVPlayer *player = [AVPlayer playerWithURL:url];
    playerLayer = [AVPlayerLayer playerLayerWithPlayer:player];
   
    playerLayer.frame = CGRectMake(, , 160, 284);
    playerLayer.position = self.view.center;
    [self.view.layer addSublayer:playerLayer];
   
    playerLayer.masksToBounds = YES;
    playerLayer.cornerRadius = 20;
    playerLayer.borderWidth = 1;
    playerLayer.borderColor = [UIColor grayColor].CGColor;
   
    [player play];
    [[NSNotificationCenter defaultCenter]
                         addObserver:self
                         selector:@selector(removePlayer)
                         name:AVPlayerItemDidPlayToEndTimeNotification
                         object:nil];
}

- (void)removePlayer {
    [playerLayer removeFromSuperlayer];
}

看了下它的網絡數據格式方面,Blink主要是打包成zip文件,里面包含json,mp4,png文件.
等有空了,把服務器也寫一下,或者誰有興趣可以把它的服務器實現下.

當然Blink還有一些添加好友,分享等的功能,這些細節還是比較好實現的.
 本文由用戶 jopen 自行上傳分享,僅供網友學習交流。所有權歸原作者,若您的權利被侵害,請聯系管理員。
 轉載本站原創文章,請注明出處,并保留原始鏈接、圖片水印。
 本站是一個以用戶分享為主的開源技術平臺,歡迎各類分享!