Thread und die Aktualisierung der Tabelle

Alles rund um die Programmierung mit Qt
rulzmaker
Beiträge: 70
Registriert: 19. Juli 2005 23:00
Kontaktdaten:

Thread und die Aktualisierung der Tabelle

Beitrag von rulzmaker »

Ich habe eine Thread Funktion die aller 1er Sekunde eine Row einer Tabelle hinzufügt und das 100 mal. Leider werden die einzelnen Rows erst nach den einhundert erstellten angezeigt. Woran liegt das?
Debian 2.4.27-1-386
[...]peace, love and empathy
Goos
Beiträge: 360
Registriert: 17. August 2004 10:10
Wohnort: Black Forest

Beitrag von Goos »

Ich vermute, dass du etwas mit deinem thread falsch gemacht hast und er dein GUI blockiert.

Goos

PS: eine etwas ausfuehrlichere Beschreibung waer gut. Das was du hier sagst ist wie "Ich steige ins Auto, trete aufs Gas und es faehrt nicht. Woran liegt das?" ;)
FlorianBecker
Beiträge: 1213
Registriert: 2. Dezember 2004 10:54
Kontaktdaten:

Beitrag von FlorianBecker »

Na ist doch logisch, das Gaspedal drückt nicht genügend Sprit in den Motor.
rulzmaker
Beiträge: 70
Registriert: 19. Juli 2005 23:00
Kontaktdaten:

Beitrag von rulzmaker »

Code: Alles auswählen

 MyThread bla(this);
 bla.start();
 bla.wait();

void MyThread::run()
{
    for(int i=0; i<100;++i)
    {
    _toni->_form4->addRow(i);
    usleep(1000000);
    }
}

void Form4::addRow(int row)
{
  Tabelle->insertRows(row);  
  Tabelle->showRow(row);
}
Nix mit Gaspedal....der main Thread hat genug Zeit um alles zu zeichnen!
Debian 2.4.27-1-386
[...]peace, love and empathy
rulzmaker
Beiträge: 70
Registriert: 19. Juli 2005 23:00
Kontaktdaten:

Beitrag von rulzmaker »

Hat keiner eine Ahnung was ich tun müsste?
Debian 2.4.27-1-386
[...]peace, love and empathy
FlorianBecker
Beiträge: 1213
Registriert: 2. Dezember 2004 10:54
Kontaktdaten:

Beitrag von FlorianBecker »

Schonmal mit update des ListViews probiert?
Goos
Beiträge: 360
Registriert: 17. August 2004 10:10
Wohnort: Black Forest

Beitrag von Goos »

FlorianBecker hat geschrieben: Na ist doch logisch, das Gaspedal drückt nicht genügend Sprit in den Motor.
...jetzt wo du das sagst :D
rulzmaker hat geschrieben: Nix mit Gaspedal....der main Thread hat genug Zeit um alles zu zeichnen!
Zeit vielleicht schon, aber du willst das doch nicht ;)
Mit deinem bla.wait() sagst du deinem Main Thread doch, dass er warten soll, bis die 100 Zeilen eingefuegt sind.

Goos
lepsai
Beiträge: 573
Registriert: 14. September 2004 21:33
Wohnort: Berlin
Kontaktdaten:

Beitrag von lepsai »

So geht es nicht. Man kann nicht aus einem Thread in der GUI was ändern.
Dafür gibt es QApplication::postEvent() und QCustomEvent. Wir haben das aber schon mal besprochen in diesem Forum....
rulzmaker
Beiträge: 70
Registriert: 19. Juli 2005 23:00
Kontaktdaten:

Beitrag von rulzmaker »

Hab nun neues Projekt mit qt designer erstellt:

Code: Alles auswählen

#include <qapplication.h>
#include "fenster.h"

#include <qtable.h>
#include <qthread.h>

QTable *tab;

class MyThread : public QThread 
{
    public:
     virtual void run();
};

void MyThread::run()
{
    for(int i=0; i<20; ++i)
    {
	tab->insertRows(i);
	tab->showRow(i);
	sleep(1);
    }
}

int main( int argc, char ** argv )
{
    QApplication a( argc, argv );
    Form1 w;
    w.show();
    a.connect( &a, SIGNAL( lastWindowClosed() ), &a, SLOT( quit() ) );
   
    tab=w.getTable();
    MyThread t;
    t.start();
    
    return a.exec();
}
Und siehe an es funktioniert...ihr scheint nicht wirklich viel Erfahrung mit thread zu haben.

PS: mit den send events hatte ich schon herumexperimentiert, kam aber nichts gescheites außer Speicherschutzverletzungen heraus (ich nahm das update event).
Debian 2.4.27-1-386
[...]peace, love and empathy
Goos
Beiträge: 360
Registriert: 17. August 2004 10:10
Wohnort: Black Forest

Beitrag von Goos »

