Using ZXing to create an Android barcode scanning app
Categories:
Building an Android Barcode Scanner with ZXing
Learn how to integrate the powerful ZXing library into your Android application to create a robust and efficient barcode and QR code scanning solution.
Barcode and QR code scanning capabilities are essential for many modern Android applications, from inventory management to retail and event ticketing. The ZXing (Zebra Crossing) library is a popular, open-source, multi-format 1D/2D barcode image processing library implemented in Java, with ports to other languages. This article will guide you through the process of integrating ZXing into your Android project to build a functional barcode scanner.
Setting Up Your Android Project
Before we dive into the scanning logic, you need to set up your Android project and include the necessary ZXing dependencies. We'll use the zxing-android-embedded
library, which provides a convenient wrapper around the core ZXing library, simplifying integration with Android's camera and UI.
1. Step 1: Create a New Android Project
Open Android Studio and create a new project with an 'Empty Activity' template. Choose a suitable name and package for your application.
2. Step 2: Add ZXing Dependency
Open your app-level build.gradle
file and add the zxing-android-embedded
dependency. Ensure you use the latest stable version.
dependencies {
implementation 'com.journeyapps:zxing-android-embedded:4.3.0'
}
Adding the ZXing Android Embedded dependency to build.gradle
Implementing the Scanner Activity
The zxing-android-embedded
library provides a CaptureActivity
that handles camera preview, barcode detection, and result processing. You can either use this activity directly or customize it. For simplicity, we'll start by launching the default scanner.
sequenceDiagram participant User participant App participant ZXingLibrary User->>App: Tap 'Scan Barcode' button App->>ZXingLibrary: Initiate BarcodeIntent ZXingLibrary-->>App: Request Camera Permission App->>User: Prompt for Camera Permission User->>App: Grant Permission App->>ZXingLibrary: Camera Preview Starts ZXingLibrary->>ZXingLibrary: Scan for Barcode ZXingLibrary-->>App: Barcode Scanned (Result) App->>User: Display Scan Result
Flow of initiating a barcode scan using ZXing
To launch the scanner, you'll typically create an Intent
and start the CaptureActivity
. The result will be returned to your calling activity via onActivityResult
.
import com.google.zxing.integration.android.IntentIntegrator;
import com.google.zxing.integration.android.IntentResult;
import androidx.appcompat.app.AppCompatActivity;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;
import android.widget.Toast;
public class MainActivity extends AppCompatActivity {
private TextView resultTextView;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
resultTextView = findViewById(R.id.resultTextView);
Button scanButton = findViewById(R.id.scanButton);
scanButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
startScanner();
}
});
}
private void startScanner() {
IntentIntegrator integrator = new IntentIntegrator(this);
integrator.setPrompt("Scan a barcode or QR code");
integrator.setOrientationLocked(false); // Allow orientation changes
integrator.initiateScan();
}
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
IntentResult result = IntentIntegrator.parseActivityResult(requestCode, resultCode, data);
if (result != null) {
if (result.getContents() == null) {
Toast.makeText(this, "Scan Cancelled", Toast.LENGTH_LONG).show();
resultTextView.setText("Scan Cancelled");
} else {
Toast.makeText(this, "Scanned: " + result.getContents(), Toast.LENGTH_LONG).show();
resultTextView.setText("Scanned: " + result.getContents());
}
} else {
super.onActivityResult(requestCode, resultCode, data);
}
}
}
MainActivity.java: Initiating the scanner and handling results
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
android:gravity="center"
android:padding="16dp"
tools:context=".MainActivity">
<Button
android:id="@+id/scanButton"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Scan Barcode" />
<TextView
android:id="@+id/resultTextView"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="24dp"
android:text="Scan result will appear here" />
</LinearLayout>
activity_main.xml: Layout for the main activity
AndroidManifest.xml
file. The zxing-android-embedded
library usually handles this, but it's good practice to verify.Customizing the Scanner Experience
While the default CaptureActivity
is functional, you might want to customize the scanner's appearance or behavior. IntentIntegrator
offers several methods to configure the scan, such as setting the prompt text, specifying desired barcode formats, or enabling/disabling beep sounds.
integrator.setDesiredBarcodeFormats(IntentIntegrator.QR_CODE); // Scan only QR codes
integrator.setPrompt("Align QR code within the viewfinder");
integrator.setBeepEnabled(false); // Disable beep sound on scan
integrator.setBarcodeImageEnabled(true); // Save barcode image to cache
integrator.initiateScan();
Customizing scanner options with IntentIntegrator
DecoratedBarcodeView
and BarcodeView
directly. This gives you full control over the UI and lifecycle.