Make Cursor a toplevel struct

This commit is contained in:
Isaac Freund 2020-05-02 16:47:10 +02:00
parent a73343c92f
commit 97d395dbfc
No known key found for this signature in database
GPG key ID: 86DED400DDFD7A11
2 changed files with 334 additions and 335 deletions

View file

@ -1,4 +1,7 @@
const Self = @This();
const std = @import("std"); const std = @import("std");
const c = @import("c.zig"); const c = @import("c.zig");
const LayerSurface = @import("layer_surface.zig"); const LayerSurface = @import("layer_surface.zig");
@ -14,29 +17,26 @@ const CursorMode = enum {
Resize, Resize,
}; };
pub const Cursor = struct { seat: *Seat,
const Self = @This(); wlr_cursor: *c.wlr_cursor,
wlr_xcursor_manager: *c.wlr_xcursor_manager,
seat: *Seat, mode: CursorMode,
wlr_cursor: *c.wlr_cursor, grabbed_view: ?*View,
wlr_xcursor_manager: *c.wlr_xcursor_manager, grab_x: f64,
grab_y: f64,
grab_width: c_int,
grab_height: c_int,
resize_edges: u32,
mode: CursorMode, listen_axis: c.wl_listener,
grabbed_view: ?*View, listen_button: c.wl_listener,
grab_x: f64, listen_frame: c.wl_listener,
grab_y: f64, listen_motion_absolute: c.wl_listener,
grab_width: c_int, listen_motion: c.wl_listener,
grab_height: c_int, listen_request_set_cursor: c.wl_listener,
resize_edges: u32,
listen_axis: c.wl_listener, pub fn init(self: *Self, seat: *Seat) !void {
listen_button: c.wl_listener,
listen_frame: c.wl_listener,
listen_motion_absolute: c.wl_listener,
listen_motion: c.wl_listener,
listen_request_set_cursor: c.wl_listener,
pub fn init(self: *Self, seat: *Seat) !void {
self.seat = seat; self.seat = seat;
// Creates a wlroots utility for tracking the cursor image shown on screen. // Creates a wlroots utility for tracking the cursor image shown on screen.
@ -88,14 +88,14 @@ pub const Cursor = struct {
self.listen_request_set_cursor.notify = handleRequestSetCursor; self.listen_request_set_cursor.notify = handleRequestSetCursor;
c.wl_signal_add(&self.seat.wlr_seat.events.request_set_cursor, &self.listen_request_set_cursor); c.wl_signal_add(&self.seat.wlr_seat.events.request_set_cursor, &self.listen_request_set_cursor);
} }
pub fn deinit(self: *Self) void { pub fn deinit(self: *Self) void {
c.wlr_xcursor_manager_destroy(self.wlr_xcursor_manager); c.wlr_xcursor_manager_destroy(self.wlr_xcursor_manager);
c.wlr_cursor_destroy(self.wlr_cursor); c.wlr_cursor_destroy(self.wlr_cursor);
} }
fn handleAxis(listener: ?*c.wl_listener, data: ?*c_void) callconv(.C) void { fn handleAxis(listener: ?*c.wl_listener, data: ?*c_void) callconv(.C) void {
// This event is forwarded by the cursor when a pointer emits an axis event, // This event is forwarded by the cursor when a pointer emits an axis event,
// for example when you move the scroll wheel. // for example when you move the scroll wheel.
const cursor = @fieldParentPtr(Self, "listen_axis", listener.?); const cursor = @fieldParentPtr(Self, "listen_axis", listener.?);
@ -113,9 +113,9 @@ pub const Cursor = struct {
event.delta_discrete, event.delta_discrete,
event.source, event.source,
); );
} }
fn handleButton(listener: ?*c.wl_listener, data: ?*c_void) callconv(.C) void { fn handleButton(listener: ?*c.wl_listener, data: ?*c_void) callconv(.C) void {
// This event is forwarded by the cursor when a pointer emits a button // This event is forwarded by the cursor when a pointer emits a button
// event. // event.
const self = @fieldParentPtr(Self, "listen_button", listener.?); const self = @fieldParentPtr(Self, "listen_button", listener.?);
@ -157,9 +157,9 @@ pub const Cursor = struct {
event.state, event.state,
); );
} }
} }
fn handleFrame(listener: ?*c.wl_listener, data: ?*c_void) callconv(.C) void { fn handleFrame(listener: ?*c.wl_listener, data: ?*c_void) callconv(.C) void {
// This event is forwarded by the cursor when a pointer emits an frame // This event is forwarded by the cursor when a pointer emits an frame
// event. Frame events are sent after regular pointer events to group // event. Frame events are sent after regular pointer events to group
// multiple events together. For instance, two axis events may happen at the // multiple events together. For instance, two axis events may happen at the
@ -167,9 +167,9 @@ pub const Cursor = struct {
const self = @fieldParentPtr(Self, "listen_frame", listener.?); const self = @fieldParentPtr(Self, "listen_frame", listener.?);
// Notify the client with pointer focus of the frame event. // Notify the client with pointer focus of the frame event.
c.wlr_seat_pointer_notify_frame(self.seat.wlr_seat); c.wlr_seat_pointer_notify_frame(self.seat.wlr_seat);
} }
fn handleMotionAbsolute(listener: ?*c.wl_listener, data: ?*c_void) callconv(.C) void { fn handleMotionAbsolute(listener: ?*c.wl_listener, data: ?*c_void) callconv(.C) void {
// This event is forwarded by the cursor when a pointer emits an _absolute_ // This event is forwarded by the cursor when a pointer emits an _absolute_
// motion event, from 0..1 on each axis. This happens, for example, when // motion event, from 0..1 on each axis. This happens, for example, when
// wlroots is running under a Wayland window rather than KMS+DRM, and you // wlroots is running under a Wayland window rather than KMS+DRM, and you
@ -183,9 +183,9 @@ pub const Cursor = struct {
); );
c.wlr_cursor_warp_absolute(self.wlr_cursor, event.device, event.x, event.y); c.wlr_cursor_warp_absolute(self.wlr_cursor, event.device, event.x, event.y);
self.processMotion(event.time_msec); self.processMotion(event.time_msec);
} }
fn handleMotion(listener: ?*c.wl_listener, data: ?*c_void) callconv(.C) void { fn handleMotion(listener: ?*c.wl_listener, data: ?*c_void) callconv(.C) void {
// This event is forwarded by the cursor when a pointer emits a _relative_ // This event is forwarded by the cursor when a pointer emits a _relative_
// pointer motion event (i.e. a delta) // pointer motion event (i.e. a delta)
const self = @fieldParentPtr(Self, "listen_motion", listener.?); const self = @fieldParentPtr(Self, "listen_motion", listener.?);
@ -200,9 +200,9 @@ pub const Cursor = struct {
// the cursor around without any input. // the cursor around without any input.
c.wlr_cursor_move(self.wlr_cursor, event.device, event.delta_x, event.delta_y); c.wlr_cursor_move(self.wlr_cursor, event.device, event.delta_x, event.delta_y);
self.processMotion(event.time_msec); self.processMotion(event.time_msec);
} }
fn handleRequestSetCursor(listener: ?*c.wl_listener, data: ?*c_void) callconv(.C) void { fn handleRequestSetCursor(listener: ?*c.wl_listener, data: ?*c_void) callconv(.C) void {
// This event is rasied by the seat when a client provides a cursor image // This event is rasied by the seat when a client provides a cursor image
const self = @fieldParentPtr(Self, "listen_request_set_cursor", listener.?); const self = @fieldParentPtr(Self, "listen_request_set_cursor", listener.?);
const event = @ptrCast( const event = @ptrCast(
@ -225,9 +225,9 @@ pub const Cursor = struct {
event.hotspot_y, event.hotspot_y,
); );
} }
} }
fn processMotion(self: Self, time: u32) void { fn processMotion(self: Self, time: u32) void {
var sx: f64 = undefined; var sx: f64 = undefined;
var sy: f64 = undefined; var sy: f64 = undefined;
if (self.surfaceAt(self.wlr_cursor.x, self.wlr_cursor.y, &sx, &sy)) |wlr_surface| { if (self.surfaceAt(self.wlr_cursor.x, self.wlr_cursor.y, &sx, &sy)) |wlr_surface| {
@ -262,12 +262,12 @@ pub const Cursor = struct {
// Clear pointer focus so future button events and such are not sent to // Clear pointer focus so future button events and such are not sent to
// the last client to have the cursor over it. // the last client to have the cursor over it.
c.wlr_seat_pointer_clear_focus(self.seat.wlr_seat); c.wlr_seat_pointer_clear_focus(self.seat.wlr_seat);
} }
/// Find the topmost surface under the output layout coordinates lx/ly /// Find the topmost surface under the output layout coordinates lx/ly
/// returns the surface if found and sets the sx/sy parametes to the /// returns the surface if found and sets the sx/sy parametes to the
/// surface coordinates. /// surface coordinates.
fn surfaceAt(self: Self, lx: f64, ly: f64, sx: *f64, sy: *f64) ?*c.wlr_surface { fn surfaceAt(self: Self, lx: f64, ly: f64, sx: *f64, sy: *f64) ?*c.wlr_surface {
// Find the output to check // Find the output to check
const root = self.seat.input_manager.server.root; const root = self.seat.input_manager.server.root;
const wlr_output = c.wlr_output_layout_output_at(root.wlr_output_layout, lx, ly) orelse const wlr_output = c.wlr_output_layout_output_at(root.wlr_output_layout, lx, ly) orelse
@ -323,11 +323,11 @@ pub const Cursor = struct {
} }
return null; return null;
} }
/// Find the topmost surface on the given layer at ox,oy. Will only check /// Find the topmost surface on the given layer at ox,oy. Will only check
/// popups if popups_only is true. /// popups if popups_only is true.
fn layerSurfaceAt( fn layerSurfaceAt(
output: Output, output: Output,
layer: std.TailQueue(LayerSurface), layer: std.TailQueue(LayerSurface),
ox: f64, ox: f64,
@ -335,7 +335,7 @@ pub const Cursor = struct {
sx: *f64, sx: *f64,
sy: *f64, sy: *f64,
popups_only: bool, popups_only: bool,
) ?*c.wlr_surface { ) ?*c.wlr_surface {
var it = layer.first; var it = layer.first;
while (it) |node| : (it = node.next) { while (it) |node| : (it = node.next) {
const layer_surface = &node.data; const layer_surface = &node.data;
@ -358,11 +358,11 @@ pub const Cursor = struct {
} }
} }
return null; return null;
} }
/// Find the topmost visible view surface (incl. popups) at ox,oy. Will /// Find the topmost visible view surface (incl. popups) at ox,oy. Will
/// check only floating views if floating is true. /// check only floating views if floating is true.
fn viewSurfaceAt(output: Output, ox: f64, oy: f64, sx: *f64, sy: *f64, floating: bool) ?*c.wlr_surface { fn viewSurfaceAt(output: Output, ox: f64, oy: f64, sx: *f64, sy: *f64, floating: bool) ?*c.wlr_surface {
var it = ViewStack(View).iterator(output.views.first, output.current_focused_tags); var it = ViewStack(View).iterator(output.views.first, output.current_focused_tags);
while (it.next()) |node| { while (it.next()) |node| {
const view = &node.view; const view = &node.view;
@ -383,5 +383,4 @@ pub const Cursor = struct {
} }
} }
return null; return null;
} }
};

View file

@ -3,7 +3,7 @@ const Self = @This();
const c = @import("c.zig"); const c = @import("c.zig");
const std = @import("std"); const std = @import("std");
const Cursor = @import("cursor.zig").Cursor; const Cursor = @import("cursor.zig");
const InputManager = @import("input_manager.zig"); const InputManager = @import("input_manager.zig");
const Keyboard = @import("keyboard.zig").Keyboard; const Keyboard = @import("keyboard.zig").Keyboard;
const LayerSurface = @import("layer_surface.zig"); const LayerSurface = @import("layer_surface.zig");