Я написал код для преобразования между OpenCV Mat в PImage (ARGB) и обратно. Я использую веб-камеру в качестве входных данных с захваченной библиотекой обработки видео. Он работает в рендерере Java2D, но не в рендерере P2D или P3D. В чем может быть проблема?
Попытка использовать операторы loadPixels()
и updatePixels()
- не работает. Также примечательно то, что изображение с камеры в P3D-рендере нельзя скопировать в PImage с помощью pimage = cam.copy();
или pimage = cam.get();
, но его нужно назначить как pimage = cam; Я не понимаю, почему это так?
Я использую родной Opencv Java 3.4.
import processing.video.*;
Capture cam;
import java.nio.*; //to convert Mat PImage
byte [] bArray;
int [] iArray;
int pixCnt1, pixCnt2;
PImage camStream;// camera frame
//----------------------
void setup() {
size(640, 480); //PImage to mat does not work with P2D for some reason?
//size(640,480,P3D);// this does NOT WORK
String[] cameras = Capture.list();
if (cameras == null) {
println("Failed to retrieve the list of available cameras, will try the default...");
cam = new Capture(this, 640, 480);
}
if (cameras.length == 0) {
println("There are no cameras available for capture.");
exit();
} else {
println("Available cameras:");
//printArray(cameras);
cam = new Capture(this, cameras[0]);
//cam = new Capture(this, 1280, 720, "c922 Pro Stream Webcam", 5);
cam.start();
}
System.loadLibrary(Core.NATIVE_LIBRARY_NAME);
println(Core.VERSION);
pixCnt1 = width*height*4;// number of bytes in the pixel buffer.
pixCnt2 = width*height;//number of integers in the PImage pixels buffer.
bArray = new byte[pixCnt1]; //temporary byte array buffer for OpenCV cv::Mat.
iArray = new int[pixCnt2];//temporary integer array buffer for PImage pixels.
camStream = createImage(640, 480, ARGB);
}
void draw() {
background(0);
if (cam.available() == true) {
cam.read();
camStream = cam;
Mat frame = toMat(camStream ); //CvType=CV_8UC4
//Mat undistorted = frame.clone();
camStream = toPImage(frame);
}
image(camStream, 0, 0, 640, 480);
}
//--------------------------------------------------------------------------
// Convert PImage (ARGB) to Mat (CvType = CV_8UC4)
Mat toMat(PImage image) {
//image.loadPixels(); //???
int w = image.width;
int h = image.height;
Mat mat = new Mat(h, w, CvType.CV_8UC4);
byte[] data8 = new byte[w*h*4];
int[] data32 = new int[w*h];
arrayCopy(image.pixels, data32);
ByteBuffer bBuf = ByteBuffer.allocate(w*h*4);
IntBuffer iBuf = bBuf.asIntBuffer();
iBuf.put(data32);
bBuf.get(data8);
mat.put(0, 0, data8);
//image.updatePixels();
return mat;
}
//---------------------------------------------------------------------------
// Convert Mat (CvType=CV_8UC4) to PImage (ARGB)
PImage toPImage(Mat mat) {
int w = mat.width();
int h = mat.height();
PImage image = createImage(w, h, ARGB);
//image.loadPixels(); //???
byte[] data8 = new byte[w*h*4];
int[] data32 = new int[w*h];
mat.get(0, 0, data8);
ByteBuffer.wrap(data8).asIntBuffer().get(data32);
arrayCopy(data32, image.pixels);
//image.updatePixels(); //???
return image;
}