Building and calibrating a stereo camera with OpenCV (<50€)

I’ve decided to try my hand at 3D reconstruction using a stereo camera. There are a few good sets of instructions on how to get started with this. I decided to take some heavy inspiration from them and will be citing them as I go in the post. I ended up not following any of the instructions precisely because I have a few goals that are not fulfilled by any single source that I could find:

  • The stereo camera should be buildable from affordable, off-the-shelf materials (under 50€)
  • Both cameras should be able to capture images in the near-infrared spectrum, since I would like to be able to use it to make NDVI pictures at some point if I so desire
  • The cameras should be able to be calibrated in a simple workflow that bases on simple, extensible code

In this post I will be showing the first steps in a processing chain that fulfills these requirements. If you follow these instructions, you should be able to easily build your own stereo camera and calibrate it. I’ll be splitting up the process into a few separate posts to keep it from getting too long.

Materials you’ll need

The important thing about calibrated stereo photography is that the cameras have the same relationship to each other in each picture. This means that the transformation from one perspective to the other is known for each picture in each stereo pair, leaving only the work of figuring out the relationship of the objects photographed to the cameras when you’re doing 3D reconstruction. So to start, you need to build a stereo rig that will hold both of your two cameras in the same position when you’re taking pictures.

I used two cameras of the same model. This is not absolutely necessary – the whole point of calibration is empirically finding out the parameters of each camera in question, and their relation to each other. Since this is an empirical process, there is no assumption and, really, no need for the cameras to be identical. They won’t be. But using the same resolution prevents postprocessing errors due to resampling, and having the same focal length just makes the whole process easier.

I ended up settling for the Logitech C270. It cost 18.83€ at the time I wrote this post on Amazon, so for both cameras you’re paying less than 40€. I picked this camera because it’s cheap and because it’s easy to modify it if you want to capture near-infrared for e.g. NDVI pictures (for a list of cameras that have been shown to be convertible to capture near-infrared, often with instructions, see this excellent site at Public Labs).

Lenovo C270

The Lenovo C270, one of the pair I’m using for the stereo vision project. According to Public Labs this is a camera that is easy to convert to be able to see near-infrared.

The rest can be made from stuff that you probably have lying around your house, or you can buy it for under 10€ just about anywhere. They are a flat board to attach the cameras to, some universal glue to attach the cameras to it and some duct tape just for good measure. You’ll also need a flat chessboard, which can either be a real chessboard or a printed chessboard glued to a flat surface (back of a cereal box, etc.).

Building the stereo camera

The first step is to find some surface that you can attach the cameras to. The most important point here is that it’s rigid so that the cameras don’t move. I did that by gluing the cameras to a thin wooden board.

The cameras on the actual board I'll be using. Right here they're held on only by glue.

The cameras on the actual board I’ll be using. Right here they’re held on only by glue.

This held them pretty firmly, but for good measure I taped them down on both sides with some duct tape. A more permanent solution would be to drill a hole through the cameras’ clips that goes through the board and then screw them into place, but as this is a prototype I didn’t do that. In a final version, I’ll surely be using other cameras without casings and something more sturdy and lighter than an entire board like this. The point is just to have something that creates 3D images so that I can profile it on different hardware platforms and use it for some rudimentary mapping.

The glued on cameras, duct taped for extra safety.

The glued on cameras, duct taped for extra safety.

As you can see, the duct tape holds them in place quite well.

As you can see, the duct tape holds them in place quite well.

In a final step, print your chessboard if you need to and glue it to something. I used this picture, generiously provided on Martin Peris’ blog (which, by the way, was a large inspiration for pretty much everything in this post):

Sample chessboard to print.

Sample chessboard to print.

After that, connect the cameras to your computer and you’re done! Toaster and fruit not included.

The entire setup - the camera rig, plus the printed chessboard taped to another board.

The entire setup – the camera rig, plus the printed chessboard taped to another board.

Capturing calibration pictures

I’ve already mentioned that I took heavy inspiration from Martin Peris. In fact, if you go to his page, you’ll find working code that will do almost all of the steps I describe in this post. I decided to write my own code nonetheless, not because the code was bad, but because the workflow is not as clear, some parts of the implementation are left to the user, and it’s in C, using the old OpenCV C API. I wrote my implementation in Python for easier understanding and maintenance, and also because I’ll probably reuse the StereoPair class that I used to access the cameras as a pair, either in further Python programs or as a prototype for a C++ class if I’m running it on a Pi or something similar. The StereoPair class makes it a bit simpler if you’re working with stereo cameras in Python, and it cleans up after itself by freeing up the cameras when an object is destroyed. Feel free to use it if you like!

First of all, test if everything works. I’ve written a package with many utilities for working with stereo cameras in general and especially for using them for 3D reconstruction called StereoVision. Get it from PyPI or GitHub to start working with it. For the moment, we’re mainly interested in using the cameras as a stereo pair, which can be done like this, once the package is installed:

me@localhost:~> show_webcams --help
usage: show_webcams [-h] [--output_folder OUTPUT_FOLDER] [--interval INTERVAL]
                    devices devices

