Announcement

Collapse
No announcement yet.

Threadübergreifend Eingabelemente freigeben

Collapse
X
  • Filter
  • Time
  • Show
Clear All
new posts

  • Threadübergreifend Eingabelemente freigeben

    Hi,

    Ich habe da ein kleines Problem: Ich erzeuge aus einem bestimmten Formular heraus einen Thread, der einen bestimmte Situation darstellt. So lange dieser Thread läuft, sollen bestimmte Eingabeelemente des Formulars freigegeben und andere gesperrt sein

    Also in etwa so:
    [highlight=vbnet]
    Public Class frmMain Inherits Windows.Forms.Form
    ...

    Private Sub mnuAktion1_Click(ByVal sender as System.Object, ByVal e As System.EventArgs) Handles mnuAktion1.Click
    Dim Spezialsitzung As New Threading.Thread(AddressOf ShowAnmeldefenster)
    Spezialsitzung.IsBackground = True
    Spezialsitzung.Start()
    End Sub

    ...

    Private Sub ShowAnmeldefenster()
    session.SpezialsitzungAktiv = True
    chkSpezialfilter.Visible = True
    chkNormalFilter.Visible = False
    Dim f as new frmAnmeldung()
    f.ShowDialog()
    chkNormalFilter.Visible = session.Benutzer.IstAdministrator Or session.Benutzer.IstGruppenleiter
    chkSpezialfilter.Visible=False
    session.SpezialsitzungAktiv=False
    End Sub

    ...

    End Class
    [/highlight]

    Hierbei erhalte ich im Debuggen eine InvalidOperationException(Ungültiger threadübergreifender Vorgang: Der Zugriff auf das Steuerelement Panel2 erfolgte von einem anderen Thread als dem Thread, für den es erstellt wurde.)

    Panel2 ist das Panel auf frmMain, das einige meiner CheckBoxes beinhaltet, und am Panel will ich ja gar nichts ändern, nur am enthaltenen chkSpezialfilter. Außerdem sind Checkbox, Panel und das Object session in demselben Thread erzeugt worden, und zwar dem Thread, in dem auch der Thread Spezialsitzung erzeugt wird, und beim Zugriff auf das Object session, beschwert er sich ja auch nicht

    Nun, wennn ich vom Thread aus nicht mal auf die Bestandteile der eigenen Klasse (frmMain) zugreifen kann, weil die in einem anderen Thread erzeugt wurden, wie kann ich die Sache dann lösen? Gut, das Umschalten vor Anzeigen der zur Spezialsitzung angemeldeter Personen kann ich auch vor den Thraedaufruf in mnuAktion1_Click ziehen, aber was mache ich mit dem Aufräumen? Da werde ich ebensowenig die Möglichkeit haben, den Spezialfilter wieder unsichtbar zu schalten. Und einen Timer einzubauen, der alle paar Sekunden session.SpezialsitzungAktiv abprüft, um seinerseits diese Umschaltung vorzunehmen, kommt mir irgendwie sehr umständlich vor.

    Kann ich diesem Formular irgendwie ein Signal schicken (ein Event auslösen), wenn ich schon nicht selbst auf das Control zugreifen kann? Oder hat jemand eine noch einfachere Idee, wie ich das Problem lösen kann?

    Mit freundlichen Grüßen
    Martin Dietz

  • #2
    benutze doch einen Backgroundworker der stellt alles nötige bereit. Dort kannst du auch deine ShowAnmeldefenster im Hintergrund laufen lassen und und du hast ein Completed Ereignis welches dir ermöglicht nach Abschluss der Funktion deine Steuerelmente wieder freizugeben. Ich würde dir empfehlen noch eine zusätzliche Sub zu schreiben welche vom Button aufgerufen wird diese sperrt deine Eingabeelemente und sorgt dann dafür dass der Backgroundworker aktiviert wird.
    Unsere Jugend ist unerträglich, unverantwortlich und entsetzlich anzusehen! - Aristoteles

    Comment


    • #3
      Hallo,

      es gibt wie fast immer mehrere Möglichkeiten.

      1) der Thread ruft in eine Methode der Form-Klasse auf welche die Aktionen durchführt. Da das Setzen von Eigenschaften dann threadübergreifend ist muss in dieser Methode per Invoke ... (siehe Link)

      2) Forsetzung deines Vorschlags das vor dem Threadaufruf zu erledigen:
      Erstelle ein Ereignis (zB ThreadFertig) das die ausgelagerte Methode (also die im Thread) feuert wenn die Verarbeitung fertig ist. Der Ereignishandler kann dann aufräumen.

      mfG Gü
      "Any fool can write code that a computer can understand. Good programmers write code that humans can understand". - Martin Fowler

      Comment


      • #4
        Anmerkung:

        Mein 2. Vorschlag entspricht dem von das-d, nur dass dabei die Funktionalität des Backgroundworker selbst erstellt wird. Ist dann Geschmacksache.

        mfG Gü
        "Any fool can write code that a computer can understand. Good programmers write code that humans can understand". - Martin Fowler

        Comment


        • #5
          Danke,

          Ich habe mich für die Delegate- und Invoke() Sache entschieden, war am schnellsten zu programmieren.

          Gruß
          Martin

          Comment

          Working...
          X