1. 程式人生 > >iOS 二維碼 2

iOS 二維碼 2

//

//  SYQRCodeViewController.m

//  SYQRCodeDemo

//

//  Created by sunbb on 15-1-9.

//  Copyright (c) 2015 SY. All rights reserved.

//

#import "SYQRCodeViewController.h"

#import <AVFoundation/AVFoundation.h>

//裝置寬//座標

#define kDeviceWidth [UIScreen mainScreen].bounds.size.width

#define KDeviceHeight [UIScreen mainScreen].bounds.size.height

#define KDeviceFrame [UIScreen mainScreen].bounds

staticconstfloat kLineMinY = 185;

staticconstfloat kLineMaxY = 385;

staticconstfloat kReaderViewWidth = 200;

staticconstfloat kReaderViewHeight = 200;

@interface SYQRCodeViewController () <AVCaptureMetadataOutputObjectsDelegate>

@property

(nonatomic, strong) AVCaptureSession *qrSession;//回話

@property (nonatomic, strong) AVCaptureVideoPreviewLayer *qrVideoPreviewLayer;//讀取

@property (nonatomic, strong) UIImageView *line;//互動線

@property (nonatomic, strong) NSTimer *lineTimer;//互動線控制

@end

@implementation SYQRCodeViewController

- (void

)viewDidLoad

{

    [superviewDidLoad];

// Do any additional setup after loading the view.

self.view.backgroundColor = [UIColorwhiteColor];

    [selfinitUI];

    [selfsetOverlayPickerView];

    [selfstartSYQRCodeReading];

    [selfinitTitleView];

    [selfcreateBackBtn];

}

- (void)dealloc

{

if (_qrSession) {

        [_qrSessionstopRunning];

_qrSession = nil;

    }

if (_qrVideoPreviewLayer) {

_qrVideoPreviewLayer = nil;

    }

if (_line) {

_line = nil;

    }

if (_lineTimer)

    {

        [_lineTimerinvalidate];

_lineTimer = nil;

    }

}

- (void)initTitleView

{

UIView *bgView = [[UIViewalloc] initWithFrame:CGRectMake(0,0,kDeviceWidth, 64)];

    bgView.backgroundColor = [UIColorcolorWithRed:62.0/255green:199.0/255blue:153.0/255alpha:1.0];

    [self.viewaddSubview:bgView];

UILabel *titleLab = [[UILabelalloc] initWithFrame:CGRectMake((kDeviceWidth - 40) / 2.0, 28, 40, 20)];

//scanCropView.image=[UIImage imageNamed:@""];

//titleLab.layer.borderColor = [UIColor greenColor].CGColor;

//titleLab.layer.borderWidth = 2.0;

//titleLab.backgroundColor = [UIColor colorWithRed:62.0/255 green:199.0/255 blue:153.0/255 alpha:1.0];

    titleLab.text = @"掃題";

    titleLab.shadowColor = [UIColorlightGrayColor];

    titleLab.shadowOffset = CGSizeMake(0, - 1);

    titleLab.font = [UIFontboldSystemFontOfSize:18.0];

    titleLab.textColor = [UIColorwhiteColor];

    titleLab.textAlignment = NSTextAlignmentCenter;

    [self.viewaddSubview:titleLab];

}

- (void)createBackBtn

{

UIButton *btn = [UIButtonbuttonWithType:UIButtonTypeCustom];

    [btn setFrame:CGRectMake(20, 28, 60, 24)];

    [btn setImage:[UIImageimageNamed:@"bar_back"] forState:UIControlStateNormal];

    [btn addTarget:selfaction:@selector(cancleSYQRCodeReading) forControlEvents:UIControlEventTouchUpInside];

    [self.viewaddSubview:btn];

}

- (void)initUI

