Skip to content

Commit 8c00cc0

Browse files
committed
Cursor events and modifier keys
1 parent bcec836 commit 8c00cc0

4 files changed

Lines changed: 109 additions & 2 deletions

File tree

Cargo.lock

Lines changed: 1 addition & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

crates/display-proto/src/lib.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -261,6 +261,10 @@ impl InputEvent {
261261
pub const KIND_SCROLL: u32 = 3;
262262
// data1 = x delta (pixels)
263263
// data2 = y delta (pixels)
264+
265+
pub const MODE_MOUSE_MOVE: u32 = 1;
266+
pub const MODE_MOUSE_DOWN: u32 = 2;
267+
pub const MODE_MOUSE_UP: u32 = 3;
264268
}
265269

266270
unsafe impl bytemuck::Zeroable for InputEvent {}

crates/display-server/Cargo.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ bytemuck = { version = "1.19.0", default-features = false }
88
linked_list_allocator = "0.10"
99
glam = { version = "0.30", default-features = false, features = ["nostd-libm"] }
1010
thunderdome = { version = "0.6", default-features = false }
11+
bitflags = "2.8.0"
1112

1213
display-proto = { path = "../display-proto" }
1314
ulib = { path = "../ulib", features = ["heap-impl"] }

crates/display-server/src/main.rs

Lines changed: 103 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -299,6 +299,40 @@ fn load_image(img: &[u8]) -> (usize, usize, Vec<u32>) {
299299
(width, height, buf)
300300
}
301301

