Computer Vision Utilities¶
DJL comes equipped with a number of helpful image processing and object detection utilities to make model creation and training as simple as possible.
Using BufferedImageFactory to Read Images¶
The BufferedImageFactory
lets you create Image
s from a variety of sources like URLs, local files, and input streams.
// Load image from URL
URL url = new URL("https://s3.amazonaws.com/images.pdpics.com/preview/3033-bicycle-rider.jpg");
Image img = BufferedImageFactory.getInstance().fromUrl(url);
Using opencv extension for high performance image process¶
The DJL OpenCV extension provides better performance compare to java's built-in ImageIO. You only need to add it into your project and DJL will automatically pick it up:
<dependency>
<groupId>ai.djl.opencv</groupId>
<artifactId>opencv</artifactId>
</dependency>
Image Manipulation¶
Image provides a suite of image manipulation functions to let you pre- and post-process your images all within DJL.
int width = img.getWidth();
int height = img.getHeight();
Image leftHalfImg = img.getSubImage(0, 0, width / 2, height); // get left half of the image
NDManager manager = NDManager.newBaseManager();
NDArray imageArray = leftHalfImg.toNDArray(manager); // convert to NDArray
Saving and Loading Your Images¶
Now that you have done your pre or post processing, you'll probably want to save your images for future use.
Simply call the save
function from your Image
and pass in an OutputStream
and the image type (file extension).
Note: Some JDKs (openJDK) may not support saving JPG files when the image contains an alpha channel.
// Save file
OutputStream out = new FileOutputStream("bicycle.png");
img.save(out, "png");
You can then use BufferedImageFactory
to load it back in!
// Load image from local file
Image imgLoaded = BufferedImageFactory.getInstance().fromFile(Path.of("bicycle.png"));
Draw Bounding Boxes¶
Image
includes a useful function to draw bounding boxes given a DetectedObjects
instance
generated from a ObjectDetection
model. We'll use the pre-trained SingleShotDetection
model from the model zoo
to demonstrate below.
// Load Object Detection Model
Criteria<Image, DetectedObjects> criteria = Criteria.builder()
.setTypes(Image.class, DetectedObjects.class)
.optArtifactId("ssd")
.build();
ZooModel<Image, DetectedObjects> model = criteria.loadModel();
Predictor<Image, DetectedObjects> predictor = model.newPredictor();
// Detect Objects
DetectedObjects detectedObjects = predictor.predict(img);
// Draw Bounding Boxes
img.drawBoundingBoxes(detectedObjects);
// Save Image with Bounding Boxes
OutputStream out1 = new FileOutputStream("bicycleBoundBox.png");
img.save(out1, "png");
Draw Joints¶
You can also draw joints if you have a Joints
instance generated from a PoseEstimation
model.
Here, we'll use the SimplePose
model from the model zoo!
// Load Pose Detection Model
Criteria<Image, Joints> criteria = Criteria.builder()
.setTypes(Image.class, Joints.class)
.optArtifactId("simple_pose")
.build();
Predictor<Image, Joints> predictor = model.newPredictor();
// Detect Joints
Joints joints = predictor.predict(img);
// Draw Joints
img.drawJoints(joints);
// Save Image with Joints
OutputStream out2 = new FileOutputStream("bicycleJoints.png");
img.save(out2, "png");
Useful Information¶
If you want to learn more about loading models, click here.
If you want to learn more about the model zoo, click here.