{

AVCaptureDevice *device = [AVCaptureDevicedefaultDeviceWithMediaType:AVMediaTypeVideo];

//攝像頭判斷

NSError *error = nil;

AVCaptureDeviceInput *input = [AVCaptureDeviceInputdeviceInputWithDevice:device error:&error];

if (error)

    {

NSLog(@"沒有攝像頭-%@", error.localizedDescription);

return;

    }

//設定輸出(Metadata元資料)

AVCaptureMetadataOutput *output = [[AVCaptureMetadataOutputalloc] init];

//設定輸出的代理

//使用主執行緒佇列,相應比較同步,使用其他佇列,相應不同步,容易讓使用者產生不好的體驗

    [output setMetadataObjectsDelegate:selfqueue:dispatch_get_main_queue()];

    [output setRectOfInterest:[selfgetReaderViewBoundsWithSize:CGSizeMake(kReaderViewWidth, kReaderViewHeight)]];

//拍攝會話

AVCaptureSession *session = [[AVCaptureSessionalloc] init];

// 讀取質量,質量越高,可讀取小尺寸的二維碼

if ([session canSetSessionPreset:AVCaptureSessionPreset1920x1080])

    {

        [session setSessionPreset:AVCaptureSessionPreset1920x1080];

    }

elseif ([session canSetSessionPreset:AVCaptureSessionPreset1280x720])

    {

        [session setSessionPreset:AVCaptureSessionPreset1280x720];

    }

else

    {

        [session setSessionPreset:AVCaptureSessionPresetPhoto];

    }

if ([session canAddInput:input])

    {

        [session addInput:input];

    }

if ([session canAddOutput:output])

    {

        [session addOutput:output];

    }

//設定輸出的格式

//一定要先設定會話的輸出為output之後,再指定輸出的元資料型別

    [output setMetadataObjectTypes:@[AVMetadataObjectTypeQRCode]];

//設定預覽圖層

AVCaptureVideoPreviewLayer *preview = [AVCaptureVideoPreviewLayerlayerWithSession:session];

//設定preview圖層的屬性

//preview.borderColor = [UIColor redColor].CGColor;

//preview.borderWidth = 1.5;

    [preview setVideoGravity:AVLayerVideoGravityResizeAspectFill];

//設定preview圖層的大小

    preview.frame = self.view.layer.bounds;

//[preview setFrame:CGRectMake(0, 0, kDeviceWidth, KDeviceHeight)];

//將圖層新增到檢視的圖層

    [self.view.layerinsertSublayer:preview atIndex:0];

//[self.view.layer addSublayer:preview];

self.qrVideoPreviewLayer = preview;

self.qrSession = session;

}

- (CGRect)getReaderViewBoundsWithSize:(CGSize)asize

{

returnCGRectMake(kLineMinY / KDeviceHeight, ((kDeviceWidth - asize.width) / 2.0) / kDeviceWidth, asize.height / KDeviceHeight, asize.width / kDeviceWidth);

}

- (void)setOverlayPickerView

