Recently, hyprland has switched the configuration language from hyprlang to lua.
This involves a lot of calls to hyprland functions, for example binding a key is calling hl.bind() with the key combination and the function to be called on the keypress.
Configuring hyprland with homemanager, binds used to be a list of strings like so:
bind = [
"$mod, T, exec, kitty" # Launch terminal
];
Now, with the new lua config, every string in that bind will be the first parameter (the key) of the hl.bind() function, but that string needs to be escaped to actually call the proper function.
The only way I have found that can do this, is from an example on search.nixos.org (attached in full below), where the same bind would look like this:
bind = [
{
_args = [
(lib.generators.mkLuaInline "mod .. \" + T\"")
(lib.generators.mkLuaInline "hl.dsp.exec_cmd(\"kitty\")")
];
}
];
This seems like a very verbose and inefficient way to do it, adding 5 more lines to do the same thing.
I have thought of just having a lua file and linking it to the correct place with home manager, but I would like to use stylix for some color options, which would then be unable to write to the hyprland config.
Is there a better way to do this that I am missing?
If not, would it be possible to make a helper function to turn an attribute set of string=string into the proper bind list, so you’d have something that looked like this:
bind = [
generate_binds {
"${mod} + T" ''hl.dsp.exec_cmd("kitty")''
};
];
Full example from search.nixos.org:
{
mod = {
_var = "SUPER";
};
config = {
general = {
gaps_in = 5;
gaps_out = 20;
border_size = 2;
};
decoration = {
rounding = 10;
};
};
bind = [
{
_args = [
(lib.generators.mkLuaInline "mod .. \" + Q\"")
(lib.generators.mkLuaInline "hl.dsp.window.close()")
{ locked = true; }
];
}
{
_args = [
"SUPER + RETURN"
(lib.generators.mkLuaInline "hl.dsp.exec_cmd(\"kitty\")")
];
}
{
_args = [
"ALT + R"
(lib.generators.mkLuaInline "hl.dsp.submap(\"resize\")")
];
}
];
define_submap = {
_args = [
"resize"
(lib.generators.mkLuaInline "function()\n hl.bind(\"right\", hl.dsp.window.resize({ x = 10, y = 0, relative = true }), { repeating = true })\n hl.bind(\"left\", hl.dsp.window.resize({ x = -10, y = 0, relative = true }), { repeating = true })\n hl.bind(\"escape\", hl.dsp.submap(\"reset\"))\nend")
];
};
window_rule = {
match.class = "kitty";
border_size = 2;
};
on = {
_args = [
"hyprland.start"
(lib.generators.mkLuaInline "function()\n hl.exec_cmd(\"waybar\")\nend")
];
};
}