linux/x11: implement window focus (#8002)

Release Notes:
- N/A
This commit is contained in:
Dzmitry Malyshau 2024-02-19 17:54:54 -08:00 committed by GitHub
parent fddb778e5f
commit b00b65b330
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
2 changed files with 47 additions and 14 deletions

View file

@ -2,9 +2,9 @@
#![allow(unused)]
use crate::{
platform::blade::BladeRenderer, size, Bounds, GlobalPixels, Pixels, PlatformDisplay,
PlatformInput, PlatformInputHandler, PlatformWindow, Point, Size, WindowAppearance,
WindowBounds, WindowOptions, X11Display,
platform::blade::BladeRenderer, size, Bounds, GlobalPixels, Modifiers, Pixels, PlatformAtlas,
PlatformDisplay, PlatformInput, PlatformInputHandler, PlatformWindow, Point, PromptLevel,
Scene, Size, WindowAppearance, WindowBounds, WindowOptions, X11Display,
};
use blade_graphics as gpu;
use parking_lot::Mutex;
@ -27,7 +27,7 @@ use std::{
#[derive(Default)]
struct Callbacks {
request_frame: Option<Box<dyn FnMut()>>,
input: Option<Box<dyn FnMut(crate::PlatformInput) -> bool>>,
input: Option<Box<dyn FnMut(PlatformInput) -> bool>>,
active_status_change: Option<Box<dyn FnMut(bool)>>,
resize: Option<Box<dyn FnMut(Size<Pixels>, f32)>>,
fullscreen: Option<Box<dyn FnMut(bool)>>,
@ -155,6 +155,9 @@ impl X11WindowState {
x::Cw::EventMask(
x::EventMask::EXPOSURE
| x::EventMask::STRUCTURE_NOTIFY
| x::EventMask::ENTER_WINDOW
| x::EventMask::LEAVE_WINDOW
| x::EventMask::FOCUS_CHANGE
| x::EventMask::KEY_PRESS
| x::EventMask::KEY_RELEASE
| x::EventMask::BUTTON_PRESS
@ -345,6 +348,12 @@ impl X11WindowState {
}
}
}
pub fn set_focused(&self, focus: bool) {
if let Some(ref mut fun) = self.callbacks.lock().active_status_change {
fun(focus);
}
}
}
impl PlatformWindow for X11Window {
@ -374,14 +383,20 @@ impl PlatformWindow for X11Window {
Rc::clone(&self.0.display)
}
//todo!(linux)
fn mouse_position(&self) -> Point<Pixels> {
Point::default()
let cookie = self.0.xcb_connection.send_request(&x::QueryPointer {
window: self.0.x_window,
});
let reply: x::QueryPointerReply = self.0.xcb_connection.wait_for_reply(cookie).unwrap();
Point::new(
(reply.root_x() as u32).into(),
(reply.root_y() as u32).into(),
)
}
//todo!(linux)
fn modifiers(&self) -> crate::Modifiers {
crate::Modifiers::default()
fn modifiers(&self) -> Modifiers {
Modifiers::default()
}
fn as_any_mut(&mut self) -> &mut dyn std::any::Any {
@ -399,7 +414,7 @@ impl PlatformWindow for X11Window {
//todo!(linux)
fn prompt(
&self,
_level: crate::PromptLevel,
_level: PromptLevel,
_msg: &str,
_detail: Option<&str>,
_answers: &[&str],
@ -456,7 +471,7 @@ impl PlatformWindow for X11Window {
self.0.callbacks.lock().request_frame = Some(callback);
}
fn on_input(&self, callback: Box<dyn FnMut(crate::PlatformInput) -> bool>) {
fn on_input(&self, callback: Box<dyn FnMut(PlatformInput) -> bool>) {
self.0.callbacks.lock().input = Some(callback);
}
@ -489,16 +504,16 @@ impl PlatformWindow for X11Window {
}
//todo!(linux)
fn is_topmost_for_position(&self, _position: crate::Point<Pixels>) -> bool {
fn is_topmost_for_position(&self, _position: Point<Pixels>) -> bool {
unimplemented!()
}
fn draw(&self, scene: &crate::Scene) {
fn draw(&self, scene: &Scene) {
let mut inner = self.0.inner.lock();
inner.renderer.draw(scene);
}
fn sprite_atlas(&self) -> sync::Arc<dyn crate::PlatformAtlas> {
fn sprite_atlas(&self) -> sync::Arc<dyn PlatformAtlas> {
let inner = self.0.inner.lock();
inner.renderer.sprite_atlas().clone()
}