{

//畫中間的基準線

_line = [[UIImageViewalloc] initWithFrame:CGRectMake((kDeviceWidth - 300) / 2.0, kLineMinY, 300, 12 * 300 / 320.0)];

    [_linesetImage:[UIImageimageNamed:@"QRCodeLine"]];

    [self.viewaddSubview:_line];

//最上部view

UIView* upView = [[UIViewalloc] initWithFrame:CGRectMake(0, 0, kDeviceWidth, kLineMinY)];//80

    upView.alpha = 0.3;

    upView.backgroundColor = [UIColorblackColor];

    [self.viewaddSubview:upView];

//左側的view

UIView *leftView = [[UIViewalloc] initWithFrame:CGRectMake(0, kLineMinY, (kDeviceWidth - kReaderViewWidth) / 2.0, kReaderViewHeight)];

    leftView.alpha = 0.3;

    leftView.backgroundColor = [UIColorblackColor];

    [self.viewaddSubview:leftView];

//右側的view

UIView *rightView = [[UIViewalloc] initWithFrame:CGRectMake(kDeviceWidth - CGRectGetMaxX(leftView.frame), kLineMinY, CGRectGetMaxX(leftView.frame), kReaderViewHeight)];

    rightView.alpha = 0.3;

    rightView.backgroundColor = [UIColorblackColor];

    [self.viewaddSubview:rightView];

CGFloat space_h = KDeviceHeight - kLineMaxY;

//底部view

UIView *downView = [[UIViewalloc] initWithFrame:CGRectMake(0, kLineMaxY, kDeviceWidth, space_h)];

    downView.alpha = 0.3;

    downView.backgroundColor = [UIColorblackColor];

    [self.viewaddSubview:downView];

//四個邊角

UIImage *cornerImage = [UIImageimageNamed:@"QRCodeTopLeft"];

//左側的view

UIImageView *leftView_image = [[UIImageViewalloc] initWithFrame:CGRectMake(CGRectGetMaxX(leftView.frame) - cornerImage.size.width / 2.0, CGRectGetMaxY(upView.frame) - cornerImage.size.height / 2.0, cornerImage.size.width, cornerImage.size.height)];

    leftView_image.image = cornerImage;

    [self.viewaddSubview:leftView_image];

    cornerImage = [UIImageimageNamed:@"QRCodeTopRight"];

//右側的view

UIImageView *rightView_image = [[UIImageViewalloc] initWithFrame:CGRectMake(CGRectGetMinX(rightView.frame) - cornerImage.size.width / 2.0, CGRectGetMaxY(upView.frame) - cornerImage.size.height / 2.0, cornerImage.size.width, cornerImage.size.height)];

    rightView_image.image = cornerImage;

    [self.viewaddSubview:rightView_image];

    cornerImage = [UIImageimageNamed:@"QRCodebottomLeft"];

//底部view

UIImageView *downView_image = [[UIImageViewalloc] initWithFrame:CGRectMake(CGRectGetMaxX(leftView.frame) - cornerImage.size.width / 2.0, CGRectGetMinY(downView.frame) - cornerImage.size.height / 2.0, cornerImage.size.width, cornerImage.size.height)];

    downView_image.image = cornerImage;

//downView.backgroundColor = [UIColor blackColor];

    [self.viewaddSubview:downView_image];

    cornerImage = [UIImageimageNamed:@"QRCodebottomRight"];

UIImageView *downViewRight_image = [[UIImageViewalloc] initWithFrame:CGRectMake(CGRectGetMinX(rightView.frame) - cornerImage.size.width / 2.0, CGRectGetMinY(downView.frame) - cornerImage.size.height / 2.0, cornerImage.size.width, cornerImage.size.height)];

    downViewRight_image.image = cornerImage;

//downView.backgroundColor = [UIColor blackColor];

    [self.viewaddSubview:downViewRight_image];

//說明label

UILabel *labIntroudction = [[UILabelalloc] init];

    labIntroudction.backgroundColor = [UIColorclearColor];

    labIntroudction.frame = CGRectMake(CGRectGetMaxX(leftView.frame), CGRectGetMinY(downView.frame) + 25, kReaderViewWidth, 20);

    labIntroudction.textAlignment = NSTextAlignmentCenter;

    labIntroudction.font = [UIFontboldSystemFontOfSize:13.0];

    labIntroudction.textColor = [UIColorwhiteColor];

    labIntroudction.text = @"將二維碼置於框內,即可自動掃描";

    [self.viewaddSubview:labIntroudction];

UIView *scanCropView = [[UIViewalloc] initWithFrame:CGRectMake(CGRectGetMaxX(leftView.frame) - 1,kLineMinY,self.view.frame.size.width - 2 * CGRectGetMaxX(leftView.frame) + 2, kReaderViewHeight + 2)];

    scanCropView.layer.borderColor = [UIColorgreenColor].CGColor;

    scanCropView.layer.borderWidth = 2.0;

    [self.viewaddSubview:scanCropView];

}

#pragma mark -

#pragma mark 輸出代理方法

//此方法是在識別到QRCode,並且完成轉換

//如果QRCode的內容越大,轉換需要的時間就越長

- (void)captureOutput:(AVCaptureOutput *)captureOutput didOutputMetadataObjects:(NSArray *)metadataObjects fromConnection:(AVCaptureConnection *)connection

{

//掃描結果

if (metadataObjects.count > 0)

    {

        [selfstopSYQRCodeReading];

AVMetadataMachineReadableCodeObject *obj = metadataObjects[0];

if (obj.stringValue && ![obj.stringValueisEqualToString:@""] && obj.stringValue.length > 0)

        {

NSLog(@"---------%@",obj.stringValue);

if ([obj.stringValuecontainsString:@"http"])

            {

if (self.SYQRCodeSuncessBlock) {

self.SYQRCodeSuncessBlock(self,obj.stringValue);

                }

            }

else

            {

if (self.SYQRCodeFailBlock) {

self.SYQRCodeFailBlock(self);

                }

            }

        }

else

        {

if (self.SYQRCodeFailBlock) {

self.SYQRCodeFailBlock(self);

            }

        }

    }

else

    {

if (self.SYQRCodeFailBlock) {

self.SYQRCodeFailBlock(self);

        }

    }

}

#pragma mark -

#pragma mark 互動事件

- (void)startSYQRCodeReading

{

_lineTimer = [NSTimerscheduledTimerWithTimeInterval:1.0 / 20target:selfselector:@selector(animationLine) userInfo:nilrepeats