iplimage über Socket schicken.

Alles rund um die Programmierung mit Qt
Antworten
Eric_123
Beiträge: 5
Registriert: 12. März 2015 22:06

iplimage über Socket schicken.

Beitrag von Eric_123 »

img_1044.jpg
img_1044.jpg (6.35 KiB) 5795 mal betrachtet
Hallo zusammen!

ich bin dabei eine Client-Server Anwendung zu programmieren, es funktioniert leider die Videoübertragung nicht einwandfrei.
ich bekomme zwischendurch vertikale Streifen im Anzeigefenster,

Client(ist Raspberry Pi)

Code: Alles auswählen


cv::Mat             image1;

void C_Kamera::_senden_Video()
{
    if(!TpSocket)
        return;

    int maxPendingImages = 25;
    if(imagesInQue > maxPendingImages)
    {
       
        return;
    }
    if (image1.empty())
    {
        std::cout << "frame noch nicht da" << std::endl;
    }else
    {
        IplImage* img = new IplImage(image1.clone());
        //Daten schicken
        quint64 written = TpSocket->write(img->imageData, img->imageSize);
        Q_UNUSED (written);
    }
}

Server(Windows Rechner)

Code: Alles auswählen


if (TpSocket->bytesAvailable() < k_blockSize)
     {

        return;
     }

       IplBild = cvCreateImageHeader(cvSize(breite,hoehe), farbtiefe,anzkanal);

        char* Bilddaten = (char*) malloc(k_blockSize);

         TpSocket->read(Bilddaten, k_blockSize);

        cvSetData(IplBild,Bilddaten,breite*anzkanal);

         _frame_anzeige(IplBild);

         cvReleaseImageHeader(&IplBild);

         free(Bilddaten);

ich bin für jeden Tipp dankbar.

Danke im Voraus.
Christian81
Beiträge: 7319
Registriert: 26. August 2004 14:11
Wohnort: Bremen
Kontaktdaten:

Re: iplimage über Socket schicken.

Beitrag von Christian81 »

Code: Alles auswählen

IplImage* img = new IplImage(image1.clone());
Willkommen Memory-Leak und ein total unnötiges Kopieren des Images noch dazu.

Des weiteren sollte man überprüfen, ob auch alles geschrieben wurde und auch alles wieder ausgelesen - read() und write() geben nicht umsonst Werte zurück.
Abgesehen davon würde ich ein kleines Protokoll oberhalb von TCP aufsetzen so dass man vorher weiß wie viele Daten im nächsten Bild kommen anstatt davon auszugehen dass immer k_blockSize Bytes kommen. Auf der Senden-Seite sendest Du ja auch nicht k_blockSize sondern img->imageSize
MfG Christian

'Funktioniert nicht' ist keine Fehlerbeschreibung
Eric_123
Beiträge: 5
Registriert: 12. März 2015 22:06

Re: iplimage über Socket schicken.

Beitrag von Eric_123 »

Danke schön für den Tipp.

"image.Size " ist vorher festgelegt, weil ich die Kamera an den Raspberry Pi auf gewünschte Auflösung setze.

ich habe auf beide Seiten eine Ausgabe mit Image.Size und die sind identisch.

Memory-Leak wird das Problem sein. Leider weiss ich nicht wie ich das umgehen kann.

MfG
Eric
Christian81
Beiträge: 7319
Registriert: 26. August 2004 14:11
Wohnort: Bremen
Kontaktdaten:

Re: iplimage über Socket schicken.

Beitrag von Christian81 »

Eric_123 hat geschrieben: Memory-Leak wird das Problem sein. Leider weiss ich nicht wie ich das umgehen kann.
1. Warum überhaupt mit new ein Objekt anlegen
2. Wie wäre es mit 'delete' ?

Und eine Ausgabe von Image.Size nützt nix - Du sollst schauen was read() und write() zurückliefern um zu überprüfen ob wirklich alle Daten gesendet/gelesen werden!
MfG Christian

'Funktioniert nicht' ist keine Fehlerbeschreibung
Eric_123
Beiträge: 5
Registriert: 12. März 2015 22:06

Re: iplimage über Socket schicken.

Beitrag von Eric_123 »

1. Warum überhaupt mit new ein Objekt anlegen
um cv::mat in ein iplimage zu convertieren

2. Wie wäre es mit 'delete' ?

delete habe ich jetzt auch drin.

3. Und eine Ausgabe von Image.Size nützt nix - Du sollst schauen was read() und write() zurückliefern um zu überprüfen ob wirklich alle Daten gesendet/gelesen werden!

Ausgabe von read() und write() liefern das gleiche zurück.
Christian81
Beiträge: 7319
Registriert: 26. August 2004 14:11
Wohnort: Bremen
Kontaktdaten:

Re: iplimage über Socket schicken.

Beitrag von Christian81 »

Eric_123 hat geschrieben:1. Warum überhaupt mit new ein Objekt anlegen
um cv::mat in ein iplimage zu convertieren
Erklärt trotzdem nicht dass man das nicht z.B. auf dem Stack anlegt oder direkt cv::mat überträgt.
Eric_123 hat geschrieben: 3. Und eine Ausgabe von Image.Size nützt nix - Du sollst schauen was read() und write() zurückliefern um zu überprüfen ob wirklich alle Daten gesendet/gelesen werden!

Ausgabe von read() und write() liefern das gleiche zurück.
[/quote]
Wenn, wie behauptet, die Daten korrekt am Client ankommen kann es nicht an der Datenübertragung liegen.
MfG Christian

'Funktioniert nicht' ist keine Fehlerbeschreibung
Eric_123
Beiträge: 5
Registriert: 12. März 2015 22:06

Re: iplimage über Socket schicken.

Beitrag von Eric_123 »

sorry,
stimmt nicht ganz was ich geschrieben habe.
write() gibt 19200 zurück, aber by read() kommen zwischendurch andere werte 20660,33800.....
Christian81
Beiträge: 7319
Registriert: 26. August 2004 14:11
Wohnort: Bremen
Kontaktdaten:

Re: iplimage über Socket schicken.

Beitrag von Christian81 »

Also solltest Du ein Protokoll in deine TCP-Verbindung einbauen und somit sicherstellen, dass immer alles gelesen wird bzw. wenn nicht korrekt beim nächsten Bild aufsetzt wie ich im ersten Post geschrieben habe.

/edit: Demnach ist auch, wie ich schon im ersten Post schrieb, k_blockSize != img->imageSize, sonst würdest Du nicht mehr als 19200 auslesen oder du schickst eben nicht alles.
MfG Christian

'Funktioniert nicht' ist keine Fehlerbeschreibung
Eric_123
Beiträge: 5
Registriert: 12. März 2015 22:06

Re: iplimage über Socket schicken.

Beitrag von Eric_123 »

ich habe jetzt den Quellcode umgeschrieben sodass nur die geschickte Daten ausgelesen werden. läuft einwandfrei.
danke sehr für deine Hilfe.
Antworten