Java CV documentation is not always useful or is already out of date. To rectify this, I am creating some basic tutorials with links to the JavaDocs. This article explores loading and saving images and the basics behind an IplImage. These tutorials are written in Java and Scala.
These tutorials utilize GoatImage. The Image object is from this library.
Related Articles:
Why Java and Scala
Java and Scala are popular and make up a huge portion of data science libraries that exist today. Tools such as Akka allow for the stream processing of images as well.
Java CV and OpenCV
Java CV is a set of bindings for the C classes in OpenCV. Method calls are similar to their OpenCV equivalents.
The JNI is used to allow access to the OpenCV api in Java.
The Ipl Image
The IplImage stores image bytes, channel numbers, sizes and other bits of useful information. An IPL image exists at org.bytedeco.javacpp.opencv_core.IplImage.
Load an Ipl Image
Preferably, an IplImage is loaded from a file.
import org.bytedeco.javacpp.opencv_imgcodecs.cvLoadImage val impl : IplImage = cvLoadImage(fpath.getAbsolutePath)
The IplImage may be loaded from a matrix or mat, from a byte pointer, or may be specified later by using the no option constructor or the size of the raster as a Long.
import org.bytedeco.javacpp.BytePointer import org.bytedeco.javacpp.opencv_core.IplImage val bp : BytePointer = new BytePointer(ByteBuffer.wrap(bytes)) this.image = new IplImage(bp)
The BytePointer is the native pointer to an underlying C based char array. A BytePointer is loaded using a ByteBuffer. This type of Pointer can be converted to a ByteBuffer using asBuffer().
Unfortunately, the BytePointer method is not always reliable. An alternate way to load an IplImage would be to use a BufferedImage.
val m : Mat = new Mat(image.getHeight,image.getWidth,image.getType,new BytePointer(ByteBuffer.wrap(image.getRaster.getDataBuffer.asInstanceOf[DataBufferByte].getData))) new Image(new IplImage(m),name,itype)
Here, the Mat class is used to create a new image matrix.
Image Matrix
The image matrix, Mat, located under the opencv_core is a data structure wrapped around a pointer to an array of bytes with related methods including a set of mathematical operations.
Cross products, dot products, inverse, and the ability to divide values, a non-linear operation, are all available.
import org.bytedeco.javacpp.opencv_core.cvLoad import org.bytedeco.javacpp.opencv_core.{Mat,IplImage} new IplImage(new Mat(cvLoad(fpath.getAbsolutePath)))
The conversion process is shown above in addition to how to load the Mat.
Load an Image
Loading an image or image matrix is possible using the methods from org.bytedeco.javacpp.opencv_imgcodecs. The methods take a BytePointer object or file name.
import org.bytedeco.javacpp.opencv_imgcodecs._ path : File = new File("out/image.jpg") cvLoadImage(path.getAbsolutePath) mpath : File =new File("out/imageMat.mat") cvLoadImageM(mpath.getAbsolutePath)
Save an IplImage
The save functions exist in the opencv_core and imagecodecs libraries. Most are static as direct wrappers around the OpenCV library. They can be imported directly.
import org.bytedeco.javacpp.opencv_core._ directory : File = new File("out/") cvSave(new File(directory.getAbsolutePath,this.name).getAbsolutePath,myIplImage)
Constructors for cvSave include (filename : String, image : IplImage), and (filename : String, struct_ptr : Pointer).
Useful Functions
Some useful functions exist for the base IplImage. These include:
- imageData() – Get the BytePointer froom the IplImage. The resulting structure opens asBuffer()
- width() – Get the image width
- height() – Get the image height
- nchannels() – Get the number of channels with 3 corresponding to RGB and 4 to RGBA
Create an Image
At times, it is necessary to create an image from scratch. This is useful to avoid overwriting information. This requires using the cvCreateImage function. This function from opencv_core.IplImage takes the width, height, depth, and channels as arguments.
val src : IplImage = .... val dst : IplImage = cvCreateImage(cvSize((src.width() * scale).toInt,(src.height * scale).toInt),src.depth,src.nChannels)
Conclusion
Here, we discussed the basic image classes and packages in OpenCV. Some useful functions were mentioned.
5 thoughts on “Java CV Basics: IplImage”