ABOUT Visual Basic Programmieren Programmierung Download Downloads Tips & Tricks Tipps & Tricks Know-How Praxis VB VBA Visual Basic for Applications VBS VBScript Scripting Windows ActiveX COM OLE API ComputerPC Microsoft Office Microsoft Office 97 Office 2000 Access Word Winword Excel Outlook Addins ASP Active Server Pages COMAddIns ActiveX-Controls OCX UserControl UserDocument Komponenten DLL EXE
Diese Seite wurde zuletzt aktualisiert am 26.10.1999

Diese Seite wurde zuletzt aktualisiert am 26.10.1999
Aktuell im ABOUT Visual Basic-MagazinGrundlagenwissen und TechnologienKnow How, Tipps und Tricks rund um Visual BasicAddIns für die Visual Basic-IDE und die VBA-IDEVBA-Programmierung in MS-Office und anderen AnwendungenScripting-Praxis für IE, Windows Scripting Host und das Scripting-ControlTools, Komponenten und Dienstleistungen des MarktesRessourcen für Programmierer (Bücher, Job-Börse)Dies&Das...

Themen und Stichwörter im ABOUT Visual Basic-Magazin
Code, Beispiele, Komponenten, Tools im Überblick, Shareware, Freeware
Ihre Service-Seite, Termine, Job-Börse
Melden Sie sich an, um in den vollen Genuss des ABOUT Visual Basic-Magazins zu kommen!
Informationen zur AVB-Web-Site, Kontakt und Impressum

Zurück...

Zurück...

(-hg) mailto:hg_sizegrip@aboutvb.de

Seit Windows 95 können Fenster einen Griff haben. Nein, nicht jenen berüchtigten zum Wegschmeißen, sondern ein kleines, geriffelt erscheinendes Dreieck in der rechten, unteren Ecke, das gewissermaßen als "Verlängerung" der Ecke zum Ändern der Größe dient.

Genaugenommen ist es eigentlich ein kleines Quadrat, dessen Größe von der systemweiten Einstellung der Rollbalkengröße abhängt. Es ist genauso breit wie ein vertikaler Rollbalken und genauso hoch, wie ein horizontaler Rollbalken.


Mit dem avbSizeGripOCX können Sie jedes Visual Basic-Standard-Form mit einer Griffecke zur Größenänderung versehen

Eine Möglichkeit, ein Visual Basic-Form mit einer solchen Griffecke zu versehen, ist die Verwendung eines Statusbar-Steuerelements aus den CommonControls. Wird dieses fest an der Unterkante des Forms platziert (Align = 2 - Unten ausrichten), erscheint automatisch die Griffecke.

Alternativ dazu können Sie auch das hier vorgestellte Steuerelement SizeGrip verwenden. Zur Laufzeit sorgt es automatisch für seine Positionierung in der rechten, unteren Ecke und sitzt gegebenenfalls (Eigenschaft AutoZOrder = True) vor allen anderen Steuerelementen auf dem Form. Ebenso passt es selbstständig seine Größe der systemweiten Einstellung der Rollbalkengröße an.

Die automatische Positionierung beruht auf der in Lausch-EingriffeLausch-Eingriffe vorgestellten Technik und kann wegen der festen Typbindung nur auf einem VB-Standard-Form eingesetzt werden.

Private mForm As Form
Private WithEvents eForm As Form

Private Sub UserControl_ReadProperties(PropBag As PropertyBag)
  ' ...
  With UserControl
    If TypeOf .Parent Is Form Then
      If Not TypeOf .Parent Is MDIForm Then
        Set mForm = .Parent
        If Ambient.UserMode Then
          Set eForm = mForm
        End If
      End If
    End If
  End With
End Sub

Der Aufruf der Systemfunktion zur Größenänderung ähnelt der in Schiebung?!Schiebung?! vorgestellten Technik - hier wird als Systemkonstante statt HTCAPTION die Konstante HTBOTTOMRIGHT über die API-Funktion SendMessage versandt.

Private Declare Function ReleaseCapture Lib "user32" () As Long
Private Declare Function SendMessage Lib "user32" _
 Alias "SendMessageA" (ByVal Hwnd As Long, _
 ByVal wMsg As Long, ByVal wParam As Long, lParam As Any) _
 As Long 

Private Sub zSize(ByVal iHwnd As Long)
  Const WM_NCLBUTTONDOWN = &HA1
  Const HTBOTTOMRIGHT = 17

  ReleaseCapture
  SendMessage iHwnd, WM_NCLBUTTONDOWN, HTBOTTOMRIGHT, 0
