2015-09-26 02:04:55 +10:00
|
|
|
#![cfg(target_os = "windows")]
|
|
|
|
|
2017-10-26 02:12:39 +11:00
|
|
|
use std::os::raw::c_void;
|
2018-05-08 07:36:21 +10:00
|
|
|
|
2015-09-26 02:04:55 +10:00
|
|
|
use libc;
|
2017-12-25 00:46:47 +11:00
|
|
|
use winapi::shared::windef::HWND;
|
2015-09-26 02:04:55 +10:00
|
|
|
|
2019-02-06 02:30:33 +11:00
|
|
|
use event::DeviceId;
|
|
|
|
use monitor::MonitorHandle;
|
|
|
|
use event_loop::EventLoop;
|
|
|
|
use window::{Icon, Window, WindowBuilder};
|
|
|
|
use platform_impl::EventLoop as WindowsEventLoop;
|
|
|
|
|
|
|
|
/// Additional methods on `EventLoop` that are specific to Windows.
|
|
|
|
pub trait EventLoopExtWindows {
|
2018-06-15 09:42:18 +10:00
|
|
|
/// By default, winit on Windows will attempt to enable process-wide DPI awareness. If that's
|
2019-02-06 02:30:33 +11:00
|
|
|
/// undesirable, you can create an `EventLoop` using this function instead.
|
2018-06-15 09:42:18 +10:00
|
|
|
fn new_dpi_unaware() -> Self where Self: Sized;
|
|
|
|
}
|
|
|
|
|
2019-02-06 02:30:33 +11:00
|
|
|
impl<T> EventLoopExtWindows for EventLoop<T> {
|
2018-06-15 09:42:18 +10:00
|
|
|
#[inline]
|
|
|
|
fn new_dpi_unaware() -> Self {
|
2019-02-06 02:30:33 +11:00
|
|
|
EventLoop {
|
|
|
|
event_loop: WindowsEventLoop::with_dpi_awareness(false),
|
2018-06-15 09:42:18 +10:00
|
|
|
_marker: ::std::marker::PhantomData,
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2018-05-08 07:36:21 +10:00
|
|
|
|
2016-01-08 02:01:18 +11:00
|
|
|
/// Additional methods on `Window` that are specific to Windows.
|
2019-02-06 02:30:33 +11:00
|
|
|
pub trait WindowExtWindows {
|
2017-09-13 17:19:54 +10:00
|
|
|
/// Returns the native handle that is used by this window.
|
2015-09-26 02:04:55 +10:00
|
|
|
///
|
2017-09-13 17:19:54 +10:00
|
|
|
/// The pointer will become invalid when the native window was destroyed.
|
2015-09-26 02:04:55 +10:00
|
|
|
fn get_hwnd(&self) -> *mut libc::c_void;
|
2018-05-08 07:36:21 +10:00
|
|
|
|
|
|
|
/// This sets `ICON_BIG`. A good ceiling here is 256x256.
|
|
|
|
fn set_taskbar_icon(&self, taskbar_icon: Option<Icon>);
|
2015-09-26 02:04:55 +10:00
|
|
|
}
|
|
|
|
|
2019-02-06 02:30:33 +11:00
|
|
|
impl WindowExtWindows for Window {
|
2015-09-26 02:04:55 +10:00
|
|
|
#[inline]
|
|
|
|
fn get_hwnd(&self) -> *mut libc::c_void {
|
2017-06-27 05:21:13 +10:00
|
|
|
self.window.hwnd() as *mut _
|
2015-09-26 02:04:55 +10:00
|
|
|
}
|
2018-05-08 07:36:21 +10:00
|
|
|
|
|
|
|
#[inline]
|
|
|
|
fn set_taskbar_icon(&self, taskbar_icon: Option<Icon>) {
|
|
|
|
self.window.set_taskbar_icon(taskbar_icon)
|
|
|
|
}
|
2015-09-26 02:04:55 +10:00
|
|
|
}
|
2016-01-08 02:01:18 +11:00
|
|
|
|
|
|
|
/// Additional methods on `WindowBuilder` that are specific to Windows.
|
2019-02-06 02:30:33 +11:00
|
|
|
pub trait WindowBuilderExtWindows {
|
2018-05-08 07:36:21 +10:00
|
|
|
/// Sets a parent to the window to be created.
|
2017-12-25 00:46:47 +11:00
|
|
|
fn with_parent_window(self, parent: HWND) -> WindowBuilder;
|
2018-05-08 07:36:21 +10:00
|
|
|
|
|
|
|
/// This sets `ICON_BIG`. A good ceiling here is 256x256.
|
|
|
|
fn with_taskbar_icon(self, taskbar_icon: Option<Icon>) -> WindowBuilder;
|
2018-06-22 11:33:29 +10:00
|
|
|
|
|
|
|
/// This sets `WS_EX_NOREDIRECTIONBITMAP`.
|
|
|
|
fn with_no_redirection_bitmap(self, flag: bool) -> WindowBuilder;
|
2016-01-08 02:01:18 +11:00
|
|
|
}
|
|
|
|
|
2019-02-06 02:30:33 +11:00
|
|
|
impl WindowBuilderExtWindows for WindowBuilder {
|
2016-11-26 03:05:39 +11:00
|
|
|
#[inline]
|
2017-12-25 00:46:47 +11:00
|
|
|
fn with_parent_window(mut self, parent: HWND) -> WindowBuilder {
|
2016-11-26 03:05:39 +11:00
|
|
|
self.platform_specific.parent = Some(parent);
|
|
|
|
self
|
2018-05-08 07:36:21 +10:00
|
|
|
}
|
|
|
|
|
|
|
|
#[inline]
|
|
|
|
fn with_taskbar_icon(mut self, taskbar_icon: Option<Icon>) -> WindowBuilder {
|
|
|
|
self.platform_specific.taskbar_icon = taskbar_icon;
|
|
|
|
self
|
2018-06-22 11:33:29 +10:00
|
|
|
}
|
|
|
|
|
|
|
|
#[inline]
|
|
|
|
fn with_no_redirection_bitmap(mut self, flag: bool) -> WindowBuilder {
|
|
|
|
self.platform_specific.no_redirection_bitmap = flag;
|
|
|
|
self
|
2016-11-26 03:05:39 +11:00
|
|
|
}
|
2016-01-08 02:01:18 +11:00
|
|
|
}
|
2017-08-30 16:49:18 +10:00
|
|
|
|
2019-02-06 02:30:33 +11:00
|
|
|
/// Additional methods on `MonitorHandle` that are specific to Windows.
|
|
|
|
pub trait MonitorHandleExtWindows {
|
2017-10-26 02:12:39 +11:00
|
|
|
/// Returns the name of the monitor adapter specific to the Win32 API.
|
2017-08-30 16:49:18 +10:00
|
|
|
fn native_id(&self) -> String;
|
2017-10-26 02:12:39 +11:00
|
|
|
|
|
|
|
/// Returns the handle of the monitor - `HMONITOR`.
|
|
|
|
fn hmonitor(&self) -> *mut c_void;
|
2017-08-30 16:49:18 +10:00
|
|
|
}
|
|
|
|
|
2019-02-06 02:30:33 +11:00
|
|
|
impl MonitorHandleExtWindows for MonitorHandle {
|
2017-08-30 16:49:18 +10:00
|
|
|
#[inline]
|
|
|
|
fn native_id(&self) -> String {
|
|
|
|
self.inner.get_native_identifier()
|
|
|
|
}
|
2017-10-26 02:12:39 +11:00
|
|
|
|
|
|
|
#[inline]
|
|
|
|
fn hmonitor(&self) -> *mut c_void {
|
|
|
|
self.inner.get_hmonitor() as *mut _
|
|
|
|
}
|
2017-08-30 16:49:18 +10:00
|
|
|
}
|
Windows: Implement DeviceEvents (#482)
Fixes #467
All variants other than Text have been implemented. While Text can
be implemented using ToUnicode, that doesn't play nice with dead
keys, IME, etc.
Most of the mouse DeviceEvents were already implemented, but due
to the flags that were used when registering for raw input events,
they only worked when the window was in the foreground.
This is also a step forward for #338, as DeviceIds are no longer
useless on Windows. On DeviceEvents, the DeviceId contains that
device's handle. While that handle could ostensibly be used by
developers to query device information, my actual reason for
choosing it is because it's simply a very easy way to handle this.
As a fun bonus, this enabled me to create this method:
DevideIdExt::get_persistent_identifier() -> Option<String>
Using this gives you a unique identifier for the device that
persists across replugs/reboots/etc., so it's ideal for something
like device-specific configuration.
There's a notable caveat to the new DeviceIds, which is that the
value will always be 0 for a WindowEvent. There doesn't seem to be
any straightforward way around this limitation.
I was concerned that multi-window applications would receive n
copies of every DeviceEvent, but Windows only sends them to one
window per application.
Lastly, there's a chance that these additions will cause
antivirus/etc. software to detect winit applications as keyloggers.
I don't know how likely that is to actually happen to people, but
if it does become an issue, the raw input code is neatly
sequestered and would be easy to make optional during compilation.
2018-04-29 02:42:33 +10:00
|
|
|
|
|
|
|
/// Additional methods on `DeviceId` that are specific to Windows.
|
2019-02-06 02:30:33 +11:00
|
|
|
pub trait DeviceIdExtWindows {
|
Windows: Implement DeviceEvents (#482)
Fixes #467
All variants other than Text have been implemented. While Text can
be implemented using ToUnicode, that doesn't play nice with dead
keys, IME, etc.
Most of the mouse DeviceEvents were already implemented, but due
to the flags that were used when registering for raw input events,
they only worked when the window was in the foreground.
This is also a step forward for #338, as DeviceIds are no longer
useless on Windows. On DeviceEvents, the DeviceId contains that
device's handle. While that handle could ostensibly be used by
developers to query device information, my actual reason for
choosing it is because it's simply a very easy way to handle this.
As a fun bonus, this enabled me to create this method:
DevideIdExt::get_persistent_identifier() -> Option<String>
Using this gives you a unique identifier for the device that
persists across replugs/reboots/etc., so it's ideal for something
like device-specific configuration.
There's a notable caveat to the new DeviceIds, which is that the
value will always be 0 for a WindowEvent. There doesn't seem to be
any straightforward way around this limitation.
I was concerned that multi-window applications would receive n
copies of every DeviceEvent, but Windows only sends them to one
window per application.
Lastly, there's a chance that these additions will cause
antivirus/etc. software to detect winit applications as keyloggers.
I don't know how likely that is to actually happen to people, but
if it does become an issue, the raw input code is neatly
sequestered and would be easy to make optional during compilation.
2018-04-29 02:42:33 +10:00
|
|
|
/// Returns an identifier that persistently refers to this specific device.
|
|
|
|
///
|
|
|
|
/// Will return `None` if the device is no longer available.
|
|
|
|
fn get_persistent_identifier(&self) -> Option<String>;
|
|
|
|
}
|
|
|
|
|
2019-02-06 02:30:33 +11:00
|
|
|
impl DeviceIdExtWindows for DeviceId {
|
Windows: Implement DeviceEvents (#482)
Fixes #467
All variants other than Text have been implemented. While Text can
be implemented using ToUnicode, that doesn't play nice with dead
keys, IME, etc.
Most of the mouse DeviceEvents were already implemented, but due
to the flags that were used when registering for raw input events,
they only worked when the window was in the foreground.
This is also a step forward for #338, as DeviceIds are no longer
useless on Windows. On DeviceEvents, the DeviceId contains that
device's handle. While that handle could ostensibly be used by
developers to query device information, my actual reason for
choosing it is because it's simply a very easy way to handle this.
As a fun bonus, this enabled me to create this method:
DevideIdExt::get_persistent_identifier() -> Option<String>
Using this gives you a unique identifier for the device that
persists across replugs/reboots/etc., so it's ideal for something
like device-specific configuration.
There's a notable caveat to the new DeviceIds, which is that the
value will always be 0 for a WindowEvent. There doesn't seem to be
any straightforward way around this limitation.
I was concerned that multi-window applications would receive n
copies of every DeviceEvent, but Windows only sends them to one
window per application.
Lastly, there's a chance that these additions will cause
antivirus/etc. software to detect winit applications as keyloggers.
I don't know how likely that is to actually happen to people, but
if it does become an issue, the raw input code is neatly
sequestered and would be easy to make optional during compilation.
2018-04-29 02:42:33 +10:00
|
|
|
#[inline]
|
|
|
|
fn get_persistent_identifier(&self) -> Option<String> {
|
|
|
|
self.0.get_persistent_identifier()
|
|
|
|
}
|
|
|
|
}
|