Search in sources :

Example 1 with StereoParameters

use of boofcv.struct.calib.StereoParameters in project BoofCV by lessthanoptimal.

the class CalibrateStereoPlanarGuiApp method process.

public void process(String outputFileName) {
    // displays progress so the impatient don't give up
    final ProcessThread monitor = new ProcessThread();
    monitor.start();
    // load images
    calibrator.reset();
    int N = leftImages.size();
    for (int i = 0; i < N; i++) {
        final BufferedImage leftOrig = media.openImage(leftImages.get(i).getPath());
        final BufferedImage rightOrig = media.openImage(rightImages.get(i).getPath());
        if (leftOrig != null && rightOrig != null) {
            GrayF32 leftInput = ConvertBufferedImage.convertFrom(leftOrig, (GrayF32) null);
            GrayF32 rightInput = ConvertBufferedImage.convertFrom(rightOrig, (GrayF32) null);
            CalibrationObservation calibLeft, calibRight;
            if (!detector.process(leftInput)) {
                System.out.println("Feature detection failed in " + leftImages.get(i));
                continue;
            }
            calibLeft = detector.getDetectedPoints();
            if (!detector.process(rightInput)) {
                System.out.println("Feature detection failed in " + rightImages.get(i));
                continue;
            }
            calibRight = detector.getDetectedPoints();
            calibrator.addPair(calibLeft, calibRight);
            final int number = i;
            SwingUtilities.invokeLater(() -> {
                gui.addPair("Image " + number, leftImages.get(number), rightImages.get(number));
                gui.repaint();
                monitor.setMessage(0, "Image " + number);
            });
        } else {
            System.out.println("Failed to load left  = " + leftImages.get(i));
            System.out.println("Failed to load right = " + rightImages.get(i));
        }
    }
    // SwingUtilities.invokeLater(new Runnable() {
    // public void run() {
    // gui.setObservations(calibrator.getCalibLeft().getObservations(),calibrator.getCalibLeft().getErrors(),
    // calibrator.getCalibRight().getObservations(),calibrator.getCalibRight().getErrors());
    // }});
    // gui.repaint();
    SwingUtilities.invokeLater(new Runnable() {

        public void run() {
            monitor.setMessage(1, "Estimating Parameters");
        }
    });
    StereoParameters param = calibrator.process();
    SwingUtilities.invokeLater(new Runnable() {

        public void run() {
            gui.setObservations(calibrator.getCalibLeft().getObservations(), calibrator.getCalibLeft().getErrors(), calibrator.getCalibRight().getObservations(), calibrator.getCalibRight().getErrors());
        }
    });
    gui.repaint();
    // compute stereo rectification
    setRectification(param);
    monitor.stopThread();
    calibrator.printStatistics();
    param.print();
    if (outputFileName != null)
        CalibrationIO.save(param, outputFileName);
}
Also used : GrayF32(boofcv.struct.image.GrayF32) StereoParameters(boofcv.struct.calib.StereoParameters) BufferedImage(java.awt.image.BufferedImage) ConvertBufferedImage(boofcv.io.image.ConvertBufferedImage) CalibrationObservation(boofcv.alg.geo.calibration.CalibrationObservation)

Example 2 with StereoParameters

use of boofcv.struct.calib.StereoParameters in project BoofCV by lessthanoptimal.

the class ExampleCalibrateStereo method process.

/**
 * Process calibration images, compute intrinsic parameters, save to a file
 */
