美文网首页开发必用啊
AVFoundation二维码扫描和录制视频

AVFoundation二维码扫描和录制视频

作者: 月咏蝴蝶 | 来源:发表于2016-04-01 17:19 被阅读196次

    之前使用过AVFoundation实现二维码扫描的功能,当初第一次接触这个框架,只是搜索资料,实现功能就草草了事了,最近要实现视频的录制功能,又用到了这个框架,而且发现,步骤跟实现二维码的时候十分相似,所以来总结一下。

    使用AVFoundation拍照和录制视频的一般步骤如下:

    1. 创建AVCaptureSession对象。
    2. 使用AVCaptureDevice的静态方法获得需要使用的设备,例如拍照和录像就需要获得摄像头设备,录音就要获得麦克风设备。
    3. 利用输入设备AVCaptureDevice初始化AVCaptureDeviceInput对象。
    4. 初始化输出数据管理对象,如果要拍照就初始化AVCaptureStillImageOutput对象;如果拍摄视频就初始化AVCaptureMovieFileOutput对象。
    5. 将数据输入对象AVCaptureDeviceInput、数据输出对象AVCaptureOutput添加到媒体会话管理对象AVCaptureSession中。
    6. 创建视频预览图层AVCaptureVideoPreviewLayer并指定媒体会话,添加图层到显示容器中,调用AVCaptureSession的startRuning方法开始捕获。
    7. 将捕获的音频或视频数据输出到指定文件。

    录制视频

    @property (weak, nonatomic) IBOutlet UIView *viewContainer;
    @property (weak, nonatomic) IBOutlet UIButton *videoButton;
    
    @property (strong, nonatomic) AVCaptureSession *captureSession;
    @property (strong, nonatomic) AVCaptureDevice *audioDevice;
    @property (strong, nonatomic) AVCaptureDevice *captureDevice;
    @property (strong, nonatomic) AVCaptureDeviceInput *audioDeviceInput;
    @property (strong, nonatomic) AVCaptureDeviceInput *captureDeviceInput;
    @property (strong, nonatomic) AVCaptureMovieFileOutput *captureMovieOutput; //视频输出流
    @property (strong, nonatomic) AVCaptureVideoPreviewLayer *capturePreviewLayer; // 相机预览化图层
    
        // 初始化会话
        if ([self.captureSession canSetSessionPreset:AVCaptureSessionPreset640x480]) {
            // 设置分辨率
            self.captureSession.sessionPreset = AVCaptureSessionPreset640x480;
        }
        
        // 获取输入数据 视频和音频
        NSError *error;
        self.captureDeviceInput = [[AVCaptureDeviceInput alloc] initWithDevice:self.captureDevice error:&error];
        if (error) {
            NSLog(@"Error Description:%@", error.localizedDescription);
        }
    
        self.audioDeviceInput = [[AVCaptureDeviceInput alloc] initWithDevice:self.audioDevice error:&error];
        if (error) {
            NSLog(@"Error Description:%@", error.localizedDescription);
        }
        
        // 初始化输出对象
        self.captureMovieOutput = [[AVCaptureMovieFileOutput alloc] init];
        
        // 将设备输入添加到会话
        if ([self.captureSession canAddInput:self.captureDeviceInput] && [self.captureSession canAddInput:self.audioDeviceInput]) {
            [self.captureSession addInput:self.audioDeviceInput];
            [self.captureSession addInput:self.captureDeviceInput];
            
            AVCaptureConnection *captureConnection = [self.captureMovieOutput connectionWithMediaType:AVMediaTypeVideo];
            if ([captureConnection isVideoStabilizationSupported]) {
                captureConnection.preferredVideoStabilizationMode = AVCaptureVideoStabilizationModeAuto;
            }
        }
        
        // 将设备输出添加到会话中
        if ([self.captureSession canAddOutput:self.captureMovieOutput]) {
            [self.captureSession addOutput:self.captureMovieOutput];
        }
        
        // 创建预览化图层
        self.capturePreviewLayer = [[AVCaptureVideoPreviewLayer alloc] initWithSession:self.captureSession];
        CALayer *layer = self.viewContainer.layer;
        self.capturePreviewLayer.frame = layer.bounds;
        // 填充模式
        self.capturePreviewLayer.videoGravity = AVLayerVideoGravityResizeAspectFill;
        [layer insertSublayer:self.capturePreviewLayer below:self.videoButton.layer];
    
    #pragma mark - Getter And Setter
    - (AVCaptureSession *)captureSession{
        if (_captureSession == nil) {
            _captureSession = [[AVCaptureSession alloc] init];
        }
        return _captureSession;
    }
    
    - (AVCaptureDevice *)audioDevice{
        if (_audioDevice == nil) {
            _audioDevice = [[AVCaptureDevice devicesWithMediaType:AVMediaTypeAudio] firstObject];
        }
        return _audioDevice;
    }
    
    - (AVCaptureDevice *)captureDevice{
        if (_captureDevice == nil) {
            NSArray *cameras = [AVCaptureDevice devicesWithMediaType:AVMediaTypeVideo];
            for (AVCaptureDevice *camera in cameras) {
                if ([camera position] == AVCaptureDevicePositionBack) {
                    return camera;
                }
            }
        }
        return _captureDevice;
    }
    

    二维码扫描

        // 初始化捕捉设备(AVCaptureDevice),类型为AVMediaTypeVideo
        AVCaptureDevice *captureDevice = [AVCaptureDevice defaultDeviceWithMediaType:AVMediaTypeVideo];
        // captureDevice创建输出流
        AVCaptureDeviceInput *input = [AVCaptureDeviceInput deviceInputWithDevice:captureDevice error:&error];
        if (!input) {
            NSLog(@"%@",[error localizedDescription]);
            return;
        }
        // 创建媒体数据输出流
        AVCaptureMetadataOutput *output = [[AVCaptureMetadataOutput alloc] init];
        // 实例化捕捉会话
        _caputureSession = [[AVCaptureSession alloc] init];
        // 输入流,输出流添加到会话
        [_caputureSession addInput:input];
        [_caputureSession addOutput:output];
        // 设置代理
        [output setMetadataObjectsDelegate:self queue:dispatch_get_main_queue()];
        // 设置输出媒体数据类型为QRCode
        [output setMetadataObjectTypes:[NSArray arrayWithObjects:AVMetadataObjectTypeQRCode,AVMetadataObjectTypeCode39Code, AVMetadataObjectTypeUPCECode, AVMetadataObjectTypeCode39Mod43Code, AVMetadataObjectTypeEAN13Code, AVMetadataObjectTypeEAN8Code, AVMetadataObjectTypeCode93Code, AVMetadataObjectTypeCode128Code, AVMetadataObjectTypeInterleaved2of5Code, nil]];
        // 实例化预览图层
        _videoPreviewLayer = [[AVCaptureVideoPreviewLayer alloc] initWithSession:_caputureSession];
        // 设置图层填充方式
        [_videoPreviewLayer setVideoGravity:AVLayerVideoGravityResizeAspectFill];
    //    _videoPreviewLayer.frame = _viewPreview.layer.bounds;
        _videoPreviewLayer.frame = [UIScreen mainScreen].bounds;
        // 添加到预览图层
        [_viewPreview.layer addSublayer:_videoPreviewLayer];
        // 扫描范围
    //    CGSize size = _viewPreview.bounds.size;
        CGSize size = [UIScreen mainScreen].bounds.size;
        CGRect cropRect = CGRectMake(_videoPreviewLayer.bounds.size.width/2 - (105/375.0)*SCREEN_WIDTH, (200/667.5)*SCREEN_HEIGHT, (210/375.0)*SCREEN_WIDTH, (210/667.5)*SCREEN_HEIGHT);
        [output setRectOfInterest:CGRectMake(cropRect.origin.y/size.height, cropRect.origin.x/size.width, cropRect.size.height/size.height, cropRect.size.width/size.width)];
        // 扫描框
        _boxView = [[UIView alloc] initWithFrame:_videoPreviewLayer.frame];
        _boxView.backgroundColor = [UIColor clearColor];
        UIImageView *scanView = [[UIImageView alloc] initWithFrame:_boxView.frame];
        scanView.image = [UIImage imageNamed:@"device_QR_scanning"];
        [_boxView addSubview:scanView];
        [_viewPreview addSubview:_boxView];
        // 开始扫描
        [_caputureSession startRunning];
    

    相关文章

      网友评论

      • 27792e7e0abd:谢谢了,已经保存,用到会调出来认真看

      本文标题:AVFoundation二维码扫描和录制视频

      本文链接:https://www.haomeiwen.com/subject/dfeylttx.html