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 ResultFlow 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.