Thread soll Daten im Statusfenster anzeigen

Hi,

ich habe folgendes Problem:
Ein Hauptprogramm erstellt ein Statusfenster. Das Hauptprogramm erstellt desweiteren einen neuen Thread, der eine längere Berechnung ausführt. Währenddessen wartet das Hauptprogramm auf die Terminierung des Threads mit WaitForSingleObject(xxx,INFINITE).
Der Thread gibt nun Daten an das Statusfenster, die angezeigt werden sollen. Das Problem ist nun aber, das die CPU nie für das Hauptprogramm rechnet (wartet ja auf das Ende des Threads…), und somit das Statusfenster nicht aktualisieren kann.
Besteht eine andere Möglichkeit, als mit einem parallelen Thread der das Statusfenster bedient, diesen Fehler zu umgehen?

Vielen Dank
Philipp

Hi Philipp,

ich habe ein paar Fragen: Erzeugst Du den Thread mit AfxBeginThread? Wenn ja, erstellst Du einen Worker-Thread oder einen Userinterface-Thread? Ist Dein Statusfenster ein CWnd-Objekt?

Vielleicht postest Du einfach mal den Code, der das Fenster und den Thread erstellt.

Gruß
Uwe

[Bei dieser Antwort wurde das Vollzitat nachträglich automatisiert entfernt]

ich habe ein paar Fragen: Erzeugst Du den Thread mit
AfxBeginThread? Wenn ja, erstellst Du einen Worker-Thread oder
einen Userinterface-Thread? Ist Dein Statusfenster ein
CWnd-Objekt?

Vielleicht postest Du einfach mal den Code, der das Fenster
und den Thread erstellt.

Gruß
Uwe


Hm, die Befehle kenn ich nicht (bin in dem Gebiet kein Experte…). Ich verwende die Befehle der Windows-Api in der Borland 5.02 Umgebung:

*************************************************
Thread erschaffen:
HANDLE hMutex = CreateMutex(NULL,false,„MyName“);
HANDLE hMutex_2;
DuplicateHandle(GetCurrentProcess(),hMutex,
GetCurrentProcess(),&hMutex_2,
0,false,DUPLICATE_SAME_ACCESS);
HANDLE myThread = CreateThread(NULL,0,ThreadFunktion,
LPVOID lpParameter,DWORD dwCreationFlags,
LPDWORD lpThreadId);

Hauptprogramm wartet so:
WaitForSingleObject(myThread,INFINITE);
*************************************************

Dialog wird so erstellt:
p_Dlg = new My_Dlg(this, idd, 0);
p_Dlg->Create();
p_Dlg->ShowWindow(SW_SHOW);

//dann hier die Threadberechnung mit Datenanzeige

und so gelöscht:
p_Dlg->CmCancel();
delete p_Dlg;

Grüße
Philipp

Tja, leider habe ich noch nie mit dem Builder gearbeitet. Ich kenne mich nur mit MFC unter VisualC aus. Und selbst da stecken meine Erfahrungen mit Thread-Programmierung noch in den Kinderschuhen.

Ich kann Dir also nur sagen, wie ich es unter MFC angehen würde:

  1. Möglichkeit: Windows-Messages
    Für das Statusfenster wird eine eigene Fensterklasse erstellt, die User-definierte Windows-Messages empfängt. Der Arbeitsthread schickt eine Nachricht an das Statusfenster, das entsprechend der Nachricht reagiert (z.B. eine Prozentanzeige akualisiert oder einen Button aktiviert/deaktiviert).
    Damit der Thread weiß, an welches Fenster er seine Nachrichten verschickt, wird dem Thread beim Start der Handle des Statusfensters übergeben.

  2. Möglichkeit: Direkte Zugriffe auf das Statusfenster
    Wieder wird dem Thread beim Start der Handle des Statusfensters übergeben. Aber in diesem Fall steuert der Worker-Thread das Fenster nicht über Messages, sondern greift direkt auf die Elemente und Methoden der Statusfensterklasse zu.

Vielleicht gibt Dir das einen kleinen Anhaltspunkt, wo Du ansetzen kannst. Ich hoffe, ich konnte Dir wenigstens ein wenig helfen.

