Events von Control in Klassen auslagern

  • VB.NET

Es gibt 22 Antworten in diesem Thema. Der letzte Beitrag () ist von VaporiZed.

    Events von Control in Klassen auslagern

    ,Hallo,

    mal sehen ob ich das vernünftig erklären kann.

    Ich habe ein Projekt ==> Sagen wir Projekt X. Hier gibt es nur eine Form1 und in der Form1 ein ControlX und 3 Buttons.

    Ich möchte jetzt vom ControlX MouseDown, MouseMove und diverse andere Events in eine Klasse auslagern. Diese Klasse soll dann als DLL unter Verweis eingefügt werden.

    Also die Events MouseDown und etc, sollen dann aus der Klasse auf das ControlX zugreifen.

    Wie könnte der Code für sowas aussehen?

    LG
    Drags
    Ich habe mir erste gestern eine dll gebaut, weil ich etwas versuchen wollte.
    Ob das nun genau das ist was Du suchst....
    Letztendlich lasse ich in der dll "Events" feuern die dann auf dem Form ausgewertet werden.

    Spoiler anzeigen

    dll

    VB.NET-Quellcode

    1. Public Event TimerInsertElapsed As EventHandler
    2. Private Sub Timer_TickI(sender As Object, e As EventArgs) Handles timerInsert.Elapsed
    3. timerInsert.Stop()
    4. RaiseEvent TimerInsertElapsed(Me, EventArgs.Empty)
    5. End Sub

    Form

    VB.NET-Quellcode

    1. Private Sub Monitor_TimerInsertElapsed(sender As Object, e As EventArgs) Handles _Monitor.TimerInsertElapsed
    2. _message = "Timer abgelaufen"
    3. Monitor_EventInfos(_message)
    4. 'ToDos
    5. End Sub

    Asperger Autistin. Brauche immer etwas um gewisse Sachen zu verstehen. :huh:

    DragsTrail schrieb:

    die Events MouseDown und etc, sollen dann aus der Klasse auf das ControlX zugreifen.
    Und wer feuert die Events ab? Ich kapier das Konstrukt nicht. Ein Event ist ein Teil einer Klasse. Letztenendes ist das Senden und Empfangen eines Events nur Folgendes:
    Wenn Klasse A ein Event an die Methode M von Klasse B sendet, sodass B das Event mit dessen Daten D in B empfängt und die Daten auswerten kann, dann ist das in Wirklichkeit so, dass A sich die Methode M von B z.B. zu Programmbeginn merkt und beim "Event-Feuern" diese Methode aufruft und dabei die Daten D als Parameter übergibt.
    Also:
    in A: RaiseEvent E
    in B: M(D) Handles A.E
    ist in Wirklichkeit:
    in A: Call M.B(D)

    Von daher: Wie ist sein Sende- und Empfangsplan?
    Dieser Beitrag wurde bereits 5 mal editiert, zuletzt von „VaporiZed“, mal wieder aus Grammatikgründen.

    Aufgrund spontaner Selbsteintrübung sind all meine Glaskugeln beim Hersteller. Lasst mich daher bitte nicht den Spekulatiusbackmodus wechseln.
    Ich betreib' sowas schon länger, das muss dann zur Laufzeit entsprechend abonniert werden.
    Die beiden Beispiel-Subs liegen in einem Modul in einem anderen Projekt bei mir:

    VB.NET-Quellcode

    1. ''' <summary> Bewirkt, dass nur Dezimalzahlen (mit Komma) in Textboxen akzeptiert werden </summary>
    2. Public Sub RegisterDecimalInput(ParamArray decimalTextBoxes As TextBox())
    3. For Each dctb In decimalTextBoxes
    4. AddHandler dctb.KeyDown, AddressOf dctb_KeyDown
    5. AddHandler dctb.Enter, AddressOf TextBox_Enter
    6. AddHandler dctb.MouseClick, AddressOf TextBox_MouseDoubleClick
    7. AddHandler dctb.Leave, AddressOf TextBox_numericLeave
    8. Next
    9. End Sub
    10. Private Sub dctb_KeyDown(sender As Object, e As KeyEventArgs)
    11. Dim tb = DirectCast(sender, TextBox)
    12. Select Case e.KeyCode
    13. Case Keys.Space : tb.Text = Date.Today.Year.ToString
    14. Case Keys.D0 To Keys.D9, Keys.NumPad0 To Keys.NumPad9, Keys.Decimal, Keys.Back, Keys.Subtract, Keys.OemMinus, Keys.Oemcomma 'nur Ziffern "," "-" und Backspace zulassen
    15. Case Keys.Shift, Keys.Home, Keys.End, Keys.Delete, Keys.Left, Keys.Right, Keys.OemMinus
    16. Case Else : e.SuppressKeyPress = True 'alle anderen Eingaben ablehnen
    17. End Select
    18. End Sub
    "Na, wie ist das Wetter bei dir?"
    "Caps Lock."
    "Hä?"
    "Shift ohne Ende!" :thumbsup:
    Wie ist wenn man ein konkretes Beispiel machen.

    Form1 mir PictureBox1 und Label1.

    KlasseX ( in einem Modul von mir aus ) mit einem MouseMove. Dieses Event soll in der Form1.Label1 die Mauskoordinaten ausgeben wenn sich der Mauszeiger über Form1.PictureBox1 befindet.

    Form1.OnLoad() ==> Die KlasseX mit PictureBox1 und Label1 irgendwie verknüpfen?? ?(

    Könnte mir bitte jemand für diesen konkreten Fall einen Code zeigen?

    LG

    DragsTrail schrieb:

    Dieses Event soll in der Form1.Label1 die Mauskoordinaten ausgeben wenn sich der Mauszeiger über Form1.PictureBox1 befindet.
    Was soll das, das MouseMove-Event nach extern umzuleiten, um dann doch wieder in Form1 eine Anzeige zu realisieren?
    Hast Du kein "echtes" Problem mit diesem Szenario?
    Z.B.
    Eine Hardware (z.B. eine Kamera) mit ihrer eigenen DLL sendet ein Event, dass Daten abzuholen sind.
    Falls Du diesen Code kopierst, achte auf die C&P-Bremse.
    Jede einzelne Zeile Deines Programms, die Du nicht explizit getestet hast, ist falsch :!:
    Ein guter .NET-Snippetkonverter (der ist verfügbar).
    Programmierfragen über PN / Konversation werden ignoriert!

    VB.NET-Quellcode

    1. Private Sub Form1_Load(sender As Object, e As EventArgs) Handles Me.Load
    2. AddHandler DeinControl.MouseMove, AddressOf ZeigeMauskoordinatenInLabel
    3. End Sub
    4. Private Sub ZeigeMauskoordinatenInLabel(sender As Object, e As MouseEventArgs)
    5. Label1.Text = e.Location.ToString
    6. End Sub

    Das ist Grundlagenwissen.
    Das einzig Besondere ist, dass Du Dein ModulControl instanziieren musst, falls Du es nicht normal auf's Form ziehen kannst.
    Dieser Beitrag wurde bereits 5 mal editiert, zuletzt von „VaporiZed“, mal wieder aus Grammatikgründen.

    Aufgrund spontaner Selbsteintrübung sind all meine Glaskugeln beim Hersteller. Lasst mich daher bitte nicht den Spekulatiusbackmodus wechseln.

    Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von „VaporiZed“ ()

    DragsTrail schrieb:

    Form1 mir PictureBox1 und Label1.
    KlasseX ( in einem Modul von mir aus ) mit einem MouseMove. Dieses Event soll in der Form1.Label1 die Mauskoordinaten ausgeben wenn sich der Mauszeiger über Form1.PictureBox1 befindet.


    Lass das.
    Sowas ist Anti-Architektur.
    Label1 ist auf Form1, Picturebox1 ist auf Form1 - wieso soll nun der Code, der in Label1 die Mauspos über PB1 anzeigt woanders sein als in Form1?

    Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von „ErfinderDesRades“ ()

    Du kannst eine "Behavior-Klasse" schreiben. Der übergiibst du das Control, dessen Mouse-Events du überwachen willst.

    VB.NET-Quellcode

    1. public class MouseBehaviors
    2. private WithEvents _Ctl as Control
    3. public sub new(ctl as Control)
    4. _Ctl =ctl
    5. end sub
    6. 'alle möglichen Handler, zB
    7. private sub _Ctl_MouseDown(sender as object, e as MouseEventArgs)handles _ctl.MouseDown
    8. '...
    9. end sub
    10. '...
    11. end class

    Ich kann das jetzt nur aufgrund des Testprojekts beurteilen:
    • den Modulrumpf braucht es nicht
    • die Klasse MouseControls_PictureBox muss von gar nichts erben, da sie keine Dinge der PicBox-Klasse braucht
    • die _Labels und _PictureBox können Private sein, da sie nicht von außen abgerufen werden
    • die _Labels müssen nicht WithEvents sein, da deren Events nicht verwendet werden
    • in MouseDown muss die Mausposition nicht in das Label geschrieben werden, darum kümmert sich der MouseMove-EventHandler
    Interessant für mich ist, dass ich erst durch das Testprojekt begriffen habe, was Dein Vorhaben ist/war

    ##########

    Und im MainForm: Statt mit Konstruktor, Overrides OnLoad-Methode und MyBase.OnLoad zu arbeiten, reicht eigentlich auch:

    VB.NET-Quellcode

    1. Private Sub Form1_Load(sender As Object, e As EventArgs) Handles Me.Load
    2. Label1.Text = "Label1"
    3. Label2.Text = "Label2"
    4. mh1 = New MouseControls_PictureBox(Label1, Label2, PictureBox1)
    5. mh2 = New MouseControls_PictureBox(Label1, Label2, PictureBox2)
    6. mh3 = New MouseControls_PictureBox(Label1, Label2, PictureBox3)
    7. mh4 = New MouseControls_PictureBox(Label1, Label2, PictureBox4)
    8. End Sub

    Oder übersehe ich da eine Relevanz?
    Dieser Beitrag wurde bereits 5 mal editiert, zuletzt von „VaporiZed“, mal wieder aus Grammatikgründen.

    Aufgrund spontaner Selbsteintrübung sind all meine Glaskugeln beim Hersteller. Lasst mich daher bitte nicht den Spekulatiusbackmodus wechseln.

    Dieser Beitrag wurde bereits 2 mal editiert, zuletzt von „VaporiZed“ ()

    So ich habe das jetzt geändert. Wenn euch sonnst nichts auffällt würde ich die im Video gezeigte Funktion jetzt in dem Stil umbauen?

    Ich habe die Form1 jetzt als MDI um zu schauen ob das mit den Childs funktioniert. Schaut soweit gut aus.

    Nagelt mich bitte wegen der Child-Sortierfunktion nicht fest. Im meinem Projekt ist die PRO Version drin :D
    Dateien
    • EventsToClass.zip

      (106,13 kB, 37 mal heruntergeladen, zuletzt: )
    Wie im Video erwähnt benötige ich diese Funktion in 15 verschiedenen Windows.Forms und drei verschiedenen Projekten. Den Vorteil sehe ich darin, dass man bei einer Änderung nur eine Klasse ändern muss und nicht in 15 verschiedenen Fenstern und drei unterschiedlichen Projekten die Änderung machen muss.

    Jetzt habe ich in einer Klasse (Constraints_Class) alle nötigen Funktionen vereint ( teste noch ) :
    1. Events vom 3D-Fenster
    2. Die Zwangsbedienungen
    3. Die Animationsklasse

    Wenn ich die Funktion in einem neuen Projekt haben möchte dann:
    1. Verweis einfügen ==> Constraints_Class, ImportExport_Class
    2. 3 Buttons
    3. 3D-Fenster
    4. und läuft schon :D

    Danke noch mal an ALLE für die Hilfe.
    LG
    hmm - durch das

    VB.NET-Quellcode

    1. Private _form As Form_Child
    bist du leider an die Klasse Form_Child gebunden, und kannst dieses Behavior nur für Form_Child-Objekte benutzen.

    Ein wirklich mehrfach verwendbares Behavior kannste durch eine kleine Änderung erreichen:

    VB.NET-Quellcode

    1. 'ersetze
    2. Private _form As Form_Child
    3. 'durch:
    4. Private _form As Form
    Dann ist das Behavior für alle Forms verwendbar, die 2 Labels und mindest 1 Picturebox enthalten.



    hmm - wenn ichs recht bedenke - dürfte dein Plan eher nicht funktionieren.
    Es sei denn, du verwendest in jedem Projekt dasselbe "3D-Fenster".
    Jo, und dann hätteste wie gesagt die Logik auch da rein machen können - mit demselben Gewinn: Nur an dieser einen Stelle sind Eingriffe in diese Logik nötig.

    Dieser Beitrag wurde bereits 2 mal editiert, zuletzt von „ErfinderDesRades“ ()