Show video from two webcams. Press 'q' to exit.

positional arguments:
  devices               Device numbers for the cameras that should be accessed
                        in order (left, right).

optional arguments:
  -h, --help            show this help message and exit
  --output_folder OUTPUT_FOLDER
                        Folder to write output images to.
  --interval INTERVAL   Interval (s) to take pictures in.

When you run it without any options besides the device numbers, you should see something like this:

If your rig is set up right, the program should show something like this when you run it - the video from both perspectives in two separate windows.

If your rig is set up right, the program should show something like this when you run it – the video from both perspectives in two separate windows.

Things to watch out for are using the right device numbers. My computer recognizes its built in webcam as device 0, but if I connect both cameras before starting up it’s 1, whereas the cameras are 0 and 2, respectively. Also, if you get messages that your USB controller is out of memory, try switching to use different ports. To be sure, I always connected my cameras at startup and left them connected the entire time, but it theoretically shouldn’t matter if you unplug and reconnect them from a live system.

For the calibration, you will need lots of pictures of the chessboard. It’s important that the chessboard is visible for both cameras simultaneously, and optimally it should be photographed from several different angles and positions. You can either write your own software to do that, or manually take a lot of pictures with both cameras and match them up later, or you can use capture_chessboards that takes care of all of that for you. If you want to both capture chessboards and calibrate the camera in one step, you can use the calibrate_cameras utility.

The script asks you for the details on the cameras, the number of inside corners in the chessboard’s rows and columns (the example picture I show above, for example, does not use an 8×8 board and that’s just fine), how many pictures you want and where to save it to. It then keeps on checking the pictures to see if it can find a chessboard in both camera captures. If it does, it stores both pictures in the output folder and waits five seconds so you can reposition. For my purposes, I set it to take 50 pictures.

me@localhost:~> capture_chessboards --help
usage: capture_chessboards [-h] [--rows ROWS] [--columns COLUMNS]
                           [--square-size SQUARE_SIZE]
                           [--calibration-folder CALIBRATION_FOLDER]
                           left right num_pictures output_folder

Take a number of pictures with a stereo camera in which a chessboard is
visible to both cameras. The program waits until a chessboard is detected in
both camera frames. The pictures are then saved to a file in the specified
output folder. After five seconds, the cameras are rescanned to find another
chessboard perspective. This continues until the specified number of pictures
has been taken.

positional arguments:
  left                  Device numbers for the left camera.
  right                 Device numbers for the right camera.
  num_pictures          Number of valid chessboard pictures that should be
                        taken.
  output_folder         Folder to save the images to.

optional arguments:
  -h, --help            show this help message and exit
  --rows ROWS           Number of inside corners in the chessboard's rows.
  --columns COLUMNS     Number of inside corners in the chessboard's columns.
  --square-size SQUARE_SIZE
                        Size of chessboard squares in cm.
  --calibration-folder CALIBRATION_FOLDER
                        Folder to save camera calibration to.
A selection of the stereo images my stereo rig collected.

A selection of the stereo images my stereo rig collected.

Now you’ve got the raw data that you need to calibrate your cameras. Check out the next post to find out how to complete the last steps of the camera calibration and start shooting depth maps!

About

My name’s Daniel Lee. I've founded a company for planning solar power. I've worked on analog space suit interfaces, drones and a bunch of other things in my free time. I'm also involved in standards work for meteorological data. I worked for a while German Weather Service on improving forecasts for weather and renewable power production. I led the team for data ingest there before moving to EUMETSAT.

