5 Stimmen

Wie kann ich die Breite des übergeordneten Fensters in MS-Access ermitteln?

Ich versuche, ein MS-Access-Formular zu zwingen, eine bestimmte Position relativ zum rechten Rand des Hauptfensters einzunehmen (eigentlich möchte ich es zentrieren, aber ich kann mir auch vorstellen, dass ich es an die eine oder andere Seite andocken möchte). Ich kann das Formular folgendermaßen positionieren Me.Move , z.B.,

    Me.Move newWindowLeft, newWindowTop, newWidth, newHeight

Aber wie kann ich herausfinden, wie breit das übergeordnete Fenster ist?

8voto

DJ. Punkte 15727

Sie können eine Windows-API verwenden:

(AKTUALISIERT, um Twips zurückzugeben)

Type Rect
    x1 As Long
    y1 As Long
    x2 As Long
    y2 As Long
End Type

Declare Function GetClientRect Lib "user32" (ByVal hwnd As Long, lpRect As Rect) As Long

Declare Function GetDC Lib "user32" (ByVal hwnd As Long) As Long

Declare Function ReleaseDC Lib "user32" (ByVal hwnd As Long, ByVal hdc As Long) As Long

Declare Function GetDeviceCaps Lib "gdi32" (ByVal hdc As Long, ByVal nIndex As Long) As Long

Const LOGPIXELSX = 88
Const LOGPIXELSY = 90
Const DIRECTION_VERTICAL = 1
Const DIRECTION_HORIZONTAL = 0

Public Function GetMainWindowSize()

    Dim MDIRect As Rect
    Dim lWidthPixels As Long
    Dim lWidthTwips As Long

    ' Get the screen coordinates and window size of the MDIClient area'
    GetClientRect Application.hWndAccessApp, MDIRect

    lWidthPixels = MDIRect.x2 - MDIRect.x1
    lWidthTwips = PixelsToTwips(lWidthPixels, DIRECTION_HORIZONTAL)

    MsgBox "Width (Pixels) = " & lWidthPixels & "  Width (Twips) = " & lWidthTwips

End Function

Function PixelsToTwips(lPixels As Long, lDirection As Long) As Long

    Dim lDeviceHandle As Long
    Dim lPixelsPerInch As Long

    lDeviceHandle = GetDC(0)

    If lDirection = DIRECTION_HORIZONTAL Then
        lPixelsPerInch = GetDeviceCaps(lDeviceHandle, LOGPIXELSX)
    Else

        lPixelsPerInch = GetDeviceCaps(lDeviceHandle, LOGPIXELSY)
    End If

    lDeviceHandle = ReleaseDC(0, lDeviceHandle)

    PixelsToTwips = lPixels * 1440 / lPixelsPerInch

End Function

4voto

Stewbob Punkte 16520

Ich weiß nicht, welche Version von Access Sie verwenden, aber in Access 2003 scheint es keine Möglichkeit zu geben, diese Informationen direkt abzurufen.

Hier ist ein Hack:

DoCmd.Maximize

w = Forms("yourForm").WindowWidth
h = Forms("yourForm").WindowHeight

Dadurch wird das aktuelle Fenster maximiert, nehmen wir an, dass es sich um Ihr Formular handelt. Sie können dann das Formular messen, um die Größe des Anzeigebereichs des übergeordneten Fensters zu ermitteln, dann die Maximierung aufheben und das Formular auf der Grundlage der nun bekannten Größe des übergeordneten Fensters verschieben.

Wenn es eine Möglichkeit gibt, die Bildschirmaktualisierung in Access zu deaktivieren, können Sie dies vor dem Maximierungs- und Messcode tun und sie dann wieder einschalten, ohne dass es für den Benutzer merklich länger dauert.

EDITAR: Auch ohne den Maximierungsbefehl vor dem Benutzer zu verbergen, läuft der gesamte Vorgang des Maximierens und Verschiebens schneller ab, als der Benutzer sehen kann.

Es ist ein hässlicher Hack, aber er funktioniert.

4voto

DaveRandom Punkte 85940

