|
Bei einem transparenten UserControl scheint es wenig Sinn zu haben, es wie etwa eine PictureBox als Steuerelement-Container (Eigenschaft ControlContainer = True) verwenden zu wollen. Darauf später platzierte Steuerelemente werden einfach unsichtbar. Nur Steuerelemente, die Sie im UserControl-Designer direkt auf dem UserControl platzieren, werden sichtbar.
Da dies auch für Shape-Elemente gilt, können Sie für jedes auf dem transparenten Container zu platzierende Steuerelement ein Shape-Steuerelement direkt auf das UserControl an die gleiche Position und mit den gleichen Abmessungen platzieren. Ein Shape-Element stanzt gewissermaßen "Löcher" in die Durchsichtigkeit - und in diesen Löchern werden die auf dem Container platzierten Steuerelemente wieder sichtbar.
Allerdings ist dieser Trick noch nicht sonderlich hilfreich. Sie können ja nicht von vornherein wissen, wo später Steuerelemente auf dem Container platziert werden sollen. Sie müssen also das UserControl dazu bringen, selbst die auf ihm platzierten Steuerelemente und deren Positionen und Abmessungen zu ermitteln. Dann kann es entsprechend viele Shape-Elemente (in einem Control-Array) laden und positionieren. Natürlich sollen für Steuerelemente, deren Visible-Eigenschaft auf False gesetzt ist, nicht unnötig Löcher gestanzt werden, in denen dann nichts zu sehen wäre. Und außerdem brauchen zur Laufzeit sowieso unsichtbare Steuerelemente, wie etwa ein Timer, auch kein eigenes "Loch".
Glücklicherweise stellt das UserControl in seiner Eigenschaft ContainedControls eine Collection der auf ihm platzierten Steuerelemente zur Verfügung. Sie durchlaufen diese Collection einfach in einer Schleife, laden für jedes darin enthaltene sichtbare Steuerelement ein Shape-Element und positionieren es passend. Sie prüfen dazu zunächst, ob die Eigenschaft Visible des Steuerelements auf True gesetzt ist. Ist dies der Fall, versuchen Sie, die Breite des Steuerelements zu ermitteln. Alle zur Laufzeit nicht sichtbaren Steuerelemente (Timer & Co.) verfügen nicht über diese Eigenschaft, so dass sie den dabei auftretenden Laufzeitfehler auswerten können. Gleiches gilt für das Line-Steuerelement, für das sich ja ein rechteckiges Shape-Element auch nicht als "Loch-Stanze" eigenen würde. Tritt kein Fehler auf, wird ein Shape-Element geladen, positioniert und sichtbar gemacht. Handelt es sich bei dem Steuerelement selbstauch um ein Shape-Element, können Sie sogar die Eigenschaften BackStyle, BorderStyle und Shape für das Stanzen-Shape übernehmen - die Charakteristik dieser Eigenschaften bleibt dann auch für das auf dem Container platzierte Shape-Element erhalten. Zum Abschluss entladen Sie noch alle eventuell vorhandenen überzähligen Stanzen-Shape-Elemente.
Am Besten packen Sie diese Geschichte in das Resize-Ereignis des UserControls.
Private Sub UserControl_Resize()
Dim i As Integer
Dim nWidth As Single
Dim nLoaded As Integer
Dim nControl As Control
On Error Resume Next
With UserControl
For i = 0 To .ContainedControls.Count - 1
Err.Clear
Set nControl = .ContainedControls(i)
With nControl
If .Visible Then
nWidth = .Width
If Err.Number = 0 Then
nLoaded = nLoaded + 1
Load shp(nLoaded)
shp(nLoaded).Move .Left, .Top, nWidth, .Height
If TypeOf nControl Is Shape Then
shp(nLoaded).Shape = .Shape
shp(nLoaded).BackStyle = .BackStyle
shp(nLoaded).BorderStyle = .BorderStyle
Else
shp(nLoaded).Shape = 0
shp(nLoaded).BackStyle = 1
shp(nLoaded).BorderStyle = 6
End If
shp(nLoaded).Visible = True
End If
End If
End With
Next 'i
For i = nLoaded + 1 To shp.ubound
Unload shp(i)
Next 'i
End With
End Sub
Damit dies auch beim ersten Sichtbarwerden des UserControls funktioniert, rufen Sie die Ereignisprozedur UserControl_Resize auch aus dem Show-Ereignis des UserControls auf. Und für den Fall, dass zur Laufzeit Steuerelemente nachträglich auf dem Container platziert oder entfernt werden sollen, brauchen Sie eine Methode namens Refresh, um per Code die Auffrischung der "Löcher" anzustoßen.
Public Sub Refresh()
UserControl_Resize
End Sub
Private Sub UserControl_Show()
UserControl_Resize
End Sub
Da es zur Entwicklungszeit nicht sehr praktisch ist, jedes Mal die Größe Ihres Containers (UserControls) zu ändern, um ein verschobenes oder neu darauf platziertes Steuerelement korrekt zu Gesicht zu bekommen, und da Sie ja dann auch die Refresh-Methode nicht aufrufen können, hilft eine "Schalter"-Eigenschaft weiter
(siehe: "'Wert'-lose Aktions-Eigenschaften"). In deren Property Let-Prozedur können Sie ebenfalls die Ereignisprozedur UserControl_Resize aufrufen, um mit einem einfachen Doppelklick auf diese Eigenschaft im Eigenschaften-Fenster eine Aktualisierung anzustoßen.
Public Property Get ShowCtls() As Boolean
'
End Property
Public Property Let ShowCtls(New_ShowCtls As Boolean)
UserControl_Resize
End Property
Sicher ist dieses Verfahren nicht übermäßig benutzerfreundlich. Das Arrangieren von auf dem Container zu platzierenden Steuerelementen wird leicht etwas fummelig. Daher sollten Sie vielleicht die Transparenz beim UserControl zumindest zur Entwicklungszeit abschaltbar machen. Dann können Sie die Steuerelemente bequem positionieren und erst später die Transparenz setzen und das beschriebene Verfahren zur Sichtbarmachung der platzierten Steuerelemente nutzen.
|