End Sub

Damit das Steuerelement eine Änderung der Rollbalkengröße durch den Anwender mitbekommt und diese daraufhin nachvollziehen kann, wird im UserControl_Paint-Ereignis jedes Mal die Ereignis-Prozedur des UserControl_Resize-Ereignisses aufgerufen und seine Darstellung mit Hilfe der API-Funktion MSDN-Library - DrawFrameControlDrawFrameControl neu gezeichnet.

Private Type RECT
  Left As Long
  Top As Long
  Right As Long
  Bottom As Long
End Type

Private Declare Function DrawFrameControl Lib "user32" _
 (ByVal hDC As Long, lpRect As RECT, ByVal nCtlType As Long, _
ByVal nFlags As Long) As Long

Private Sub UserControl_Paint()
  Dim nRect As RECT
  
  Const DFC_SCROLL = 3
  Const DFCS_SCROLLSIZEGRIP = &H8

  Static sInProc As Boolean
  
  If sInProc Then
    Exit Sub
  Else
    sInProc = True
  End If
  UserControl_Resize
  With UserControl
    nRect.Right = .ScaleWidth
    nRect.Bottom = .ScaleHeight
    DrawFrameControl .hDC, nRect, DFC_SCROLL, DFCS_SCROLLSIZEGRIP
    If Not Ambient.UserMode Then
      UserControl.Line (0, 0)-(.ScaleWidth - 1, .ScaleHeight - 1), _
       vbBlack, B
    End If
  End With
  sInProc = False
End Sub

In der Ereignis-Prozedur des UserControl_Resize-Ereignisses wird zunächst das Steuerelement über die ZOrder-Eigenschaft des Extender-Objekts gegebenenfalls in den Vordergrund vor alle anderen Steuerelemente des Eltern-Forms gesetzt.

Danach werden die aktuellen Rollbalken-Maße über die API-Funktion MSDN-Library - GetSystemMetricsGetSystemMetrics ermittelt. Sollten sich diese geändert haben, werden sie in den modulweit gültigen Variablen pVScrollWidth und pHScrollHeight festgehalten und es wird die Änderung vermerkt (nChanged = True). Zur Laufzeit werden die Positionierung und die Größe des Steuerelements nachgeführt, wenn es sich auf einem VB-Standard-Form befindet. Ist dies nicht der Fall, wird lediglich die Größe an die Rollbalken-Abmessungen angepasst. Zur Designzeit geschieht immer nur letzteres. Abschließend wird die Darstellung des Steuerelements über den Aufruf von UserControl_Paint aufgefrischt.

Als kleines Abfallprodukt wird nun noch bei einer vermerkten Änderung der Rollbalken-Abmessungen das steuerelementeigene Ereignis ScrollbarSizeChanged ausgelöst. Die Rollbalken-Abmessungen können außerdem auch jederzeit über die Eigenschaften VScrollWidth und HScrollHeight abgefragt werden.

Weil sich die beiden Ereignis-Prozeduren UserControl_Paint und UserControl_Resize jeweils gegenseitig aufrufen, wird in beiden eine mehrfache vollständige Ausführung blockiert (Aller guten Dinge ist einsAller guten Dinge ist eins), damit keine endlose Rekursion entsteht.

Private Declare Function GetSystemMetrics Lib "user32" _
 (ByVal nIndex As Long) As Long

Public Event ScrollbarSizeChanged(ByVal VScrollWidth As Long, _
 ByVal HScrollHeight As Long)

