Rubrik: Controls · Sonstiges | VB-Versionen: VB6 | 17.05.01 |
Eine Klasse für eine SplitterBar Hier ein Lösungsansatz für die Realisierung einer SplitterBar. | ||
Autor: Manfred Hoffmann | Bewertung: | Views: 21.105 |
www.Data-Source.de | System: Win9x, WinNT, Win2k, WinXP, Win7, Win8, Win10, Win11 | Beispielprojekt auf CD |
Wie oft versucht man, den Bildschirm zu teilen? Das ist an sich gar kein Problem - aber wie erlaubt man dem Benutzer, diese Einteilung frei einzustellen? Hier ein Lösungsansatz. Benötigt wird in dem Projekt entweder eine Form oder MDI-Form sowie ein Klassenmodul.
Der Quellcode ist so gut auskommentiert, daß es unserer Meinung nach keinerlei weiterer Extra-Beschreibung bedarf
Der Code des Klassenmoduls:
Option Explicit ' API-Funktion zum Anzeigen der beweglichen Splitterbar Private Declare Function SetParent Lib "user32" ( _ ByVal hWndChild As Long, _ ByVal hWndNewParent As Long) As Long ' Die Kopie des Controls, das der Benutzer als ' Splitter ansieht Private WithEvents mSplitCtrl As PictureBox ' Die intern benötigten Objekte und Variablen Private mSlideCtrl As PictureBox Private msngMin As Single Private msngMax As Single ' Das Ereignis, das ausgelöst wird, sobald der ' "Zieh-Vorgang" beendet ist Public Event OnUpdate(ByVal LEdge As Single, _ ByVal REdge As Single) Public Property Let Max(ByVal vMax As Single) ' Der Wert, den die bewegliche Splitterbar nicht ' überschreiten darf msngMax = vMax End Property Public Property Let Min(ByVal vMin As Single) ' Der Wert, den die bewegliche Splitterbar nicht ' unterschreiten darf msngMin = vMin End Property Public Property Set SlideCtrl(ByVal oCtrl As Object) ' Das Control, das der Benutzer sieht, wenn die ' Splitterbar verschoben wird. Set mSlideCtrl = oCtrl ' Garantieren, daß der bewegliche Teil des ' Splitters vorerst nicht sichtbar ist. mSlideCtrl.Visible = False End Property Public Property Set SplitCtrl(ByVal oCtrl As Object) ' Das Control, das der Benutzer als den eigentlichen ' Splitter sieht Set mSplitCtrl = oCtrl ' Die Prüfung auf den Parent des Controls ist notwendig, ' da die Top- bzw. Height-Eigenschaften des Controls auf ' einer MDI-Form nicht änderbar sind. Außerdem wird ' sichergestellt, daß das Control auch direkt auf einer ' Form oder MDI-Form plaziert ist. If Not TypeOf mSplitCtrl.Parent Is MDIForm Then If TypeOf mSplitCtrl.Parent Is Form Then ' Position und Höhe des Controls festlegen mSplitCtrl.Top = 0 mSplitCtrl.Height = mSplitCtrl.Parent.Height Else ' Ausgeben der Fehlermeldung, da weder eine Form ' noch eine MDI-Form als Parent des Controls ' genutzt wurde. Err.Raise -1, _ "Splitter", "Das ObjectSplitCtrl MUSS auf " & _ "einer Form oder MDIForm plaziert sein!" Exit Property End If End If End Property Private Sub mSplitCtrl_MouseDown(Button As Integer, _ Shift As Integer, X As Single, Y As Single) If Button = vbLeftButton Then ' Beginnen mit dem Drag-Vorgang ShowSplitter End If End Sub Private Sub mSplitCtrl_MouseMove(Button As Integer, _ Shift As Integer, X As Single, Y As Single) If Button = vbLeftButton Then ' Den beweglichen Teil des Splitters auf die ' Position des Mauszeigers setzen. MoveSplitter X End If End Sub Private Sub mSplitCtrl_MouseUp(Button As Integer, _ Shift As Integer, X As Single, Y As Single) If Button = vbLeftButton Then ' Den Drag-Vorgang beenden SetSplitter End If End Sub Private Sub ShowSplitter() ' Der bewegliche Teil des Splitters MUSS ein Child des ' dauerhaft sichtbaren Teils sein. Das ist notwendig, ' falls der Parent eine MDI-Form ist und dadurch der ' bewegliche Teil nicht verschoben werden könnte ' (durch die Align-Eigenschaft). Ist der Parent des ' beweglichen Teils alledings ein Container ' (PictureBox) dann muss die Align-Eigenschaft nicht ' gesetzt sein(vbAlignNone). SetParent mSlideCtrl.hWnd, mSplitCtrl.Parent.hWnd ' Den beweglichen Teil dem dauerhaft sichtbaren Teil ' anpassen und danach auch anzeigen. mSlideCtrl.Height = mSplitCtrl.Height mSlideCtrl.Top = mSplitCtrl.Top mSlideCtrl.Left = mSplitCtrl.Left mSlideCtrl.Width = mSplitCtrl.Width mSlideCtrl.Visible = True End Sub Private Sub MoveSplitter(ByVal X As Single) ' Sicherstellen, daß die Min/Max-Werte eingehalten ' werden. Select Case mSplitCtrl.Left + X Case Is < msngMin mSlideCtrl.Move msngMin - 1 Case Is > msngMax mSlideCtrl.Move msngMax + 1 Case Else ' Den beweglichen Teil des Splitters entsprechend ' dem Mauszeiger positionieren. mSlideCtrl.Move mSplitCtrl.Left + X End Select End Sub Private Sub SetSplitter() ' Die Oberfläche über das Ende des Vorgangs ' unterrichten und die linken zw. rechten ' Koordinaten des Splitters liefern. RaiseEvent OnUpdate(mSlideCtrl.Left, _ mSlideCtrl.Left + mSlideCtrl.Width) ' Den beweglichen Teil wieder verstecken und den ' sichtbaren Splitter neu positionieren. mSlideCtrl.Visible = False mSplitCtrl.Left = mSlideCtrl.Left ' Den beweglichen Teil des Splitters wieder seinem ' ursprünglichen Parent zuweisen, damit bei weiterer ' Bewegung der ganze Vorgang immer noch korrekt ' ablaufen kann. SetParent mSlideCtrl.hWnd, mSplitCtrl.hWnd End Sub
Beispiel für den Einsatz der Klasse "cSplitter"
Auf der Form wird benötigt:
* 4 Picture-Elemente
Das Element picSlider in dem Beispiel ist ein Child des Element picSplitter. Im Hinblick auf die Benutzung innerhalb einer MDIForm MUSS dies auch so sein. Picture1 ist auf der linken Seite von PicSplitter positioniert, Picture2 auf der rechten.
Nun der Code:
Option Explicit ' Klassenobjekt des Splitters Private WithEvents Splitter As cSplitter Private Sub Form_Load() ' Die Splitterklasse anlegen Set Splitter = New cSplitter ' Zuweisen der Objekte die benötigt werden. ' HINWEIS: picSlider MUSS vom Typ PictureBox sein und ' ein Child des Controls picSplitter ' picSplitter MUSS vom Typ PictureBox sein. Set Splitter.SplitCtrl = picSplitter Set Splitter.SlideCtrl = picSlider Splitter.Min = 500 Splitter.Max = Me.Width - 500 End Sub Private Sub Splitter_OnUpdate(ByVal LEdge As Single, _ ByVal REdge As Single) ' Der Drag-Vorgang wurde beendet und die ' Positionierungsmaßnahmen an der Oberfläche ' können beginnen. Picture1.Width = LEdge Picture2.Left = REdge Picture2.Width = Me.Width - REdge End Sub