基于OpenCV的条形码区域分割

重磅干货,第一时间送达

本期,我们将一起学习如何从图像中提取出含有条形码的区域。下面的代码,我们将在Anaconda中采用Python 2.7 完成,当然OpenCV中的图像处理库也是必不可少的。

分割是识别图像内一个或多个对象的位置的过程。我们要介绍的技术其实非常简单,它利用了形态算子的扩张和侵蚀,以及诸如开运算,闭运算和黑帽算子的组合。

01.简介

安装Anaconda后,让我们从Anaconda的提示符下使用以下命令转到OpenCV安装:

conda install -c https://conda.anaconda.org/menpo opencv

现在,让我们从Anaconda启动器启动Spyder IDE。

Anaconda启动器

一旦运行了Spyder,建议验证OpenCV安装是否成功。在Python控制台的右下角,我们进行以下测试:

import cv2

代码讲解

我们已经创建了一个启动GitHub存储库。小伙伴可以使用以下方法直接克隆它:

git clone --branch step1https://github.com/lucapiccinelli/BarcodesTutorial.git

现在,我们将要下载测试图像,并对他们进行读取和显示。

测试图片

import cv2import matplotlib.pyplot as plt
im = cv2.imread(r’img\barcodes.jpg’, cv2.IMREAD_GRAYSCALE)plt.imshow(im, cmap=’Greys_r’)

接下来,我们将对图像进行二值化处理,这样可以通过阈值的设定来提取出我们感兴趣的部分。使用黑帽运算符,我们可以增加较暗的图像元素。我们可以首先使用简单的全局阈值安全地对图像进行二值化处理。黑帽运算符使我们可以使用非常低的阈值,而不必过多地关注噪声。

在应用blackhat时,我们使用的内核会更加重视垂直图像元素。内核具有固定的大小,因此可以缩放图像,这也可以提高性能(并支持某种输入归一化)。

黑帽+阈值处理

它遵循其他形态运算符的采用,顺序地将它们组合在一起以获得条形码位置中的连接组件。

#riscalatura dell'immaginescale = 800.0 / im.shape[1]im = cv2.resize(im, (int(im.shape[1] * scale), int(im.shape[0] * scale)))
#blackhatkernel = np.ones((1, 3), np.uint8)im = cv2.morphologyEx(im, cv2.MORPH_BLACKHAT, kernel, anchor=(1, 0))
#sogliaturathresh, im = cv2.threshold(im, 10, 255, cv2.THRESH_BINARY)

膨胀和闭合的这种组合在测试图像上效果很好,但可能无法在其他图像上达到相同的效果。这没有关系,大家可以尝试改变参数和运算符的组合,直到对结果满意为止。

膨胀+闭运算

最后的预处理步骤是应用具有很大内核的开运算符,以删除太少而无法适合条形码形状的元素。

kernel = np.ones((21, 35), np.uint8)im = cv2.morphologyEx(im, cv2.MORPH_OPEN, kernel, iterations=1)

这是我们希望得到的最终结果:

使用35x21内核打开

现在,我们可以运行连接的组件的检测算法,并检索带有坐标和尺寸的条形码矩形。如大家在上一张图像中所看到的那样,最后的形态学步骤并未滤除全部的噪声。但是,在这种情况下,将它们过滤掉非常简单,以矩形区域值作为阈值就可以了。

#rilettura dell'immagine, stavolta a coloriim_out = cv2.imread(r'img\barcodes.jpg')
#estrazione dei componenti connessicontours, hierarchy = cv2.findContours(im, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_NONE)
unscale = 1.0 / scaleif contours != None: for contour in contours: # se l'area non è grande a sufficienza la salto if cv2.contourArea(contour) <= 2000: continue #estraggo il rettangolo di area minima (in formato (centro_x, centro_y), (width, height), angolo) rect = cv2.minAreaRect(contour) #l'effetto della riscalatura iniziale deve essere eliminato dalle coordinate rilevate rect = \ ((int(rect[0][0] * unscale), int(rect[0][1] * unscale)), \ (int(rect[1][0] * unscale), int(rect[1][1] * unscale)), \ rect[2]) #disegno il tutto sull'immagine originale box = np.int0(cv2.cv.BoxPoints(rect)) cv2.drawContours(im_out, [box], 0, (0, 255, 0), thickness = 2) plt.imshow(im_out)#scrittura dell' immagine finalecv2.imwrite(r'img\out.png', im_out)

最后,在上面的代码中,我使用提取的矩形绘制它们,并将其覆盖在原始图像上。

最终结果,条形码以绿色框突出显示。

结论

· 提出的技术非常简单有效,但存在一些令人讨厌的缺点:

· 它对条形码偏斜非常敏感;它可以很好地工作到大约45度,然后您必须执行第二遍,修改内核的方向。

· 它只能在固定尺寸范围内找到条形码。

· 尽管对矩形区域施加了过滤,但仍有可能无法清除某些非条形码。

第一个和第二个可能不是真正的问题,但是最后一个可能会花费大家大量时间来尝试解码非条形码的内容。

一个很好的解决方案是将条形码特征(图像梯度,傅立叶变换)输入给神经网络(或一些其他一些分类器),并在第二时刻过滤掉噪声。

下面给出完整的示例代码。

