Something went wrong. Try again.
The cutest scrollable window manager for Windows
Something went wrong. Try again.
12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182const WindowHook = @This();
pub const Error = error{SetWinEventHookFailed};
const events = [_]struct { min: u32, max: u32 }{ .{ .min = win32.ui.windows_and_messaging.EVENT_SYSTEM_MINIMIZESTART, .max = win32.ui.windows_and_messaging.EVENT_SYSTEM_MINIMIZEEND }, .{ .min = win32.ui.windows_and_messaging.EVENT_SYSTEM_MOVESIZESTART, .max = win32.ui.windows_and_messaging.EVENT_SYSTEM_MOVESIZEEND },};
hooks: [events.len]win32.ui.accessibility.HWINEVENTHOOK,
pub fn start() !WindowHook { var window_hook: WindowHook = undefined;
for (events, 0..) |event, i| { log.debug("setting up a hook for events 0x{x}..0x{x}", .{ event.min, event.max }); window_hook.hooks[i] = win32.ui.accessibility.SetWinEventHook( event.min, event.max, null, &winEventProc, 0, 0, win32.ui.windows_and_messaging.WINEVENT_OUTOFCONTEXT | win32.ui.windows_and_messaging.WINEVENT_SKIPOWNPROCESS, ) orelse { log.err("couldn't hook events 0x{x}..0x{x}", .{ event.min, event.max }); for (window_hook.hooks[0..i]) |hook| { _ = win32.ui.accessibility.UnhookWinEvent(hook); } return Error.SetWinEventHookFailed; }; }
return window_hook;}
pub fn stop(window_hook: WindowHook) void { for (window_hook.hooks, events) |hook, event| { log.debug("removing hook for events 0x{x}..0x{x}", .{ event.min, event.max }); _ = win32.ui.accessibility.UnhookWinEvent(hook); }}
fn winEventProc( _: ?win32.ui.accessibility.HWINEVENTHOOK, _: u32, hwnd: ?win32.foundation.HWND, id_object: i32, id_child: i32, _: u32, _: u32,) callconv(.winapi) void { if (hwnd == null) return;
if (id_object != @intFromEnum(win32.ui.windows_and_messaging.OBJID_WINDOW)) return;
if (id_child != @as(i32, @intCast(win32.ui.windows_and_messaging.CHILDID_SELF))) return;
const window: Window = .{ .handle = hwnd.? };
if (!window.shouldManage()) return;
const screen: *Screen = &wm.screens.items[0]; screen.windows.ensureUnusedCapacity(wm.allocator, 1) catch |e| { log.err("couldn't add window: {s}", .{@errorName(e)}); std.debug.panic("{s}", .{@errorName(e)}); }; screen.windows.appendAssumeCapacity(window);
log.info("manageable window (now {d})", .{screen.windows.items.len});}
const wm = &@import("main.zig").wm;
const log = std.log.scoped(.window_hook);
const Screen = @import("Screen.zig");const Window = @import("Window.zig");
const win32 = @import("win32");const std = @import("std");