Files
dots/wm/.config/hypr/host.lua
T

97 lines
4.1 KiB
Lua

-- wm host layer — loaded by gui/.config/hypr/hyprland.lua via check_require("host").
-- Ports wm/.config/hypr/{monitors,host,nvidia}.conf to the Lua chain.
-- ── Monitors ─────────────────────────────────────────────────────────────────
-- DP-2 (the LG 4K) is the only fixed screen. Anything else works when plugged in,
-- without editing this file: the 1080 Ti has four other connectors (DP-1, DVI-D-1,
-- HDMI-A-1, HDMI-A-2), so extras are read from hl.get_monitors() in connection
-- order instead of being named here. The first extra sits right of DP-2 and owns
-- workspaces 11-20, a second sits left and owns 21-30.
local mainScreen = "DP-2"
local mainW, mainH, mainScale = 3840, 2160, 1.25
hl.monitor({ output = mainScreen, mode = mainW .. "x" .. mainH .. "@60", position = "0x0", scale = mainScale })
-- Catch-all for a screen with no rule of its own yet (the empty output name is
-- the default rule) — covers the moment between plug-in and the re-pin reload.
-- Not scale "auto": that picked 2 for a 1080p screen.
hl.monitor({ output = "", mode = "preferred", position = "auto-right", scale = 1 })
local function extra_screens()
local ok, monitors = pcall(hl.get_monitors)
local found = {}
for _, m in ipairs(ok and monitors or {}) do
if m.name ~= mainScreen and not m.is_mirror then
found[#found + 1] = m
end
end
table.sort(found, function(a, b)
return a.id < b.id
end)
return found
end
-- A 4K extra gets DP-2's scale, anything smaller 1; placed beside DP-2 and
-- vertically centred on it (what the old fixed 3072x350 rule approximated).
local function place(m, side)
local scale = m.width >= 3840 and mainScale or 1
local w, h = math.floor(m.width / scale), math.floor(m.height / scale)
local x = side == "right" and math.floor(mainW / mainScale) or -w
local y = math.max(0, math.floor((mainH / mainScale - h) / 2))
hl.monitor({ output = m.name, mode = "preferred", position = x .. "x" .. y, scale = scale })
end
local extras = extra_screens()
local rightScreen, leftScreen
if extras[1] then
rightScreen = extras[1].name
place(extras[1], "right")
end
if extras[2] then
leftScreen = extras[2].name
place(extras[2], "left")
end
-- ── Workspace pins (1-10 main, 11-20 right, 21-30 left) ──────────────────────
-- These are what make the r~N binds land on the focused monitor's set.
for i = 1, 10 do
hl.workspace_rule({ workspace = tostring(i), monitor = mainScreen, default = (i == 1) })
if rightScreen then
hl.workspace_rule({ workspace = tostring(i + 10), monitor = rightScreen, default = (i == 1) })
end
if leftScreen then
hl.workspace_rule({ workspace = tostring(i + 20), monitor = leftScreen, default = (i == 1) })
end
end
-- Pins are only computed at load, so a hotplug that changes the set of extras
-- reloads once to re-pin. DP-2's own link drop/return (it sleeps as a hotplug)
-- leaves the extras unchanged and does not reload.
local function names(list)
local out = {}
for i, m in ipairs(list) do
out[i] = m.name
end
return table.concat(out, ",")
end
local pinned = names(extras)
local function repin_if_changed()
if names(extra_screens()) ~= pinned then
hl.exec_cmd("hyprctl reload")
end
end
hl.on("monitor.added", repin_if_changed)
hl.on("monitor.removed", repin_if_changed)
-- ── Theme overrides (was host.conf) ──────────────────────────────────────────
-- Loads after dynamic.lua's theme state, so these still win over the theme.
hl.config({
general = { gaps_in = 2, gaps_out = 4 },
decoration = { rounding = 8 },
})
-- ── NVIDIA extras (was nvidia.conf) ──────────────────────────────────────────
-- LIBVA_DRIVER_NAME / __GLX_VENDOR_LIBRARY_NAME / GBM_BACKEND are already set
-- by HyDE's env.lua when the driver probe passes; only the two extras remain.
hl.env("NVD_BACKEND", "direct") -- va-api via libva-nvidia-driver
hl.config({ cursor = { no_hardware_cursors = true } }) -- avoid cursor hitches