2

I am trying to read an opencv image in a python socket that is sent from c++.

I am able to read the image into another c++ program or VB program and build an image but with python I don't understand what's happening.

The sending code where I send the mat.data:

char *start_s = "<S><size>43434234<cols>64<rows>64<SE>";//plus I send the image size, cols, rows, which varies, not like the static char string shown
char *end_e = "<E>";
cv::Mat image_send = some_mat;
iResult = send( ConnectSocket, start_s, (int)strlen(start_s), 0 );
iResult = send( ConnectSocket, (const char *) image_send.data, i_buffer_size, 0 );
iResult = send( ConnectSocket, end_e, (int)strlen(end_e), 0 );

This is what I have tried with the python, but haven't had any success yet. The image_cols and Image_rows are filtered from the socket, not shown here, and only the image_mat.data from the c++ mat is in the socket that I am trying to put into the image:

data = conn.recv(4757560)
        if(i_Read_Image == 2) & (image_cols != 0) & (image_rows != 0):
            print ("Entering")
            #print(data)
            data2 = np.fromstring(data, dtype='uint8')
            img_np = cv2.imdecode(data2,cv2.IMREAD_COLOR )
            cv2.imshow('image',img_np)
            cv2.waitKey(0)

            #Also tried this
            #img = Image.new('RGB', (image_cols, image_rows))
            #img.putdata(data)

        #img5 = np.reshape(data2,(image_rows,image_cols))
        i_Read_Image = 0
9
  • What do you mean by "haven't had any success yet"? What happens? I assume this is just trial code trying to get it to work, but in reality you don't want to hard code the number of bytes to recv. You've already read image_cols and image_rows so you can compute the number of additional bytes needed from the socket. Commented Dec 22, 2017 at 5:46
  • The code above, I get an error that the size needs to be greater than 0. if I print(data2), everything looks fine:[154 207 255 ..., 51 56 79] but line with img_np throws error : error: (-215) size.width>0 && size.height>0 in function cv::imshow Commented Dec 22, 2017 at 5:50
  • Did you send the raw pixel data on the socket? I think all you need to do is reshape data into the correctly sized 2D array. I don't quite understand why you are calling fromstring or imdecode. Commented Dec 22, 2017 at 6:03
  • Does this help: stackoverflow.com/questions/47881656/… Commented Dec 22, 2017 at 6:09
  • 1
    Something like img_np = data.reshape((image_rows, image_cols, image_channels)) Commented Dec 22, 2017 at 6:10

1 Answer 1

1

With the help of the comments I was able to get a working answer. The original image is in a single array RGB, this needs to be reshaped and placed into a 'RGB' image, it can be done in one line:

img = Image.fromarray(data2.reshape(image_rows,image_cols,3), 'RGB')

and when reading an opencv data array from a socket: this works:

data = conn.recv(567667)
if(i_Read_Image == 2) & (image_cols != 0) & (image_rows != 0):
    data2 = np.fromstring(data, dtype='uint8')
    img = Image.fromarray(data2.reshape(image_rows,image_cols,3), 'RGB')
    img.show()
Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.