Tagged with: , ,
Posted in Uncategorized
66 comments on “Building and calibrating a stereo camera with OpenCV (<50€)
  1. […] my last posts, I showed you how to build a stereo camera, calibrate it and tune a block matching algorithm to produce disparity maps. The code is written in […]

    Liked by 1 person

  2. […] the code for the project from my repository on Github Put together your stereo camera Calibrate the […]

    Like

  3. strr says:

    what was the c270 camera’s focal length and did you get efficient results? what was your mean projection error and did you calculate the distance of the objects??
    Buona sera…

    Like

    • erget says:

      The calibration is independent of the focal length, although you will get best results with cameras that have focal lengths of around 50mm – this is pretty close to the undistorted view from a human eye.

      Due to the calibration, you can minimize your projection error, but it’s always going to be different depending on your camera, how you pit together your stereo rig and what calibration pictures you took – in this respect lighting plays an important role too. In my specific instance, I managed to get a projection error of under a pixel, but remember that 1. The reprojection error will be different depending on the pictures you take and 2. It tells you he reprojection error for the chessboards in the calibration pictures.

      Measuring the error objectively is difficult because when you produce a point cloud, it’s a huge number of points that normally match with varying degrees of accuracy to objects that you may have limited knowledge about, so I haven’t converted that into any kind of skill score. However, the results are very plausible, if you take a look at the posts following this one I have a lot of examples that might interest you.

      Like

  4. luisferrel says:

    Greetings Daniel,
    thanks for your tutorial and contribition on this site. I have resently started on working on linux achitecture Ubuntu 12.04 – and very interested on this Opencv working on a stereovision project. First of all, I should mentioned – that I am a beginner on a linux machine coming from a pc environment.
    At any rate, I have been following Martin Peris blog and instructions here on first time on calibrating this chessboard here: http://blog.martinperis.com/2011/01/opencv-stereo-camera-calibration.html
    I have of course all the appropriate software and libraries (like OpenCv running on ubuntu 12.04 LTS on a 32bit machine etc) How ever, on Martins site – he mentions about using Coriander to shot the various checker board angles. Hence, I have installed this coriander – but theres really now documentantion on how to run this program with my USB webcams.
    BTW, I have ran both my webcames from Martin’s source code here: http://blog.martinperis.com/2011/11/opencv-stereo-webcam.html
    I could only get one webcam LEFT to run and another and the RIGHT webcam appears as a black box.
    Lastly, you could point me into some alternatives I would greatly appreciate this!!!
    Thanks in advance! Please contact me by email: mngr5@msn.com Thanks
    Luis Ferrel

    Like

    • erget says:

      Hi Luis,

      I’m not familiar with Coriander, but the software I present in this blog entry should work just fine. Have you tried using it?

      Like

      • luisferrel says:

        Hi Daniel,
        thanks for your reply! And are you referring about the link above called “calibrate camera utility”? Or are you referring about the first link called “capture chessboard”? Hence, when I’ve clicked them both – they both are linked to something highlighted blue saying “stereovision”….
        Could you send me a direct link to mngr5@msn.com with some directions on installing this in the terminal.
        Many Thanks——-

        Like

      • erget says:

        Hi Luis,
        Yes, that’s the link I’m referring to. It’s part of the StereoVision package, which is also linked in this post. I suggest you follow the links and take a look at the packages there. If you click on the StereoVision link, for example, you’ll call up the documentation for StereoVision. The first page is quite short and has the instructions for installing the software – a single line for the command line – highlighted so you can’t miss it. The other links to single parts of the package also lead you to a page where you can find those same instructions.
        I really appreciate your interest in the content and code here and am happy to help you, but so many people visit this blog that I don’t help people by email. If I answer questions here, they are more likely to be found by people who want to ask the same question.
        As far as instructions for installing things on the command line are concerned, see the instructions in the links. If you don’t unerstand those, then your best course of action would be to consult some general manuals on working on the command line or maybe ask a friend who can help you out – it’s really hard to find the exact cause of trouble remotely and it sounds like what you’re probably missing are the basics, so it’s hard to say exactly how I could help you there.
        Also, if you’re interested in working more with your stereo camera, e.g. in using it to create 3D point clouds of objects you image, see the posts following this one. They’ve got detailed instructions on how to do that.

        Like

  5. luisferrel says:

    Hi Daniel,
    Thanks for the feed-back. I actually tried to install Stereovision but got a error message in the terminal with this code: “pip install StereoVision” But I got a error message saying: “error: could not create ‘/usr/local/lib/python2.7/dist-packages/stereovision’: Permission denied”
    I was maybe doing a tar install on the desktop than move it to the appropriate folder later. Any feed back would be appreciated.
    Saludos.
    Luis

    Like

    • erget says:

      Hi Luis,
      Prefix the command with “sudo” and it should work. The error message is telling you that you don’t have write permission on that directory, which is due to the fact that you are executing the command as a normal user, not as admin.

      Like

      • luisferrel says:

        Hi,

        I was able to install this on my desktop. However I was wondering, how I could luanch it, based on your steps about. As I’m uncertain on how to set this up with my webcams connected. If you can give me, 1-2-3 steps to but into the terminal would be very useful for me as I’m truly beginner – hence I’m growing and approving. :))))
        Thanks again!

        Like

      • erget says:

        I’m honestly not sure how to help you more than referring to the blog – there you see a way of calling up the program’s help printout, which explains all of the options that the program offers you. I realize that you’re just starting off and I don’t want to discourage you in any way, but you’ll have to be more specific if you want more than the instructions contained here, for the simple reason that I don’t know what the problem is.

        Like

  6. Haroun says:

    Hi,

    A common problem faced by people when using 2 cameras with linux is a resolution restriction due to bandwidth limitations. In my case im using a PCduino with a single usb port which allows me a max resolution of 320×240 per camera.

    In the StereoVision libraries, VideoCapture() is used which defaults to 640×480. This in turn results in an error : libv4l2: error turning on stream: No space left on device VIDIOC_STREAMON: No space left on device.

    I’ve tried editing (/usr/local/lib/python2.7/dist-packages/stereovision/stereovision.py):

    def __init__(self, devices):
    “””
    Initialize cameras.

    “devices“ is an iterable containing the device numbers.
    “””
    #: Video captures associated with the “StereoPair“
    self.captures = [cv2.VideoCapture(device) for device in devices]

    to set the capture resolution with no success. Until i am able to reduce the resolution, I’m not able to use any of the functions. Your help would be much appreciated.

    Like

    • erget says:

      Hi there,

      I think you mean stereovision/stereo_cameras.py, right? stereovision.py doesn’t exist, but the code snippet you show is from stereo_cameras.py. I don’t see what you changed there though – it looks like lines 51-58 of the original code without being touched. Did you edit the file, or am I missing the difference?

      You should be able to set the resolution using the VideoCapture.set method, like this:


      self.captures = [cv2.VideoCapture(device) for device in devices]
      for capture in self.captures:
      # Use your imagination for the indentation because WordPress doesn't like indented comments ;)
      capture.set(3, 320)
      capture.set(4, 240)

      That would set the capture size of each capture to 320×240. Does that work for you?

      Cheers,
      Daniel

      Like

  7. Abhishek says:

    Awesome post. I wrote another version of stereo calibration code where you can calibrate a stereo camera in real time. I think it can be helpful for someone else.

    Source: https://github.com/upperwal/opencv/blob/master/samples/cpp/stereo_calibrate_real_time.cpp
    Sample Video: http://youtu.be/kizO_s-YUDU

    Like

  8. Yahya says:

    I am using the webcam C270 HD 720p for my project and to do some calculation I need the sensor name and dimentions and also the camera’s focal length. I would appreciate if you can send me this information.

    Best regards,

    Like

    • erget says:

      Hi there.

      Sorry, but I can’t help you here – I don’t know the sensor name, dimensions, or the camera’s focal length. If you read the blog you’ll notice I have no affiliation with Logitech and all the calibration is done empirically, without any a priori knowledge of how the camera’s built. If you’re looking to duplicate my results, you don’t need that knowledge. Otherwise my suggestion would be to contact Logitech – the use of that specific webcam was simply a recommendation from me because it’s what I used.

      Take care!

      Like

  9. Cagdas SECKİN says:

    Hi,

    I’m new at stereo vision and python. I want to try your example codes but argparse didnt find any device or file etc. Can you give examples without argparse? or how can I fix argparse errors?

    Thank you.

    Sincerly

    example error:
    show_webcams.py

    runfile(‘C:/Users/ACS/Documents/Python/erget/show_webcams.py’, wdir=r’C:/Users/ACS/Documents/Python/erget’)
    usage: show_webcams.py [-h] [–output_folder OUTPUT_FOLDER]
    [–interval INTERVAL]
    devices devices
    show_webcams.py: error: too few arguments

    Like

    • erget says:

      Hi there,

      Those aren’t argparse errors – the program is designed to be run from the command line and requires some input to function correctly. So running it from inside a Python interpreter isn’t the intended usage, although that definitely can work.

      If you read the output you’ll see its usage description. It tells you how to use the program from the command line. Try giving it the inputs it needs and it should work. Further description is on the blog – I would suggest reading the entire post so you know what the program wants.

      Cheers,
      Daniel

      Like

    • Maverick says:

      That in’sihtgs just what I’ve been looking for. Thanks!

      Like

  10. Cioby says:

    I am working at the same thing.but is there a problem if the cameras record a little different?I mean there is a slight difference in color from both cameras…could this affect the calibration?

    Like

    • erget says:

      That shouldn’t be a problem, the calibration concerts to black and white first. Later on it should also be fine – the block matchers convert to black and white to find the matching points. The point clouds are colored using the input from the left camera, if I remember correctly, so you won’t have any conflicts there either.

      Like

  11. tasneem says:

    hi
    thanks for this nice tutorial
    but i have a problem when im running the show_webcams file i face this error /

    C:\Python27\python.exe C:/StereoVision-master/bin/show_webcams
    usage: show_webcams [-h] [–output_folder OUTPUT_FOLDER] [–interval INTERVAL]
    devices devices
    show_webcams: error: too few arguments

    Process finished with exit code 2

    im using pycharm2.7.3 with python 27 interpreter
    please help 😦

    Like

    • erget says:

      The error you’re seeing is actually the usage guide for the program. It requires a few arguments in order to be able to run, which are shown. If you provide these required arguments it should run – you called the program without any arguments, so it doesn’t know how to access your webcams.

      Like

      • tasneem says:

        thanx alot for replying but im new to python and idont know how and where to provide this argument can u help or give me a link ?

        Like

      • erget says:

        I don’t know Windows at all, normally I’d just start things from the command line but in Windows it’s probably harder to get there than in Linux. In PyCharm there should be plenty if ways to provide the arguments – google around and you should find them.

        Like

  12. tasneem says:

    ok thanx i will search and tell you if i find the way 🙂

    Like

  13. Cioby says:

    Does your cameras get the same image?I get a slightly different colour from one of them

    Like

    • erget says:

      That shouldn’t be a problem, the algorithm works with black and white images anyway and is robust to slight changes in lighting. The picture is not exactly the same because both are taken from different angles – the differences are what are used to produce the 3d image.

      Like

  14. I am facing some error when i tried to run your code and i don’t know how to fix it.
    The error is that “OpenCV Error: Assertion failed(size.width>0 && size.height>0 in cv::imshow, file ..\..\..\opencv\modules\highgui\src\window.cpp, line 261
    Trackeback(most recent call last):
    File show_webcams”,line 66, in (module)
    main()
    File “show_webcams”, line 50, in main
    pair.show_video()
    File “C:\Python27\lib\site-packages\stereovision\stereo_camera.py”, line 86, in show_videos
    Self.show_frame(1)
    File “C:\Python27\lib\site-packages\stereovision\stereo_camera.py”, line 80, in show_frames
    cv2.imshow(window, frame)
    cv2.error:..\..\..\..\opencv\module\highgui\src\window.cpp:261: error: (-215)
    size.width>0 && size.height>0 in function cv::imshow

    I am using Python 2.7 and opencv 2.4.10

    Like

    • erget says:

      If you look carefully at the traceback you’ll see that it comes down to an assertion error – OpenCV requires both the width and height of the picture it shows to be greater than 0 pixels. This isn’t the case. Did you enter a valid device number?

      Like

  15. draganaat says:

    Hello Daniel!

    First of all, thanks for the great posts!

    I have a couple of questions regarding the camera chosen for this process.
    On this site that you mentioned in the post: http://publiclab.org/wiki/infragram-convertible-cameras it says ”Logitech C270 – This camera no longer has a removable IF filter, it has a coated IF filter. Therefore you cannot change the filter.” – 1. did you succeed in removing the filter on these cameras that you used? Have you tried?
    2. is there any other type of WebCam you would recommend for purposes of making a stereo pair for 3D point clouds (having in mind the desirable maximum simplicity of the process and ability to remove IR filter) ?

    I’m looking forward to your answer, it would mean a lot to me, because I find this topic interesting and would like to make a paper about something similar.

    Greetings!
    Dragana

    Like

    • erget says:

      Hi Dragana,

      I’m glad you like them! 🙂

      I have not tried removing the filter on the cameras I used, and if you’re looking into doing that I would suggest using the site you just referenced – Public Labs does the best job of anybody I know of maintaining good lists for cameras with removable filters thta let you get into NIR. The Creative Notebook Live camera looks quite promising and can be had for cheap – $8 according to the wiki page.

      What are you working on exactly? Would you be interested in collaborating more closely?

      Cheers,
      Daniel

      Like

  16. Harshad Sawalakhe says:

    hi Daniel,
    Thanx for such useful work.


    from argparse import ArgumentParser
    import os

    import cv2
    from progressbar import ProgressBar, Bar, Percentage
    from stereovision.stereo_cameras import ChessboardFinder
    from stereovision.ui_utils import calibrate_folder, CHESSBOARD_ARGUMENTS
    from stereovision.ui_utils import find_files

    PROGRAM_DESCRIPTION=(
    "Take a number of pictures with a stereo camera in which a chessboard is "
    "visible to both cameras. The program waits until a chessboard is detected in "
    "both camera frames. The pictures are then saved to a file in the specified "
    "output folder. After five seconds, the cameras are rescanned to find another "
    "chessboard perspective. This continues until the specified number of pictures "
    "has been taken."
    )

    def main():
    parser = ArgumentParser(description=PROGRAM_DESCRIPTION,
    parents=[CHESSBOARD_ARGUMENTS])
    parser.add_argument("left", metavar="left", type=int,
    help="Device numbers for the left camera.")
    parser.add_argument("right", metavar="right", type=int,
    help="Device numbers for the right camera.")
    parser.add_argument("num_pictures", type=int, help="Number of valid "
    "chessboard pictures that should be taken.")
    parser.add_argument("output_folder", help="Folder to save the images to.")
    parser.add_argument("--calibration-folder", help="Folder to save camera "
    "calibration to.")
    args = parser.parse_args()
    if args.calibration_folder and not args.square_size:
    args.print_help()

    progress = ProgressBar(maxval=args.num_pictures,
    widgets=[Bar("=", "[", "]"),
    " ", Percentage()])
    if not os.path.exists(args.output_folder):
    os.makedirs(args.output_folder)
    progress.start()
    with ChessboardFinder((args.left, args.right)) as pair:
    for i in range(args.num_pictures):
    frames = pair.get_chessboard(args.columns, args.rows, True)
    for side, frame in zip(("left", "right"), frames):
    number_string = str(i + 1).zfill(len(str(args.num_pictures)))
    filename = "{}_{}.ppm".format(side, number_string)
    output_path = os.path.join(args.output_folder, filename)
    cv2.imwrite(output_path, frame)
    progress.update(progress.maxval - (args.num_pictures - i))
    for i in range(10):
    pair.show_frames(1)
    progress.finish()
    if args.calibration_folder:
    args.input_files = find_files(args.output_folder)
    args.output_folder = args.calibration_folder
    args.show_chessboards = True
    calibrate_folder(args)

    if __name__ == "__main__":
    main()

    Im new to python please . Im getting error while running this code ,

    And getting following reply


    harshad@harshad-Lenovo-G580:~/StereoVision-master$ python calibrate_camera.py 7 10
    7
    Traceback (most recent call last):
    File "calibrate_camera.py", line 55, in
    main()
    File "calibrate_camera.py", line 50, in main
    args.input_files = find_files(args.input_folder)
    File "/home/harshad/StereoVision-master/stereovision/ui_utils.py", line 68, in find_files
    files = [i for i in os.listdir(folder) if i.startswith("left")]
    OSError: [Errno 2] No such file or directory: '7'

    Like

    • erget says:

      Hi Harshad,

      It looks like you pasted in the code for calibrate_camera.py into the comment box? Or is that modified code by you? It’s considered polite to prepare the content you’re wanting to troubleshoot, reducing it to the minimal amount necessary to understand the problem. This also ensures that you look over the problem yourself. I won’t be reading through those 60 lines of code – sorry 🙂

      Also, in Python indentation is syntax relevant, so the code you pasted in at the top wouldn’t work.

      Concerning the lower block of code where you call up calibrate_camera.py – you’re looking at a classic user error there. Why don’t you read the help for the program? You can call up any program’s help text like this:


      $PROGRAM_NAME -h

      or


      $PROGRAM_NAME --help

      for a longer version of the help. Also, if you read the following post, which I reference in the post you’re reading right now, you’ll find even more information that will help you out.

      Cheers,
      Daniel

      Like

  17. Harshad Sawalakhe says:

    ~$ show webcams
    The program ‘show’ is currently not installed. You can install it by typing:
    sudo apt-get install nmh
    :~$ sudo apt-get install nmh
    Reading package lists… Done
    Building dependency tree
    Reading state information… Done
    nmh is already the newest version.
    0 upgraded, 0 newly installed, 0 to remove and 34 not upgraded.

    Hey Daniel if ‘show’ is installed as shown above why its showing that ‘show’ is not installed?

    Like

    • erget says:

      Hi Harshad,

      You’re misspelling the command when you type it in. The computer is pretty dumb and won’t interpret what you enter – you have to use commands exactly according to the way they’re written. Here you’ve got a space in the middle of the program’s name, which is incorrect. Check your spelling and try it out again. Good luck!

      Daniel

      Like

  18. tonz1992 says:

    HI i would please like to ask what is the recommended resolution to use when capturing images with the camera. i imagine the higher the resolution of the camera , the more computing time it would take. have you got any idea on the optimum resolution?

    Like

    • erget says:

      The resolution is really the result of your needs – for real time applications you might need less to save time, if you’re performing offline reconstructions and detail is a priority you can use high resolution. Also, it should be noted that you don’t have to compute the reconstructions on the same device that captured the images – the computations could be offloaded to a dedicated device, or a cloud application if you’re willing to build it.

      Liked by 1 person

  19. Dan says:

    Hi Daniel,

    I’m new to Raspberry Pi and OpenCV. This looks like an interesting project I would like to try out.

    However, I’m facing some issues when trying to download and install your StereoVision package. I get the following error when I type pip install StereoVision.

    Exception:
    Traceback (most recent call last):
    File “/usr/local/lib/python2.7/dist-packages/pip/basecommand.py”, line 215, in main
    status = self.run(options, args)
    File “/usr/local/lib/python2.7/dist-packages/pip/commands/install.py”, line 317, in run
    prefix=options.prefix_path,
    File “/usr/local/lib/python2.7/dist-packages/pip/req/req_set.py”, line 742, in install
    **kwargs
    File “/usr/local/lib/python2.7/dist-packages/pip/req/req_install.py”, line 831, in install
    self.move_wheel_files(self.source_dir, root=root, prefix=prefix)
    File “/usr/local/lib/python2.7/dist-packages/pip/req/req_install.py”, line 1032, in move_wheel_files
    isolated=self.isolated,
    File “/usr/local/lib/python2.7/dist-packages/pip/wheel.py”, line 346, in move_wheel_files
    clobber(source, lib_dir, True)
    File “/usr/local/lib/python2.7/dist-packages/pip/wheel.py”, line 317, in clobber
    ensure_dir(destdir)
    File “/usr/local/lib/python2.7/dist-packages/pip/utils/__init__.py”, line 83, in ensure_dir
    os.makedirs(path)
    File “/usr/lib/python2.7/os.py”, line 157, in makedirs
    mkdir(name, mode)
    OSError: [Errno 13] Permission denied: ‘/usr/local/lib/python2.7/dist-packages/StereoVision-1.0.3.dist-info’

    Would happen to be able to solve my problem?

    Thanks in Advance
    Dan

    Like

    • erget says:

      Hi Dan,
      First of all my apologies for getting back to you so late! I don’t know why, but I didn’t see the alert about your comment until just now.
      You’ll find the solution to your problem in the last line of the error message:
      OSError: [Errno 13] Permission denied: ...
      You don’t have write permissions for that directory. The reason is that it’s in the root area of your file system, not in your user area. One of the following things will fix it:

      1. Install the package into your userspace, i.e. pip install --user StereoVision
      2. Install the package as root, i.e. sudo pip install StereoVision

      Cheers,
      Daniel

      Like

  20. Dr. Chao Wu says:

    Erget,

    Thanks for sharing. I have a question why the distance between two cameras are not used in the calibration process. By default, I think that is a very important parameter in the stereo system . Any reference on this?

    Thanks.

    Like

    • erget says:

      Yes, all that call does is calibrate using OpenCV. You can check their documentation for more information. I think OpenCV extracts the metrics from the size of the squares in the chessboard you use for calibration.

      Like

  21. yugspatel says:

    Hi daniel,
    i am yogi, new to python scripting and stereo vision field. i am using stereovision concept to develop 3D point cloud data of honeycomb structure.
    can you please tell me which softwares do i need to install for getting started with this project at initial step.
    e.x. openCV?
    visual studio?
    Python?

    Like

    • erget says:

      Hi Yogi, this is the first of a series of tutorials – they’re all connected by links. If you read them you’ll find out everything you need to know in order to get the things working. If you’re looking for general tips on how to program this is probably not the right place to find it but if you want materials for absolute beginners, I might suggest the other, bigger project I’m working on right now: fullstackembedded.com. You might also try Data Camp, which has great resources for anybody getting started.

      Like

  22. Ansuman Pradhan says:

    Hi Daniel,

    Thank you for this post. I am new to Computer Vision and it will be very helpful to me for getting started. Currently, I am trying to use stereo vision for ego-estimation of a small four wheeled bot. I came across your blog while I was looking for ways to build my own stereo rig. Buying a stereo-camera set is out of question as it is too expensive. What I have realized is that the major problem people face is related to synchronizing the two separate cameras of the stereo rig. The calibration that you did in this post, I am curious if it takes care of synchronisation as well. Or is it just for producing 3D point clouds given two separate images from the two cameras? Do you have any suggestions of how to perform synchronization? I mean, if you have done something of this sort it would be great if you can share your experience. Thank you.

    Like

  23. erget says:

    I’m glad you like the tutorial! In practice, the cameras fire in a synchronized fashion – but that’s in practice. The code itself doesn’t deal with picture synchronization – that’s very connected to how you set up your rig and where you obtain your images from, whereas the library I show here is mostly concerned with producing point clouds, with obtaining the images as a secondary concern. As such, the calls to the cameras are issued sequentially, directly after one another. I’ve never noticed a lag between the two pictures, but if lag is absolutely unacceptable to you, this might be an issue.

    If you want to have true synchronization, you’ll probably need to have some kind of a microchip which you delegate the task of firing the cameras to. That way it can do that simultaneously. I’m not aware of any way of guaranteeing synchronicity using USB in Linux, as you’re issuing the call from userspace and then the kernel schedules the task. If truly synchronized firing is an issue for you, at the end of the day you’ll probably be better off buying a stereo rig rather than building one.

    Like

    • Ansuman Pradhan says:

      Thank you for the reply Daniel. I get the general idea. Seems a difficult task for achieving complete sync, unless it is hardware synchronised. I will try with simple cameras and may be an arduino chip and see how much synchronisation I achieve.

      Like

  24. Hi Daniel,

    does your library work with more than two cameras? I would like to start testing with four cameras. Is it possible? What should I set to do this?

    Like

    • erget says:

      Hi Artur,

      Out of the box it won’t, but I’d be interested in hearing what you plan to do with 4 cameras. Strictly speak that goes beyond the realm of stereovision and indeed I don’t see the benefit of using stereovision with 4 cameras. With that many poses, what would benefit you the most would be structure from motion, which is a cooler algorithm anyway. It’s not supported by this package though, unfortunately.

      Like

      • I thought that more cameras gives more information about 3D points and better accuracy.

        Can you send information about minimal requirements for python, cv2 and other packages version in order to run your library? I had some errors in calibration and tuning scripts.

        Like

  25. kahlju says:

    Hey Daniel,

    I’m struggling a little with your bin files you’re running. You’re using shebang files so I’m also using python 2.7. I think there is something not working with the parser for me. I can run your help file so the program seems to work fine. I installed it in windows. It seems you’re using linux. Can you tell me more about your environment? Python Version, OS, other programs and modules needed to be installed. Is this referencing C code that I can’t see? I’m a mechanical engineer trying to integrate a sensor into my project, so programming isn’t my strong-suite. I’m using Eclipse as my IDLE with pydev. I can’t seem to just run the program without any options. It just gives me the error “Show_webcams: error: too few arguments” and “calibrate_cameras: error: too few arguments.” Is there something I missed? Is there a program that needs to be edited or modified first? How does it know which device to choose?

    Thank you,
    ~Justin Kahl

    Like

    • kahlju says:

      Actually, you can disregard a lot of that. I got it to work in command prompt. I guess it wasn’t as clear to me that you needed to input a number that is related to the order of the device manager menu (arcsoft web share is 0, hp hd webca fixed is 1 and this is 2). The code didn’t exactly say the format of the devices but there may be a help file for something I didn’t do in the correct order. Now, I have a different question. I’m using LI-OV580 from leopard imaging which if read like this would put a image side by side in each of the windows that show. The device has two pins if you open up graphedit and render the pins. Do you have any idea how I would modifiy this code to be able to reference each of the pins as a camera right and the other pin as camera left? I’m having trouble tracing the programs and libraries. Which library file directs to the the camera’s reference number and how would I modify that to look at the pins.

      Like

    • erget says:

      Hi Kahlju,

      Sorry for taking so long to get back to you – I don’t always see comments right away. It looks like you got some pretty involved help on the SO thread so I’ll leave you in the hands of those experts. Your question is pretty involved, and most of it seems to be related to drilling down into the pin handling with the camera.

      My tip would be to subclass StereoPair to deal with your specific case of camera. Then you can process the images you obtain with it using the methods of the superclass.

      HTH,
      Daniel

      Like

      • kahlju says:

        Yeah, I had figured that part out and I found one of the github extensions had a later release that took care of it in the class. I wasn’t using the latest Stereovision release. However, I see 3 releases on github and there is a 1.0.4 in pypi. Is this from you? Do you know why Douglas Gibbons split off his own version of the code?

        I have some issues with the GUI crashing but I believe it’s a problem with versions of the modules/libraries I’m using. I’m also trying to run in windows and I’m sure that’s not the best for this. Do you have a working copy right now and what versions of python, argparse, opencv, matplotlib, numpy and what is your IDE? I’m using Python 2.7.14, OpenCV 3.3. I think the code was not made for opencv 3.3 or something. I reverted back to opencv 3.1 and got a little further but then the GUI starts crashing when I adjust it. It looks like the code was converted to Python 3 at some point but I’m not sure why somethings stopped working even going through the debugger. I’d just like a set of known working versions of the program that I can still download. I felt like it may have been a video or something you made that mentioned anaconda. If so, what version?

        Thank you for all your help,
        ~Justin Kahl

        Like

      • erget says:

        Hi Justin, no, I’ve never used Anaconda for StereoVision but I don’t think it’s a bad idea. Right now I don’t have a stereo rig that I work with so it’s hard to test the code (I am an avid tester, but when hardware is involved it becomes difficult). Python 2.7 should be fine – that’s the version I developed with – but I was using opencv2, not opencv3.
        Also, I would suggest working in Linux – it makes it a lot easier to find the answers to problem. I’m not sure what exactly is the problem in your case, and since I’m in Accra in Ghana right now I only have Internet very sporadically. I also haven’t been involved in any of the other forks so I can’t really say why they were made or not made. Maybe you should ask those developers? They’re sure to have their reasons 🙂

        Take care!
        Daniel

        Like

  26. Jeff Gair says:

    hey this is really very nice and informative article.

    Like

  27. Hi Daniel, I am Atmadeep Arya, an undergrad student in computer sciences. I have cloned your GitHub repository and have all the files. Can you please help me with the following errors occurred:
    1. I cannot run any of your files in my system from the terminal.
    2. I have StereoVision on pip (2 and 3) as well, can’t use them.
    Can you please also guide me in Stereo vision and image processing stuff?
    Thanks for help.

    Like

    • erget says:

      Hi Atmadeep, you’re probably having trouble with your search path – I suggest reading up on installing things with pip and finding the binaries on the search path, it’s beyond the scope of this blog.

      Like

  28. Arpit Srivastava says:

    Traceback (most recent call last):
    File “/usr/local/bin/calibrate_cameras”, line 24, in
    from stereovision.ui_utils import (find_files, calibrate_folder,
    File “/usr/local/bin/stereovision.py”, line 4, in
    __import__(‘pkg_resources’).run_script(‘StereoVision==0.4.dev0’, ‘stereovision.py’)
    File “/usr/lib/python2.7/dist-packages/pkg_resources/__init__.py”, line 719, in run_script
    self.require(requires)[0].run_script(script_name, ns)
    File “/usr/lib/python2.7/dist-packages/pkg_resources/__init__.py”, line 943, in require
    needed = self.resolve(parse_requirements(requirements))
    File “/usr/lib/python2.7/dist-packages/pkg_resources/__init__.py”, line 834, in resolve
    raise VersionConflict(dist, req).with_context(dependent_req)
    pkg_resources.VersionConflict: (StereoVision 1.0.4 (/usr/local/lib/python2.7/dist-packages), Requirement.parse(‘StereoVision==0.4.dev0’))

    can you help me??

    Like

  29. Brian Meier says:

    Thank you very much for these tutorials and code! Will be using it to automate and improve calibration of an industrial robot.

    Like

  30. HongSeeHee says:

    Atmadeep arya says:
    January 27, 2018 at 17:57
    Hi Daniel, I am Hong Seo hee, an undergrad student in Game software.
    I want to know the actual distance between pictures and objects through stereo vision, but I don’t know how to calculate them.
    I try to use Visual Studio 2015(C++) ,opencv and two cameras.
    After measuring the distance, I want to put on the screen two pictures and the calculated distance together.
    Can you help me?

    Like

  31. […] kind of setup. If you want to make your own dual camera system for better results you should check Daniel Lee’s blog about […]

    Like

  32. Dhruv says:

    Hello, I am trying to implement the stereo vision using rpi 4 and 2 logitech webcams but whenever I try to calibrate the cameras, the whole thing hangs up and I have to restart it. Although everything was fine when I did it using my computer. I think lowering the resolution of the camera might work but I dont know how to do it for two cameras. Can somebody please help me? Btw I am new to linux and python.

    Like

Leave a comment

From the archive