Search in sources :

Example 1 with ImageDistort

use of boofcv.alg.distort.ImageDistort 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.calibrationMatrix(param.getLeft(), (DMatrixRMaj) null);
    DMatrixRMaj K2 = PerspectiveOps.calibrationMatrix(param.getRight(), (DMatrixRMaj) null);
    rectifyAlg.process(K1, new Se3_F64(), K2, leftToRight);
    // rectification matrix for each image
    DMatrixRMaj rect1 = rectifyAlg.getRect1();
    DMatrixRMaj rect2 = rectifyAlg.getRect2();
    // 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);
    // RectifyImageOps.allInsideLeft(param.left, leftHanded, rect1, rect2, rectK);
    // undistorted and rectify images
    // TODO simplify code some how
    FMatrixRMaj rect1_F32 = new FMatrixRMaj(3, 3);
    FMatrixRMaj rect2_F32 = new FMatrixRMaj(3, 3);
    ConvertMatrixData.convert(rect1, rect1_F32);
    ConvertMatrixData.convert(rect2, rect2_F32);
    ImageDistort rectifyImageLeft = RectifyImageOps.rectifyImage(param.getLeft(), rect1_F32, BorderType.SKIP, distLeft.getImageType());
    ImageDistort rectifyImageRight = RectifyImageOps.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
    ListDisplayPanel 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) ImageDistort(boofcv.alg.distort.ImageDistort) RectifiedPairPanel(boofcv.gui.stereo.RectifiedPairPanel) BufferedImage(java.awt.image.BufferedImage) ConvertBufferedImage(boofcv.io.image.ConvertBufferedImage) GrayF32(boofcv.struct.image.GrayF32) StereoParameters(boofcv.struct.calib.StereoParameters) File(java.io.File) Se3_F64(georegression.struct.se.Se3_F64)

Example 2 with ImageDistort

use of boofcv.alg.distort.ImageDistort in project BoofCV by lessthanoptimal.

the class BatchRemoveLensDistortion method main.

public static void main(String[] args) {
    String inputPath, regex, pathIntrinsic, outputDir;
    AdjustmentType adjustmentType = AdjustmentType.FULL_VIEW;
    boolean rename = false;
    if (args.length >= 4) {
        int numFlags = args.length - 4;
        for (int i = 0; i < numFlags; i++) {
            if (args[i].compareToIgnoreCase("-rename") == 0) {
                rename = true;
            } else if (args[i].compareToIgnoreCase("-EXPAND") == 0) {
                adjustmentType = AdjustmentType.EXPAND;
            } else if (args[i].compareToIgnoreCase("-FULL_VIEW") == 0) {
                adjustmentType = AdjustmentType.FULL_VIEW;
            } else {
                System.err.println("Unknown flag " + args[i]);
            }
        }
        inputPath = args[numFlags];
        regex = args[numFlags + 1];
        pathIntrinsic = args[numFlags + 2];
        outputDir = args[numFlags + 3];
    } else {
        printHelpAndExit(args);
        System.exit(0);
        return;
    }
    System.out.println("AdjustmentType = " + adjustmentType);
    System.out.println("rename         = " + rename);
    System.out.println("input path     = " + inputPath);
    System.out.println("name regex     = " + regex);
    System.out.println("output dir     = " + outputDir);
    File fileOutputDir = new File(outputDir);
    if (!fileOutputDir.exists()) {
        if (!fileOutputDir.mkdirs()) {
            throw new RuntimeException("Output directory did not exist and failed to create it");
        } else {
            System.out.println("  created output directory");
        }
    }
    CameraPinholeRadial param = CalibrationIO.load(pathIntrinsic);
    CameraPinholeRadial paramAdj = new CameraPinholeRadial();
    List<File> files = Arrays.asList(UtilIO.findMatches(new File(inputPath), regex));
    Collections.sort(files);
    System.out.println("Found a total of " + files.size() + " matching files");
    Planar<GrayF32> distoredImg = new Planar<>(GrayF32.class, param.width, param.height, 3);
    Planar<GrayF32> undistoredImg = new Planar<>(GrayF32.class, param.width, param.height, 3);
    ImageDistort distort = LensDistortionOps.changeCameraModel(adjustmentType, BorderType.ZERO, param, new CameraPinhole(param), paramAdj, (ImageType) distoredImg.getImageType());
    CalibrationIO.save(paramAdj, new File(outputDir, "intrinsicUndistorted.yaml").getAbsolutePath());
    BufferedImage out = new BufferedImage(param.width, param.height, BufferedImage.TYPE_INT_RGB);
    int numDigits = BoofMiscOps.numDigits(files.size() - 1);
    String format = "%0" + numDigits + "d";
    for (int i = 0; i < files.size(); i++) {
        File file = files.get(i);
        System.out.println("processing " + file.getName());
        BufferedImage orig = UtilImageIO.loadImage(file.getAbsolutePath());
        if (orig == null) {
            throw new RuntimeException("Can't load file: " + file.getAbsolutePath());
        }
        if (orig.getWidth() != param.width || orig.getHeight() != param.height) {
            System.err.println("intrinsic parameters and image size do not match!");
            System.exit(-1);
        }
        ConvertBufferedImage.convertFromPlanar(orig, distoredImg, true, GrayF32.class);
        distort.apply(distoredImg, undistoredImg);
        ConvertBufferedImage.convertTo(undistoredImg, out, true);
        String nameOut;
        if (rename) {
            nameOut = String.format("image" + format + ".png", i);
        } else {
            nameOut = file.getName().split("\\.")[0] + "_undistorted.png";
        }
        UtilImageIO.saveImage(out, new File(outputDir, nameOut).getAbsolutePath());
    }
}
Also used : ImageDistort(boofcv.alg.distort.ImageDistort) CameraPinhole(boofcv.struct.calib.CameraPinhole) BufferedImage(java.awt.image.BufferedImage) ConvertBufferedImage(boofcv.io.image.ConvertBufferedImage) AdjustmentType(boofcv.alg.distort.AdjustmentType) GrayF32(boofcv.struct.image.GrayF32) CameraPinholeRadial(boofcv.struct.calib.CameraPinholeRadial) Planar(boofcv.struct.image.Planar) File(java.io.File)