302+
bitflags::bitflags! {
303+
#[derive(Debug, Copy, Clone)]
304+
pub struct Modifiers: u8 {
305+
const L_SHIFT = 1 << 0;
306+
const L_CTRL = 1 << 1;
307+
const L_ALT = 1 << 2;
308+
const L_SUPER = 1 << 3;
309+
const R_SHIFT = 1 << 4;
310+
const R_CTRL = 1 << 5;
311+
const R_ALT = 1 << 6;
312+
const R_SUPER = 1 << 7;
313+
314+
const SHIFT = Self::L_SHIFT.bits() | Self::R_SHIFT.bits();
315+
const CTRL = Self::L_CTRL.bits() | Self::R_CTRL.bits();
316+
const ALT = Self::L_ALT.bits() | Self::R_ALT.bits();
317+
const SUPER = Self::L_SUPER.bits() | Self::R_SUPER.bits();
318+
}
319+
}
320+
321+
impl Modifiers {
322+
pub fn shift_pressed(self) -> bool {
323+
self.intersects(Self::SHIFT)
324+
}
325+
pub fn ctrl_pressed(self) -> bool {
326+
self.intersects(Self::CTRL)
327+
}
328+
pub fn alt_pressed(self) -> bool {
329+
self.intersects(Self::ALT)
330+
}
331+
pub fn super_pressed(self) -> bool {
332+
self.intersects(Self::SUPER)
333+
}
334+
}
335+
302336
fn handle_conns(mut fb: framebuffer::Framebuffer, server_socket: FileDesc) {
303337
let mut clients = Arena::new();
304338

@@ -341,6 +375,8 @@ fn handle_conns(mut fb: framebuffer::Framebuffer, server_socket: FileDesc) {
341375

342376
let mut any_updated = true;
343377

378+
let mut modifiers = Modifiers::empty();
379+
344380
loop {
345381
let mut buf = [0u64; 32];
346382
while let Ok((len, msg)) = recv_nonblock(server_socket, bytemuck::bytes_of_mut(&mut buf)) {
@@ -358,6 +394,8 @@ fn handle_conns(mut fb: framebuffer::Framebuffer, server_socket: FileDesc) {
358394

359395
// TODO: better scheduling for this
360396
loop {
397+
use proto::ScanCode;
398+
361399
let key = unsafe { ulib::sys::sys_poll_key_event() };
362400
if key < 0 {
363401
break;
@@ -372,6 +410,14 @@ fn handle_conns(mut fb: framebuffer::Framebuffer, server_socket: FileDesc) {
372410
window_manager.alt_tab();
373411
continue;
374412
}
413+
(ScanCode::LEFT_SHIFT, p) => modifiers.set(Modifiers::L_SHIFT, p),
414+
(ScanCode::RIGHT_SHIFT, p) => modifiers.set(Modifiers::R_SHIFT, p),
415+
(ScanCode::LEFT_CTRL, p) => modifiers.set(Modifiers::L_CTRL, p),
416+
(ScanCode::RIGHT_CTRL, p) => modifiers.set(Modifiers::R_CTRL, p),
417+
(ScanCode::LEFT_ALT, p) => modifiers.set(Modifiers::L_ALT, p),
418+
(ScanCode::RIGHT_ALT, p) => modifiers.set(Modifiers::R_ALT, p),
419+
(ScanCode::LEFT_SUPER, p) => modifiers.set(Modifiers::L_SUPER, p),
420+
(ScanCode::RIGHT_SUPER, p) => modifiers.set(Modifiers::R_SUPER, p),
375421
_ => (),
376422
}
377423

@@ -425,6 +471,24 @@ fn handle_conns(mut fb: framebuffer::Framebuffer, server_socket: FileDesc) {
425471
window_manager.dragging = None;
426472
window_manager.mouse_down = false;
427473
}
474+
475+
match hovered {
476+
HoveredState::Window(idx, local_pos) => {
477+
let window = &window_manager.windows[idx];
478+
let client = clients.get_mut(window.client).unwrap();
479+
let event = proto::InputEvent {
480+
kind: proto::InputEvent::KIND_MOUSE,
481+
data1: if pressed { 2 } else { 3 },
482+
data2: local_pos.x as u32,
483+
data3: local_pos.y as u32,
484+
data4: button as u32,
485+
};
486+
let queue = client.handle.server_to_client_queue();
487+
queue.try_send_data(event).ok();
488+
}
489+
HoveredState::None => (),
490+
_ => (),
491+
}
428492
}
429493
_ => (),
430494
}
@@ -442,8 +506,45 @@ fn handle_conns(mut fb: framebuffer::Framebuffer, server_socket: FileDesc) {
442506
.as_u16vec2();
443507
window_manager.mouse_move(cursor);
444508
cursor_moved = true;
509+
510+
// TODO: dragging off window, still send mouse up to original window
511+
let hovered = window_manager.hovered(cursor);
512+
match hovered {
513+
HoveredState::Window(idx, local_pos) => {
514+
let window = &window_manager.windows[idx];
515+
let client = clients.get_mut(window.client).unwrap();
516+
let event = proto::InputEvent {
517+
kind: proto::InputEvent::KIND_MOUSE,
518+
data1: 1,
519+
data2: local_pos.x as u32,
520+
data3: local_pos.y as u32,
521+
data4: 0,
522+
};
523+
let queue = client.handle.server_to_client_queue();
524+
queue.try_send_data(event).ok();
525+
}
526+
_ => (),
527+
}
445528
} else if ev.code == ulib::sys::REL_WHEEL {
446-
println!("Mouse wheel: {}", ev.value as i32);
529+
// println!("Mouse wheel: {}", ev.value as i32);
530+
531+
let hovered = window_manager.hovered(cursor);
532+
match hovered {
533+
HoveredState::Window(idx, _local_pos) => {
534+
let window = &window_manager.windows[idx];
535+
let client = clients.get_mut(window.client).unwrap();
536+
let event = proto::InputEvent {
537+
kind: proto::InputEvent::KIND_SCROLL,
538+
data1: ev.value as u32,
539+
data2: 0,
540+
data3: 0,
541+
data4: 0,
542+
};
543+
let queue = client.handle.server_to_client_queue();
544+
queue.try_send_data(event).ok();
545+
}
546+
_ => (),
547+
}
447548
}
448549
}
449550
}
@@ -713,7 +814,7 @@ fn remap_keycode(code: isize) -> proto::ScanCode {
713814
0xE0 => ScanCode::LEFT_CTRL,
714815
0xE1 => ScanCode::LEFT_SHIFT,
715816
0xE2 => ScanCode::LEFT_ALT,
716-
0xE3 => ScanCode::LEFT_SHIFT,
817+
0xE3 => ScanCode::LEFT_SUPER,
717818
0xE4 => ScanCode::RIGHT_CTRL,
718819
0xE5 => ScanCode::RIGHT_SHIFT,
719820
0xE6 => ScanCode::RIGHT_ALT,

0 commit comments

Comments
 (0)