public void process() {
    // Declare and setup the calibration algorithm
    var calibratorAlg = new CalibrateStereoPlanar(detector.getLayout());
    calibratorAlg.configure(/*zero skew*/
    true, /* radial */
    4, /* tangential */
    false);
    // Uncomment to print more information to stdout
    // calibratorAlg.setVerbose(System.out,null);
    // ensure the lists are in the same order
    Collections.sort(left);
    Collections.sort(right);
    for (int i = 0; i < left.size(); i++) {
        BufferedImage l = UtilImageIO.loadImageNotNull(left.get(i));
        BufferedImage r = UtilImageIO.loadImageNotNull(right.get(i));
        GrayF32 imageLeft = ConvertBufferedImage.convertFrom(l, (GrayF32) null);
        GrayF32 imageRight = ConvertBufferedImage.convertFrom(r, (GrayF32) null);
        CalibrationObservation calibLeft, calibRight;
        if (!detector.process(imageLeft)) {
            System.out.println("Failed to detect target in " + left.get(i));
            continue;
        }
        calibLeft = detector.getDetectedPoints();
        if (!detector.process(imageRight)) {
            System.out.println("Failed to detect target in " + right.get(i));
            continue;
        }
        calibRight = detector.getDetectedPoints();
        calibratorAlg.addPair(calibLeft, calibRight);
    }
    // Process and compute calibration parameters
    StereoParameters stereoCalib = calibratorAlg.process();
    // print out information on its accuracy and errors
    calibratorAlg.printStatistics();
    // save results to a file and print out
    CalibrationIO.save(stereoCalib, "stereo.yaml");
    stereoCalib.print();
// Note that the stereo baseline translation will be specified in the same units as the calibration grid.
// Which is in millimeters (mm) in this example.
}
Also used : CalibrateStereoPlanar(boofcv.abst.geo.calibration.CalibrateStereoPlanar) GrayF32(boofcv.struct.image.GrayF32) StereoParameters(boofcv.struct.calib.StereoParameters) BufferedImage(java.awt.image.BufferedImage) ConvertBufferedImage(boofcv.io.image.ConvertBufferedImage) CalibrationObservation(boofcv.alg.geo.calibration.CalibrationObservation)

Example 3 with StereoParameters

use of boofcv.struct.calib.StereoParameters in project BoofCV by lessthanoptimal.

the class ExampleOverheadView method main.

public static void main(String[] args) {
    BufferedImage input = UtilImageIO.loadImageNotNull(UtilIO.pathExample("road/left01.png"));
    Planar<GrayU8> imageRGB = ConvertBufferedImage.convertFromPlanar(input, null, true, GrayU8.class);
    StereoParameters stereoParam = CalibrationIO.load(UtilIO.pathExample("road/stereo01.yaml"));
    Se3_F64 groundToLeft = CalibrationIO.load(UtilIO.pathExample("road/ground_to_left_01.yaml"));
    CreateSyntheticOverheadView<Planar<GrayU8>> generateOverhead = new CreateSyntheticOverheadViewPL<>(InterpolationType.BILINEAR, 3, GrayU8.class);
    // size of cells in the overhead image in world units
    double cellSize = 0.05;
    // You can use this to automatically select reasonable values for the overhead image
    SelectOverheadParameters selectMapSize = new SelectOverheadParameters(cellSize, 20, 0.5);
    selectMapSize.process(stereoParam.left, groundToLeft);
    int overheadWidth = selectMapSize.getOverheadWidth();
    int overheadHeight = selectMapSize.getOverheadHeight();
    Planar<GrayU8> overheadRGB = new Planar<>(GrayU8.class, overheadWidth, overheadHeight, 3);
    generateOverhead.configure(stereoParam.left, groundToLeft, selectMapSize.getCenterX(), selectMapSize.getCenterY(), cellSize, overheadRGB.width, overheadRGB.height);
    generateOverhead.process(imageRGB, overheadRGB);
    // note that the left/right values are swapped in the overhead image. This is an artifact of the plane's
    // 2D coordinate system having +y pointing up, while images have +y pointing down.
    BufferedImage output = ConvertBufferedImage.convertTo(overheadRGB, null, true);
    ShowImages.showWindow(input, "Input Image", true);
    ShowImages.showWindow(output, "Overhead Image", true);
}
Also used : CreateSyntheticOverheadViewPL(boofcv.alg.sfm.overhead.CreateSyntheticOverheadViewPL) SelectOverheadParameters(boofcv.alg.sfm.overhead.SelectOverheadParameters) Planar(boofcv.struct.image.Planar) GrayU8(boofcv.struct.image.GrayU8) StereoParameters(boofcv.struct.calib.StereoParameters) BufferedImage(java.awt.image.BufferedImage) ConvertBufferedImage(boofcv.io.image.ConvertBufferedImage) Se3_F64(georegression.struct.se.Se3_F64)