Ich weiß, dass dies eine sehr alte Frage ist, aber ich möchte einige Codes teilen, die ich erstellt habe, um das gewünschte Endergebnis des ursprünglichen Zwecks dieser Frage zu behandeln - Neupositionierung von Fenstern, so dass sie mit einem anderen vorhandenen Element ausgerichtet sind.

Dieses Modul stellt 3 Funktionen zur Verfügung:


TwipsToPixels ( _
    Twips As Long, _
    Optional Dimension As Dimension = DIMENSION_X _
) As Long

PixelsToTwips ( _
    Pixels As Long, _
    Optional Dimension As Dimension = DIMENSION_X _
) As Long

Diese konvertieren einfach zwischen einer Maßeinheit und der anderen. Beide akzeptieren ein Long-Integer-Argument als Eingabe und einen Wert aus der Dimension enum, entweder X oder Y, mit dem angegeben werden kann, ob die Konvertierung gemäß den horizontalen oder vertikalen Anzeigeeinstellungen erfolgen soll. Es ist erwähnenswert, dass der Wert in 99,99999% der Fälle in beiden Dimensionen gleich ist, so dass Sie das zweite Argument normalerweise weglassen können. Beide geben eine lange Ganzzahl zurück.

Das Modul verwendet intern Pixel für alles, so dass diese Konvertierungsfunktionen nur als Annehmlichkeit für Anwendungen bereitgestellt werden, die es vorziehen, in Twips zu arbeiten.


PositionWindow ( _
    hWnd As Long, _
    Mode As PositionMode, _
    Optional OffsetX As Long = 0, _
    Optional OffsetY As Long = 0 _
)
  • hWnd ist das Handle des zu positionierenden Fensters (um beispielsweise ein Formularfenster zu positionieren, kann dies mit objForm.hWnd ).
  • Mode ist eine Bitmaske, die aus den Optionen in der Datei PositionMode enum (siehe unten).
  • OffsetX ist die Anzahl der Pixel, um die die Position in der horizontalen Dimension angepasst werden soll, nachdem Mode bewertet worden.
  • OffsetY ist die Anzahl der Pixel, um die die Position in der vertikalen Dimension angepasst werden soll, nachdem Mode bewertet worden.

Modi

Jeder Positionierungsaufruf erfordert eine X-Komponente und eine Y-Komponente. Diese Komponenten bestehen aus zwei Unterkomponenten, einer Basis und einer Position.

Die Basis ist eine Entität, die als Referenz für die Berechnung der neuen Position verwendet wird, und kann eine der folgenden sein DISPLAY (die aktive physische Anzeige auf dem Gerät), WINDOW (das Hauptfenster von Access) oder CURSOR (der Mauszeiger). Der Einfachheit halber werden diese in den Werten der PositionMode enum.

Die aktive Anzeige wird anhand des mittleren Pixels des Hauptfensters von Access bestimmt. Liegt dieser Wert außerhalb des Bereichs, der auf den physischen Bildschirmen des Geräts angezeigt wird, wird der Wert angepasst, um dies auszugleichen, und der Bildschirm mit dem größten sichtbaren Teil der Anwendung wird verwendet.

Die Position der X-Komponente kann eine der folgenden sein LEFT , RIGHT o X_CENTER . Die Y-Komponente hat TOP , BOTTOM y Y_CENTER .

使用する LEFT bewirkt, dass das äußerste linke Pixel des Zielfensters auf das äußerste linke Pixel des Basisobjekts ausgerichtet wird, und dieses Muster gilt für RIGHT , TOP y BOTTOM . Die CENTER Positionen bewirken, dass die Mittellinie des Zielfensters an der Mittellinie des Basisobjekts ausgerichtet wird.

Die Werte aus dem PositionMode enum werden mit dem bitweisen Or Operator, um den gewünschten Ausdruck zu erhalten.

Behandlung von Anzeigeüberlauf

