{
  "source_file": "0930",
  "source_platform": "技术平台",
  "author": "Adrian Rosebrock / PyImageSearch",
  "title_listed": "An OpenCV barcode and QR code scanner with ZBar",
  "keywords": "OpenCV,二维码,条形码",
  "domain": "图像处理",
  "content_type": "教程",
  "is_paid_flag": "否",
  "url": "https://pyimagesearch.com/2018/05/21/an-opencv-barcode-and-qr-code-scanner-with-zbar/",
  "publish_date": "2018-05",
  "corpus_stage": "预训练/SFT",
  "notes": "OpenCV二维码扫描器",
  "id": "c4c7b2636b98",
  "collected_at": "2026-10-02T17:24:23",
  "title": "An OpenCV barcode and QR code scanner with ZBar - PyImageSearch",
  "body_markdown": "Click here to download the source code to this post\nToday’s blog post on reading barcodes and QR codes with OpenCV is inspired by a question I received from PyImageSearch reader, Hewitt:\nHey Adrian, I really love the PyImageSearch blog. I look forward to your emails each week. Keep doing what you’re doing.\nI have a question for you:\nDoes OpenCV have any modules that can be used to read barcodes or QR codes? Or do I need to use an entirely separate library?\nThanks Adrian.\nGreat question, Hewitt.\nThe short answer is\nno\n, OpenCV does not have any dedicated modules that can be used to read and decode barcodes and QR codes.\nHowever\n, what OpenCV can do is\nfacilitate the process of reading barcodes and QR codes\n, including loading an image from disk, grabbing a new frame from a video stream, and processing it.\nOnce we have the image or frame we can then\npass it to a dedicated Python barcode decoding library such as a Zbar.\nThe ZBar library will then decode the barcode or QR code. OpenCV can come back in to perform any further processing and display the result.\nIf this sounds like a complicated process, it’s actually pretty straightforward. The ZBar library, along with its various forks and variations, have come a long way. One set of ZBar bindings in particular,\npyzbar\n, is my personal favorite.\nInside today’s tutorial, I will show you how to read barcodes and QR codes with OpenCV and ZBar.\nAnd as an added bonus, I’ll demonstrate how to deploy our barcode scanner to the Raspberry Pi as well!\nTo learn more about reading barcodes and QR codes with OpenCV and ZBar,\njust keep reading.\nLooking for the source code to this post?\nJump Right To The Downloads Section\nAn OpenCV barcode and QR code scanner with ZBar\nToday’s blog post is broken into four parts.\nIn the first part, I’ll show you how to install the\nZBar library\n(with Python bindings).\nThe ZBar library will be used together with OpenCV to scan and decode barcodes and QR codes.\nOnce ZBar and OpenCV are properly configured I’ll demonstrate how to scan barcodes and QR codes in a\nsingle image\n.\nStarting with a single image will give us the practice we need to prepare for the next step: Reading barcodes and QR codes in real-time with OpenCV and ZBar,\nFinally, I’ll demonstrate how to deploy our real-time barcode scanner to the Raspberry Pi.\nInstalling ZBar (with Python bindings) for barcode decoding\nA few weeks ago Satya Mallick from the LearnOpenCV blog posted a really great tutorial on\nusing the ZBar library to scan barcodes\n.\nThe instructions to install ZBar in today’s post are largely based on his instructions, but with a few updates, the largest one being related to how we install the Python\nzbar\nbindings themselves, ensuring we can:\nUse Python 3\n(the official\nzbar\nPython bindings only support Python 2.7)\nDetect and localize\nexactly where in the image the barcode is.\nInstalling the necessary software is an easy 3-step process.\nStep 1:\nInstall\nzbar\nfrom the\napt\nor\nbrew\nrepository\nInstalling ZBar for Ubuntu or Raspbian\nInstalling ZBar for Ubuntu can be accomplished with the following command:\n$ sudo apt-get install libzbar0\nInstalling ZBar for macOS\nInstalling ZBar for macOS using brew is equally as easy (assuming you have Homebrew installed):\n$ brew install zbar\nStep 2 (Optional):\nCreate a virtual environment and install OpenCV\nYou have two options here:\nUse an existing virtual environment that has OpenCV ready to go (skip this step and head to\nStep 3\n).\nOr create a new, isolated virtual environment which involves installing OpenCV.\nVirtual environments are a best practice for Python development and I highly encourage you to make use of them.\nI elected to create a new, isolated Python 3 virtual environment and followed the Ubuntu (or macOS, depending on which machine I was using) OpenCV installation instructions linked on\nthis page\n. The only change I made while following those instructions was to name my environment\nbarcode\n:\n$ mkvirtualenv barcode -p python3\nNote:\nIf you already have OpenCV installed on your system you can skip the OpenCV compile process and simply sym-link your\ncv2.so\nbindings into the\nsite-packages\ndirectory of your new Python virtual environment.\nStep 3:\nInstall\npyzbar\nNow that I have a Python 3 virtual environment named\nbarcode\non my machine, I activated the\nbarcode\nenvironment (yours might have a different name) and installed\npyzbar\n:\n$ workon barcode\n$ pip install pyzbar\nIf you are not using a Python virtual environment you can just do:\n$ pip install pyzbar\nIf you’re trying to install\npyzbar\ninto the system version of Python make sure you use the\nsudo\ncommand as well.\nDecoding barcodes and QR codes with OpenCV in single images\nFigure 1:\nBoth QR and 1D barcodes can be read with our Python app using ZBar + OpenCV.\nBefore we implement real-time barcode and QR code reading, let’s first start with a\nsingle image\nscanner to get our feet wet.\nOpen up a new file, name it\nbarcode_scanner_image.py\nand insert the following code:\n# import the necessary packages\nfrom pyzbar import pyzbar\nimport argparse\nimport cv2\n\n# construct the argument parser and parse the arguments\nap = argparse.ArgumentParser()\nap.add_argument(\"-i\", \"--image\", required=True,\n\thelp=\"path to input image\")\nargs = vars(ap.parse_args())\nOn\nLines 2-4\nwe import our required packages.\nBoth\npyzbar\nand\ncv2\n(OpenCV) need to be installed following the instructions in the previous section.\nIn contrast,\nargparse\nis included with the Python install and it is responsible for parsing command line arguments.\nWe have one\nrequired\ncommand line argument for this script (\n--image\n) and it is parsed on\nLines 7-10\n.\nYou’ll see at the end of this section how to run the script while passing a\ncommand line argument\ncontaining the input image path.\nNow, let’s take the input image and put\npyzbar\nto work:\n# load the input image\nimage = cv2.imread(args[\"image\"])\n\n# find the barcodes in the image and decode each of the barcodes\nbarcodes = pyzbar.decode(image)\nOn\nLine 13\n, we load the input\nimage\nvia its path (contained in our convenient\nargs\ndictionary).\nFrom there, we call\npyzbar.decode\nto find and decode the\nbarcodes\nin the\nimage\n(\nLine 16\n). This is where all the magic of ZBar happens.\nWe aren’t finished yet — now we need to parse the information contained within the\nbarcodes\nvariable:\n# loop over the detected barcodes\nfor barcode in barcodes:\n\t# extract the bounding box location of the barcode and draw the\n\t# bounding box surrounding the barcode on the image\n\t(x, y, w, h) = barcode.rect\n\tcv2.rectangle(image, (x, y), (x + w, y + h), (0, 0, 255), 2)\n\n\t# the barcode data is a bytes object so if we want to draw it on\n\t# our output image we need to convert it to a string first\n\tbarcodeData = barcode.data.decode(\"utf-8\")\n\tbarcodeType = barcode.type\n\n\t# draw the barcode data and barcode type on the image\n\ttext = \"{} ({})\".format(barcodeData, barcodeType)\n\tcv2.putText(image, text, (x, y - 10), cv2.FONT_HERSHEY_SIMPLEX,\n\t\t0.5, (0, 0, 255), 2)\n\n\t# print the barcode type and data to the terminal\n\tprint(\"[INFO] Found {} barcode: {}\".format(barcodeType, barcodeData))\n\n# show the output image\ncv2.imshow(\"Image\", image)\ncv2.waitKey(0)\nBeginning on\nLine 19\n, we loop over the detected\nbarcodes\n.\nIn this loop, we proceed to:\nExtracting the bounding box\n(x, y)-\ncoordinates from the\nbarcode.rect\nobject (\nLine 22\n), enabling us to\nlocalize\nand determine\nwhere\nin the input image the current barcode is.\nDraw draw a bounding box rectangle on the\nimage\naround the detected\nbarcode\n(\nLine 23\n).\nDecode the\nbarcode\ninto a\n\"utf-8\"\nstring and extract the type of barcode (\nLines 27 and 28\n). It is critical to call the\n.decode(\"utf-8\")\nfunction on the object to convert from a byte array to a string. You can experiment by removing/commenting it out to see what happens — I’ll leave this as an experiment for you to try.\nFormat and draw the\nbarcodeData\nand\nbarcodeType\non the image (\nLines 31-33\n).\nAnd finally, output the same data and type information to the terminal for debugging purposes (\nLine 36\n).\nLet’s test our OpenCV barcode scanner. You should use the\n“Downloads”\nsection at the bottom of this blog post to download the code and example image.\nFrom there, open up your terminal and execute this command:\n$ python barcode_scanner_image.py --image barcode_example.png\n[INFO] Found QRCODE barcode: {\"author\": \"Adrian\", \"site\": \"PyImageSearch\"}\n[INFO] Found QRCODE barcode: https://pyimagesearch.com/\n[INFO] Found QRCODE barcode: PyImageSearch\n[INFO] Found CODE128 barcode: AdrianRosebrock\nAs you can see in the terminal, all four of the barcodes were found and properly decoded!\nRefer to\nFigure 1\nfor the processed image which has overlaid red rectangles and text for each barcode our software found.\nReal-time barcode and QR code reading with OpenCV\nIn the previous section, we learned how to create a Python + OpenCV barcode scanner for single images.\nOur barcode and QR code scanner worked well — but it raises the question,\ncan we detect and decode barcode + QR codes in real-time?\nTo find out, open up a new file, name it\nbarcode_scanner_video.py\n, and insert the following code:\n# import the necessary packages\nfrom imutils.video import VideoStream\nfrom pyzbar import pyzbar\nimport argparse\nimport datetime\nimport imutils\nimport time\nimport cv2\n\n# construct the argument parser and parse the arguments\nap = argparse.ArgumentParser()\nap.add_argument(\"-o\", \"--output\", type=str, default=\"barcodes.csv\",\n\thelp=\"path to output CSV file containing barcodes\")\nargs = vars(ap.parse_args())\nOn\nLines 2-8\nwe import our required packages.\nAt this point, recalling the above explanation, you should recognize\npyzbar\n,\nargparse\n, and\ncv2\n.\nWe’ll also use\nVideoStream\nto handle capturing video frames in an efficient, threaded approach. You can\nlearn more about the VideoStream class here\n. And if you do not have\nimutils\ninstalled on your system, just use the following command:\n$ pip install imutils\nWe’re going to parse one\noptional\ncommand line argument,\n--output\n, which contains the path to the output Comma Separated Values (CSV) file. This file will contain the timestamp and payload of each detected and decoded barcode from our video stream. If this argument isn’t specified, the CSV file will be placed in our current working directory with a name of\n\"barcodes.csv\"\n(\nLines 11-14\n).\nFrom there, let’s initialize our video stream and open our CSV file:\n# initialize the video stream and allow the camera sensor to warm up\nprint(\"[INFO] starting video stream...\")\n# vs = VideoStream(src=0).start()\nvs = VideoStream(usePiCamera=True).start()\ntime.sleep(2.0)\n\n# open the output CSV file for writing and initialize the set of\n# barcodes found thus far\ncsv = open(args[\"output\"], \"w\")\nfound = set()\nOn\nLines 18 and 19\nwe initialize and start our\nVideoStream\n. You may either:\nUse your USB webcam (uncomment\nLine 18\nand comment\nLine 19\n)\nOr if you’re using a Raspberry Pi (like me) you can use the PiCamera (uncomment\nLine 19\nand comment\nLine 18\n).\nI chose to use my Raspberry Pi PiCamera, as is shown in the next section.\nWe then pause for two seconds to allow the camera can warm up (\nLine 20\n).\nWe’ll be writing all barcodes we find to disk in a CSV file (but ensuring duplicates are not written).\nThis is meant to be a (trivial) example of logging barcodes.\nYou could, of course, do whatever you want once a barcode is detected and read such as:\nSave it in a SQL database\nSend it to a server\nUpload it to the cloud\nSend an email or text message\nThe actual action is arbitrary\n— we’re simply using the CSV file as an example.\nFeel free to update the code to include any notification you may wish.\nWe open the\ncsv\nfile for writing on\nLine 24\n. If you are modifying the code to append to the file, you can simply change the 2nd parameter from\n\"w\"\nto\n\"a\"\n(but you’ll have to search the file for duplicates in a different way).\nWe also initialize a\nset\nfor\nfound\nbarcodes. This set will contain unique barcodes while preventing duplicates.\nLet’s begin capturing + processing frames:\n# loop over the frames from the video stream\nwhile True:\n\t# grab the frame from the threaded video stream and resize it to\n\t# have a maximum width of 400 pixels\n\tframe = vs.read()\n\tframe = imutils.resize(frame, width=400)\n\n\t# find the barcodes in the frame and decode each of the barcodes\n\tbarcodes = pyzbar.decode(frame)\nOn\nLine 28\nwe start our loop and proceed to grab and and resize a\nframe\nfrom our video stream (\nLines 31 and 32\n).\nFrom there, we call\npyzbar.decode\nto detect and decode any QR + barcodes in the\nframe\n.\nLet’s proceed to loop over the detected\nbarcodes\n:\n# loop over the detected barcodes\n\tfor barcode in barcodes:\n\t\t# extract the bounding box location of the barcode and draw\n\t\t# the bounding box surrounding the barcode on the image\n\t\t(x, y, w, h) = barcode.rect\n\t\tcv2.rectangle(frame, (x, y), (x + w, y + h), (0, 0, 255), 2)\n\n\t\t# the barcode data is a bytes object so if we want to draw it\n\t\t# on our output image we need to convert it to a string first\n\t\tbarcodeData = barcode.data.decode(\"utf-8\")\n\t\tbarcodeType = barcode.type\n\n\t\t# draw the barcode data and barcode type on the image\n\t\ttext = \"{} ({})\".format(barcodeData, barcodeType)\n\t\tcv2.putText(frame, text, (x, y - 10),\n\t\t\tcv2.FONT_HERSHEY_SIMPLEX, 0.5, (0, 0, 255), 2)\n\n\t\t# if the barcode text is currently not in our CSV file, write\n\t\t# the timestamp + barcode to disk and update the set\n\t\tif barcodeData not in found:\n\t\t\tcsv.write(\"{},{}\\n\".format(datetime.datetime.now(),\n\t\t\t\tbarcodeData))\n\t\t\tcsv.flush()\n\t\t\tfound.add(barcodeData)\nThis loop should look very familiar if you read the previous section.\nIn fact,\nLines 38-52\nare\nidentical\nto those the\nsingle image\nscript. Please refer to the single image barcode detection and scanning section for a detailed review of this code block.\nLines 56-60\nare new. On these lines, we check if we’ve found a unique (not previously found) barcode (\nLine 56\n).\nIf that’s the case, we write the timestamp and data to the\ncsv\nfile (\nLines 57-59\n). We also append the\nbarcodeData\nto a\nfound\nset as a simple way to handle duplicates.\nIn the remaining lines of the real-time barcode scanner script, we display the frame, check if the quit key is pressed, and perform cleanup:\n# show the output frame\n\tcv2.imshow(\"Barcode Scanner\", frame)\n\tkey = cv2.waitKey(1) & 0xFF\n \n\t# if the `q` key was pressed, break from the loop\n\tif key == ord(\"q\"):\n\t\tbreak\n\n# close the output CSV file do a bit of cleanup\nprint(\"[INFO] cleaning up...\")\ncsv.close()\ncv2.destroyAllWindows()\nvs.stop()\nOn\nLine 63\nwe display the output\nframe\n.\nThen on\nLines 64-68\n, we check for keys and if\n\"q\"\nis pressed, we\nbreak\nout of the main execution loop.\nFinally, we perform cleanup on\nLines 72-74\n.\nBuilding a barcode and QR code scanner on the Raspberry Pi\nFigure 2:\nMy Raspberry Pi barcode scanner project consists of a Raspberry Pi, PiCamera, 7-inch touchscreen, and battery pack.\nWhat fun is a barcode scanner if I’m limited to my desk?\nI decided that I’d like to take my barcode scanner with me using my Pi, touchscreen, and battery pack.\nShown in\nFigure 2\nis my setup — the exact one I used for my\nmobile Pokedex deep learning project\nrecently. If you’re looking to build your own with the exact peripherals shown, I’ve listed the products and links:\nRaspberry Pi 3\n(or you could use the\nlatest 3 B+\n)\nRaspberry Pi camera module\nPi Foundation 7″ touchscreen display\nPortable Charger RAVPower 22000mAh Power Bank\nBuilding the system is really easy and I’ve made step-by-step instructions in\nthis blog post\n.\nOnce your mobile ZBar barcode scanner is ready, use the\n“Downloads”\nsection of this blog post to download the code associated with this blog post.\nFrom there, open up a terminal on your Pi and launch the app with the following command (you’ll need a keyboard/mouse for this step but then you can disconnect and let the app run):\n$ python barcode_scanner_video.py\n[INFO] starting video stream...\nNow you can present barcodes to the camera and when you’re done, you can open the\nbarcodes.csv\nfile (or if you’re so inclined you can execute\ntail -f barcodes.csv\nin a separate terminal to view the data as it enters the CSV file live).\nThe first QR code that I tried is shown on a black background — it is very easy for ZBar to detect:\nFigure 3:\nA QR code with the code “PyImageSearch” is recognized with our Python + ZBar application\nThen I headed to my kitchen, with Pi, screen, and battery pack in hand, and found another QR code:\nFigure 4:\nMy website, “https://pyimagesearch.com/” is encoded in a QR code and recognized with ZBar and Python on my Raspberry Pi.\nSuccess! It even works at many angles.\nNow let’s try a QR code that is contains a JSON-blob of data:\nFigure 5:\nAn OpenCV barcode and QR scanner with ZBar decodes an image of a QR with ease. I deployed the project to my Raspberry Pi so I can take it on the go.\nNo match for my OpenCV + ZBar + Python barcode scanner project!\nAnd finally, I tried a traditional 1-D barcode:\nFigure 6:\nZBar coupled with OpenCV and Python makes for a great Raspberry Pi barcode project. My name, “AdrianRosebrock” is encoded in this CODE128 barcode.\n1-D barcodes are slightly more challenging for the system especially with a PiCamera which doesn’t support autofocus. That being said, I achieved a successful detection and decoding of this barcode as well.\nYou might have best luck with a USB webcam such as the Logitech C920 which has great autofocus. Alternatively, you can actually change the factory focus on your PiCamera using the method that Jeff Geerling describes\non his blog\n.\nThat’s a wrap!\nIf you’re interested in reading additional barcode blog posts on my website, check out the\nposts with the “barcode” tag\n.\nWhat's next? We recommend\nPyImageSearch University\n.\nCourse information:\n120+ total classes • 115+ hours of on-demand code walkthrough videos • Last updated: October 2026\n★★★★★\n4.84 (128 Ratings) • 16,000+ Students Enrolled\nI strongly believe that if you had the right teacher you could\nmaster\ncomputer vision and deep learning.\nDo you think learning computer vision and deep learning has to be time-consuming, overwhelming, and complicated? Or has to involve complex mathematics and equations? Or requires a degree in computer science?\nThat’s\nnot\nthe case.\nAll you need to master computer vision and deep learning is for someone to explain things to you in\nsimple, intuitive\nterms.\nAnd that’s exactly what I do\n. My mission is to change education and how complex Artificial Intelligence topics are taught.\nIf you're serious about learning computer vision, your next stop should be PyImageSearch University, the most comprehensive computer vision, deep learning, and OpenCV course online today. Here you’ll learn how to\nsuccessfully\nand\nconfidently\napply computer vision to your work, research, and projects. Join me in computer vision mastery.\nInside PyImageSearch University you'll find:\n✓\n120+ courses\non essential computer vision, deep learning, and OpenCV topics\n✓\n94+ Certificates\nof Completion\n✓\n115+ hours\nof on-demand video\n✓\nBrand new courses released\nregularly\n, ensuring you can keep up with state-of-the-art techniques\n✓\nPre-configured Jupyter Notebooks in Google Colab\n✓ Run all code examples in your web browser — works on Windows, macOS, and Linux (no dev environment configuration required!)\n✓ Access to\ncentralized code repos for\nall\n540+ tutorials\non PyImageSearch\n✓\nEasy one-click downloads\nfor code, datasets, pre-trained models, etc.\n✓\nAccess\non mobile, laptop, desktop, etc.\nClick here to join PyImageSearch University\nSummary\nIn today’s blog post you learned how to build an OpenCV barcode and QR code scanner.\nTo accomplish this, we used the\nZBar library\n.\nOnce the ZBar library was installed on our system, we created two Python scripts:\nThe first one to scan barcodes and QR codes in a single image\nAnd a second script to read barcodes and QR codes in real-time\nIn both cases, we used OpenCV to facilitate the process of building our barcode/QR code scanner.\nFinally, we wrapped up today’s blog post by deploying our barcode reader to the Raspberry Pi.\nThe barcode scanner is fast enough to run in real-time on the Raspberry Pi without an issue.\nFeel free to use this barcode and QR code scanner functionality in your own projects!\nAnd if you build something fun and interesting with it, be sure to share your project in the comments.\nI hope you enjoyed today’s post. I’ll see you next week.\nTo be notified when future blog posts are published here on PyImageSearch,\nbe sure to enter your email address in the form below!\nDownload the Source Code and FREE 17-page Resource Guide\nEnter your email address below to get a .zip of the code and a\nFREE 17-page Resource Guide on Computer Vision, OpenCV, and Deep Learning.\nInside you'll find my hand-picked tutorials, books, courses, and libraries to help you master CV and DL!\nDownload the code!\nWebsite",
  "metadata": {
    "title": "An OpenCV barcode and QR code scanner with ZBar - PyImageSearch",
    "description": "In this tutorial you will learn how to create an OpenCV barcode and QR code scanner/reader using Python, OpenCV, and the ZBar library.",
    "keywords": null,
    "author": "Adrian Rosebrock",
    "og:locale": "en_US",
    "og:type": "article",
    "og:title": "An OpenCV barcode and QR code scanner with ZBar - PyImageSearch",
    "og:description": "In this tutorial you will learn how to create an OpenCV barcode and QR code scanner/reader using Python, OpenCV, and the ZBar library.",
    "og:url": "https://pyimagesearch.com/2018/05/21/an-opencv-barcode-and-qr-code-scanner-with-zbar/",
    "og:site_name": "PyImageSearch",
    "og:image": "https://pyimagesearch.com/wp-content/uploads/2018/05/barcode_scanner_result_01.jpg",
    "og:image:width": "800",
    "og:image:height": "480",
    "og:image:type": "image/jpeg",
    "twitter:label1": "Written by",
    "twitter:data1": "Adrian Rosebrock",
    "twitter:label2": "Est. reading time",
    "twitter:data2": "16 minutes",
    "article:published_time": "2018-05-21T14:00:22+00:00",
    "article:modified_time": "2021-04-17T18:11:44+00:00"
  },
  "paywall": {
    "listed_paid": false,
    "detected": false,
    "marker": "",
    "public_only": false,
    "policy": "付费/会员内容只保留页面公开可见部分，不绕过付费墙"
  },
  "crawl": {
    "success": true,
    "status_code": 200,
    "error": ""
  },
  "code_blocks": [
    {
      "file": "attachments/c4c7b2636b98/code/body-000.txt",
      "chars": 32,
      "language": "text"
    },
    {
      "file": "attachments/c4c7b2636b98/code/body-001.txt",
      "chars": 20,
      "language": "text"
    },
    {
      "file": "attachments/c4c7b2636b98/code/body-002.txt",
      "chars": 34,
      "language": "text"
    },
    {
      "file": "attachments/c4c7b2636b98/code/body-003.txt",
      "chars": 38,
      "language": "text"
    },
    {
      "file": "attachments/c4c7b2636b98/code/body-004.txt",
      "chars": 21,
      "language": "text"
    },
    {
      "file": "attachments/c4c7b2636b98/code/body-005.txt",
      "chars": 279,
      "language": "text"
    },
    {
      "file": "attachments/c4c7b2636b98/code/body-006.txt",
      "chars": 155,
      "language": "text"
    },
    {
      "file": "attachments/c4c7b2636b98/code/body-007.txt",
      "chars": 852,
      "language": "text"
    },
    {
      "file": "attachments/c4c7b2636b98/code/body-008.txt",
      "chars": 282,
      "language": "text"
    },
    {
      "file": "attachments/c4c7b2636b98/code/body-009.txt",
      "chars": 404,
      "language": "text"
    },
    {
      "file": "attachments/c4c7b2636b98/code/body-010.txt",
      "chars": 22,
      "language": "text"
    },
    {
      "file": "attachments/c4c7b2636b98/code/body-011.txt",
      "chars": 341,
      "language": "text"
    },
    {
      "file": "attachments/c4c7b2636b98/code/body-012.txt",
      "chars": 322,
      "language": "text"
    },
    {
      "file": "attachments/c4c7b2636b98/code/body-013.txt",
      "chars": 941,
      "language": "text"
    },
    {
      "file": "attachments/c4c7b2636b98/code/body-014.txt",
      "chars": 300,
      "language": "text"
    },
    {
      "file": "attachments/c4c7b2636b98/code/body-015.txt",
      "chars": 66,
      "language": "text"
    }
  ],
  "images": [
    {
      "status": "ok",
      "url": "https://b2633864.assetcdn.net/2633864/wp-content/uploads/2018/05/barcode_scanneranimation.gif?lossy=2&strip=1&webp=1",
      "bytes": 909875,
      "reused": false,
      "local_path": "attachments/c4c7b2636b98/images/body-189096162008aa170e1c.gif",
      "src": "https://b2633864.assetcdn.net/2633864/wp-content/uploads/2018/05/barcode_scanneranimation.gif?lossy=2&strip=1&webp=1",
      "alt": "",
      "downloaded": true
    },
    {
      "status": "ok",
      "url": "https://b2633864.assetcdn.net/2633864/wp-content/uploads/2020/01/source-code-icon.png?lossy=2&strip=1&webp=1",
      "bytes": 884,
      "reused": false,
      "local_path": "attachments/c4c7b2636b98/images/body-0f8ec41d2103feb4399d.png",
      "src": "https://b2633864.assetcdn.net/2633864/wp-content/uploads/2020/01/source-code-icon.png?lossy=2&strip=1&webp=1",
      "alt": "",
      "downloaded": true
    },
    {
      "status": "ok",
      "url": "https://b2633864.assetcdn.net/2633864/wp-content/uploads/2018/05/barcode_scanner_output.jpg?lossy=2&strip=1&webp=1",
      "bytes": 38591,
      "reused": true,
      "local_path": "attachments/c4c7b2636b98/images/001.jpg",
      "src": "https://b2633864.assetcdn.net/2633864/wp-content/uploads/2018/05/barcode_scanner_output.jpg?lossy=2&strip=1&webp=1",
      "alt": "",
      "downloaded": true
    },
    {
      "status": "ok",
      "url": "https://b2633864.assetcdn.net/2633864/wp-content/uploads/2018/05/barcode_scanner_setup.jpg?lossy=2&strip=1&webp=1",
      "bytes": 56550,
      "reused": true,
      "local_path": "attachments/c4c7b2636b98/images/003.jpg",
      "src": "https://b2633864.assetcdn.net/2633864/wp-content/uploads/2018/05/barcode_scanner_setup.jpg?lossy=2&strip=1&webp=1",
      "alt": "",
      "downloaded": true
    },
    {
      "status": "ok",
      "url": "https://b2633864.assetcdn.net/2633864/wp-content/uploads/2018/05/barcode_scanner_result_01-300x180.jpg?lossy=2&strip=1&webp=1",
      "bytes": 7910,
      "reused": false,
      "local_path": "attachments/c4c7b2636b98/images/body-e1f07a2728c9612c682a.jpg",
      "src": "https://b2633864.assetcdn.net/2633864/wp-content/uploads/2018/05/barcode_scanner_result_01-300x180.jpg?lossy=2&strip=1&webp=1",
      "alt": "",
      "downloaded": true
    },
    {
      "status": "ok",
      "url": "https://b2633864.assetcdn.net/2633864/wp-content/uploads/2018/05/barcode_scanner_result_02-300x180.jpg?lossy=2&strip=1&webp=1",
      "bytes": 8810,
      "reused": false,
      "local_path": "attachments/c4c7b2636b98/images/body-05646518cddfc13e7528.jpg",
      "src": "https://b2633864.assetcdn.net/2633864/wp-content/uploads/2018/05/barcode_scanner_result_02-300x180.jpg?lossy=2&strip=1&webp=1",
      "alt": "",
      "downloaded": true
    },
    {
      "status": "ok",
      "url": "https://b2633864.assetcdn.net/2633864/wp-content/uploads/2018/05/barcode_scanner_result_03-300x180.jpg?lossy=2&strip=1&webp=1",
      "bytes": 7890,
      "reused": false,
      "local_path": "attachments/c4c7b2636b98/images/body-d7976403840a22fab2f3.jpg",
      "src": "https://b2633864.assetcdn.net/2633864/wp-content/uploads/2018/05/barcode_scanner_result_03-300x180.jpg?lossy=2&strip=1&webp=1",
      "alt": "",
      "downloaded": true
    },
    {
      "status": "ok",
      "url": "https://b2633864.assetcdn.net/2633864/wp-content/uploads/2018/05/barcode_scanner_result_04-300x180.jpg?lossy=2&strip=1&webp=1",
      "bytes": 8934,
      "reused": false,
      "local_path": "attachments/c4c7b2636b98/images/body-6da7e1dbf8a8b9299ca8.jpg",
      "src": "https://b2633864.assetcdn.net/2633864/wp-content/uploads/2018/05/barcode_scanner_result_04-300x180.jpg?lossy=2&strip=1&webp=1",
      "alt": "",
      "downloaded": true
    },
    {
      "status": "ok",
      "url": "https://fast.wistia.com/embed/medias/kno0cmko2z/swatch",
      "bytes": 3143,
      "reused": false,
      "local_path": "attachments/c4c7b2636b98/images/body-8ec9834d54100244f57f.img",
      "src": "https://fast.wistia.com/embed/medias/kno0cmko2z/swatch",
      "alt": "",
      "downloaded": true
    },
    {
      "status": "ok",
      "url": "https://b2633864.assetcdn.net/2633864/wp-content/uploads/2020/01/cta-source-guide-1.png?lossy=2&strip=1&webp=1",
      "bytes": 28126,
      "reused": false,
      "local_path": "attachments/c4c7b2636b98/images/body-8cd5816cf73385d96fcd.png",
      "src": "https://b2633864.assetcdn.net/2633864/wp-content/uploads/2020/01/cta-source-guide-1.png?lossy=2&strip=1&webp=1",
      "alt": "",
      "downloaded": true
    }
  ],
  "audio": [],
  "videos": [],
  "links": [
    {
      "href": "http://zbar.sourceforge.net/",
      "label": "ZBar library",
      "type": "a"
    },
    {
      "href": "https://www.learnopencv.com/barcode-and-qr-code-scanner-using-zbar-and-opencv/",
      "label": "using the ZBar library to scan barcodes",
      "type": "a"
    },
    {
      "href": "https://pyimagesearch.com/opencv-tutorials-resources-guides/",
      "label": "this page",
      "type": "a"
    },
    {
      "href": "https://pyimagesearch.com/wp-content/uploads/2018/05/barcode_scanner_output.jpg",
      "label": "",
      "type": "a"
    },
    {
      "href": "https://pyimagesearch.com/2018/03/12/python-argparse-command-line-arguments/",
      "label": "command line argument",
      "type": "a"
    },
    {
      "href": "https://pyimagesearch.com/2016/01/04/unifying-picamera-and-cv2-videocapture-into-a-single-class-with-opencv/",
      "label": "learn more about the VideoStream class here",
      "type": "a"
    },
    {
      "href": "https://pyimagesearch.com/wp-content/uploads/2018/05/barcode_scanner_setup.jpg",
      "label": "",
      "type": "a"
    },
    {
      "href": "https://pyimagesearch.com/2018/04/30/a-fun-hands-on-deep-learning-project-for-beginners-students-and-hobbyists/",
      "label": "mobile Pokedex deep learning project",
      "type": "a"
    },
    {
      "href": "https://amzn.to/2Hn1b7b",
      "label": "Raspberry Pi 3",
      "type": "a"
    },
    {
      "href": "https://amzn.to/2rmm3p9",
      "label": "latest 3 B+",
      "type": "a"
    },
    {
      "href": "https://amzn.to/2Kb9lBd",
      "label": "Raspberry Pi camera module",
      "type": "a"
    },
    {
      "href": "https://amzn.to/2KaYYOa",
      "label": "Pi Foundation 7″ touchscreen display",
      "type": "a"
    },
    {
      "href": "https://amzn.to/2HpAjmS",
      "label": "Portable Charger RAVPower 22000mAh Power Bank",
      "type": "a"
    },
    {
      "href": "https://pyimagesearch.com/wp-content/uploads/2018/05/barcode_scanner_result_01.jpg",
      "label": "",
      "type": "a"
    },
    {
      "href": "https://pyimagesearch.com/wp-content/uploads/2018/05/barcode_scanner_result_02.jpg",
      "label": "",
      "type": "a"
    },
    {
      "href": "https://pyimagesearch.com/wp-content/uploads/2018/05/barcode_scanner_result_03.jpg",
      "label": "",
      "type": "a"
    },
    {
      "href": "https://pyimagesearch.com/wp-content/uploads/2018/05/barcode_scanner_result_04.jpg",
      "label": "",
      "type": "a"
    },
    {
      "href": "https://www.jeffgeerling.com/blog/2017/fixing-blurry-focus-on-some-raspberry-pi-camera-v2-models",
      "label": "on his blog",
      "type": "a"
    },
    {
      "href": "https://pyimagesearch.com/tag/barcode/",
      "label": "posts with the “barcode” tag",
      "type": "a"
    },
    {
      "href": "https://pyimagesearch.com/pyimagesearch-university/?utm_source=blogPost&utm_medium=bottomBanner&utm_campaign=What%27s%20next%3F%20I%20recommend",
      "label": "PyImageSearch University",
      "type": "a"
    }
  ],
  "repair_version": 2,
  "repaired_at": "2026-10-14T10:54:12Z",
  "source_url": "https://pyimagesearch.com/2018/05/21/an-opencv-barcode-and-qr-code-scanner-with-zbar/",
  "papers": [],
  "actual_video_files": [
    {
      "local_path": "attachments/c4c7b2636b98/videos/kno0cmko2z.mp4",
      "bytes": 154424456,
      "valid": true,
      "height": 1080,
      "width": 1920,
      "duration": "231.500000",
      "status": "ok"
    }
  ],
  "body_chars": 20834,
  "expected_body_images": 10,
  "discovery_status": "ok",
  "delivery_status": "ok",
  "missing_reason": "",
  "raw_html": "attachments/c4c7b2636b98/pages/source.html",
  "local_html": "attachments/c4c7b2636b98/pages/article.html",
  "body_base_path": "attachments/c4c7b2636b98/pages/",
  "body_markdown_path": "attachments/c4c7b2636b98/pages/article.md"
}