import cv2import matplotlib.pyplot as pltimport numpy as np
im = cv2.imread(r'img\barcodes.jpg', cv2.IMREAD_GRAYSCALE)im_out = cv2.imread(r'img\barcodes.jpg')
#riscalatura dell'immaginescale = 800.0 / im.shape[1]im = cv2.resize(im, (int(im.shape[1] * scale), int(im.shape[0] * scale)))
#blackhatkernel = np.ones((1, 3), np.uint8)im = cv2.morphologyEx(im, cv2.MORPH_BLACKHAT, kernel, anchor=(1, 0))
#sogliaturathresh, im = cv2.threshold(im, 10, 255, cv2.THRESH_BINARY)
#operazioni morfologichekernel = np.ones((1, 5), np.uint8)im = cv2.morphologyEx(im, cv2.MORPH_DILATE, kernel, anchor=(2, 0), iterations=2) #dilatazioneim = cv2.morphologyEx(im, cv2.MORPH_CLOSE, kernel, anchor=(2, 0), iterations=2) #chiusura
kernel = np.ones((21, 35), np.uint8)im = cv2.morphologyEx(im, cv2.MORPH_OPEN, kernel, iterations=1)
#estrazione dei componenti connessicontours, hierarchy = cv2.findContours(im, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_NONE)
unscale = 1.0 / scaleif contours != None: for contour in contours: # se l'area non è grande a sufficienza la salto if cv2.contourArea(contour) <= 2000: continue #estraggo il rettangolo di area minima (in formato (centro_x, centro_y), (width, height), angolo) rect = cv2.minAreaRect(contour) #l'effetto della riscalatura iniziale deve essere eliminato dalle coordinate rilevate rect = \ ((int(rect[0][0] * unscale), int(rect[0][1] * unscale)), \ (int(rect[1][0] * unscale), int(rect[1][1] * unscale)), \ rect[2]) #disegno il tutto sull'immagine originale box = np.int0(cv2.cv.BoxPoints(rect)) cv2.drawContours(im_out, [box], 0, (0, 255, 0), thickness = 2) plt.imshow(im_out)#scrittura dell' immagine finalecv2.imwrite(r'img\out.png', im_out)

交流群

(0)

相关推荐

  • Matplotlib等高线图

    等高线图(也称"水平图")是一种在二维平面上显示 3D 图像的方法.等高线有时也被称为 "Z 切片",如果您想要查看因变量 Z 与自变量 X.Y 之间的函数图像 ...

  • (9条消息) ocr图像预处理

    说明:文字方向校正(fft方式和放射变换方式)参考了网上的代码,只做了少量修改 只针对医疗影像图像,自然场景下的另说 因为处理的图像都很大很大,居然有11000*12000这种分辨率的,有90M大小, ...

  • 弹幕君,别挡着我看小姐姐!

    某天代码写得老眼昏花,去B站上摸鱼,突然发现奇怪的现象: 哟呵,B站竟然做了视频前景提取,把弹幕藏到画面人物的后面.识别效果还意外地不错呢. 然后又翻了下,发现这是个叫做"智能防挡弹幕&qu ...

  • 基于OpenCV的区域分割、轮廓检测和阈值处理

    重磅干货,第一时间送达 OpenCV是一个巨大的开源库,广泛用于计算机视觉,人工智能和图像处理领域.它在现实世界中的典型应用是人脸识别,物体检测,人类活动识别,物体跟踪等. 现在,假设我们只需要从整个 ...

  • 基于OpenCV实战:车牌检测

    重磅干货,第一时间送达 拥有思维导图或流程将引导我们朝着探索和寻找实现目标的正确道路的方向发展.如果要给我一张图片,我们如何找到车牌并提取文字? 一般思维步骤: 识别输入数据是图像. 扫描图像以查看由 ...

  • 基于OpenCV实战的图像处理:色度分割

    重磅干货,第一时间送达 通过HSV色阶使用彩色图像可以分割来分割图像中的对象,但这并不是分割图像的唯一方法.为什么大多数人偏爱色度而不是RGB / HSV分割? 可以获得RGB / HSV通道之间的比 ...

  • 基于OpenCV的实战:轮廓检测(附代码解析)

    重磅干货,第一时间送达 利用轮廓检测物体可以看到物体的各种颜色,在这种情况下放置在静态和动态物体上.如果是统计图像,则需要将图像加载到程序中,然后使用OpenCV库,以便跟踪对象. 每当在框架中检测到 ...

  • 基于OpenCV实战:绘制图像轮廓(附代码)

    重磅干货,第一时间送达 山区和地形图中海拔高的区域划出的线称为地形轮廓,它们提供了地形的高程图.这些线条可以手动绘制,也可以由计算机生成.在本文中,我们将看到如何使用OpenCV在简单图像上绘制轮廓线 ...

  • 基于OpenCV实战:动态物体检测

    重磅干货,第一时间送达 最近,闭路电视安全系统运行着多种算法来确保安全,例如面部识别,物体检测,盗窃检测,火灾警报等.我们在运动检测的基础上实现了许多算法,因为在空闲帧上运行所有这些进程没有任何意义. ...

  • 基于OpenCV实战:对象跟踪

    重磅干货,第一时间送达 介绍 跟踪对象的基本思想是找到对象的轮廓,基于HSV颜色值. 轮廓:突出显示对象的图像片段.例如,如果将二进制阈值应用于具有(180,255)的图像,则大于180的像素将以白色 ...

  • (2条消息) 基于OpenCV使用OpenPose进行多个人体姿态估计

    目录 1.网络的体系结构 2.下载模型的权重文件 3. 第一步:生成图片对应的输出 3.1 读取神经网络 3.2 读取图像并生成输入blob 3.3 向前通过网络 3.4 样本输出 4. 第二步:关键 ...

  • 实战:基于OpenCV 的车牌识别

    重磅干货,第一时间送达 车牌识别是一种图像处理技术,用于识别不同车辆.这项技术被广泛用于各种安全检测中.现在让我一起基于OpenCV编写Python代码来完成这一任务. 车牌识别的相关步骤 1.车牌检 ...