From a968a137a168b4b8eba5fbca27c222352b5ffafe Mon Sep 17 00:00:00 2001 From: UnknownShadow200 Date: Mon, 7 Aug 2017 13:04:29 +1000 Subject: [PATCH] Significantly simplify DisplayDevice --- OpenTK/DisplayDevice.cs | 130 +----- OpenTK/GameWindow.cs | 2 + OpenTK/GameWindowFlags.cs | 41 -- OpenTK/NativeWindow.cs | 9 - OpenTK/OpenTK.csproj | 317 +++++++------- OpenTK/Platform/IDisplayDeviceDriver.cs | 33 +- .../MacOS/QuartzDisplayDeviceDriver.cs | 245 ++++------- OpenTK/Platform/Windows/WinDisplayDevice.cs | 176 ++++---- OpenTK/Platform/X11/X11DisplayDevice.cs | 409 ++++++++---------- src/Client/Window.h | 122 ++++++ 10 files changed, 650 insertions(+), 834 deletions(-) delete mode 100644 OpenTK/GameWindowFlags.cs create mode 100644 src/Client/Window.h diff --git a/OpenTK/DisplayDevice.cs b/OpenTK/DisplayDevice.cs index 2ee113e6e..b235e9ac1 100644 --- a/OpenTK/DisplayDevice.cs +++ b/OpenTK/DisplayDevice.cs @@ -20,40 +20,32 @@ namespace OpenTK { // TODO: Add properties that describe the 'usable' size of the Display, i.e. the maximized size without the taskbar etc. // TODO: Does not detect changes to primary device. - DisplayResolution current_resolution = new DisplayResolution(), original_resolution; - List available_resolutions = new List(); - IList available_resolutions_readonly; + DisplayResolution current_resolution = new DisplayResolution(); bool primary; Rectangle bounds; - static readonly List available_displays = new List(); - static readonly IList available_displays_readonly; static DisplayDevice primary_display; static Platform.IDisplayDeviceDriver implementation; static DisplayDevice() { implementation = Platform.Factory.Default.CreateDisplayDeviceDriver(); - available_displays_readonly = available_displays.AsReadOnly(); } - internal DisplayDevice() { - available_displays.Add(this); - available_resolutions_readonly = available_resolutions.AsReadOnly(); - } + internal DisplayDevice() { AvailableDisplays.Add(this); } internal DisplayDevice(DisplayResolution currentResolution, bool primary, - IEnumerable availableResolutions, Rectangle bounds) : this() { + IEnumerable resolutions, Rectangle bounds) : this() { #warning "Consolidate current resolution with bounds? Can they fall out of sync right now?" this.current_resolution = currentResolution; IsPrimary = primary; - this.available_resolutions.AddRange(availableResolutions); + AvailableResolutions.AddRange(resolutions); this.bounds = bounds == Rectangle.Empty ? currentResolution.Bounds : bounds; Debug.Print("DisplayDevice {0} ({1}) supports {2} resolutions.", - available_displays.Count, primary ? "primary" : "secondary", available_resolutions.Count); + AvailableDisplays.Count, primary ? "primary" : "secondary", AvailableResolutions.Count); } - /// Gets the bounds of this instance in pixel coordinates. + /// Returns bounds of this instance in pixel coordinates. public Rectangle Bounds { get { return bounds; } internal set { @@ -63,25 +55,25 @@ namespace OpenTK { } } - /// Gets a System.Int32 that contains the width of this display in pixels. + /// Returns width of this display in pixels. public int Width { get { return current_resolution.Width; } } - /// Gets a System.Int32 that contains the height of this display in pixels. + /// Returns height of this display in pixels. public int Height { get { return current_resolution.Height; } } - /// Gets a System.Int32 that contains number of bits per pixel of this display. Typical values include 8, 16, 24 and 32. + /// Returns number of bits per pixel of this display. Typical values include 8, 16, 24 and 32. public int BitsPerPixel { get { return current_resolution.BitsPerPixel; } internal set { current_resolution.BitsPerPixel = value; } } - /// Gets a System.Single representing the vertical refresh rate of this display. + /// Returns vertical refresh rate of this display. public float RefreshRate { get { return current_resolution.RefreshRate; } internal set { current_resolution.RefreshRate = value; } } - /// Gets a System.Boolean that indicates whether this Display is the primary Display in systems with multiple Displays. + /// Returns whether this Display is the primary Display in systems with multiple Displays. public bool IsPrimary { get { return primary; } internal set { @@ -93,108 +85,24 @@ namespace OpenTK { primary_display = this; } } + + /// Data unique to this Display. + public object Metadata; - /// Selects an available resolution that matches the specified parameters. - /// The width of the requested resolution in pixels. - /// The height of the requested resolution in pixels. - /// The bits per pixel of the requested resolution. - /// The refresh rate of the requested resolution in hertz. - /// The requested DisplayResolution or null if the parameters cannot be met. - /// If a matching resolution is not found, this function will retry ignoring the specified refresh rate, - /// bits per pixel and resolution, in this order. If a matching resolution still doesn't exist, this function will - /// return the current resolution. - /// A parameter set to 0 or negative numbers will not be used in the search (e.g. if refreshRate is 0, - /// any refresh rate will be considered valid). - /// This function allocates memory. - public DisplayResolution SelectResolution(int width, int height, int bitsPerPixel, float refreshRate) { - DisplayResolution resolution = FindResolution(width, height, bitsPerPixel, refreshRate); - if (resolution == null) - resolution = FindResolution(width, height, bitsPerPixel, 0); - if (resolution == null) - resolution = FindResolution(width, height, 0, 0); - if (resolution == null) - return current_resolution; - return resolution; - } + /// The list of objects available on this device. + public List AvailableResolutions = new List(); - /// Gets the list of objects available on this device. - public IList AvailableResolutions { - get { return available_resolutions_readonly; } - internal set - { - available_resolutions = (List)value; - available_resolutions_readonly = available_resolutions.AsReadOnly(); - } - } - - /// Changes the resolution of the DisplayDevice. - /// The resolution to set. - /// Thrown if the requested resolution could not be set. - /// If the specified resolution is null, this function will restore the original DisplayResolution. - public void ChangeResolution(DisplayResolution resolution) { - if (resolution == null) - this.RestoreResolution(); - - if (resolution == current_resolution) - return; - - if (implementation.TryChangeResolution(this, resolution)) { - if (original_resolution == null) - original_resolution = current_resolution; - current_resolution = resolution; - } else - throw new Graphics.GraphicsModeException(String.Format("Device {0}: Failed to change resolution to {1}.", - this, resolution)); - } - - /// Changes the resolution of the DisplayDevice. - /// The new width of the DisplayDevice. - /// The new height of the DisplayDevice. - /// The new bits per pixel of the DisplayDevice. - /// The new refresh rate of the DisplayDevice. - /// Thrown if the requested resolution could not be set. - public void ChangeResolution(int width, int height, int bitsPerPixel, float refreshRate) { - this.ChangeResolution(this.SelectResolution(width, height, bitsPerPixel, refreshRate)); - } - - /// Restores the original resolution of the DisplayDevice. - /// Thrown if the original resolution could not be restored. - public void RestoreResolution() { - if (original_resolution != null) { - if (implementation.TryRestoreResolution(this)) { - current_resolution = original_resolution; - original_resolution = null; - } else - throw new Graphics.GraphicsModeException(String.Format("Device {0}: Failed to restore resolution.", this)); - } - } - - /// Gets the list of available objects. - public static IList AvailableDisplays { - get { return available_displays_readonly; } - } + /// The list of available objects. + public static List AvailableDisplays = new List(); /// Gets the default (primary) display of this system. public static DisplayDevice Default { get { return primary_display; } } - DisplayResolution FindResolution(int width, int height, int bitsPerPixel, float refreshRate) { - for (int i = 0; i < available_resolutions.Count; i++) { - DisplayResolution res = available_resolutions[i]; - bool match = ((width > 0 && width == res.Width) || width == 0) && - ((height > 0 && height == res.Height) || height == 0) && - ((bitsPerPixel > 0 && bitsPerPixel == res.BitsPerPixel) || bitsPerPixel == 0) && - ((refreshRate > 0 && System.Math.Abs(refreshRate - res.RefreshRate) < 1.0) || refreshRate == 0); - - if (match) return res; - } - return null; - } - /// Returns a System.String representing this DisplayDevice. /// A System.String representing this DisplayDevice. public override string ToString() { return String.Format("{0}: {1} ({2} modes available)", IsPrimary ? "Primary" : "Secondary", - Bounds.ToString(), available_resolutions.Count); + Bounds.ToString(), AvailableResolutions.Count); } } } diff --git a/OpenTK/GameWindow.cs b/OpenTK/GameWindow.cs index adccb46ee..58c5222b6 100644 --- a/OpenTK/GameWindow.cs +++ b/OpenTK/GameWindow.cs @@ -37,6 +37,8 @@ using OpenTK.Platform; namespace OpenTK { + public enum GameWindowFlags { Default = 0 }; + /// /// The GameWindow class contains cross-platform methods to create and render on an OpenGL /// window, handle input and load resources. diff --git a/OpenTK/GameWindowFlags.cs b/OpenTK/GameWindowFlags.cs deleted file mode 100644 index 68515dc82..000000000 --- a/OpenTK/GameWindowFlags.cs +++ /dev/null @@ -1,41 +0,0 @@ -#region License -// -// The Open Toolkit Library License -// -// Copyright (c) 2006 - 2009 the Open Toolkit library. -// -// Permission is hereby granted, free of charge, to any person obtaining a copy -// of this software and associated documentation files (the "Software"), to deal -// in the Software without restriction, including without limitation the rights to -// use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of -// the Software, and to permit persons to whom the Software is furnished to do -// so, subject to the following conditions: -// -// The above copyright notice and this permission notice shall be included in all -// copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, -// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES -// OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND -// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT -// HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, -// WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING -// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR -// OTHER DEALINGS IN THE SOFTWARE. -// -#endregion - -using System; - -namespace OpenTK { - - /// Defines bitwise combianations of GameWindow construction options. - [Flags] - public enum GameWindowFlags { - /// Indicates default construction options. - Default = 0, - - /// Indicates that the GameWindow should cover the whole screen. - Fullscreen = 1, - } -} \ No newline at end of file diff --git a/OpenTK/NativeWindow.cs b/OpenTK/NativeWindow.cs index 35dc5bc71..200ccbf3b 100644 --- a/OpenTK/NativeWindow.cs +++ b/OpenTK/NativeWindow.cs @@ -86,11 +86,6 @@ namespace OpenTK { this.device = device; implementation = Factory.Default.CreateNativeWindow(x, y, width, height, title, mode, options, this.device); - - if ((options & GameWindowFlags.Fullscreen) != 0) { - this.device.ChangeResolution(width, height, mode.ColorFormat.BitsPerPixel, 0); - WindowState = WindowState.Fullscreen; - } } /// Closes the NativeWindow. @@ -271,10 +266,6 @@ namespace OpenTK { /// Releases all non-managed resources belonging to this NativeWindow. public virtual void Dispose() { if (!IsDisposed) { - if ((options & GameWindowFlags.Fullscreen) != 0) { - //if (WindowState == WindowState.Fullscreen) WindowState = WindowState.Normal; // TODO: Revise. - device.RestoreResolution(); - } implementation.Dispose(); GC.SuppressFinalize(this); IsDisposed = true; diff --git a/OpenTK/OpenTK.csproj b/OpenTK/OpenTK.csproj index 5bd00d9f8..f1f527377 100644 --- a/OpenTK/OpenTK.csproj +++ b/OpenTK/OpenTK.csproj @@ -1,160 +1,159 @@ - - - - {35FEE071-2DE6-48A1-9343-B5C1F202A12B} - Debug - AnyCPU - Library - OpenTK - OpenTK - v2.0 - - - Properties - False - True - False - False - obj\$(Configuration)\ - 4 - - - AnyCPU - 4194304 - False - Auto - 4096 - - - ..\output\debug\ - True - None - True - False - DEBUG;TRACE - obj\ - - - ..\output\release\ - False - None - True - False - TRACE - obj\ - Project - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - {4A4110EE-21CA-4715-AF67-0C8B7CE0642F} - InteropPatcher - - - - - - - - - - - + + + + {35FEE071-2DE6-48A1-9343-B5C1F202A12B} + Debug + AnyCPU + Library + OpenTK + OpenTK + v2.0 + + + Properties + False + True + False + False + obj\$(Configuration)\ + 4 + + + AnyCPU + 4194304 + False + Auto + 4096 + + + ..\output\debug\ + True + None + True + False + DEBUG;TRACE + obj\ + + + ..\output\release\ + False + None + True + False + TRACE + obj\ + Project + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + {4A4110EE-21CA-4715-AF67-0C8B7CE0642F} + InteropPatcher + + + + + + + + + + + \ No newline at end of file diff --git a/OpenTK/Platform/IDisplayDeviceDriver.cs b/OpenTK/Platform/IDisplayDeviceDriver.cs index 67f317f89..1eb444adc 100644 --- a/OpenTK/Platform/IDisplayDeviceDriver.cs +++ b/OpenTK/Platform/IDisplayDeviceDriver.cs @@ -1,18 +1,15 @@ -#region --- License --- -/* Licensed under the MIT/X11 license. - * Copyright (c) 2006-2008 the OpenTK team. - * This notice may not be removed. - * See license.txt for licensing detailed licensing details. - */ -#endregion - -using System; - -namespace OpenTK.Platform -{ - internal interface IDisplayDeviceDriver - { - bool TryChangeResolution(DisplayDevice device, DisplayResolution resolution); - bool TryRestoreResolution(DisplayDevice device); - } -} +#region --- License --- +/* Licensed under the MIT/X11 license. + * Copyright (c) 2006-2008 the OpenTK team. + * This notice may not be removed. + * See license.txt for licensing detailed licensing details. + */ +#endregion + +using System; + +namespace OpenTK.Platform +{ + internal interface IDisplayDeviceDriver { + } +} diff --git a/OpenTK/Platform/MacOS/QuartzDisplayDeviceDriver.cs b/OpenTK/Platform/MacOS/QuartzDisplayDeviceDriver.cs index 89395f32f..09d67de35 100644 --- a/OpenTK/Platform/MacOS/QuartzDisplayDeviceDriver.cs +++ b/OpenTK/Platform/MacOS/QuartzDisplayDeviceDriver.cs @@ -1,155 +1,90 @@ -using System; -using System.Collections.Generic; -using System.Drawing; -using OpenTK.Platform.MacOS.Carbon; - -namespace OpenTK.Platform.MacOS -{ - class QuartzDisplayDeviceDriver : IDisplayDeviceDriver - { - static Dictionary displayMap = - new Dictionary(); - - static IntPtr mainDisplay; - internal static IntPtr MainDisplay { get { return mainDisplay; } } - - unsafe static QuartzDisplayDeviceDriver() { - // To minimize the need to add static methods to OpenTK.Graphics.DisplayDevice - // we only allow settings to be set through its constructor. - // Thus, we save all necessary parameters in temporary variables - // and construct the device when every needed detail is available. - // The main DisplayDevice constructor adds the newly constructed device - // to the list of available devices. - const int maxDisplayCount = 20; - IntPtr[] displays = new IntPtr[maxDisplayCount]; - int displayCount; - fixed(IntPtr* displayPtr = displays) { - CG.CGGetActiveDisplayList(maxDisplayCount, displayPtr, out displayCount); - } - - Debug.Print("CoreGraphics reported {0} display(s).", displayCount); - - for (int i = 0; i < displayCount; i++) { - IntPtr curDisplay = displays[i]; - - // according to docs, first element in the array is always the main display. - bool primary = (i == 0); - if (primary) - mainDisplay = curDisplay; - - // gets current settings - int currentWidth = CG.CGDisplayPixelsWide(curDisplay); - int currentHeight = CG.CGDisplayPixelsHigh(curDisplay); - Debug.Print("Display {0} is at {1}x{2}", i, currentWidth, currentHeight); - - IntPtr displayModesPtr = CG.CGDisplayAvailableModes(curDisplay); - CFArray displayModes = new CFArray(displayModesPtr); - Debug.Print("Supports {0} display modes.", displayModes.Count); - - DisplayResolution opentk_dev_current_res = null; - List opentk_dev_available_res = new List(); - IntPtr currentModePtr = CG.CGDisplayCurrentMode(curDisplay); - CFDictionary currentMode = new CFDictionary(currentModePtr); - - for (int j = 0; j < displayModes.Count; j++) - { - CFDictionary dict = new CFDictionary(displayModes[j]); - - int width = (int) dict.GetNumberValue("Width"); - int height = (int) dict.GetNumberValue("Height"); - int bpp = (int) dict.GetNumberValue("BitsPerPixel"); - double freq = dict.GetNumberValue("RefreshRate"); - bool current = currentMode.DictRef == dict.DictRef; - - //if (current) Debug.Write(" * "); - //else Debug.Write(" "); - - //Debug.Print("Mode {0} is {1}x{2}x{3} @ {4}.", j, width, height, bpp, freq); - - DisplayResolution thisRes = new DisplayResolution(0, 0, width, height, bpp, (float)freq); - opentk_dev_available_res.Add(thisRes); - - if (current) - opentk_dev_current_res = thisRes; - } - - HIRect bounds = CG.CGDisplayBounds(curDisplay); - Rectangle newRect = new Rectangle( - (int)bounds.Origin.X, (int)bounds.Origin.Y, (int)bounds.Size.X, (int)bounds.Size.Y); - - Debug.Print("Display {0} bounds: {1}", i, newRect); - - DisplayDevice opentk_dev = - new DisplayDevice(opentk_dev_current_res, primary, opentk_dev_available_res, newRect); - - displayMap.Add(opentk_dev, curDisplay); - } - } - - internal static IntPtr HandleTo(DisplayDevice displayDevice) { - if (displayMap.ContainsKey(displayDevice)) - return displayMap[displayDevice]; - else - return IntPtr.Zero; - } - - #region IDisplayDeviceDriver Members - - Dictionary storedModes = new Dictionary(); - List displaysCaptured = new List(); - - public bool TryChangeResolution(DisplayDevice device, DisplayResolution resolution) - { - IntPtr display = displayMap[device]; - IntPtr currentModePtr = CG.CGDisplayCurrentMode(display); - - if (!storedModes.ContainsKey(display)) { - storedModes.Add(display, currentModePtr); - } - - IntPtr displayModesPtr = CG.CGDisplayAvailableModes(display); - CFArray displayModes = new CFArray(displayModesPtr); - - for (int j = 0; j < displayModes.Count; j++) { - CFDictionary dict = new CFDictionary(displayModes[j]); - - int width = (int)dict.GetNumberValue("Width"); - int height = (int)dict.GetNumberValue("Height"); - int bpp = (int)dict.GetNumberValue("BitsPerPixel"); - double freq = dict.GetNumberValue("RefreshRate"); - - if (width == resolution.Width && height == resolution.Height && - bpp == resolution.BitsPerPixel && Math.Abs(freq - resolution.RefreshRate) < 1e-6) { - if (!displaysCaptured.Contains(display)) { - CG.CGDisplayCapture(display); - } - - Debug.Print("Changing resolution to {0}x{1}x{2}@{3}.", width, height, bpp, freq); - CG.CGDisplaySwitchToMode(display, displayModes[j]); - return true; - } - - } - return false; - } - - public bool TryRestoreResolution(DisplayDevice device) { - IntPtr display = displayMap[device]; - - if (storedModes.ContainsKey(display)) { - Debug.Print("Restoring resolution."); - - CG.CGDisplaySwitchToMode(display, storedModes[display]); - CG.CGDisplayRelease(display); - displaysCaptured.Remove(display); - - return true; - } - - return false; - } - - #endregion - - } -} +using System; +using System.Collections.Generic; +using System.Drawing; +using OpenTK.Platform.MacOS.Carbon; + +namespace OpenTK.Platform.MacOS +{ + class QuartzDisplayDeviceDriver : IDisplayDeviceDriver + { + static IntPtr mainDisplay; + internal static IntPtr MainDisplay { get { return mainDisplay; } } + + unsafe static QuartzDisplayDeviceDriver() { + // To minimize the need to add static methods to OpenTK.Graphics.DisplayDevice + // we only allow settings to be set through its constructor. + // Thus, we save all necessary parameters in temporary variables + // and construct the device when every needed detail is available. + // The main DisplayDevice constructor adds the newly constructed device + // to the list of available devices. + const int maxDisplayCount = 20; + IntPtr[] displays = new IntPtr[maxDisplayCount]; + int displayCount; + fixed(IntPtr* displayPtr = displays) { + CG.CGGetActiveDisplayList(maxDisplayCount, displayPtr, out displayCount); + } + + Debug.Print("CoreGraphics reported {0} display(s).", displayCount); + + for (int i = 0; i < displayCount; i++) { + IntPtr curDisplay = displays[i]; + + // according to docs, first element in the array is always the main display. + bool primary = (i == 0); + if (primary) + mainDisplay = curDisplay; + + // gets current settings + int currentWidth = CG.CGDisplayPixelsWide(curDisplay); + int currentHeight = CG.CGDisplayPixelsHigh(curDisplay); + Debug.Print("Display {0} is at {1}x{2}", i, currentWidth, currentHeight); + + IntPtr displayModesPtr = CG.CGDisplayAvailableModes(curDisplay); + CFArray displayModes = new CFArray(displayModesPtr); + Debug.Print("Supports {0} display modes.", displayModes.Count); + + DisplayResolution opentk_dev_current_res = null; + List opentk_dev_available_res = new List(); + IntPtr currentModePtr = CG.CGDisplayCurrentMode(curDisplay); + CFDictionary currentMode = new CFDictionary(currentModePtr); + + for (int j = 0; j < displayModes.Count; j++) + { + CFDictionary dict = new CFDictionary(displayModes[j]); + + int width = (int) dict.GetNumberValue("Width"); + int height = (int) dict.GetNumberValue("Height"); + int bpp = (int) dict.GetNumberValue("BitsPerPixel"); + double freq = dict.GetNumberValue("RefreshRate"); + bool current = currentMode.DictRef == dict.DictRef; + + //if (current) Debug.Write(" * "); + //else Debug.Write(" "); + + //Debug.Print("Mode {0} is {1}x{2}x{3} @ {4}.", j, width, height, bpp, freq); + + DisplayResolution thisRes = new DisplayResolution(0, 0, width, height, bpp, (float)freq); + opentk_dev_available_res.Add(thisRes); + + if (current) + opentk_dev_current_res = thisRes; + } + + HIRect bounds = CG.CGDisplayBounds(curDisplay); + Rectangle newRect = new Rectangle( + (int)bounds.Origin.X, (int)bounds.Origin.Y, (int)bounds.Size.X, (int)bounds.Size.Y); + + Debug.Print("Display {0} bounds: {1}", i, newRect); + + DisplayDevice opentk_dev = + new DisplayDevice(opentk_dev_current_res, primary, opentk_dev_available_res, newRect); + opentk_dev.Metadata = curDisplay; + } + } + + internal static IntPtr HandleTo(DisplayDevice device) { + if (device == null || device.Metadata == null) return IntPtr.Zero; + return (IntPtr)device.Metadata; + } + } +} diff --git a/OpenTK/Platform/Windows/WinDisplayDevice.cs b/OpenTK/Platform/Windows/WinDisplayDevice.cs index 0d51fbdc2..8f004a11d 100644 --- a/OpenTK/Platform/Windows/WinDisplayDevice.cs +++ b/OpenTK/Platform/Windows/WinDisplayDevice.cs @@ -1,101 +1,75 @@ -#region --- License --- -/* Licensed under the MIT/X11 license. - * Copyright (c) 2006-2008 the OpenTK team. - * This notice may not be removed. - * See license.txt for licensing detailed licensing details. - */ -#endregion - -using System; -using System.Collections.Generic; - -namespace OpenTK.Platform.Windows { - - internal class WinDisplayDeviceDriver : IDisplayDeviceDriver { - - static Dictionary available_device_names = - new Dictionary(); // Needed for ChangeDisplaySettingsEx - - /// Queries available display devices and display resolutions. - static WinDisplayDeviceDriver() { - // To minimize the need to add static methods to OpenTK.Graphics.DisplayDevice - // we only allow settings to be set through its constructor. - // Thus, we save all necessary parameters in temporary variables - // and construct the device when every needed detail is available. - // The main DisplayDevice constructor adds the newly constructed device - // to the list of available devices. - DisplayResolution currentRes = null; - List availableRes = new List(); - bool devPrimary = false; - int deviceNum = 0; - - // Get available video adapters and enumerate all monitors - WindowsDisplayDevice winDev = new WindowsDisplayDevice(); - while (API.EnumDisplayDevices(null, deviceNum++, winDev, 0)) { - if ((winDev.StateFlags & DisplayDeviceStateFlags.AttachedToDesktop) == 0) - continue; - - DeviceMode mode = new DeviceMode(); - - // The second function should only be executed when the first one fails (e.g. when the monitor is disabled) - if (API.EnumDisplaySettings(winDev.DeviceName, (int)DisplayModeSettings.Current, mode) || - API.EnumDisplaySettings(winDev.DeviceName, (int)DisplayModeSettings.Registry, mode)) { - if (mode.BitsPerPel > 0) { - currentRes = new DisplayResolution( - mode.Position.X, mode.Position.Y, - mode.PelsWidth, mode.PelsHeight, - mode.BitsPerPel, mode.DisplayFrequency); - devPrimary = (winDev.StateFlags & DisplayDeviceStateFlags.PrimaryDevice) != 0; - } - } - - availableRes.Clear(); - int i = 0; - while (API.EnumDisplaySettings(winDev.DeviceName, i++, mode)) { - // For example, the device \.\DISPLAYV1 returns a single resolution with bits per pixel of 0 - // We must skip these resolutions - if (mode.BitsPerPel <= 0) continue; - - availableRes.Add(new DisplayResolution( - mode.Position.X, mode.Position.Y, - mode.PelsWidth, mode.PelsHeight, - mode.BitsPerPel, mode.DisplayFrequency)); - } - - // This device has no valid resolutions, ignore it - if (availableRes.Count == 0 || currentRes == null) continue; - - // Construct the OpenTK DisplayDevice through the accumulated parameters. - // The constructor automatically adds the DisplayDevice to the list of available devices. - DisplayDevice device = new DisplayDevice(currentRes, devPrimary, availableRes, currentRes.Bounds); - available_device_names.Add(device, winDev.DeviceName); - currentRes = null; - } - } - - public WinDisplayDeviceDriver() { - } - - public bool TryChangeResolution(DisplayDevice device, DisplayResolution resolution) { - DeviceMode mode = null; - - if (resolution != null) { - mode = new DeviceMode(); - mode.PelsWidth = resolution.Width; - mode.PelsHeight = resolution.Height; - mode.BitsPerPel = resolution.BitsPerPixel; - mode.DisplayFrequency = (int)resolution.RefreshRate; - mode.Fields = Constants.DM_BITSPERPEL | Constants.DM_PELSWIDTH - | Constants.DM_PELSHEIGHT | Constants.DM_DISPLAYFREQUENCY; - } - - return Constants.DISP_CHANGE_SUCCESSFUL == - API.ChangeDisplaySettingsEx(available_device_names[device], mode, IntPtr.Zero, - ChangeDisplaySettingsEnum.Fullscreen, IntPtr.Zero); - } - - public bool TryRestoreResolution(DisplayDevice device) { - return TryChangeResolution(device, null); - } - } -} +#region --- License --- +/* Licensed under the MIT/X11 license. + * Copyright (c) 2006-2008 the OpenTK team. + * This notice may not be removed. + * See license.txt for licensing detailed licensing details. + */ +#endregion + +using System; +using System.Collections.Generic; + +namespace OpenTK.Platform.Windows { + + internal class WinDisplayDeviceDriver : IDisplayDeviceDriver { + + /// Queries available display devices and display resolutions. + static WinDisplayDeviceDriver() { + // To minimize the need to add static methods to OpenTK.Graphics.DisplayDevice + // we only allow settings to be set through its constructor. + // Thus, we save all necessary parameters in temporary variables + // and construct the device when every needed detail is available. + // The main DisplayDevice constructor adds the newly constructed device + // to the list of available devices. + DisplayResolution currentRes = null; + List availableRes = new List(); + bool devPrimary = false; + int deviceNum = 0; + + // Get available video adapters and enumerate all monitors + WindowsDisplayDevice winDev = new WindowsDisplayDevice(); + while (API.EnumDisplayDevices(null, deviceNum++, winDev, 0)) { + if ((winDev.StateFlags & DisplayDeviceStateFlags.AttachedToDesktop) == 0) + continue; + + DeviceMode mode = new DeviceMode(); + + // The second function should only be executed when the first one fails (e.g. when the monitor is disabled) + if (API.EnumDisplaySettings(winDev.DeviceName, (int)DisplayModeSettings.Current, mode) || + API.EnumDisplaySettings(winDev.DeviceName, (int)DisplayModeSettings.Registry, mode)) { + if (mode.BitsPerPel > 0) { + currentRes = new DisplayResolution( + mode.Position.X, mode.Position.Y, + mode.PelsWidth, mode.PelsHeight, + mode.BitsPerPel, mode.DisplayFrequency); + devPrimary = (winDev.StateFlags & DisplayDeviceStateFlags.PrimaryDevice) != 0; + } + } + + availableRes.Clear(); + int i = 0; + while (API.EnumDisplaySettings(winDev.DeviceName, i++, mode)) { + // For example, the device \.\DISPLAYV1 returns a single resolution with bits per pixel of 0 + // We must skip these resolutions + if (mode.BitsPerPel <= 0) continue; + + availableRes.Add(new DisplayResolution( + mode.Position.X, mode.Position.Y, + mode.PelsWidth, mode.PelsHeight, + mode.BitsPerPel, mode.DisplayFrequency)); + } + + // This device has no valid resolutions, ignore it + if (availableRes.Count == 0 || currentRes == null) continue; + + // Construct the OpenTK DisplayDevice through the accumulated parameters. + // The constructor automatically adds the DisplayDevice to the list of available devices. + DisplayDevice device = new DisplayDevice(currentRes, devPrimary, availableRes, currentRes.Bounds); + currentRes = null; + } + } + + public WinDisplayDeviceDriver() { + } + } +} diff --git a/OpenTK/Platform/X11/X11DisplayDevice.cs b/OpenTK/Platform/X11/X11DisplayDevice.cs index 62252398f..32187ac14 100644 --- a/OpenTK/Platform/X11/X11DisplayDevice.cs +++ b/OpenTK/Platform/X11/X11DisplayDevice.cs @@ -1,240 +1,169 @@ -#region License -/* Licensed under the MIT/X11 license. - * Copyright (c) 2006-2008 the OpenTK Team. - * This notice may not be removed from any source distribution. - * See license.txt for licensing detailed licensing details. - */ -#endregion - -using System; -using System.Collections.Generic; -using System.Drawing; -using System.Runtime.InteropServices; - -namespace OpenTK.Platform.X11 { - - internal class X11DisplayDevice : IDisplayDeviceDriver { - // Store a mapping between resolutions and their respective - // size_index (needed for XRRSetScreenConfig). The size_index - // is simply the sequence number of the resolution as returned by - // XRRSizes. This is done per available screen. - static List> screenResolutionToIndex = - new List>(); - // Store a mapping between DisplayDevices and their default resolutions. - static Dictionary deviceToDefaultResolution = new Dictionary(); - // Store a mapping between DisplayDevices and X11 screens. - static Dictionary deviceToScreen = new Dictionary(); - // Keep the time when the config of each screen was last updated. - static List lastConfigUpdate = new List(); - - static bool xinerama_supported, xrandr_supported, xf86_supported; - - static X11DisplayDevice() { - List devices = new List(); - try { - xinerama_supported = QueryXinerama(devices); - } catch { - Debug.Print("Xinerama query failed."); - } - - if (!xinerama_supported) { - // We assume that devices are equivalent to the number of available screens. - // Note: this won't work correctly in the case of distinct X servers. - for (int i = 0; i < API.ScreenCount; i++) { - DisplayDevice dev = new DisplayDevice(); - dev.IsPrimary = i == API.XDefaultScreen(API.DefaultDisplay); - devices.Add(dev); - deviceToScreen.Add(dev, i); - } - } - - try { - xrandr_supported = QueryXRandR(devices); - } catch { } - - if (!xrandr_supported) { - Debug.Print("XRandR query failed, falling back to XF86."); - try { - xf86_supported = QueryXF86(devices); - } catch { } - - if (!xf86_supported) { - Debug.Print("XF86 query failed, no DisplayDevice support available."); - } - } - } - - internal X11DisplayDevice() { } - - static bool QueryXinerama(List devices) { - // Try to use Xinerama to obtain the geometry of all output devices. - int event_base, error_base; - if (NativeMethods.XineramaQueryExtension(API.DefaultDisplay, out event_base, out error_base) && - NativeMethods.XineramaIsActive(API.DefaultDisplay)) { - XineramaScreenInfo[] screens = NativeMethods.XineramaQueryScreens(API.DefaultDisplay); - bool first = true; - foreach (XineramaScreenInfo screen in screens) { - DisplayDevice dev = new DisplayDevice(); - dev.Bounds = new Rectangle(screen.X, screen.Y, screen.Width, screen.Height); - if (first) { - // We consider the first device returned by Xinerama as the primary one. - // Makes sense conceptually, but is there a way to verify this? - dev.IsPrimary = true; - first = false; - } - devices.Add(dev); - // It seems that all X screens are equal to 0 is Xinerama is enabled, at least on Nvidia (verify?) - deviceToScreen.Add(dev, 0 /*screen.ScreenNumber*/); - } - } - return true; - } - - static bool QueryXRandR(List devices) { - // Get available resolutions. Then, for each resolution get all available rates. - foreach (DisplayDevice dev in devices) { - int screen = deviceToScreen[dev]; - - IntPtr lastUpdateTimestamp; - API.XRRTimes(API.DefaultDisplay, screen, out lastUpdateTimestamp); - lastConfigUpdate.Add(lastUpdateTimestamp); - List available_res = new List(); - - // Add info for a new screen. - screenResolutionToIndex.Add(new Dictionary()); - int[] depths = API.XListDepths(API.DefaultDisplay, screen); - - int resolution_count = 0; - foreach (XRRScreenSize size in FindAvailableResolutions(screen)) { - if (size.Width == 0 || size.Height == 0) { - Debug.Print("[Warning] XRandR returned an invalid resolution ({0}) for display device {1}", size, screen); - continue; - } - short[] rates = API.XRRRates(API.DefaultDisplay, screen, resolution_count); - - // It seems that XRRRates returns 0 for modes that are larger than the screen - // can support, as well as for all supported modes. On Ubuntu 7.10 the tool - // "Screens and Graphics" does report these modes, though. - foreach (short rate in rates) { - // Note: some X servers (like Xming on Windows) do not report any rates other than 0. - // If we only have 1 rate, add it even if it is 0. - if (rate != 0 || rates.Length == 1) - foreach (int depth in depths) - available_res.Add(new DisplayResolution(0, 0, size.Width, size.Height, depth, rate)); - } - // Keep the index of this resolution - we will need it for resolution changes later. - foreach (int depth in depths) { - // Note that Xinerama may return multiple devices for a single screen. XRandR will - // not distinguish between the two as far as resolutions are supported (since XRandR - // operates on X screens, not display devices) - we need to be careful not to add the - // same resolution twice! - DisplayResolution res = new DisplayResolution(0, 0, size.Width, size.Height, depth, 0); - if (!screenResolutionToIndex[screen].ContainsKey(res)) - screenResolutionToIndex[screen].Add(res, resolution_count); - } - ++resolution_count; - } - - IntPtr screenConfig = API.XRRGetScreenInfo(API.DefaultDisplay, API.XRootWindow(API.DefaultDisplay, screen)); - ushort curRotation; - int curResolutionIndex = API.XRRConfigCurrentConfiguration(screenConfig, out curRotation); - float curRefreshRate = API.XRRConfigCurrentRate(screenConfig); - int curDepth = API.XDefaultDepth(API.DefaultDisplay, screen); - API.XRRFreeScreenConfigInfo(screenConfig); - - if (dev.Bounds == Rectangle.Empty) - dev.Bounds = new Rectangle(0, 0, available_res[curResolutionIndex].Width, available_res[curResolutionIndex].Height); - dev.BitsPerPixel = curDepth; - dev.RefreshRate = curRefreshRate; - dev.AvailableResolutions = available_res; - - deviceToDefaultResolution.Add(dev, curResolutionIndex); - } - return true; - } - - static bool QueryXF86(List devices) { - return false; - } - - static XRRScreenSize[] FindAvailableResolutions(int screen) { - XRRScreenSize[] resolutions = API.XRRSizes(API.DefaultDisplay, screen); - if (resolutions == null) - throw new NotSupportedException("XRandR extensions not available."); - return resolutions; - } - - static bool ChangeResolutionXRandR(DisplayDevice device, DisplayResolution resolution) { - int screen = deviceToScreen[device]; - IntPtr root = API.XRootWindow(API.DefaultDisplay, screen); - IntPtr screen_config = API.XRRGetScreenInfo(API.DefaultDisplay, root); - - ushort current_rotation; - int current_resolution_index = API.XRRConfigCurrentConfiguration(screen_config, out current_rotation); - int new_resolution_index; - if (resolution != null) - new_resolution_index = screenResolutionToIndex[screen] - [new DisplayResolution(0, 0, resolution.Width, resolution.Height, resolution.BitsPerPixel, 0)]; - else - new_resolution_index = deviceToDefaultResolution[device]; - - Debug.Print("Changing size of screen {0} from {1} to {2}", - screen, current_resolution_index, new_resolution_index); - - return 0 == API.XRRSetScreenConfigAndRate(API.DefaultDisplay, screen_config, root, new_resolution_index, - current_rotation, (short)(resolution != null ? resolution.RefreshRate : 0), lastConfigUpdate[screen]); - } - - static bool ChangeResolutionXF86(DisplayDevice device, DisplayResolution resolution) { - return false; - } - - public bool TryChangeResolution(DisplayDevice device, DisplayResolution resolution) { - // If resolution is null, restore the default resolution (new_resolution_index = 0). - if (xrandr_supported) { - return ChangeResolutionXRandR(device, resolution); - } else if (xf86_supported) { - return ChangeResolutionXF86(device, resolution); - } - return false; - } - - public bool TryRestoreResolution(DisplayDevice device) { - return TryChangeResolution(device, null); - } - - static class NativeMethods { - const string Xinerama = "libXinerama"; - - [DllImport(Xinerama)] - public static extern bool XineramaQueryExtension(IntPtr dpy, out int event_basep, out int error_basep); - - [DllImport(Xinerama)] - public static extern bool XineramaIsActive(IntPtr dpy); - - [DllImport(Xinerama)] - static extern IntPtr XineramaQueryScreens(IntPtr dpy, out int count); - - public unsafe static XineramaScreenInfo[] XineramaQueryScreens(IntPtr dpy) { - int count; - IntPtr screen_ptr = XineramaQueryScreens(dpy, out count); - XineramaScreenInfo* ptr = (XineramaScreenInfo*)screen_ptr; - - XineramaScreenInfo[] screens = new XineramaScreenInfo[count]; - for( int i = 0; i < screens.Length; i++ ) { - screens[i] = *ptr++; - } - return screens; - } - } - - [StructLayout(LayoutKind.Sequential, Pack = 1)] - struct XineramaScreenInfo { - public int ScreenNumber; - public short X; - public short Y; - public short Width; - public short Height; - } - } -} +#region License +/* Licensed under the MIT/X11 license. + * Copyright (c) 2006-2008 the OpenTK Team. + * This notice may not be removed from any source distribution. + * See license.txt for licensing detailed licensing details. + */ +#endregion + +using System; +using System.Collections.Generic; +using System.Drawing; +using System.Runtime.InteropServices; + +namespace OpenTK.Platform.X11 { + + internal class X11DisplayDevice : IDisplayDeviceDriver { + static bool xinerama_supported, xrandr_supported, xf86_supported; + + static X11DisplayDevice() { + List devices = new List(); + try { + xinerama_supported = QueryXinerama(devices); + } catch { + Debug.Print("Xinerama query failed."); + } + + if (!xinerama_supported) { + // We assume that devices are equivalent to the number of available screens. + // Note: this won't work correctly in the case of distinct X servers. + for (int i = 0; i < API.ScreenCount; i++) { + DisplayDevice dev = new DisplayDevice(); + dev.IsPrimary = i == API.XDefaultScreen(API.DefaultDisplay); + dev.Metadata = i; + devices.Add(dev); + } + } + + try { + xrandr_supported = QueryXRandR(devices); + } catch { } + + if (!xrandr_supported) { + Debug.Print("XRandR query failed, falling back to XF86."); + try { + xf86_supported = QueryXF86(devices); + } catch { } + + if (!xf86_supported) { + Debug.Print("XF86 query failed, no DisplayDevice support available."); + } + } + } + + internal X11DisplayDevice() { } + + static bool QueryXinerama(List devices) { + // Try to use Xinerama to obtain the geometry of all output devices. + int event_base, error_base; + if (NativeMethods.XineramaQueryExtension(API.DefaultDisplay, out event_base, out error_base) && + NativeMethods.XineramaIsActive(API.DefaultDisplay)) { + XineramaScreenInfo[] screens = NativeMethods.XineramaQueryScreens(API.DefaultDisplay); + bool first = true; + foreach (XineramaScreenInfo screen in screens) { + DisplayDevice dev = new DisplayDevice(); + dev.Bounds = new Rectangle(screen.X, screen.Y, screen.Width, screen.Height); + if (first) { + // We consider the first device returned by Xinerama as the primary one. + // Makes sense conceptually, but is there a way to verify this? + dev.IsPrimary = true; + first = false; + } + devices.Add(dev); + // It seems that all X screens are equal to 0 is Xinerama is enabled, at least on Nvidia (verify?) + dev.Metadata = 0; /*screen.ScreenNumber*/ + } + } + return true; + } + + static bool QueryXRandR(List devices) { + // Get available resolutions. Then, for each resolution get all available rates. + foreach (DisplayDevice dev in devices) { + int screen = (int)dev.Metadata; + List available_res = new List(); + int[] depths = API.XListDepths(API.DefaultDisplay, screen); + + int resolution_count = 0; + foreach (XRRScreenSize size in FindAvailableResolutions(screen)) { + if (size.Width == 0 || size.Height == 0) { + Debug.Print("[Warning] XRandR returned an invalid resolution ({0}) for display device {1}", size, screen); + continue; + } + short[] rates = API.XRRRates(API.DefaultDisplay, screen, resolution_count); + + // It seems that XRRRates returns 0 for modes that are larger than the screen + // can support, as well as for all supported modes. On Ubuntu 7.10 the tool + // "Screens and Graphics" does report these modes, though. + foreach (short rate in rates) { + // Note: some X servers (like Xming on Windows) do not report any rates other than 0. + // If we only have 1 rate, add it even if it is 0. + if (rate != 0 || rates.Length == 1) + foreach (int depth in depths) + available_res.Add(new DisplayResolution(0, 0, size.Width, size.Height, depth, rate)); + } + ++resolution_count; + } + + IntPtr screenConfig = API.XRRGetScreenInfo(API.DefaultDisplay, API.XRootWindow(API.DefaultDisplay, screen)); + ushort curRotation; + int curResolutionIndex = API.XRRConfigCurrentConfiguration(screenConfig, out curRotation); + float curRefreshRate = API.XRRConfigCurrentRate(screenConfig); + int curDepth = API.XDefaultDepth(API.DefaultDisplay, screen); + API.XRRFreeScreenConfigInfo(screenConfig); + + if (dev.Bounds == Rectangle.Empty) + dev.Bounds = new Rectangle(0, 0, available_res[curResolutionIndex].Width, available_res[curResolutionIndex].Height); + dev.BitsPerPixel = curDepth; + dev.RefreshRate = curRefreshRate; + dev.AvailableResolutions = available_res; + } + return true; + } + + static bool QueryXF86(List devices) { + return false; + } + + static XRRScreenSize[] FindAvailableResolutions(int screen) { + XRRScreenSize[] resolutions = API.XRRSizes(API.DefaultDisplay, screen); + if (resolutions == null) + throw new NotSupportedException("XRandR extensions not available."); + return resolutions; + } + + static class NativeMethods { + const string Xinerama = "libXinerama"; + + [DllImport(Xinerama)] + public static extern bool XineramaQueryExtension(IntPtr dpy, out int event_basep, out int error_basep); + + [DllImport(Xinerama)] + public static extern bool XineramaIsActive(IntPtr dpy); + + [DllImport(Xinerama)] + static extern IntPtr XineramaQueryScreens(IntPtr dpy, out int count); + + public unsafe static XineramaScreenInfo[] XineramaQueryScreens(IntPtr dpy) { + int count; + IntPtr screen_ptr = XineramaQueryScreens(dpy, out count); + XineramaScreenInfo* ptr = (XineramaScreenInfo*)screen_ptr; + + XineramaScreenInfo[] screens = new XineramaScreenInfo[count]; + for( int i = 0; i < screens.Length; i++ ) { + screens[i] = *ptr++; + } + return screens; + } + } + + [StructLayout(LayoutKind.Sequential, Pack = 1)] + struct XineramaScreenInfo { + public int ScreenNumber; + public short X; + public short Y; + public short Width; + public short Height; + } + } +} diff --git a/src/Client/Window.h b/src/Client/Window.h new file mode 100644 index 000000000..7bcafca3b --- /dev/null +++ b/src/Client/Window.h @@ -0,0 +1,122 @@ +#ifndef CS_WINDOW_H +#define CS_WINDOW_H +#include "Typedefs.h" +#include "String.h" +#include "Compiler.h" +#include "Bitmap.h" +/* Abstracts creating and managing a native window. + Copyright 2017 ClassicalSharp | Licensed under BSD-3 +*/ + +/* Gets the current contents of the clipboard. */ +void Window_GetClipboardText(STRING_TRANSIENT String* value); + +/* Sets the current contents of the clipboard. */ +void Window_SetClipboardText(STRING_TRANSIENT String* value); + +/* Sets the icon of this window. */ +void Window_SetIcon(Bitmap* bmp); + +/* Sets the title of the window. */ +void Window_SetTitle(STRING_TRANSIENT String* title); + +/* Gets whether this window has input focus. */ +bool Window_GetFocused(void); + +/* Gets whether whether this window is visible. */ +bool Window_GetVisible(void); + +/* Gets whether this window has been created and has not been destroyed. */ +bool Window_GetExists(void); + + /// Gets the for this window. + IWindowInfo WindowInfo{ get; } + + /// Gets or sets the for this window. + WindowState WindowState{ get; set; } + + /// Gets or sets a structure the contains the external bounds of this window, in screen coordinates. + /// External bounds include the title bar, borders and drawing area of the window. + Rectangle Bounds{ get; set; } + + /// Gets or sets a structure that contains the location of this window on the desktop. + Point Location{ get; set; } + + /// Gets or sets a structure that contains the external size of this window. + Size Size{ get; set; } + + /// Gets or sets a structure that contains the internal bounds of this window, in client coordinates. + /// The internal bounds include the drawing area of the window, but exclude the titlebar and window borders. + Rectangle ClientRectangle{ get; set; } + + /// Gets or sets a structure that contains the internal size this window. + Size ClientSize{ get; set; } + + /// Closes this window. + void Close(); + + /// Processes pending window events. + void ProcessEvents(); + + /// Transforms the specified point from screen to client coordinates. + /// A to transform. + /// The point transformed to client coordinates. + Point PointToClient(Point point); + + /// Transforms the specified point from client to screen coordinates. + /// A to transform. + /// The point transformed to screen coordinates. + Point PointToScreen(Point point); + + /// Gets the available KeyboardDevice. + KeyboardDevice Keyboard{ get; } + + /// Gets the available MouseDevice. + MouseDevice Mouse{ get; } + + /// Gets or sets the cursor position in screen coordinates. + Point DesktopCursorPos{ get; set; } + + /// Gets or sets whether the cursor is visible in the window. + bool CursorVisible{ get; set; } + + /// Occurs whenever the window is moved. + event EventHandler Move; + + /// Occurs whenever the window is resized. + event EventHandler Resize; + + /// Occurs when the window is about to close. + event EventHandler Closing; + + /// Occurs after the window has closed. + event EventHandler Closed; + + /// Occurs when the window is disposed. + event EventHandler Disposed; + + /// Occurs when the property of the window changes. + event EventHandler IconChanged; + + /// Occurs when the property of the window changes. + event EventHandler TitleChanged; + + /// Occurs when the property of the window changes. + event EventHandler VisibleChanged; + + /// Occurs when the property of the window changes. + event EventHandler FocusedChanged; + + /// Occurs when the property of the window changes. + event EventHandler WindowStateChanged; + + /// Occurs whenever a character is typed. + event EventHandler KeyPress; + + /// Occurs whenever the mouse cursor leaves the window . + event EventHandler MouseLeave; + + /// Occurs whenever the mouse cursor enters the window . + event EventHandler MouseEnter; + +#endif \ No newline at end of file