Example 3 with ImageDistort

use of boofcv.alg.distort.ImageDistort in project BoofCV by lessthanoptimal.

the class TestFDistort method setBorderChange.

/**
 * Makes sure that border recycling doesn't mess things up
 */
@Test
public void setBorderChange() {
    ImageMiscOps.fillUniform(input, rand, 0, 200);
    GrayU8 found = new GrayU8(width / 2, height / 2);
    GrayU8 expected = new GrayU8(width / 2, height / 2);
    FDistort alg = new FDistort();
    alg.init(input, found).scaleExt().apply();
    ImageDistort distorter = alg.distorter;
    InterpolatePixel interp = alg.interp;
    ;
    PixelTransform2_F32 outputToInput = alg.outputToInput;
    // Set it to the default border, nothing should change
    expected.setTo(found);
    alg.border(BorderType.EXTENDED).apply();
    assertTrue(distorter == alg.distorter);
    assertTrue(interp == alg.interp);
    assertTrue(outputToInput == alg.outputToInput);
    BoofTesting.assertEquals(expected, found, 1e-4);
    // change border now a fixed value
    alg.border(10).apply();
    new FDistort(input, expected).scale().border(10).apply();
    BoofTesting.assertEquals(expected, found, 1e-4);
    // change value
    alg.border(1).apply();
    new FDistort(input, expected).scale().border(1).apply();
    BoofTesting.assertEquals(expected, found, 1e-4);
}
Also used : GrayU8(boofcv.struct.image.GrayU8) ImageDistort(boofcv.alg.distort.ImageDistort) InterpolatePixel(boofcv.alg.interpolate.InterpolatePixel) PixelTransform2_F32(boofcv.struct.distort.PixelTransform2_F32) Test(org.junit.Test)

Example 4 with ImageDistort

use of boofcv.alg.distort.ImageDistort in project BoofCV by lessthanoptimal.

the class TestFDistort method setRefs.

/**
 * Makes sure that setRefs doesn't cause it to blow up
 */
