实现类似qq扫一扫功能

最近公司项目需要实现一个类似qq扫一扫功能,该功能主要分为三个部分:扫一扫、扫描相册中二维码图片、开灯(我的二维码不是主要功能)

1.扫一扫

iOS7以后,AVFoundation.framework框架支持扫一扫功能,详细代码,可以参考http://www.jianshu.com/p/6b7d54b3f88b

但该博客中的代码只能简单的实现扫一扫功能,周围的背景并不是半透明的。


通过以下代码可以实现中间透明,旁边半透明的效果


-(void)setupBgView{
    self.view.backgroundColor = [UIColor blackColor];
    //绘制扫一扫背景,中间透明,旁边半透明
    UIGraphicsBeginImageContext(self.view.frame.size);
    CGContextRef ctx = UIGraphicsGetCurrentContext();
    CGContextSetRGBFillColor(ctx, 0,0,0,0.5);
    CGRect drawRect =CGRectMake(0, 0, Screen_Width, Screen_height);
    
    //draw the transparent layer
    CGContextFillRect(ctx, drawRect);
    
    //clear the center rect  of the layer
    drawRect = self.scanBg.frame;
    CGContextClearRect(ctx, drawRect);
    
    UIImage* returnimage = UIGraphicsGetImageFromCurrentImageContext();
    UIImageView * img = [[UIImageView alloc] initWithImage:returnimage];
    [self.view addSubview:img];
    UIGraphicsEndImageContext();
}
但以上代码仍然存在一点小问题:这张背景图片是直接盖在最上层,导致扫一扫界面上的图片和文字效果不好(左图)。

 

只需将背景图片移到视图的最上层即可(右图):

    [self.view addSubview:img];
    [self.view sendSubviewToBack:img];

2.扫描相册中二维码图片

在网上寻找了很久,发现AVFoundation.framework框架并不支持扫描相册中二维码图片功能。

于是,开始寻找支持扫描相册中二维码图片的第三方类库,目前只有ZBar和ZXingObjC支持,而前者很久没更新,故而选择后者。

通过以下代码可以实现点击相册,选择图片,获取图片中的二维码信息。

- (IBAction)clickPhotoAlbum:(id)sender 
{
    UIImagePickerController *picker = [[UIImagePickerController alloc] init];
    picker.allowsEditing = YES;
    picker.delegate = self;
    picker.sourceType = UIImagePickerControllerSourceTypePhotoLibrary;
    [self presentViewController:picker animated:YES completion:^{}];
}
#pragma mark - UIImagePickerControllerDelegate
- (void)imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary *)info
{
    UIImage *image = [info objectForKey:@"UIImagePickerControllerEditedImage"];
    [self dismissViewControllerAnimated:YES completion:^{
        [self getURLWithImage:image];
    }
    ];

}
-(void)getURLWithImage:(UIImage *)img{
    
    UIImage *loadImage= img;
    CGImageRef imageToDecode = loadImage.CGImage;
    
    ZXLuminanceSource *source = [[ZXCGImageLuminanceSource alloc] initWithCGImage:imageToDecode];
    ZXBinaryBitmap *bitmap = [ZXBinaryBitmap binaryBitmapWithBinarizer:[ZXHybridBinarizer binarizerWithSource:source]];
    
    NSError *error = nil;
    
    ZXDecodeHints *hints = [ZXDecodeHints hints];
    
    ZXMultiFormatReader *reader = [ZXMultiFormatReader reader];
    ZXResult *result = [reader decode:bitmap
                                hints:hints
                                error:&error];
    if (result) {
        // The coded result as a string. The raw data can be accessed with
        // result.rawBytes and result.length.
        NSString *contents = result.text;
        NSLog(@"contents =%@",contents);
        UIAlertView *alter = [[UIAlertView alloc] initWithTitle:@"解析成功" message:contents delegate:nil cancelButtonTitle:@"确定" otherButtonTitles: nil];
        [alter show];

    } else {
        UIAlertView *alter1 = [[UIAlertView alloc] initWithTitle:@"解析失败" message:nil delegate:nil cancelButtonTitle:@"确定" otherButtonTitles: nil];
        [alter1 show];
    }
}
但,以上代码存在一点小问题,跳转到相册后,选择一张图片,这张图片是可编辑的状态

picker.allowsEditing = YES;
改为
picker.allowsEditing = NO;
结果,闪退。调试发现跳转到以下代码,image为空。

UIImage *image = [info objectForKey:@"UIImagePickerControllerEditedImage"];
打印info,发现info中还有UIImagePickerControllerOriginalImage,将image该为UIImagePickerControllerOriginalImage即可。

UIImage *image = [info objectForKey:@"UIImagePickerControllerOriginalImage"];

3.开灯

这里的开灯其实就是打开手电筒,手电筒也是基于AVFoundation.framework框架,通过以下代码可以实现开灯和关灯功能。

- (IBAction)clickLight:(id)sender {
    AVCaptureDevice *device = [AVCaptureDevice defaultDeviceWithMediaType:AVMediaTypeVideo];
    if ([device hasTorch]) {
        [device lockForConfiguration:nil];
        if(isLedOn){
            //关灯
            [device setTorchMode: AVCaptureTorchModeOff];
        }else{
            //开灯
            [device setTorchMode: AVCaptureTorchModeOn];
        }
        
        [device unlockForConfiguration];
    }
    isLedOn = !isLedOn;
}

但是,光有以上代码是不够的,在离开扫一扫界面时,如果没有关闭手电筒,手电筒一直会是开启的状态。这时,需要添加以下代码,在离开页面时,关闭手电筒。

-(void)viewWillDisappear:(BOOL)animated{
    AVCaptureDevice *device = [AVCaptureDevice defaultDeviceWithMediaType:AVMediaTypeVideo];
    if ([device hasTorch]) {
        [device lockForConfiguration:nil];
        [device setTorchMode: AVCaptureTorchModeOff];
        
        [device unlockForConfiguration];
    }
    isLedOn = NO;
}

以上三部分代码,即可完成类似qq扫一扫功能。



  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值