Example 4 with StereoParameters

use of boofcv.struct.calib.StereoParameters in project BoofCV by lessthanoptimal.

the class ExampleStereoDisparity method main.

public static void main(String[] args) {
    String calibDir = UtilIO.pathExample("calibration/stereo/Bumblebee2_Chess/");
    String imageDir = UtilIO.pathExample("stereo/");
    StereoParameters param = CalibrationIO.load(new File(calibDir, "stereo.yaml"));
    // load and convert images into a BoofCV format
    BufferedImage origLeft = UtilImageIO.loadImage(imageDir, "chair01_left.jpg");
    BufferedImage origRight = UtilImageIO.loadImage(imageDir, "chair01_right.jpg");
    GrayU8 distLeft = ConvertBufferedImage.convertFrom(origLeft, (GrayU8) null);
    GrayU8 distRight = ConvertBufferedImage.convertFrom(origRight, (GrayU8) null);
    // rectify images
    GrayU8 rectLeft = distLeft.createSameShape();
    GrayU8 rectRight = distRight.createSameShape();
    rectify(distLeft, distRight, param, rectLeft, rectRight);
    // compute disparity
    int disparityRange = 60;
    GrayU8 disparity = denseDisparity(rectLeft, rectRight, 5, 10, disparityRange);
    // GrayF32 disparity = denseDisparitySubpixel(rectLeft, rectRight, 5, 10, disparityRange);
    // show results
    BufferedImage visualized = VisualizeImageData.disparity(disparity, null, disparityRange, 0);
    var gui = new ListDisplayPanel();
    gui.addImage(rectLeft, "Rectified");
    gui.addImage(visualized, "Disparity");
    ShowImages.showWindow(gui, "Stereo Disparity", true);
}
Also used : ListDisplayPanel(boofcv.gui.ListDisplayPanel) GrayU8(boofcv.struct.image.GrayU8) StereoParameters(boofcv.struct.calib.StereoParameters) File(java.io.File) BufferedImage(java.awt.image.BufferedImage) ConvertBufferedImage(boofcv.io.image.ConvertBufferedImage)

Example 5 with StereoParameters

use of boofcv.struct.calib.StereoParameters in project BoofCV by lessthanoptimal.

the class ExampleRectifyCalibratedStereo method main.

