idle-inhibit: implement protocol

This commit is contained in:
dfangx 2022-05-11 08:14:01 -04:00 committed by GitHub
parent 90b37645cf
commit d5c915e3cb
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
5 changed files with 111 additions and 0 deletions

34
river/IdleInhibitor.zig Normal file
View File

@ -0,0 +1,34 @@
const Self = @This();
const std = @import("std");
const wlr = @import("wlroots");
const wl = @import("wayland").server.wl;
const server = &@import("main.zig").server;
const util = @import("util.zig");
const IdleInhibitorManager = @import("IdleInhibitorManager.zig");
inhibitor_manager: *IdleInhibitorManager,
inhibitor: *wlr.IdleInhibitorV1,
destroy: wl.Listener(*wlr.IdleInhibitorV1) = wl.Listener(*wlr.IdleInhibitorV1).init(handleDestroy),
pub fn init(self: *Self, inhibitor: *wlr.IdleInhibitorV1, inhibitor_manager: *IdleInhibitorManager) !void {
self.inhibitor_manager = inhibitor_manager;
self.inhibitor = inhibitor;
self.destroy.setNotify(handleDestroy);
inhibitor.events.destroy.add(&self.destroy);
inhibitor_manager.idleInhibitCheckActive();
}
fn handleDestroy(listener: *wl.Listener(*wlr.IdleInhibitorV1), _: *wlr.IdleInhibitorV1) void {
const self = @fieldParentPtr(Self, "destroy", listener);
self.destroy.link.remove();
const node = @fieldParentPtr(std.TailQueue(Self).Node, "data", self);
server.idle_inhibitor_manager.inhibitors.remove(node);
util.gpa.destroy(node);
self.inhibitor_manager.idleInhibitCheckActive();
}

View File

@ -0,0 +1,65 @@
const Self = @This();
const std = @import("std");
const wlr = @import("wlroots");
const wl = @import("wayland").server.wl;
const server = &@import("main.zig").server;
const util = @import("util.zig");
const View = @import("View.zig");
const IdleInhibitor = @import("IdleInhibitor.zig");
idle_inhibit_manager: *wlr.IdleInhibitManagerV1,
new_idle_inhibitor: wl.Listener(*wlr.IdleInhibitorV1),
inhibitors: std.TailQueue(IdleInhibitor) = .{},
idle: *wlr.Idle,
pub fn init(self: *Self, idle: *wlr.Idle) !void {
self.idle_inhibit_manager = try wlr.IdleInhibitManagerV1.create(server.wl_server);
self.idle = idle;
self.new_idle_inhibitor.setNotify(handleNewIdleInhibitor);
self.idle_inhibit_manager.events.new_inhibitor.add(&self.new_idle_inhibitor);
}
pub fn deinit(self: *Self) void {
while (self.inhibitors.pop()) |inhibitor| {
inhibitor.data.destroy.link.remove();
util.gpa.destroy(inhibitor);
}
self.new_idle_inhibitor.link.remove();
}
pub fn idleInhibitCheckActive(self: *Self) void {
var inhibited = false;
var it = self.inhibitors.first;
while (it) |node| : (it = node.next) {
if (View.fromWlrSurface(node.data.inhibitor.surface)) |v| {
// If view is visible,
if (v.current.tags & v.output.current.tags != 0) {
inhibited = true;
break;
}
} else {
// If for whatever reason the inhibitor does not have a view, then
// assume it is visible.
inhibited = true;
break;
}
}
self.idle.setEnabled(null, !inhibited);
}
fn handleNewIdleInhibitor(listener: *wl.Listener(*wlr.IdleInhibitorV1), inhibitor: *wlr.IdleInhibitorV1) void {
const self = @fieldParentPtr(Self, "new_idle_inhibitor", listener);
const inhibitor_node = util.gpa.create(std.TailQueue(IdleInhibitor).Node) catch return;
inhibitor_node.data.init(inhibitor, self) catch {
util.gpa.destroy(inhibitor_node);
return;
};
self.inhibitors.append(inhibitor_node);
self.idleInhibitCheckActive();
}

View File

@ -395,6 +395,7 @@ fn commitTransaction(self: *Self) void {
output.damage.addWhole();
}
server.input_manager.updateCursorState();
server.idle_inhibitor_manager.idleInhibitCheckActive();
}
/// Send the new output configuration to all wlr-output-manager clients

View File

@ -36,6 +36,7 @@ const StatusManager = @import("StatusManager.zig");
const View = @import("View.zig");
const ViewStack = @import("view_stack.zig").ViewStack;
const XwaylandUnmanaged = @import("XwaylandUnmanaged.zig");
const IdleInhibitorManager = @import("IdleInhibitorManager.zig");
const log = std.log.scoped(.server);
@ -69,6 +70,7 @@ config: Config,
control: Control,
status_manager: StatusManager,
layout_manager: LayoutManager,
idle_inhibitor_manager: IdleInhibitorManager,
pub fn init(self: *Self) !void {
self.wl_server = try wl.Server.create();
@ -123,6 +125,7 @@ pub fn init(self: *Self) !void {
try self.control.init();
try self.status_manager.init();
try self.layout_manager.init();
try self.idle_inhibitor_manager.init(self.input_manager.idle);
// These all free themselves when the wl_server is destroyed
_ = try wlr.DataDeviceManager.create(self.wl_server);
@ -148,6 +151,7 @@ pub fn deinit(self: *Self) void {
self.root.deinit();
self.input_manager.deinit();
self.idle_inhibitor_manager.deinit();
self.wl_server.destroy();

View File

@ -436,6 +436,13 @@ pub fn fromWlrSurface(surface: *wlr.Surface) ?*Self {
return @intToPtr(*Self, xwayland_surface.data);
}
}
if (surface.isSubsurface()) {
if (wlr.Subsurface.fromWlrSurface(surface)) |ss| {
if (ss.parent) |s| {
return fromWlrSurface(s);
}
}
}
return null;
}