rulzmaker hat geschrieben:Und siehe an es funktioniert...ihr scheint nicht wirklich viel Erfahrung mit thread zu haben.
Wie kommst darauf?
rulzmaker
Beiträge: 70
Registriert: 19. Juli 2005 23:00
Kontaktdaten:

Beitrag von rulzmaker »

Ach verdammt. Es funxt doch nicht...ich Trottel ;-(

Ich probiers nun doch nochmal mit den Events...Könnt ihr mir dabei Helfen - hab es gestern vergeblich versucht.

Code: Alles auswählen

#include <qapplication.h>
#include "fenster.h"

#include <qtable.h>
#include <qthread.h>
#include <qevent.h>

class MyThread : public QThread 
{
    public:
     MyThread(QTable *tabelle,QApplication *app);	
     virtual void run();
    private:
    QTable *_tabelle;
    QApplication *_app;
};

MyThread::MyThread(QTable *tabelle,QApplication *app)
    :QThread()
{
    _tabelle=tabelle;
    _app=app;
}
void MyThread::run()
{
    QEvent *event=new QEvent(QEvent::Paint);
    for(int i=0; i<10; ++i)
    {
	_tabelle->insertRows(i);
	_tabelle->showRow(i);
	_app->postEvent(_tabelle, event);
	sleep(1);
    }
}

int main( int argc, char ** argv )
{
    QApplication a( argc, argv );
    Form1 w;
    w.show();
    a.connect( &a, SIGNAL( lastWindowClosed() ), &a, SLOT( quit() ) );

    MyThread t(w.getTable(), &a);
    t.start();
    
    return a.exec();
}
Seitdem ich das mit dem Event drin habe, kommt kurz nach dem Aufruf des Programmes eine Speicherschutzverletzung.
Debian 2.4.27-1-386
[...]peace, love and empathy
rulzmaker
Beiträge: 70
Registriert: 19. Juli 2005 23:00
Kontaktdaten:

Beitrag von rulzmaker »

Mit sendEvent() scheint es zu funktionieren. Doch wenn ich das Fenster andauernd verkleicher/vergößere kommt folgendes:

Xlib: unexpected async reply (sequence 0x6292)!
Debian 2.4.27-1-386
[...]peace, love and empathy
rulzmaker
Beiträge: 70
Registriert: 19. Juli 2005 23:00
Kontaktdaten:

Beitrag von rulzmaker »

Habs gelöst (jippie aufschrei). Das lag warscheinlich daran das auch noch andere Threads auf das Tabellen widget zugreifen und mein Thread mit den anderen ins Gehege kam. QMutex löst das Problem:

Code: Alles auswählen

#include <qapplication.h>
#include "fenster.h"

#include <qtable.h>
#include <qthread.h>
#include <qevent.h>
#include <qmutex.h>

QTable *tab;

class MyThread : public QThread 
{
    public:
     MyThread(QTable *tabelle,QApplication *app, Form1 *fenster);	
     virtual void run();
    private:
    QTable *_tabelle;
    QApplication *_app;
    Form1 *_fenster;
};

MyThread::MyThread(QTable *tabelle,QApplication *app,Form1 *fenster)
    :QThread()
{
    _tabelle=tabelle;
    _app=app;
    _fenster=fenster;
}
void MyThread::run()
{
    QMutex mutex;
    QEvent *event=new QEvent(QEvent::Paint);
    for(int i=0; i<100; ++i)
    {
	_tabelle->insertRows(i);
	mutex.lock();
	_tabelle->showRow(i);
	_app->sendEvent(_fenster, event);
	mutex.unlock();
	sleep(1);
    }
    _app->sendEvent(_fenster, event);
}

int main( int argc, char ** argv )
{
    QApplication a( argc, argv );
    Form1 w;
    w.show();
    a.connect( &a, SIGNAL( lastWindowClosed() ), &a, SLOT( quit() ) );

    MyThread t(w.getTable(), &a, &w);
    t.start();
    
    return a.exec();
}
EDIT: lol...shit happens. Wennich das Fenster ganz ganz schnell verkleinere/vergrößere kommt folgendes:
Xlib: unexpected async reply (sequence 0x58a2)!
Debian 2.4.27-1-386
[...]peace, love and empathy
Goos
Beiträge: 360
Registriert: 17. August 2004 10:10
Wohnort: Black Forest

Beitrag von Goos »

Du hast das mit dem Mutex nicht begriffen, scheint mir :)
rulzmaker
Beiträge: 70
Registriert: 19. Juli 2005 23:00
Kontaktdaten:

Beitrag von rulzmaker »

ölö...ICh hatte es aus einem anderen Forum aufgeschnappt. Derjenige schrieb das er mutex überall dort eingesetzt hat wo irgednwas mit den widgets getan wurde (gezeichnet)...
Debian 2.4.27-1-386
[...]peace, love and empathy
Antworten