Note: the signature for DwmGetWindowAttribute in this snippet is incorrect for uses other than DWMWA_EXTENDED_FRAME_BOUNDS or anything that uses something else than a RECT for the pvAttribute.
Public Declare Function DwmGetWindowAttribute Lib "dwmapi" (ByVal hwnd As IntPtr, ByVal dwAttribute As Integer, ByRef pvAttribute As RECT, ByVal cbAttribute As Integer) As Integer
Const DWMWA_EXTENDED_FRAME_BOUNDS As Integer = 9
<System.Runtime.InteropServices.DllImport("user32.dll")>
Public Function GetWindowRect(ByVal hWnd As IntPtr, ByRef lpRect As RECT) As Boolean : End Function
<System.Runtime.InteropServices.StructLayout(System.Runtime.InteropServices.LayoutKind.Sequential)>
Public Structure RECT
Public left, top, right, bottom As Integer
End Structure
Current Form:
Public Function GetScalingPercent() As Integer
Dim rcFrame As RECT
DwmGetWindowAttribute(Me.Handle, DWMWA_EXTENDED_FRAME_BOUNDS, rcFrame, System.Runtime.InteropServices.Marshal.SizeOf(rcFrame))
Dim rcWind As RECT
GetWindowRect(Me.Handle, rcWind)
Return Int((rcFrame.right - rcFrame.left) / (rcWind.right - rcWind.left) * 100 / 25) * 25 + If(Me.FormBorderStyle = FormBorderStyle.None, 0, 25)
End Function
Your window must be shown on the screen you wish to get the scaling from. So don't use this in the Form.Load Event
Extension to Screen Object:
<System.Runtime.CompilerServices.Extension()>
Public Function ScalingPercent(scrn As Screen) As Integer
Dim grab As New InactiveForm With {
.FormBorderStyle = FormBorderStyle.None,
.TransparencyKey = Color.Red,
.BackColor = Color.Red,
.ShowInTaskbar = False,
.StartPosition = FormStartPosition.Manual,
.Location = scrn.Bounds.Location
}
AddHandler grab.Shown, Sub()
grab.Location += New Point(1, 1) 'need to update the location so the frame changes
Dim rcFrame As RECT
DwmGetWindowAttribute(grab.Handle, DWMWA_EXTENDED_FRAME_BOUNDS, rcFrame, System.Runtime.InteropServices.Marshal.SizeOf(rcFrame))
Dim rcWind As RECT
GetWindowRect(grab.Handle, rcWind)
grab.Tag = Int((rcFrame.right - rcFrame.left) / (rcWind.right - rcWind.left) * 100 / 25) * 25
grab.Close()
End Sub
grab.ShowDialog()
Return grab.Tag
End Function
Private Class InactiveForm : Inherits Form
Protected Overloads Overrides ReadOnly Property ShowWithoutActivation() As Boolean
Get
Return True
End Get
End Property
End Class
Example usage:
For Each scrn As Screen In Screen.AllScreens
Debug.Print(scrn.ScalingPercent)
Next