简体   繁体   中英

Opencv send mat from java to python with socket

I have found many examples in opencv of sending a mat through socket from java to java or c++, but I can't get it to work on python.

The server code:

MatOfByte bytemat = new MatOfByte();
    Highgui.imencode(".jpg", out, bytemat);
    byte[] bytes = bytemat.toArray();
    r.write(String.valueOf(bytes.length));
    Log.d(TAG, String.valueOf(bytes.length));
    r.write(bytes);

The python code:

def recvall(sock, count):
buf = b''
while count:
    newbuf = sock.recv(count)
    if not newbuf: return None
    buf += newbuf
    count -= len(newbuf)
return buf

length = recvall(camera_socket, 5)
if not length:
    continue
print length
data = recvall(camera_socket, int(length))
if not data:
    continue

nparr = np.fromstring(data, np.uint8)
frame = cv2.imdecode(nparr, cv2.CV_LOAD_IMAGE_UNCHANGED)

window = cv2.namedWindow('frame', cv2.WINDOW_NORMAL)
cv2.imshow('frame', frame)

The weird part is that imdecode returns None always. I just can't get it to work. PS: the java client works using ObjectInputStream

----EDIT---- Thanks all for advices, I've replaced the byte stream with predefined bytes and discovered that Java was sending some headers when sending bytes because it was using ObjectOutputStream.

Now the java code for writing to socket is:

    DataOutputStream oos = null;
    try {
        oos = new DataOutputStream(os);
        oos.write(byteImage);
    } catch (Exception e) {
        Log.e(TAG, "Error while writing to OutputStream", e);
        cancel();
        setState(STATE_NONE, this.type);
    }

Try using np.uint8(nparr) for conversion as in:

frame = np.uint8(nparr)

This example works:

import numpy as np
import cv2

nparr = np.zeros((512, 512))
nparr[200:300, 400:450]=255

cv2.imshow("Result", np.uint8(nparr))
cv2.waitKey()

[EDIT] In case of a colour image please keep in mind that OpenCV2 images are BGR instaed of RGB, so you may vae to use

rgb = cv2.cvtColor(frame_in_bgr, cv2.COLOR_BGR2RGB)

在此处输入图片说明

Thanks all for advices, I've replaced the byte stream with predefined bytes and discovered that Java was sending some headers when sending bytes because it was using ObjectOutputStream.

Now the java code for writing to socket is:

DataOutputStream oos = null;
        try {
            oos = new DataOutputStream(os);
            oos.write(byteImage);
        } catch (Exception e) {
            Log.e(TAG, "Error while writing to OutputStream", e);
            cancel();
            setState(STATE_NONE, this.type);
        }

This now works. The only problem left is that the colors are inverted. Any tip on how to invert them again?

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM