How to Detect and Decode QR Code with YOLO, OpenCV, and Dynamsoft Barcode Reader

In the past two weeks, I trained a custom YOLOv3 model for QR code detection and tested it with Darknet. In this article, I will use OpenCV’s DNN (Deep Neural Network) module to load the YOLO model for making detection from static images and real-time camera video stream. Besides, I will use Dynamsoft Barcode Reader to decode QR codes from the regions detected by YOLO.

YOLO QR Code Detection with OpenCV Python

pip install opencv-python

You can get qrcode.names, qrcode-yolov3-tiny.cfg and qrcode-yolov3-tiny.weights files from the package YOLOv3-tiny-QR.

To quickly get familiar with the OpenCV DNN APIs, we can refer to object_detection.py, which is a sample included in the OpenCV GitHub repository.

Now, let’s implement the QR detection code logic step by step.

First, we need to read an image to a Mat object using the imread() function. In case the image size is too large to display, I defined the maximum width and height values:

frame = cv.imread("416x416.jpg")threshold = 0.6maxWidth = 1280; maxHeight = 720imgHeight, imgWidth = frame.shape[:2]hScale = 1; wScale = 1thickness = 1if imgHeight > maxHeight:    hScale = imgHeight / maxHeight    thickness = 6if imgWidth > maxWidth:    wScale = imgWidth / maxWidth    thickness = 6

The next step is to initialize the network by loading the *.names, *.cfg and *.weights files:

classes = open('qrcode.names').read().strip().split('\n')net = cv.dnn.readNetFromDarknet('qrcode-yolov3-tiny.cfg', 'qrcode-yolov3-tiny.weights')net.setPreferableBackend(cv.dnn.DNN_BACKEND_OPENCV)

The network requires a blob object as the input, therefore we can convert the Mat object to a blob object as follows:

blob = cv.dnn.blobFromImage(frame, 1/255, (416, 416), swapRB=True, crop=False)

Determine the output layer, and then input the blob object to the network and perform a forward pass:

ln = net.getLayerNames()ln = [ln[i[0] - 1] for i in net.getUnconnectedOutLayers()]

As we get the network outputs, we can extract class names, confidence scores, and bounding boxes. In the meantime, we can draw them with OpenCV APIs:

Finally, we could adjust the image size to display appropriately on screen:

if hScale > wScale:    frame = cv.resize(frame, (int(imgWidth / hScale), maxHeight))elif hScale < wScale:    frame = cv.resize(frame, (maxWidth, int(imgHeight / wScale)))cv.imshow('QR Detection', frame)cv.waitKey()

Decoding QR Code with Dynamsoft Barcode Reader

Install Dynamsoft Barcode Reader:

pip install dbr

According to the coordinates of bounding boxes, we can decode the QR code by setting region parameters. Region decoding is much faster than the full image decoding:

On my screenshot, you can see the decoding result is obfuscated because I didn’t use a valid license key. If you want to experience the full functionalities of Dynamsoft Barcode Reader, you’d better apply for a free trial license.

References

Source Code

Originally published at https://www.dynamsoft.com on November 20, 2020.

Manager of Dynamsoft Open Source Projects | Tech Lover