public static void main(String[] args) {
    String dir = UtilIO.pathExample("calibration/stereo/Bumblebee2_Chess/");
    StereoParameters param = CalibrationIO.load(new File(dir, "stereo.yaml"));
    // load images
    BufferedImage origLeft = UtilImageIO.loadImage(dir, "left05.jpg");
    BufferedImage origRight = UtilImageIO.loadImage(dir, "right05.jpg");
    // distorted images
    Planar<GrayF32> distLeft = ConvertBufferedImage.convertFromPlanar(origLeft, null, true, GrayF32.class);
    Planar<GrayF32> distRight = ConvertBufferedImage.convertFromPlanar(origRight, null, true, GrayF32.class);
    // storage for undistorted + rectified images
    Planar<GrayF32> rectLeft = distLeft.createSameShape();
    Planar<GrayF32> rectRight = distRight.createSameShape();
    // Compute rectification
    RectifyCalibrated rectifyAlg = RectifyImageOps.createCalibrated();
    Se3_F64 leftToRight = param.getRightToLeft().invert(null);
    // original camera calibration matrices
    DMatrixRMaj K1 = PerspectiveOps.pinholeToMatrix(param.getLeft(), (DMatrixRMaj) null);
    DMatrixRMaj K2 = PerspectiveOps.pinholeToMatrix(param.getRight(), (DMatrixRMaj) null);
    rectifyAlg.process(K1, new Se3_F64(), K2, leftToRight);
    // rectification matrix for each image
    DMatrixRMaj rect1 = rectifyAlg.getUndistToRectPixels1();
    DMatrixRMaj rect2 = rectifyAlg.getUndistToRectPixels2();
    // New calibration matrix,
    // Both cameras have the same one after rectification.
    DMatrixRMaj rectK = rectifyAlg.getCalibrationMatrix();
    // Adjust the rectification to make the view area more useful
    RectifyImageOps.fullViewLeft(param.left, rect1, rect2, rectK, null);
    // RectifyImageOps.allInsideLeft(param.left, rect1, rect2, rectK, null);
    // undistorted and rectify images
    // TODO simplify code some how
    var rect1_F32 = new FMatrixRMaj(3, 3);
    var rect2_F32 = new FMatrixRMaj(3, 3);
    ConvertMatrixData.convert(rect1, rect1_F32);
    ConvertMatrixData.convert(rect2, rect2_F32);
    ImageDistort<Planar<GrayF32>, Planar<GrayF32>> rectifyImageLeft = RectifyDistortImageOps.rectifyImage(param.getLeft(), rect1_F32, BorderType.SKIP, distLeft.getImageType());
    ImageDistort<Planar<GrayF32>, Planar<GrayF32>> rectifyImageRight = RectifyDistortImageOps.rectifyImage(param.getRight(), rect2_F32, BorderType.SKIP, distRight.getImageType());
    rectifyImageLeft.apply(distLeft, rectLeft);
    rectifyImageRight.apply(distRight, rectRight);
    // convert for output
    BufferedImage outLeft = ConvertBufferedImage.convertTo(rectLeft, null, true);
    BufferedImage outRight = ConvertBufferedImage.convertTo(rectRight, null, true);
    // show results and draw a horizontal line where the user clicks to see rectification easier
    var panel = new ListDisplayPanel();
    panel.addItem(new RectifiedPairPanel(true, origLeft, origRight), "Original");
    panel.addItem(new RectifiedPairPanel(true, outLeft, outRight), "Rectified");
    ShowImages.showWindow(panel, "Stereo Rectification Calibrated", true);
}
Also used : FMatrixRMaj(org.ejml.data.FMatrixRMaj) ListDisplayPanel(boofcv.gui.ListDisplayPanel) RectifyCalibrated(boofcv.alg.geo.rectify.RectifyCalibrated) DMatrixRMaj(org.ejml.data.DMatrixRMaj) RectifiedPairPanel(boofcv.gui.stereo.RectifiedPairPanel) BufferedImage(java.awt.image.BufferedImage) ConvertBufferedImage(boofcv.io.image.ConvertBufferedImage) GrayF32(boofcv.struct.image.GrayF32) Planar(boofcv.struct.image.Planar) StereoParameters(boofcv.struct.calib.StereoParameters) File(java.io.File) Se3_F64(georegression.struct.se.Se3_F64)

Aggregations

StereoParameters (boofcv.struct.calib.StereoParameters)27 Se3_F64 (georegression.struct.se.Se3_F64)12 ConvertBufferedImage (boofcv.io.image.ConvertBufferedImage)9 BufferedImage (java.awt.image.BufferedImage)9 GrayF32 (boofcv.struct.image.GrayF32)8 Test (org.junit.jupiter.api.Test)8 CameraPinholeBrown (boofcv.struct.calib.CameraPinholeBrown)7 GrayU8 (boofcv.struct.image.GrayU8)7 File (java.io.File)5 Point2D_F64 (georegression.struct.point.Point2D_F64)4 Point3D_F64 (georegression.struct.point.Point3D_F64)4 RectifyCalibrated (boofcv.alg.geo.rectify.RectifyCalibrated)3 ListDisplayPanel (boofcv.gui.ListDisplayPanel)3 CalibrationObservation (boofcv.alg.geo.calibration.CalibrationObservation)2 Planar (boofcv.struct.image.Planar)2 DMatrixRMaj (org.ejml.data.DMatrixRMaj)2 ConfigSpeckleFilter (boofcv.abst.disparity.ConfigSpeckleFilter)1 CalibrateStereoPlanar (boofcv.abst.geo.calibration.CalibrateStereoPlanar)1 CreateSyntheticOverheadViewPL (boofcv.alg.sfm.overhead.CreateSyntheticOverheadViewPL)1 SelectOverheadParameters (boofcv.alg.sfm.overhead.SelectOverheadParameters)1