2012-03-30 6 views
8

Ich habe eine OpenCV Android App. Der meiste Code ist in Java, aber ich habe eine Funktion, die in C ist. Die Funktion erhält ein Mat-Objekt und gibt ein neues zurück.Mat-Objekt von nativem Code in Java in OpenCV zurückgeben

Meine Frage ist, wie gebe ich eine Matte aus dem nativen Code nach Java? Konnte kein Beispiel dafür finden.

Danke.

Antwort

20

Heute musste ich eine Matte aus nativem Code zurückgeben. Ich habe mit "Tutorial 2 Advanced - 2. Mix Java + Native OpenCV" begonnen und übergibt bereits zwei Mat (Bilder von der Kamera aufgenommen) Objekte an den nativen Code. Aber ich wollte extrahiert Funktion zurückzukehren, habe ich so jlong addrDescriptor zur Unterzeichnung:

extern "C" { 
JNIEXPORT void JNICALL Java_org_opencv_samples_tutorial4_Sample4View_FindFeatures(JNIEnv* env, jobject thiz, jlong addrGray, jlong addrRgba, jlong addrDescriptor) 
{ 
    Mat* pMatGr=(Mat*)addrGray; 
    Mat* pMatRgb=(Mat*)addrRgba; 
    Mat* pMatDesc=(Mat*)addrDescriptor; 
    vector<KeyPoint> v; 

    //OrbFeatureDetector detector(50); 
    OrbFeatureDetector detector; 
    OrbDescriptorExtractor extractor; 
    detector.detect(*pMatGr, v); 
    extractor.compute(*pMatGr, v, *pMatDesc); 
    circle(*pMatRgb, Point(100,100), 10, Scalar(5,128,255,255)); 
    for(size_t i = 0; i < v.size(); i++) { 
     circle(*pMatRgb, Point(v[i].pt.x, v[i].pt.y), 10, Scalar(255,128,0,255)); 
    } 
    } 
} 

im Java-Teil habe ich die Matte

private Mat descriptor; 
descriptor = new Mat(); 

Die Methode getNativeObjAddr() funktioniert der Trick. Die Mat wird in Java zugewiesen und ihre Adresse wird an den systemeigenen Code übergeben, daher gibt es keine explizite Rückgabe.

FindFeatures(mGraySubmat.getNativeObjAddr(), mRgba.getNativeObjAddr(), descriptor.getNativeObjAddr()); 
Log.i("desc:" , descriptor.dump()); 

Die Matte wurde mit den erforderlichen Daten gefüllt und ist in dem Java-Code nach der JNI Invokation kehrt direkt zugänglich.

Somwhere sonst im Code der Matte freigesetzt wird:

if (descriptor != null) 
    descriptor.release(); 
descriptor = null; 
+0

Hallo Stapler, änderte mein nativen Code zu diesem: Mat * image = (Mat *) addrDescriptor; \t Mat-Verarbeitung (* image.size(), CV_8UC3); \t cv :: medianBlur (* Bild, Verarbeitung, 5); Jetzt erhalte ich die folgende Fehlermeldung: jni/objDetector.cpp: 23: Fehler: Anforderung für die 'Größe' des Mitglieds in 'image', die vom Nicht-Klassen-Typ ist 'cv :: Mat * –

+0

@SaqibRazaq die Signatur ist' void medianBlur (const Mat & src, Mat & dst, int ksize) 'Sie müssen es mit einem Verweis auf die Verarbeitung aufrufen. versuchen Sie '& processing'. Oder definieren Sie es als 'Mat & processing (image.size(), CV_8UC3);' – stacker

+0

@SaqibRazaq Wenn Sie 'Mat & dst' zurückgeben wollen, dann sollten Sie es in Ihrem Java-Code deklarieren und zum Aufruf der JNI-Methode hinzufügen So haben Sie 'image' hinzugefügt. – stacker

Verwandte Themen