2015-01-03 13 views
6

Ich möchte Objekte von OpenCV direkt mit JavaFX anzeigen. Ich habe gesehen, dass es möglich ist, ein Mat Objekt in ein BufferedImage umzuwandeln. Aber soweit ich weiß, kann man mit JavaFX keinen BufferedImage anzeigen, so dass eine andere Konvertierung stattfinden müsste.Anzeige OpenCV Mat mit JavaFX

Gibt es einen Weg zu direkt konvertieren Sie es in eine Datenstruktur, die von JavaFX angezeigt werden kann?

+0

Es ist wahrscheinlich möglich, direkt mit einem 'WritableImage' in FX zu konvertieren. Entweder durch Kopieren von Pixeln vom 'Mat' zum' PixelWriter' des WritableImage's, oder durch Implementieren eines 'PixelReader', der von der' Mat' unterstützt wird, und zum direkten Instanziieren des 'WritableImage'. – haraldK

Antwort

6

Ich habe einen direkten Weg gefunden, ein Objekt in ein JavaFX Image Objekt zu konvertieren.

MatOfByte byteMat = new MatOfByte(); 
Highgui.imencode(".bmp", mat, byteMat); 
return new Image(new ByteArrayInputStream(byteMat.toArray())); 

Sie können es auch zu .jpg kodieren, aber .bmp ist schneller.

+0

Warum ist mein OpenCV nicht mit der HighGUI-Bibliothek/Klasse? –

+1

Ich habe stattdessen "Imgcodecs.imencode" verwendet und es funktionierte –

2

Der dumme Art und Weise, dies zu tun ist, um die Mat zu einem BufferedImage, konvertieren und dann zu einem Image, so dass sie innerhalb eines ImageView angezeigt werden kann:

Mat >> BufferedImage >> Image >> ImageView 

Sie wissen Unter der Annahme, wie die ersten zu tun Umwandlung, der Rest wäre etwas wie folgt:

Ich habe den Code nicht getestet, aber das ist die allgemeine Idee.

2

TomToms Antwort war sehr hilfreich und löste das Problem, aber Highgui hat keine Bindung mehr in Java.

Ab OpenCV 3.0.0, der up-to-date-Code ist mehr wie:

MatOfByte byteMat = new MatOfByte(); 
Imgcodecs.imencode(".bmp", mat, byteMat); 
return new Image(new ByteArrayInputStream(byteMat.toArray())); 
+0

Ihre Antwort ist die Lösung für OpenCV Version 3. Frühere Versionen verwenden Highgui. – Roland

+0

Vielen Dank für Ihre Präzision, ich habe gerade meine Antwort bearbeitet und korrigiert. – deb0ch

0

statt Codierung und Decodierung den Byte-Array erhalten Sie benötigen, können Sie nur ein Array deklarieren und zu verwenden die get Methode. Dies ist Scala Code aber hoffentlich ist es verständlich:

val arr = new Array[Byte](w * h * 3) 
mat.get(0, 0, arr) 
pw.setPixels(0, 0, w, h, PixelFormat.getByteRgbInstance, arr, 0, w * 3) 

Dieser Code deklariert das Array arr vom Typ byte[] mit der Größe zu einem Bild von h durch w und 3 Kanäle entspricht. Dann werden die Daten vom Objekt mat in das Array kopiert und vom PixelWriter Objekt pw an die setPixels-Methode übergeben.