2016-09-13 17 views
0

私はちょうどロボットコントローラで作業を始めましたが、私はカメラの部品を動作させていません。私はMat cを送信するサーバーからtcp経由でwebcamストリームを受け取り、この情報をクライアント側で表示したいと考えています。ネットワーク経由でopencv Matを転送するには?

キャストの結果として潜在的にサーバーが間違った情報を送信するか、クライアントがこの情報を誤って解釈するか、潜在的にキャストの結果として潜在的に発生します。どちらの方法でも、この問題を解決する方法がわかりません。

これまでのところ、私のserver.cppは次のようになります。

#include "opencv2/opencv.hpp" 
#include <stdio.h> 
#include <stdlib.h> 
#include <string.h> 
#include <unistd.h> 
#include <sys/types.h> 
#include <sys/socket.h> 
#include <netinet/in.h> 

using namespace cv; 
int main(int argc, char** argv) 
{ 
    int socket_desc , client_sock , c , read_size; 
    struct sockaddr_in server , client; 

    //Create socket 
    socket_desc = socket(AF_INET , SOCK_STREAM , 0); 
    if (socket_desc == -1) 
    { 
     printf("Could not create socket"); 
    } 
    puts("Socket created"); 

    //Prepare the sockaddr_in structure 
    server.sin_family = AF_INET; 
    server.sin_addr.s_addr = INADDR_ANY; 
    server.sin_port = htons(1111); 

    //Bind 
    if(bind(socket_desc,(struct sockaddr *)&server , sizeof(server)) < 0) 
    { 
     //print the error message 
     perror("bind failed. Error"); 
     return 1; 
    } 
    puts("bind done"); 

    //Listen 
    listen(socket_desc , 3); 

    //Accept and incoming connection 
    puts("Waiting for incoming connections..."); 
    c = sizeof(struct sockaddr_in); 

    //accept connection from an incoming client 
    client_sock = accept(socket_desc, (struct sockaddr *)&client, (socklen_t*)&c); 
    if (client_sock < 0) 
    { 
     perror("accept failed"); 
     return 1; 
    } 
    puts("Connection accepted"); 

    VideoCapture cap; 
    // open the default camera, use something different from 0 otherwise; 
    // Check VideoCapture documentation. 
    if(!cap.open(0)) 
     return 0; 
    for(;;) 
    { 
      Mat frame; 
      cap >> frame; 
      if(frame.empty()) break; // end of video stream 
      //imshow("Input :)", frame); 
      write(client_sock,(char *)frame.data,strlen((char *)frame.data)); 
      if(waitKey(1) == 27) break; // stop capturing by pressing ESC 
    } 
    // the camera will be closed automatically upon exit 
    // cap.close(); 
    return 0; 
} 

そして、私のクライアントは、次のようになります。

#include "opencv2/opencv.hpp" 
#include <SFML/Network.hpp> 
using namespace cv; 
int main() { 
    sf::TcpSocket socket; 
    sf::Socket::Status status = socket.connect("127.0.0.1", 1111); 
    if (status != sf::Socket::Done) 
    { 
     puts("Bye\n"); 
     return 0; 
    } 
    while(true) { 
     Mat frame; 
     char data[1000000]; //strlen gave me around 930000 when I was debugging. 
     std::size_t received; 

     // TCP socket: 
     if (socket.receive(data, 1000000, received) != sf::Socket::Done) 
     { 
      continue; 
     }else { 
      frame.data = (unsigned char *)data; 
      imshow("Hello",frame); //Error occurs here, not sure what causes it 
     } 
    } 

} 

エラー

OpenCV Error: Assertion failed (size.width>0 && size.height>0) in imshow, file /build/opencv-SviWsf/opencv-2.4.9.1+dfsg/modules/highgui/src/window.cpp, line 269 
terminate called after throwing an instance of 'cv::Exception' 
    what(): /build/opencv-SviWsf/opencv-2.4.9.1+dfsg/modules/highgui/src/window.cpp:269: error: (-215) size.width>0 && size.height>0 in function imshow 

Aborted 
+3

生データに対して 'strlen'を呼び出さないでください。最初の '\ 0'文字の前のバイト数を返します(そして、まったく終了しないかもしれません)。それはあなたの配列の長さではありません... – Lanting

答えて

2

私はあなたからだと推測していますMatのデータのみを送信してください。 Matオブジェクトには、とりわけMatサイズを含むヘッダーが含まれています。

また、私はそれがだ場合は十分だろうか分からないマットのSizeTypeを送信してから、新しいMat

Mat frame(receivedSize, receivedType)

を作成するためにそれを使用するために最低でもお勧めしたいですしかし、それはスタートです。

また、(char *)&frameの代わりにdataを送信してからMatにキャストする理由がありますか?

+0

私はそれがうまくいくとは思わなかった。私は今それを試してみましょう。 –

+0

私は本当にそれを働かせなかった、私は情報を横断して、それを表示することができた。しかし、ピクセル単位でレンダリングすると、それを処理するのは本当に悪い方法でした。そのため、見るのが非常に醜い結果に終わりました。 –

+0

これはどう関連しているのですか?あなたの質問は、データの伝送に関するものでした。どのようにレンダリングに関連していますか? –

関連する問題