From 838773e1538b77f2d7a74fb78d31063d54cd688b Mon Sep 17 00:00:00 2001 From: Syed Daanish Date: Thu, 10 Sep 2026 18:32:17 +0100 Subject: [PATCH] Move initial ruby code out of line --- src/main.ml | 56 ++------------ src/mruby/initial.ml | 177 +++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 182 insertions(+), 51 deletions(-) create mode 100644 src/mruby/initial.ml diff --git a/src/main.ml b/src/main.ml index 032d111..a630718 100644 --- a/src/main.ml +++ b/src/main.ml @@ -1,62 +1,16 @@ let () = let startup_script = - if Array.length Sys.argv <> 2 then ( - Printf.eprintf "usage: kutu \n"; - exit 1) - else Sys.argv.(1) + if Array.length Sys.argv <> 2 then None else Some Sys.argv.(1) in let state = Kutu.State.new_state in print_endline "Started Kutu WM"; Bindings.Core.register_callbacks state; - Mruby.Core.mrb_load_string state.mrb - {|#ruby - MOD_MAP = { - none: 0, - alt: 8, - super: 64 - } - KEY_MAP = { - "tab" => 23, - "q" => 24, - "w" => 25, - "e" => 26, - "r" => 27, - "f" => 41, - "n" => 57, - "b" => 56, - "m" => 58, - "v" => 55, - "]" => 35, - "[" => 34, - "1" => 10, - "2" => 11, - "3" => 12, - "4" => 13, - "5" => 14, - "6" => 15, - "7" => 16, - "8" => 17, - "9" => 18, - "0" => 19 - } - def bind(key, mod = :alt, &block) - key_ = key.is_a?(String) ? KEY_MAP[key] : key - mod = MOD_MAP[mod] - raise "unknown key #{key.to_s}" unless key_ - raise "unknown modifier" unless mod - _bind key_, mod, &block - end - def unbind(key, mod = :alt) - key_ = key.is_a?(String) ? KEY_MAP[key] : key - mod = MOD_MAP[mod] - raise "unknown key #{key.to_s}" unless key_ - raise "unknown modifier" unless mod - _unbind key_, mod - end - |}; - Mruby.Core.mrb_load_file state.mrb startup_script; + Mruby.Core.mrb_load_string state.mrb Mruby.Initial.initial_code; + (match startup_script with + | None -> () + | Some s -> Mruby.Core.mrb_load_file state.mrb s); Mruby.Core.error_check state.mrb; if Xcb.Connection.flush state.conn <= 0 then exit 1; diff --git a/src/mruby/initial.ml b/src/mruby/initial.ml new file mode 100644 index 0000000..bb4e85a --- /dev/null +++ b/src/mruby/initial.ml @@ -0,0 +1,177 @@ +let initial_code = + {|#ruby +MOD_MAP = { + none: 0, + alt: 8, + super: 64 +} +KEY_MAP = { + "tab" => 23, + "q" => 24, + "w" => 25, + "e" => 26, + "r" => 27, + "f" => 41, + "n" => 57, + "b" => 56, + "m" => 58, + "v" => 55, + "]" => 35, + "[" => 34, + "1" => 10, + "2" => 11, + "3" => 12, + "4" => 13, + "5" => 14, + "6" => 15, + "7" => 16, + "8" => 17, + "9" => 18, + "0" => 19 +} +def bind(key, mod = :alt, &block) + key_ = key.is_a?(String) ? KEY_MAP[key] : key + mod = MOD_MAP[mod] + raise "unknown key #{key.to_s}" unless key_ + raise "unknown modifier" unless mod + _bind key_, mod, &block +end +def unbind(key, mod = :alt) + key_ = key.is_a?(String) ? KEY_MAP[key] : key + mod = MOD_MAP[mod] + raise "unknown key #{key.to_s}" unless key_ + raise "unknown modifier" unless mod + _unbind key_, mod +end + +# ==== State ==== + +MAX_PROJECTS = 9 +SUBS = 2 # workspaces per project + +$current_project = 1 # 1..MAX_PROJECTS +$current_sub = 0 # 0..SUBS-1 + +# For each special workspace, remembers which workspace you were on +# before you jumped into it -- so hitting the mode key again toggles back. +$special_origin = {} + +SPECIAL = { + terminal: { cmd: "kitty" }, + browser: { cmd: "firefox" }, + music: { cmd: "spotify" }, + misc: { cmd: nil }, # doesn't start anything + todo: { cmd: nil }, # doesn't start anything +} + +# ==== Helpers ==== + +def project_ws(n, sub) + :"p#{n}_#{sub}" +end + +def running?(process) + system("pgrep -x #{process} > /dev/null 2>&1") +end + +def go_project(n, sub) + $current_project = n + $current_sub = sub + jump_ws project_ws(n, sub) +end + +def in_project?(ws) + !SPECIAL.key?(ws) +end + +# Toggle between a special-mode workspace (terminal/browser/music/misc/todo) +# and whatever workspace you were last on. Starts the associated app if +# it isn't already running. `ws` is the current workspace, passed in by +# the bind block (bind gives us (window, current_ws)). +def go_special(name, ws) + cfg = SPECIAL.fetch(name) + + if ws == name + target = $special_origin[name] || project_ws($current_project, $current_sub) + jump_ws target + else + $special_origin[name] = ws + jump_ws name + system("#{cfg[:cmd]} >/dev/null 2>&1 &") if cfg[:cmd] && !running?(cfg[:cmd]) + end +end + +# ==== Untouched bindings ==== + +bind ?q do |x| + kill x +end + +bind ?w do + system "kitty >/dev/null 2>&1 &" +end + +bind ?e do + exit +end + +bind ?f do |x| + toggle_float x +end + +# ==== Mode switches ==== + +bind ?[ do |_, ws| + go_special :terminal, ws +end + +bind ?] do |_, ws| + go_special :misc, ws +end + +bind "tab" do |_, ws| + go_special :browser, ws +end + +bind 89 do |_, ws| + go_special :music, ws +end + +bind 81 do |_, ws| + go_special :todo, ws +end + +# ==== Project navigation ==== + +(1..MAX_PROJECTS).each do |n| + bind n.to_s do + go_project(n, $current_sub) + end +end + +bind 86 do |_, ws| + next unless in_project?(ws) + n = (($current_project - 2) % MAX_PROJECTS) + 1 + go_project(n, $current_sub) +end + +bind 82 do |_, ws| + next unless in_project?(ws) + n = ($current_project % MAX_PROJECTS) + 1 + go_project(n, $current_sub) +end + +bind 79 do |_, ws| + next unless in_project?(ws) + go_project($current_project, ($current_sub + 1) % SUBS) +end + +bind 80 do |_, ws| + next unless in_project?(ws) + go_project($current_project, ($current_sub - 1 + SUBS) % SUBS) +end + +# ==== Startup ==== + +go_project(1, 0) +|}