Manchmal, wenn WINDOW o CURSOR als Basis für eine der Komponenten verwendet werden, kann das Zielfenster so positioniert werden, dass es sich ganz oder teilweise nicht auf einem sichtbaren Bildschirm befindet. Um dies zu vermeiden, können Sie die PREVENT_OVERFLOW_X y PREVENT_OVERFLOW_Y Flaggen. Diese können einfach in die Bitmaske aufgenommen werden, die an die Funktion Mode Argument unter Verwendung der bitweisen Or Betreiber.

Diese Flaggen bewirken, dass die Position ggf. angepasst wird, um sicherzustellen, dass sich das gesamte Zielfenster innerhalb der Ränder des aktiven Monitors befindet.

Der Einfachheit halber wird eine PREVENT_OVERFLOW Element auch in der Aufzählung enthalten ist, ist dies dasselbe wie die Angabe von sowohl PREVENT_OVERFLOW_X y PREVENT_OVERFLOW_Y .

Der Überlaufschutz wird nicht angewendet bei DISPLAY -basierten Positionen.

Verrechnungen

En OffsetX y OffsetY Argumente können verwendet werden, um die Position des Fensters zu korrigieren, nachdem es in der Weise ausgerichtet wurde, die durch Mode . Beide können eine positive oder negative Zahl sein, die eine Anzahl von Pixeln angibt, um die die Position in der betreffenden Dimension geändert werden soll.

Die Offsets werden immer noch angewendet, aber wenn die resultierende Position dazu führt, dass ein Teil oder das gesamte Zielfenster außerhalb der aktiven Anzeige liegt, wird die Position so angepasst, dass es wieder innerhalb der Grenzen liegt.

Beschränkungen

Der Code für die Behandlung mehrerer Anzeigen geht von 2 Annahmen aus:

  • Der virtuelle Anzeigebereich (die Kombination aller Bildschirme, die als ein einziger Bildschirm behandelt werden) ist einheitlich, so dass er sich nicht mit L-förmigen Konfigurationen oder anderen lächerlichen Konfigurationen verträgt.
  • dass alle aktiven Bildschirme die gleiche Auflösung verwenden.

Meiner Erfahrung nach sind dies in der realen Welt ziemlich sichere Annahmen.

Es gibt keine Unterstützung für die gleichzeitige Neupositionierung und Größenänderung (wie bei objForm.Move ). Sie müssen diese als separate Aufgaben behandeln.

Beispiele

' Get the window handle for frm_MyForm
Dim hWnd As Long
hWnd  = Forms("frm_MyForm").hWnd

' Align the form to the top left corner of the active display
PositionWindow hWnd, DISPLAY_LEFT Or DISPLAY_TOP

' Align the form to the center of the Access main window
PositionWindow hWnd, WINDOW_X_CENTER Or WINDOW_Y_CENTER

' Align the form to the bottom right of the mouse pointer position, prevent the
' window from disappearing off the screen
' This effectively sets the top left corner of the window to the pointer location
PositionWindow hWnd, CURSOR_RIGHT Or CURSOR_BOTTOM Or PREVENT_OVERFLOW

' Horizontally center the form on the display, vertically center on the mouse
PositionWindow hWnd, DISPLAY_X_CENTER Or CURSOR_Y_CENTER

' Center the window on the mouse pointer then move it 200px right and 30px up
PositionWindow hWnd, CURSOR_X_CENTER Or CURSOR_Y_CENTER, 200, -30

3voto

BIBD Punkte 14729

Hier ist der eigentliche Code, den ich verwendet habe

Application.Echo False  'turn off screen updates

DoCmd.Maximize
w = Me.WindowWidth
h = Me.WindowHeight
DoCmd.Restore           'restore the window to it's old size

Application.Echo True   'turn on screen updates

DoCmd.MoveSize w / 2 - myWidth / 2, _
            h / 2 - myHeigth / 2, _
            myWidth, _
            myHeigth

0voto

Fionnuala Punkte 89346

Dies könnte von Interesse sein: http://www.mvps.org/access/downloads/clFormWindow.bas

Hier steht es:

 '' Moves and resizes a window in the coordinate system        *
 '' of its parent window.                                      *
 '' N.B.: This class was developed for use on Access forms     *
 ''       and has not been tested for use with other window    *
 ''       types.                                               *

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X