Private Sub UserControl_Resize()
  Dim nVScrollWidth As Long
  Dim nHScrollHeight As Long
  Dim nChanged As Boolean
  Dim nWidth As Single
  Dim nHeight As Single
  
  Const SM_CXVSCROLL = 2
  Const SM_CYHSCROLL = 3
  
  Static sInProc As Boolean
  
  If sInProc Then
    Exit Sub
  Else
    sInProc = True
  End If
  On Error Resume Next
  If pAutoZOrder Then
    Extender.ZOrder 1
  End If
  nVScrollWidth = GetSystemMetrics(SM_CXVSCROLL)
  nHScrollHeight = GetSystemMetrics(SM_CYHSCROLL)
  If CBool(nVScrollWidth <> pVScrollWidth) _
   Or CBool(nHScrollHeight <> pHScrollHeight) Then
    pVScrollWidth = nVScrollWidth
    pHScrollHeight = nHScrollHeight
    nChanged = True
  End If
  If Ambient.UserMode Then
    If mForm Is Nothing Then
      UserControl.Size pVScrollWidth * Screen.TwipsPerPixelX, _
       pHScrollHeight * Screen.TwipsPerPixelY
    Else
      With mForm
        nWidth = .ScaleX(pVScrollWidth, vbPixels, .ScaleMode)
        nHeight = .ScaleY(pHScrollHeight, vbPixels, .ScaleMode)
        Extender.Move .ScaleWidth - nWidth, _
         .ScaleHeight - nHeight, nWidth, nHeight
      End With
    End If
  Else
    UserControl.Size pVScrollWidth * Screen.TwipsPerPixelX, _
     pHScrollHeight * Screen.TwipsPerPixelY
  End If
  UserControl_Paint
  If nChanged Then
    RaiseEvent ScrollbarSizeChanged
  End If
  sInProc = False
End Sub

Weitere Korrekturen und ErgänzungenDa es wenig Sinn macht, dass das Steuerelement den Fokus bekommen kann, setzen Sie die Eigenschaft MSDN-Library - UserControl-Eigenschaft CanGetFocusCanGetFocus des UserControls gleich False.

Sollte das Steuerelement auf einem anderen Container als einem VB-Standard-Form platziert sein, erfolgt keine automatische Positionierung in der rechten unteren Ecke des Containers, sondern nur die Größenanpassung. Außerdem werden lediglich die Mausereignisse des UserControls über die Ereignisse MouseDown, MouseMove und MouseUp nach außen weitergereicht. Dann kann extern bestimmt werden, für welches Fenster die Größenänderung stattfinden soll, und dessen Fenster-Handle an die separate und unabhängige Methode DoSize übergeben werden. Diese Methode ruft ebenfalls die bereits oben beschriebene private Methode zur Größenänderung über die API-Message auf.

Public Event MouseDown(Button As Integer, Shift As Integer, _
 X As Single, Y As Single)
Public Event MouseMove(Button As Integer, Shift As Integer, _
 X As Single, Y As Single)
Public Event MouseUp(Button As Integer, Shift As Integer, _
 X As Single, Y As Single)

Private Sub UserControl_MouseDown(Button As Integer, _
 Shift As Integer, X As Single, Y As Single)
  If mForm Is Nothing Then
    RaiseEvent MouseDown(Button, Shift, X, Y)
  Else
    Select Case Button
      Case vbLeftButton
        zSize mForm.Hwnd
    End Select
  End If
End Sub

Private Sub UserControl_MouseMove(Button As Integer, _
 Shift As Integer, X As Single, Y As Single)
  RaiseEvent MouseMove(Button, Shift, X, Y)
End Sub

Private Sub UserControl_MouseUp(Button As Integer, _
 Shift As Integer, X As Single, Y As Single)
  RaiseEvent MouseUp(Button, Shift, X, Y)
End Sub

Public Sub DoSize(ByVal AnyHwnd As Long)
  zSize AnyHwnd
End Sub

Weitere Korrekturen und ErgänzungenWeil das Steuerelement nur aus einem Modul besteht, brauchen Sie nicht unbedingt eine als OCX kompilierte Version zu verwenden. Sie können die UserControl-Datei SizeGrip.ctl auch direkt in ein Projekt aufnehmen. In diesem Fall sollten Sie die Datei SizeGrip.ctl und deren binäre Zusatzdatei SizeGrip.ctx im Ordner ...\Template\Userctls Ihres Visual Basic-Ordners ablegen. Dann können Sie das Steuerelement als Vorlage wiederverwenden und direkt im Einfügen-Dialog auswählen.

Korrekturen und Ergänzungen

26.10.1999

Ergänzung: Eigenschaft CanGetFocus des UserControls

Eigenschaft CanGetFocus des UserControls (Download des OCX ist binärkompatibel!)

Ergänzung: UserControl als Template direkt verwenden

UserControl als Template direkt verwenden


Code des Controls SizeGrip Code des Controls SizeGrip

Das Projekt avbSizeGripOCX (sizegrip.zip - ca. 5 KB)

ActiveX-Control als Setup (ohne VB 6-Runtime!) (sizegrips.zip - ca. 272 KB)



Komponenten-Übersicht

Zum Seitenanfang

Copyright © 1999 - 2023 Harald M. Genauck, ip-pro gmbh  /  Impressum

Zum Seitenanfang

Zurück...

Zurück...