@Test
public void setRefs() {
    ImageMiscOps.fillUniform(input, rand, 0, 200);
    FDistort alg = new FDistort();
    alg.setRefs(input, output).interp(InterpolationType.BILINEAR).scaleExt().apply();
    ImageDistort distorter = alg.distorter;
    InterpolatePixel interp = alg.interp;
    ;
    PixelTransform2_F32 outputToInput = alg.outputToInput;
    // a new image shouldn't cause new memory to be declared bad stuff to happen
    GrayU8 found = new GrayU8(width / 2, height / 2);
    GrayU8 expected = new GrayU8(width / 2, height / 2);
    alg.setRefs(input, found).scale().apply();
    assertTrue(distorter == alg.distorter);
    assertTrue(interp == alg.interp);
    assertTrue(outputToInput == alg.outputToInput);
    new FDistort(input, expected).scaleExt().apply();
    BoofTesting.assertEquals(expected, found, 1e-4);
}
Also used : GrayU8(boofcv.struct.image.GrayU8) ImageDistort(boofcv.alg.distort.ImageDistort) InterpolatePixel(boofcv.alg.interpolate.InterpolatePixel) PixelTransform2_F32(boofcv.struct.distort.PixelTransform2_F32) Test(org.junit.Test)

Example 5 with ImageDistort

use of boofcv.alg.distort.ImageDistort in project BoofCV by lessthanoptimal.

the class TestStitchingFromMotion2D method resizeStitchImage_Transform.

@Test
public void resizeStitchImage_Transform() {
    HelperMotion motion = new HelperMotion();
    InterpolatePixelS interp = FactoryInterpolation.createPixelS(0, 255, InterpolationType.BILINEAR, BorderType.EXTENDED, GrayF32.class);
    ImageDistort distorter = FactoryDistort.distortSB(false, interp, GrayF32.class);
    StitchingTransform trans = FactoryStitchingTransform.createAffine_F64();
    StitchingFromMotion2D<GrayF32, Affine2D_F64> alg = new StitchingFromMotion2D<>(motion, distorter, trans, 0.3);
    alg.configure(200, 300, null);
    assertTrue(alg.process(image));
    ImageMiscOps.fill(alg.getStitchedImage().subimage(2, 3, 30, 40, null), 1);
    Affine2D_F64 transform = new Affine2D_F64(1, 0, 0, 1, -2, 4);
    alg.resizeStitchImage(250, 400, transform);
    // see if the image is where it should be
    checkBlock(4, 0, 32, 36, alg.getStitchedImage());
    // check the stitched image size
    assertEquals(250, alg.getStitchedImage().width);
    assertEquals(400, alg.getStitchedImage().height);
    // check to see if translation was correctly applied
    Affine2D_F64 found = alg.getWorldToCurr();
    assertEquals(1 - 2, found.tx, 1e-5);
    assertEquals(-2 + 4, found.ty, 1e-5);
}
Also used : InterpolatePixelS(boofcv.alg.interpolate.InterpolatePixelS) GrayF32(boofcv.struct.image.GrayF32) Affine2D_F64(georegression.struct.affine.Affine2D_F64) ImageDistort(boofcv.alg.distort.ImageDistort) Test(org.junit.Test)

Aggregations

ImageDistort (boofcv.alg.distort.ImageDistort)6 GrayF32 (boofcv.struct.image.GrayF32)4 ConvertBufferedImage (boofcv.io.image.ConvertBufferedImage)3 BufferedImage (java.awt.image.BufferedImage)3 File (java.io.File)3 Test (org.junit.Test)3 InterpolatePixel (boofcv.alg.interpolate.InterpolatePixel)2 CameraPinhole (boofcv.struct.calib.CameraPinhole)2 CameraPinholeRadial (boofcv.struct.calib.CameraPinholeRadial)2 PixelTransform2_F32 (boofcv.struct.distort.PixelTransform2_F32)2 GrayU8 (boofcv.struct.image.GrayU8)2 AdjustmentType (boofcv.alg.distort.AdjustmentType)1 RectifyCalibrated (boofcv.alg.geo.rectify.RectifyCalibrated)1 InterpolatePixelS (boofcv.alg.interpolate.InterpolatePixelS)1 ListDisplayPanel (boofcv.gui.ListDisplayPanel)1 RectifiedPairPanel (boofcv.gui.stereo.RectifiedPairPanel)1 StereoParameters (boofcv.struct.calib.StereoParameters)1 Planar (boofcv.struct.image.Planar)1 Affine2D_F64 (georegression.struct.affine.Affine2D_F64)1 Se3_F64 (georegression.struct.se.Se3_F64)1