• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

dapplo / Dapplo.Windows / 22231723592

20 Feb 2026 04:16PM UTC coverage: 33.416% (-0.07%) from 33.49%
22231723592

push

github

Lakritzator
Small fixes for tests and namespaces

611 of 1948 branches covered (31.37%)

Branch coverage included in aggregate %.

2 of 8 new or added lines in 2 files covered. (25.0%)

231 existing lines in 16 files now uncovered.

1668 of 4872 relevant lines covered (34.24%)

30.47 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

86.44
/src/Dapplo.Windows.User32/DisplayInfo.cs
1
// Copyright (c) Dapplo and contributors. All rights reserved.
2
// Licensed under the MIT license. See LICENSE file in the project root for full license information.
3

4
using System;
5
using System.Linq;
6
using Dapplo.Windows.Common.Extensions;
7
using Dapplo.Windows.Common.Structs;
8
using System.Reactive.Linq;
9
using Dapplo.Windows.Messages;
10

11
#if !NETSTANDARD2_0
12
using System.Threading;
13
using Dapplo.Windows.Messages.Enumerations;
14
#endif
15

16
namespace Dapplo.Windows.User32;
17

18
/// <summary>
19
///     The DisplayInfo class is like the Screen class, only not cached.
20
/// </summary>
21
public class DisplayInfo
22
{
23
    private static NativeRect? _screenBounds;
24
    private static DisplayInfo[] _allDisplayInfos;
25
#if !NETSTANDARD2_0
26
    private static IDisposable _displayInfoUpdate;
27
#endif
28

29
    /// <summary>
30
    ///     Desktop working area
31
    /// </summary>
32
    public IntPtr MonitorHandle { get; set; }
1✔
33

34

35
    /// <summary>
36
    /// Index of the Display, as specified in the "control panel".
37
    /// </summary>
38
    public int? Index { get; set; }
2✔
39

40
    /// <summary>
41
    ///     Screen bounds
42
    /// </summary>
43
    public NativeRect Bounds { get; set; }
7✔
44

45
    /// <summary>
46
    ///     Device name
47
    /// </summary>
48
    public string DeviceName { get; set; }
2✔
49

50
    /// <summary>
51
    ///     Is this the primary monitor
52
    /// </summary>
53
    public bool IsPrimary { get; set; }
3✔
54

55
    /// <summary>
56
    ///     Height of  the screen
57
    /// </summary>
58
    public int ScreenHeight { get; set; }
1✔
59

60
    /// <summary>
61
    ///     Width of the screen
62
    /// </summary>
63
    public int ScreenWidth { get; set; }
1✔
64

65
    /// <summary>
66
    ///     Desktop working area
67
    /// </summary>
68
    public NativeRect WorkingArea { get; set; }
1✔
69

70
    /// <summary>
71
    /// Get the bounds of the complete screen
72
    /// </summary>
73
    public static NativeRect ScreenBounds
74
    {
75
        get
76
        {
77
            if (_screenBounds.HasValue)
5✔
78
            {
79
                return _screenBounds.Value;
4✔
80
            }
81

82
            int left = 0, top = 0, bottom = 0, right = 0;
4✔
83
            foreach (var display in AllDisplayInfos)
4✔
84
            {
85
                var currentBounds = display.Bounds;
1✔
86
                left = Math.Min(left, currentBounds.X);
1✔
87
                top = Math.Min(top, currentBounds.Y);
1✔
88
                var screenAbsRight = currentBounds.X + currentBounds.Width;
1✔
89
                var screenAbsBottom = currentBounds.Y + currentBounds.Height;
1✔
90
                right = Math.Max(right, screenAbsRight);
1✔
91
                bottom = Math.Max(bottom, screenAbsBottom);
1✔
92
            }
93
            _screenBounds = new NativeRect(left, top, right + Math.Abs(left), bottom + Math.Abs(top));
1✔
94

95
            return _screenBounds.Value;
1✔
96
        }
97
    }
98

99
    /// <summary>
100
    ///     Return all DisplayInfo
101
    /// </summary>
102
    /// <returns>array of DisplayInfo</returns>
103
    public static DisplayInfo[] AllDisplayInfos
104
    {
105
        get
106
        {
107
            if (_allDisplayInfos != null)
4✔
108
            {
109
                return _allDisplayInfos;
3✔
110
            }
111

112
            _allDisplayInfos = User32Api.EnumDisplays().ToArray();
1✔
113

114
#if !NETSTANDARD2_0
115

116
            // Subscribe to display changes, but only when we didn't yet
117
            if (_displayInfoUpdate == null && Thread.CurrentThread.GetApartmentState() == ApartmentState.STA)
1!
118
            {
NEW
119
                _displayInfoUpdate = SharedMessageWindow.Listen().Where(m => m.Msg == (uint)WindowsMessages.WM_DISPLAYCHANGE)
×
NEW
120
                        .Subscribe(m =>
×
NEW
121
                        {
×
NEW
122
                            _allDisplayInfos = null;
×
NEW
123
                            _screenBounds = null;
×
NEW
124
                        });
×
125
            }
126
#endif
127
            return _allDisplayInfos;
1✔
128
        }
129
    }
130

131
    /// <summary>
132
    ///     Implementation like <a href="https://msdn.microsoft.com/en-us/library/6d7ws9s4(v=vs.110).aspx">Screen.GetBounds</a>
133
    /// </summary>
134
    /// <param name="point">NativePoint</param>
135
    /// <returns>NativeRect</returns>
136
    public static NativeRect GetBounds(NativePoint point)
137
    {
138
        DisplayInfo returnValue = null;
1✔
139
        foreach (var display in AllDisplayInfos)
4✔
140
        {
141
            if (display.IsPrimary && returnValue == null)
1✔
142
            {
143
                returnValue = display;
1✔
144
            }
145
            if (display.Bounds.Contains(point))
1✔
146
            {
147
                returnValue = display;
1✔
148
            }
149
        }
150
        return returnValue?.Bounds ?? NativeRect.Empty;
1!
151
    }
152
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc