一些扫描二维码的工作 一般都可以由Zxing库来实现,其使用也是比较方便,有时候在扫描二维码的过程中可能需要开启闪光灯的操作。最近一个项目里使用了Zxing库来实现扫描二维码的操作,其中就需要开启闪光灯。目前手机调用闪光灯的教程在网上一搜有很多,但是在使用Zxing扫码过程中再调用闪光灯as会报错,因为一个项目中只能有一个Camer对象。所以我就想研究一下能不能在Zxing库中实现开启闪光灯的操作。
然后就开始观察源码,在DecoratedBarcodeView类中发现下面几个方法。
public void setTorchOn() {
barcodeView.setTorch(true);
if (torchListener != null) {
torchListener.onTorchOn();
}
}
public void setTorchOff() {
barcodeView.setTorch(false);
if (torchListener != null) {
torchListener.onTorchOff();
}
}
public void setTorchListener(TorchListener listener) {
this.torchListener = listener;
}
public interface TorchListener {
void onTorchOn();
void onTorchOff();
}
第一个方法是Zxing中开启闪光灯的操作;第二个方法是关闭闪光灯的操作;第三个是开启闪光灯的监听;第四个是闪光灯监听的接口。
那这样就好办了,直接新建一个DecoratedBarcodeView对象,实现其闪光灯监听的方法就行,直接上代码。
package com.project.orderbar.contoller.activity;
import android.app.Activity;
import android.content.pm.PackageManager;
import android.hardware.Camera;
import android.os.Bundle;
import android.view.KeyEvent;
import android.view.View;
import android.widget.ImageView;
import android.widget.Toast;
import androidx.annotation.NonNull;
import com.bumptech.glide.Glide;
import com.journeyapps.barcodescanner.CaptureManager;
import com.journeyapps.barcodescanner.DecoratedBarcodeView;
import com.project.orderbar.R;
public class ScanActivity extends Activity {
private CaptureManager capture;
private DecoratedBarcodeView barcodeScannerView;
private Camera camera;
//ImageView
private ImageView iv_scan_back, iv_scan_turnon;
//设置监听变量
private OnClickListener listener;
//设置闪光灯变化变量
private boolean isOpen = false;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_scan);
//初始化变量
barcodeScannerView = (DecoratedBarcodeView)findViewById(R.id.db_scsn);
iv_scan_back = (ImageView)findViewById(R.id.iv_scan_back);
iv_scan_turnon = (ImageView)findViewById(R.id.iv_scan_turnon);
//初始化监听
listener = new OnClickListener();
iv_scan_back.setOnClickListener(listener);
iv_scan_turnon.setOnClickListener(listener);
capture = new CaptureManager(this, barcodeScannerView);
capture.initializeFromIntent(getIntent(), savedInstanceState);
capture.decode();
//闪光灯变化的监听
barcodeScannerView.setTorchListener(new DecoratedBarcodeView.TorchListener() {
@Override
public void onTorchOn() {
isOpen = true;
Glide.with(ScanActivity.this).load(R.drawable.ic_turnon).into(iv_scan_turnon);
}
@Override
public void onTorchOff() {
isOpen = false;
Glide.with(ScanActivity.this).load(R.drawable.ic_turnoff).into(iv_scan_turnon);
}
});
}
//监听事件
private class OnClickListener implements View.OnClickListener{
@Override
public void onClick(View v) {
switch(v.getId()){
case R.id.iv_scan_back: //返回按钮
finish();
break;
case R.id.iv_scan_turnon: //打开手电筒,预留接口
flashLight();
break;
default:break;
}
}
}
@Override
protected void onResume() {
super.onResume();
capture.onResume();
}
@Override
protected void onPause() {
super.onPause();
capture.onPause();
}
@Override
protected void onDestroy() {
super.onDestroy();
capture.onDestroy();
//在活动结束时释放闪光灯
release();
}
@Override
protected void onSaveInstanceState(Bundle outState) {
super.onSaveInstanceState(outState);
capture.onSaveInstanceState(outState);
}
@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String permissions[], @NonNull int[] grantResults) {
capture.onRequestPermissionsResult(requestCode, permissions, grantResults);
}
@Override
public boolean onKeyDown(int keyCode, KeyEvent event) {
return barcodeScannerView.onKeyDown(keyCode, event) || super.onKeyDown(keyCode, event);
}
//闪光灯的控制逻辑
private void flashLight(){
if(hasFlashlight()){
if(isOpen){
barcodeScannerView.setTorchOff();
}else {
barcodeScannerView.setTorchOn();
}
}else {
Toast.makeText(ScanActivity.this, "无闪光灯!", Toast.LENGTH_LONG).show();
}
}
/**
* 判断设备是否有闪光灯
*
* @return true 有 false 没有
*/
private boolean hasFlashlight() {
return ScanActivity.this.getPackageManager().hasSystemFeature(PackageManager.FEATURE_CAMERA_FLASH);
}
/**
* 释放
*/
private void release() {
if (camera != null) {
camera.release();
camera = null;
}
}
}
首先定义一个boolean型对向isOpen,通过isOpen的状态来辨别闪光灯当前的状态,判断点击闪光灯之后的状态,闪光灯的变化会触发setTorchListener方法,在这个方法中实现isOpen状态的变化和闪光灯图标的变化,就可以成功调用闪光灯了。当然,最后不要忘了在onDestory中释放camer。
另外,com.google.zxing:core:3.4.0库是不支持android7.0及其以下版本的,如果要兼容Android7.0及其以下版本,可以使用com.google.zxing:core:3.3.3这个版本。