Entwickler-Ecke

WinForms - Backgroundworker


peterbe - Sa 02.08.14 22:54
Titel: Backgroundworker
hallo,

ich arbeite zum Ersten Mal mit dem Backgroundworker und bin auf ein Problem gestoßen.
Über ein Start-Button starte ich eine Anlage.
Wenn ich nun den Abbrech-Button betätige, wird der Abbruch-Code ausgeführt(Alle Ports am Modul auf false), aber dann läuft die Anlage von selber weiter,wo ich abgebrochen habe.
Dies soll aber verhindert werden.
Könnt ihr mir helfen?

mfg
peter


Christian S. - So 03.08.14 00:02

Ohne dass Du den relevanten Quelltext zeigst, wird Dir da niemand helfen können. Das sind einfach zu wenig Informationen. :nixweiss:


avoid - So 03.08.14 02:19

mir stellen sich zwei fragen.
- was macht dein Stopp Button?
- benutzt du "backgroundWorker1.CancelAsync();" ?

wie auch immer, ich hänge dir mal ein mini Projekt an.
damit hab ich den BG-Worker erforscht. ;)
da kannst du evtl. was abkucken.


peterbe - So 03.08.14 20:09

Danke zunächst!!!
HIer mal mein Code


C#-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
14:
15:
16:
17:
18:
19:
20:
21:
private void btn1_Click(object sender, EventArgs e)
        {
            if (!backgroundWorker1.IsBusy)
            {
                backgroundWorker1.RunWorkerAsync();
            }
        }

        private void button1_Click(object sender, EventArgs e)
        {
            if (backgroundWorker1.IsBusy)
            {
                backgroundWorker1.CancelAsync();
                 //hier mein code der bei Abbruch ausgeführt werden soll.Wird allerdings nur kurz ausgeführt!!!

             }
        }
 private void backgroundWorker1_DoWork(object sender, DoWorkEventArgs e)
        {
            //for schleife mit 10 durchgängen, die jederzeit abgebrochen werden soll
         }



Wenn ich den Stop Button betätige, soll die for SChleife jederzeit abgebrochen werden.
Und erst bei erneuten Betätigen des Start Button Neustarten.
Werde leider durch dein Beispiel nicht schlau:(

Moderiert von user profile iconChristian S.: C#-Tags hinzugefügt


Ralf Jansen - So 03.08.14 20:33

Prüfst du denn auch auf CancellationPending irgendwo in deiner DoWork Methode?


peterbe - So 03.08.14 21:32

Ne nicht wirklich.
Wie muss ich den denn einbinden?


Palladin007 - So 03.08.14 21:53

Naja, das einzige, was die CancleAsync-Methode tut, ist den Wert der CancellationPending-Property auf true zu setzen.
Mehr passiert da nicht.

Deshalb gibt es den sender-Parameter, der ist bei Events immer das Objekt, welches das Event ausgelöst hat.
In deinem Fall also dein BackgroundWorker-Objekt.

Du musst in der DoWork-Methode also direkt bei jedem Schleifendurchlauf den Zustand der CancellationPending-Property prüfen und die Schleife abbrechen, wenn es gefordert wird.
Das hat den Sinn, dass der Hintergrund-Thread nicht einfach hart abgebrochen wird und irgendwelche Objekte in irgendeinem unbekannten oder nicht funktionsfähigen Zustand zurück lässt.
So kannst du den Abbruch einleiten und dafür Sorge tragen, dass der auch sauber und kontrolliert ab läuft.


peterbe - Mo 04.08.14 12:51

Super Danke!
Mit der CancellationPending Abfrage funktionierts-


avoid - Mo 04.08.14 23:11

hier nochmal der ausschnitt der Methode wie er in meinem Beispiel zu finden ist.


C#-Quelltext
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
private void backgroundWorker1_DoWork(object sender, DoWorkEventArgs e)
        {
            int percentFinished = (int)e.Argument;
            while (!backgroundWorker1.CancellationPending && percentFinished < 100
            {
                percentFinished++;
                backgroundWorker1.ReportProgress(percentFinished);
                System.Threading.Thread.Sleep(50);
            }
            e.Result = percentFinished; 
        }


ich lasse den backgroundWorker quasi solange abarbeiten wie kein "Abbrechen" zur Verarbeitung an steht.
in der schleife kann ich dann alles verarbeiten lassen.
der Thread.Sleep(50) verzögert nur die Arbeit damit der Balken nicht sofort voll ist.
ist leider schon einige Jahre alt das Projekt, so 100% im Kopf hab ich das nicht mehr.

hoffe die kleine Erklärung hilft beim Verständnis.

Gruß,
avoid