Gruß, und viel Erfolg!
Uwe

[Bei dieser Antwort wurde das Vollzitat nachträglich automatisiert entfernt]

…ich machs so :
Hi Uwe,

wo erzeugst Du das Statusfenster ? Im Hauptprogram ?
Ich würd das Statusfenster dem 2.Thread bekannt machen, dann kann dieser direkt Status- oder Fortschrittsmeldungen an das Statusfenster weitergeben.
Wenn der Status gar nix mit dem Hauptprogramm zu tun hat, soll p_Dlg im Thread erzeugt, upgedatet und auch wieder vernichtet werden, bevor der Thread sich selbst schliesst. Das Hauptprogramm macht währenddessen gar nix, bzw. wartet auf das Beeenden des Thread.

Gruss
Hans

[Bei dieser Antwort wurde das Vollzitat nachträglich automatisiert entfernt]

wo erzeugst Du das Statusfenster ? Im Hauptprogram ?

Ja

Ich würd das Statusfenster dem 2.Thread bekannt machen, dann
kann dieser direkt Status- oder Fortschrittsmeldungen an das
Statusfenster weitergeben.

Ist schon geschehen. Handle wird übergeben…

Wenn der Status gar nix mit dem Hauptprogramm zu tun hat, soll
p_Dlg im Thread erzeugt, upgedatet und auch wieder vernichtet
werden, bevor der Thread sich selbst schliesst. Das
Hauptprogramm macht währenddessen gar nix, bzw. wartet auf das
Beeenden des Thread.

Siehe unteren Abschnitt.

Gruss
Hans

Hi Hans

Tja, das Problem ist (hab ich leider vergessen zu erwähnen), dass ich mit dem Fenster auch Botschaften verarbeiten muss (Cancel-Button z.B.). Wie soll ich aber das Fenster schließen, wenn der Thread in Berechnungen vertieft ist? Er wird nicht auf das Event reagieren, da er ja noch mit der Ausführung von Code beschäftigt ist. Meiner Meinung nach bleibt mir als einzige Möglichkeit einen eigenen Thread für das Statusfenster zu erstellen, der dann aufgrund der Zeitscheiben in der Verfassung wäre, auf den Button-Event zu reageren.
Oder gibt es eine andere - elegantere Methode?

Gruß
Philipp

Tja, leider habe ich noch nie mit dem Builder gearbeitet. Ich
kenne mich nur mit MFC unter VisualC aus. Und selbst da
stecken meine Erfahrungen mit Thread-Programmierung noch in
den Kinderschuhen.

Ich kann Dir also nur sagen, wie ich es unter MFC angehen
würde:

  1. Möglichkeit: Windows-Messages
    Für das Statusfenster wird eine eigene Fensterklasse erstellt,
    die User-definierte Windows-Messages empfängt. Der
    Arbeitsthread schickt eine Nachricht an das Statusfenster, das
    entsprechend der Nachricht reagiert (z.B. eine Prozentanzeige
    akualisiert oder einen Button aktiviert/deaktiviert).
    Damit der Thread weiß, an welches Fenster er seine Nachrichten
    verschickt, wird dem Thread beim Start der Handle des
    Statusfensters übergeben.

  2. Möglichkeit: Direkte Zugriffe auf das Statusfenster
    Wieder wird dem Thread beim Start der Handle des
    Statusfensters übergeben. Aber in diesem Fall steuert der
    Worker-Thread das Fenster nicht über Messages, sondern greift
    direkt auf die Elemente und Methoden der Statusfensterklasse
    zu.

Ja, ich denke, dass der 2.Teil die richtige Lösung ist (für meinen Fall). Und das Statusfenster wird mit einem eigenen Thread erzeugt, damit es Meldungen von einem Button-Event verarbeiten kann, auch wenn der Thread für Berechnungen viel zu tun hat…
Oder liege ich da falsch?

Vielleicht gibt Dir das einen kleinen Anhaltspunkt, wo Du
ansetzen kannst. Ich hoffe, ich konnte Dir wenigstens ein
wenig helfen.

Vielen Dank!!
Philipp

Gruß, und viel Erfolg!
Uwe