diff --git a/config/aerospace/aerospace.toml b/config/aerospace/aerospace.toml new file mode 100644 index 0000000..8eef6c2 --- /dev/null +++ b/config/aerospace/aerospace.toml @@ -0,0 +1,104 @@ +config-version = 2 + +after-startup-command = [ + "workspace 10", + "layout h_accordion", + "workspace-back-and-forth" +] + +persistent-workspaces = ['1', '2', '3', '4', '5', '6', '7', '8', '9', '10'] +enable-normalization-flatten-containers = false +enable-normalization-opposite-orientation-for-nested-containers = false +on-focused-monitor-changed = ['move-mouse monitor-lazy-center'] +exec-on-workspace-change = ['/bin/bash', '-c', + '/run/current-system/sw/bin/sketchybar --trigger aerospace_workspace_change FOCUSED_WORKSPACE=$AEROSPACE_FOCUSED_WORKSPACE PREV_WORKSPACE=$AEROSPACE_PREV_WORKSPACE && /etc/profiles/per-user/rayandrew/bin/aerospace-scratchpad hook pull-window $AEROSPACE_PREV_WORKSPACE $AEROSPACE_FOCUSED_WORKSPACE' +] + +[gaps] + inner.horizontal = [{ monitor.'^built-in retina display$' = 10 }, 15] + inner.vertical = [{ monitor.'^built-in retina display$' = 10 }, 15] + outer.left = [{ monitor.'^built-in retina display$' = 5 }, 15] + outer.right = [{ monitor.'^built-in retina display$' = 5 }, 15] + outer.bottom = [{ monitor.'^built-in retina display$' = 5 }, 15] + outer.top = [{ monitor.'^built-in retina display$' = 15 }, 50] + +[mode.main.binding] + alt-enter = 'exec-and-forget open -na Ghostty' + + alt-h = 'focus --boundaries-action wrap-around-the-workspace left' + alt-j = 'focus --boundaries-action wrap-around-the-workspace down' + alt-k = 'focus --boundaries-action wrap-around-the-workspace up' + alt-l = 'focus --boundaries-action wrap-around-the-workspace right' + + alt-shift-h = 'move --boundaries all-monitors-outer-frame left' + alt-shift-j = 'move --boundaries all-monitors-outer-frame down' + alt-shift-k = 'move --boundaries all-monitors-outer-frame up' + alt-shift-l = 'move --boundaries all-monitors-outer-frame right' + + alt-v = 'split vertical' + alt-shift-v = 'split horizontal' + + alt-f = 'fullscreen' + + alt-s = 'layout v_accordion' + alt-e = 'layout tiles horizontal vertical' + alt-space = 'layout floating tiling' + + alt-1 = 'workspace 1' + alt-2 = 'workspace 2' + alt-3 = 'workspace 3' + alt-4 = 'workspace 4' + alt-5 = 'workspace 5' + alt-6 = 'workspace 6' + alt-7 = 'workspace 7' + alt-8 = 'workspace 8' + alt-9 = 'workspace 9' + alt-0 = 'workspace 10' + + alt-shift-1 = 'move-node-to-workspace 1' + alt-shift-2 = 'move-node-to-workspace 2' + alt-shift-3 = 'move-node-to-workspace 3' + alt-shift-4 = 'move-node-to-workspace 4' + alt-shift-5 = 'move-node-to-workspace 5' + alt-shift-6 = 'move-node-to-workspace 6' + alt-shift-7 = 'move-node-to-workspace 7' + alt-shift-8 = 'move-node-to-workspace 8' + alt-shift-9 = 'move-node-to-workspace 9' + alt-shift-0 = 'move-node-to-workspace 10' + + alt-shift-semicolon = 'mode service' + alt-r = 'mode resize' + + + cmd-ctrl-1 = "exec-and-forget aerospace-scratchpad show Finder" + +[mode.resize.binding] + h = 'resize width -50' + j = 'resize height +50' + k = 'resize height -50' + l = 'resize width +50' + enter = 'mode main' + esc = 'mode main' + +[mode.service.binding] + c = ['reload-config', 'mode main'] + r = ['flatten-workspace-tree', 'mode main'] + f = ['layout floating tiling', 'mode main'] + backspace = ['close-all-windows-but-current', 'mode main'] + + alt-shift-h = ['join-with left', 'mode main'] + alt-shift-j = ['join-with down', 'mode main'] + alt-shift-k = ['join-with up', 'mode main'] + alt-shift-l = ['join-with right', 'mode main'] + +[[on-window-detected]] + if.app-id = 'com.apple.finder' + run = ['layout floating'] + +[[on-window-detected]] + if.app-id = 'com.apple.ActivityMonitor' + run = ['layout floating'] + +[[on-window-detected]] + if.app-id = 'com.1password.1password' + run = ['layout floating'] diff --git a/config/home/.hammerspoon/keyboard/init.lua b/config/home/.hammerspoon/keyboard/init.lua index 75d3c1a..9b62aa7 100644 --- a/config/home/.hammerspoon/keyboard/init.lua +++ b/config/home/.hammerspoon/keyboard/init.lua @@ -1,12 +1,12 @@ local keymap = require 'keyboard.keymaps' -require 'keyboard.yabai' +-- require 'keyboard.yabai' -- General keymap -- reload config -keymap.super { - key = 'c', - mods = { 'shift' }, - message = 'Reload Hammerspoon config', - fn = function() hs.reload() end, -} +-- keymap.super { +-- key = 'c', +-- mods = { 'shift' }, +-- message = 'Reload Hammerspoon config', +-- fn = function() hs.reload() end, +-- } diff --git a/config/home/.hammerspoon/keyboard/yabai.lua b/config/home/.hammerspoon/keyboard/yabai.lua index 7fef483..f3b907b 100644 --- a/config/home/.hammerspoon/keyboard/yabai.lua +++ b/config/home/.hammerspoon/keyboard/yabai.lua @@ -63,6 +63,17 @@ yabai_key { key = "'", commands = { 'space --layout stack' } } yabai_key { key = ';', commands = { 'space --layout bsp' } } yabai_key { key = 'tab', commands = { 'space --focus recent' } } +-- toggle between bsp and stack layout +keymap.super { + key = 's', + message = 'Toggle layout (bsp/stack)', + fn = function() + local current_type = yabai_query('--spaces --space', "'.type'") + local new_layout = current_type == 'bsp' and 'stack' or 'bsp' + os.execute(yabai_cmd .. ' -m space --layout ' .. new_layout) + end, +} + -- navigation yabai_key { key = 'h', commands = { 'window --focus west', 'display --focus west' }, logic = 'or' } yabai_key { key = 'j', commands = { 'window --focus south', 'display --focus south' }, logic = 'or' } diff --git a/config/sketchybar/items/aerospace.lua b/config/sketchybar/items/aerospace.lua index 852c034..585157e 100644 --- a/config/sketchybar/items/aerospace.lua +++ b/config/sketchybar/items/aerospace.lua @@ -1,51 +1,57 @@ --- https://github.com/Tnixc/nix-config/blob/main/home/programs/aerospace-sketchybar/sbar-config-libs/items/aerospaces.lua - local Promise = require 'promise' local colors = require 'colors' local utils = require 'utils' local settings = require 'settings' local app_icons = require 'app_icons' +local aerospace_cmd = '/opt/homebrew/bin/aerospace' + local function getAllWorkspaces() - return utils.sbarExecP "aerospace list-workspaces --all --format '%{workspace}%{monitor-appkit-nsscreen-screens-id}%{monitor-id}%{monitor-name}' --json" + return utils.sbarExecP( + aerospace_cmd .. " list-workspaces --all --format '%{workspace}%{monitor-appkit-nsscreen-screens-id}%{monitor-id}%{monitor-name}' --json" + ) end local function getVisibleWorkspaces() - return utils.sbarExecP "aerospace list-workspaces --visible --monitor all --format '%{workspace}%{monitor-appkit-nsscreen-screens-id}%{monitor-id}%{monitor-name}' --json" + return utils.sbarExecP( + aerospace_cmd .. " list-workspaces --visible --monitor all --format '%{workspace}%{monitor-appkit-nsscreen-screens-id}%{monitor-id}%{monitor-name}' --json" + ) end local function getAllWindows() - return utils.sbarExecP "aerospace list-windows --all --format '%{app-name}%{window-title}%{workspace}%{monitor-id}%{monitor-appkit-nsscreen-screens-id}%{monitor-name}' --json" + return utils.sbarExecP( + aerospace_cmd + .. " list-windows --all --format '%{app-name}%{window-title}%{workspace}%{monitor-id}%{monitor-appkit-nsscreen-screens-id}%{monitor-name}' --json" + ) end local function getMonitorId(obj) if obj['monitor-name'] then if obj['monitor-name'] == 'ZOWIE XL LCD' then - return '2' + return 2 elseif obj['monitor-name'] == 'LG ULTRAWIDE' then - return '1' + return 1 end end - if obj['monitor-appkit-nsscreen-screens-id'] then return obj['monitor-appkit-nsscreen-screens-id'] end - return obj['monitor-id'] + if obj['monitor-appkit-nsscreen-screens-id'] then return tonumber(obj['monitor-appkit-nsscreen-screens-id']) or 1 end + return tonumber(obj['monitor-id']) or 1 end local spaces = {} local space_paddings = {} -local brackets = {} local state = { workspaces = {}, updating = false, } -function getState() - local newstate = { - workspaces = {}, - } +local function getState() + local newstate = { workspaces = {} } - for workspaceid, space in pairs(spaces) do + -- Pre-initialize all workspaces from the spaces table + for workspaceid, _ in pairs(spaces) do newstate.workspaces[workspaceid] = { - monitor = 0, + id = workspaceid, + monitor = 1, active = false, empty = true, apps = {}, @@ -55,22 +61,24 @@ function getState() return Promise.all({ getAllWorkspaces(), getVisibleWorkspaces(), getAllWindows() }):thenCall(function(values) local all, visible, apps = values[1], values[2], values[3] + for _, workspace in ipairs(all) do local workspaceid = workspace['workspace'] - newstate.workspaces[workspaceid]['id'] = workspaceid - newstate.workspaces[workspaceid]['monitor'] = getMonitorId(workspace) + if newstate.workspaces[workspaceid] then newstate.workspaces[workspaceid]['monitor'] = getMonitorId(workspace) end end for _, workspace in ipairs(visible) do local workspaceid = workspace['workspace'] - newstate.workspaces[workspaceid]['active'] = true + if newstate.workspaces[workspaceid] then newstate.workspaces[workspaceid]['active'] = true end end for _, window in ipairs(apps) do local workspaceid = window['workspace'] local appname = window['app-name'] - newstate.workspaces[workspaceid]['apps'][appname] = true - newstate.workspaces[workspaceid]['empty'] = false + if newstate.workspaces[workspaceid] then + newstate.workspaces[workspaceid]['apps'][appname] = true + newstate.workspaces[workspaceid]['empty'] = false + end end for workspaceid, workspacestate in pairs(newstate.workspaces) do @@ -88,7 +96,6 @@ function getState() else workspacestate['appicons'] = '' end - -- print(utils.dump(workspacestate)) end return newstate @@ -98,68 +105,26 @@ end local function updateState() if not state.updating then state.updating = true - return getState():thenCall(function(newstate) - state.workspaces = newstate.workspaces - state.updating = false - end) + return getState() + :thenCall(function(newstate) + state.workspaces = newstate.workspaces + state.updating = false + end) + :catch(function(err) + state.updating = false + print('Error updating state: ' .. tostring(err)) + end) end - return Promise.reject 'State is already updating' -end - -local function highlightSpace(space, space_padding, space_bracket, selected) - space:set { - drawing = true, - icon = { highlight = selected }, - label = { highlight = selected }, - -- background = { border_color = selected and colors.white or colors.bg2 } - } - space_padding:set { - drawing = true, - } - if space_bracket then - space_bracket:set { - -- background = { border_color = selected and colors.grey or colors.bg2 }, - } - end -end - -local function onActiveSpaceChange(env) - local focused_workspace = env.FOCUSED_WORKSPACE - local last_workspace = env.PREV_WORKSPACE - -- print("aerospace_workspace_change from " .. last_workspace .. " to " .. focused_workspace) - - local space = spaces[focused_workspace] - local space_padding = space_paddings[focused_workspace] - - local prev_space = spaces[last_workspace] - local prev_space_padding = space_paddings[last_workspace] - - sbar.animate('tanh', 10, function() - highlightSpace(space, space_padding, nil, true) - if state.workspaces[last_workspace]['monitor'] == state.workspaces[focused_workspace]['monitor'] then - highlightSpace(prev_space, prev_space_padding, nil, false) - end - end) - - updateState() + return Promise.resolve() end local function syncState() sbar.animate('tanh', 10, function() for workspaceid, workspacestate in pairs(state.workspaces) do - if not workspacestate['empty'] then + if not workspacestate['empty'] or workspacestate['active'] then spaces[workspaceid]:set { drawing = true, display = workspacestate['monitor'], - -- label = { - -- string = workspaceid, - -- highlight = workspacestate["active"], - -- }, - -- icon = { - -- string = workspaceid, - -- color = colors.white, - -- highlight = workspacestate["active"], - -- }, label = { string = workspacestate['appicons'], highlight = workspacestate['active'], @@ -170,7 +135,6 @@ local function syncState() } space_paddings[workspaceid]:set { drawing = true } else - -- These should be hidden spaces[workspaceid]:set { drawing = false, display = workspacestate['monitor'], @@ -184,7 +148,38 @@ end local function updateStateAndSync() return updateState():thenCall(syncState) end -function setup() +local function onActiveSpaceChange(env) + local focused_workspace = env.FOCUSED_WORKSPACE + local prev_workspace = env.PREV_WORKSPACE + + -- Immediately show the focused workspace with animation + if spaces[focused_workspace] then + sbar.animate('tanh', 10, function() + spaces[focused_workspace]:set { + drawing = true, + icon = { highlight = true }, + label = { highlight = true }, + } + space_paddings[focused_workspace]:set { drawing = true } + + if spaces[prev_workspace] then + spaces[prev_workspace]:set { + icon = { highlight = false }, + label = { highlight = false }, + } + -- Hide previous workspace if it's empty + if state.workspaces[prev_workspace] and state.workspaces[prev_workspace]['empty'] then + spaces[prev_workspace]:set { drawing = false } + space_paddings[prev_workspace]:set { drawing = false } + end + end + end) + end + + updateStateAndSync() +end + +local function setup() getAllWorkspaces() :thenCall(function(workspaces) for _, workspace in ipairs(workspaces) do @@ -192,7 +187,7 @@ function setup() local display = getMonitorId(workspace) local space = sbar.add('item', 'space.' .. workspaceid, { - drawing = false, -- default to not showing the space -- we'll show if it has windows or is activated + drawing = false, updates = 'when_shown', display = display, icon = { @@ -206,11 +201,10 @@ function setup() highlight_color = colors.blue, font = 'sketchybar-app-font:Regular:14.0', y_offset = -1, - -- drawing = false }, padding_left = 1, padding_right = 1, - click_script = 'aerospace workspace ' .. workspaceid, + click_script = aerospace_cmd .. ' workspace ' .. workspaceid, }) spaces[workspaceid] = space @@ -226,6 +220,8 @@ function setup() end end) :thenCall(function() + sbar.add('event', 'aerospace_workspace_change') + local space_window_observer = sbar.add('item', { drawing = false, updates = true, diff --git a/config/sketchybar/items/init.lua b/config/sketchybar/items/init.lua index 0fac057..3c0fca2 100644 --- a/config/sketchybar/items/init.lua +++ b/config/sketchybar/items/init.lua @@ -22,6 +22,7 @@ local function load_module_if_program_exists(module_name, binary_path) end require 'items.apple' +-- require 'items.aerospace' load_module_if_program_exists('items.aerospace', '/opt/homebrew/bin/aerospace') load_module_if_program_exists('items.yabai', '/etc/profiles/per-user/rayandrew/bin/yabai') require 'items.front_app' diff --git a/darwin/aerospace.nix b/darwin/aerospace.nix index bda5403..2666269 100644 --- a/darwin/aerospace.nix +++ b/darwin/aerospace.nix @@ -1,8 +1,9 @@ { - pkgs, lib, config, - home-dir, + dots, + pkgs, + inputs, ... }: @@ -13,305 +14,310 @@ in options.custom.gui = with lib; { aerospace = { enable = mkEnableOption "Enable aerospace"; - logFile = mkOption { - type = types.str; - default = "${home-dir}/Library/Logs/aerospace.log"; - description = "Filepath of log output"; - }; + # logFile = mkOption { + # type = types.str; + # default = "${home-dir}/Library/Logs/aerospace.log"; + # description = "Filepath of log output"; + # }; }; }; config = lib.mkIf cfg.enable { - launchd.user.agents.aerospace.serviceConfig = { - StandardErrorPath = cfg.logFile; - StandardOutPath = cfg.logFile; - }; - - services.aerospace = { - enable = true; - # package = pkgs.custom.aerospace; - settings = { - enable-normalization-flatten-containers = false; - enable-normalization-opposite-orientation-for-nested-containers = false; - accordion-padding = 0; - on-focused-monitor-changed = [ "move-mouse monitor-lazy-center" ]; - default-root-container-layout = "tiles"; - default-root-container-orientation = "auto"; - after-startup-command = [ - "workspace 10" - "layout h_accordion" - "workspace-back-and-forth" - ]; - - gaps = { - inner = { - horizontal = 15; - vertical = 15; - }; - outer = { - left = 10; - bottom = 5; - top = [ - { monitor."LG ULTRAWIDE" = 50; } - { monitor."ZOWIE XL LCD" = 50; } - 12 - ]; - right = 10; - }; - }; - - mode = { - main = { - binding = { - alt-enter = - let - script = pkgs.writeText "ghostty.applescript" '' - do shell script "open -n -a Ghostty" - ''; - in - "exec-and-forget osascript ${script}"; - - # alt-enter = "exec-and-forget \"open -n -a /Applications/Slack.app\""; - - alt-shift-f = "fullscreen"; - alt-shift-q = "close --quit-if-last-window"; - alt-space = "layout floating tiling"; - alt-e = "layout tiles horizontal vertical"; - alt-t = "layout h_accordion"; - alt-s = "layout v_accordion"; - alt-v = "split vertical"; - alt-shift-v = "split horizontal"; - # alt-v = "join-with down"; - # alt-shift-v = "join-with right"; - alt-h = "focus --boundaries-action wrap-around-the-workspace left"; - alt-l = "focus --boundaries-action wrap-around-the-workspace right"; - alt-j = "focus --boundaries-action wrap-around-the-workspace down"; - alt-k = "focus --boundaries-action wrap-around-the-workspace up"; - alt-shift-h = "move left"; - alt-shift-l = "move right"; - alt-shift-j = "move down"; - alt-shift-k = "move up"; - - cmd-h = [ ]; # Disable "hide application" - cmd-alt-h = [ ]; # Disable "hide others" - cmd-q = [ ]; # Disable "quit" - cmd-shift-q = [ ]; # Disable "logout" - - alt-1 = "workspace 1"; - alt-2 = "workspace 2"; - alt-3 = "workspace 3"; - alt-4 = "workspace 4"; - alt-5 = "workspace 5"; - alt-6 = "workspace 6"; - alt-7 = "workspace 7"; - alt-8 = "workspace 8"; - alt-9 = "workspace 9"; - alt-0 = "workspace 10"; - - alt-shift-1 = [ - "move-node-to-workspace 1" - # "workspace 1" - ]; - alt-shift-2 = [ - "move-node-to-workspace 2" - # "workspace 2" - ]; - alt-shift-3 = [ - "move-node-to-workspace 3" - # "workspace 3" - ]; - alt-shift-4 = [ - "move-node-to-workspace 4" - # "workspace 4" - ]; - alt-shift-5 = [ - "move-node-to-workspace 5" - # "workspace 5" - ]; - alt-shift-6 = [ - "move-node-to-workspace 6" - # "workspace 6" - ]; - alt-shift-7 = [ - "move-node-to-workspace 7" - # "workspace 7" - ]; - alt-shift-8 = [ - "move-node-to-workspace 8" - # "workspace 8" - ]; - alt-shift-9 = [ - "move-node-to-workspace 9" - # "workspace 9" - ]; - alt-shift-0 = [ - "move-node-to-workspace 10" - # "workspace 10" - ]; - - alt-shift-c = "reload-config"; - alt-tab = "workspace-back-and-forth"; - alt-shift-tab = "move-workspace-to-monitor --wrap-around next"; - alt-r = "mode resize"; - alt-shift-semicolon = "mode service"; - }; - }; - - service = { - binding = { - esc = [ - "reload-config" - "mode main" - ]; - r = [ - "flatten-workspace-tree" - "mode main" - ]; - f = [ - "layout floating tiling" - "mode main" - ]; - backspace = [ - "close-all-windows-but-current" - "mode main" - ]; - - alt-shift-h = [ - "join-with left" - "mode main" - ]; - alt-shift-j = [ - "join-with down" - "mode main" - ]; - alt-shift-k = [ - "join-with up" - "mode main" - ]; - alt-shift-l = [ - "join-with right" - "mode main" - ]; - - # down = "volume down"; - # up = "volume up"; - # shift-down = [ "volume set 0" "mode main" ]; - }; - }; - - resize = { - binding = { - h = "resize width -50"; - j = "resize height +50"; - k = "resize height -50"; - l = "resize width +50"; - enter = "mode main"; - esc = "mode main"; - }; - }; - }; - - workspace-to-monitor-force-assignment = { - "1" = "main"; - "2" = "main"; - "3" = "main"; - "4" = "main"; - "5" = "main"; - "6" = "main"; - "7" = [ - "2" - "main" - ]; - "8" = "main"; - "9" = "main"; - "10" = [ - "2" - "main" - ]; - }; - - on-window-detected = [ - # workspace - # media - { - "if".app-id = "com.spotify.client"; - run = [ "move-node-to-workspace 7" ]; - } - # browser - { - "if".app-id = "app.zen-browser.zen"; - run = [ "move-node-to-workspace 10" ]; - } - { - "if".app-id = "com.kagi.kagimacOS"; - run = [ - "move-node-to-workspace 10" - ]; - } - # { - # "if".app-id = "com.openai.chat"; - # run = [ - # "move-node-to-workspace 10" - # ]; - # } - # { - # "if".app-id = "app.mozilla.firefox"; - # run = [ "move-node-to-workspace 10" ]; - # } - # { - # "if".app-id = "com.google.Chrome"; - # run = [ "move-node-to-workspace 10" ]; - # } - # { - # "if".app-id = "org.chromium.Chromium"; - # run = [ "move-node-to-workspace 10" ]; - # } - # communications - { - "if".app-id = "com.tinyspeck.slackmacgap"; - run = [ "move-node-to-workspace 9" ]; - } - { - "if".app-id = "com.microsoft.teams2"; - run = [ "move-node-to-workspace 9" ]; - } - # special app's layout - ## tiling - { - "if".app-id = "com.mitchellh.ghostty"; - run = [ "layout tiling" ]; - } - ## floating - { - "if".app-id = "com.renfei.SnippetsLab"; - run = [ "layout floating" ]; - } - { - "if".app-id = "com.colliderli.iina"; - run = [ "layout tiling" ]; - } - { - "if".app-id = "com.apple.ActivityMonitor"; - run = [ "layout floating" ]; - } - { - "if".app-id = "com.apple.calculator"; - run = [ "layout floating" ]; - } - { - "if".app-id = "com.apple.finder"; - run = [ "layout floating" ]; - } - { - "if".app-id = "com.1password.1password"; - run = [ "layout floating" ]; - } - { - "if".app-id = "com.chabomakers.Antinote"; - run = [ "layout floating" ]; - } - ]; - }; - }; + hm.home.packages = [ + inputs.aerospace-scratchpad.packages.${pkgs.stdenv.hostPlatform.system}.default + ]; + hm.xdg.configFile."aerospace".source = + config.hm.lib.file.mkOutOfStoreSymlink "${dots}/config/aerospace"; + # launchd.user.agents.aerospace.serviceConfig = { + # StandardErrorPath = cfg.logFile; + # StandardOutPath = cfg.logFile; + # }; + # + # services.aerospace = { + # enable = true; + # # package = pkgs.custom.aerospace; + # settings = { + # enable-normalization-flatten-containers = false; + # enable-normalization-opposite-orientation-for-nested-containers = false; + # accordion-padding = 0; + # on-focused-monitor-changed = [ "move-mouse monitor-lazy-center" ]; + # default-root-container-layout = "tiles"; + # default-root-container-orientation = "auto"; + # after-startup-command = [ + # "workspace 10" + # "layout h_accordion" + # "workspace-back-and-forth" + # ]; + # + # gaps = { + # inner = { + # horizontal = 15; + # vertical = 15; + # }; + # outer = { + # left = 10; + # bottom = 5; + # top = [ + # { monitor."LG ULTRAWIDE" = 50; } + # { monitor."ZOWIE XL LCD" = 50; } + # 12 + # ]; + # right = 10; + # }; + # }; + # + # mode = { + # main = { + # binding = { + # alt-enter = + # let + # script = pkgs.writeText "ghostty.applescript" '' + # do shell script "open -n -a Ghostty" + # ''; + # in + # "exec-and-forget osascript ${script}"; + # + # # alt-enter = "exec-and-forget \"open -n -a /Applications/Slack.app\""; + # + # alt-shift-f = "fullscreen"; + # alt-shift-q = "close --quit-if-last-window"; + # alt-space = "layout floating tiling"; + # alt-e = "layout tiles horizontal vertical"; + # alt-t = "layout h_accordion"; + # alt-s = "layout v_accordion"; + # alt-v = "split vertical"; + # alt-shift-v = "split horizontal"; + # # alt-v = "join-with down"; + # # alt-shift-v = "join-with right"; + # alt-h = "focus --boundaries-action wrap-around-the-workspace left"; + # alt-l = "focus --boundaries-action wrap-around-the-workspace right"; + # alt-j = "focus --boundaries-action wrap-around-the-workspace down"; + # alt-k = "focus --boundaries-action wrap-around-the-workspace up"; + # alt-shift-h = "move left"; + # alt-shift-l = "move right"; + # alt-shift-j = "move down"; + # alt-shift-k = "move up"; + # + # cmd-h = [ ]; # Disable "hide application" + # cmd-alt-h = [ ]; # Disable "hide others" + # cmd-q = [ ]; # Disable "quit" + # cmd-shift-q = [ ]; # Disable "logout" + # + # alt-1 = "workspace 1"; + # alt-2 = "workspace 2"; + # alt-3 = "workspace 3"; + # alt-4 = "workspace 4"; + # alt-5 = "workspace 5"; + # alt-6 = "workspace 6"; + # alt-7 = "workspace 7"; + # alt-8 = "workspace 8"; + # alt-9 = "workspace 9"; + # alt-0 = "workspace 10"; + # + # alt-shift-1 = [ + # "move-node-to-workspace 1" + # # "workspace 1" + # ]; + # alt-shift-2 = [ + # "move-node-to-workspace 2" + # # "workspace 2" + # ]; + # alt-shift-3 = [ + # "move-node-to-workspace 3" + # # "workspace 3" + # ]; + # alt-shift-4 = [ + # "move-node-to-workspace 4" + # # "workspace 4" + # ]; + # alt-shift-5 = [ + # "move-node-to-workspace 5" + # # "workspace 5" + # ]; + # alt-shift-6 = [ + # "move-node-to-workspace 6" + # # "workspace 6" + # ]; + # alt-shift-7 = [ + # "move-node-to-workspace 7" + # # "workspace 7" + # ]; + # alt-shift-8 = [ + # "move-node-to-workspace 8" + # # "workspace 8" + # ]; + # alt-shift-9 = [ + # "move-node-to-workspace 9" + # # "workspace 9" + # ]; + # alt-shift-0 = [ + # "move-node-to-workspace 10" + # # "workspace 10" + # ]; + # + # alt-shift-c = "reload-config"; + # alt-tab = "workspace-back-and-forth"; + # alt-shift-tab = "move-workspace-to-monitor --wrap-around next"; + # alt-r = "mode resize"; + # alt-shift-semicolon = "mode service"; + # }; + # }; + # + # service = { + # binding = { + # esc = [ + # "reload-config" + # "mode main" + # ]; + # r = [ + # "flatten-workspace-tree" + # "mode main" + # ]; + # f = [ + # "layout floating tiling" + # "mode main" + # ]; + # backspace = [ + # "close-all-windows-but-current" + # "mode main" + # ]; + # + # alt-shift-h = [ + # "join-with left" + # "mode main" + # ]; + # alt-shift-j = [ + # "join-with down" + # "mode main" + # ]; + # alt-shift-k = [ + # "join-with up" + # "mode main" + # ]; + # alt-shift-l = [ + # "join-with right" + # "mode main" + # ]; + # + # # down = "volume down"; + # # up = "volume up"; + # # shift-down = [ "volume set 0" "mode main" ]; + # }; + # }; + # + # resize = { + # binding = { + # h = "resize width -50"; + # j = "resize height +50"; + # k = "resize height -50"; + # l = "resize width +50"; + # enter = "mode main"; + # esc = "mode main"; + # }; + # }; + # }; + # + # workspace-to-monitor-force-assignment = { + # "1" = "main"; + # "2" = "main"; + # "3" = "main"; + # "4" = "main"; + # "5" = "main"; + # "6" = "main"; + # "7" = [ + # "2" + # "main" + # ]; + # "8" = "main"; + # "9" = "main"; + # "10" = [ + # "2" + # "main" + # ]; + # }; + # + # on-window-detected = [ + # # workspace + # # media + # { + # "if".app-id = "com.spotify.client"; + # run = [ "move-node-to-workspace 7" ]; + # } + # # browser + # { + # "if".app-id = "app.zen-browser.zen"; + # run = [ "move-node-to-workspace 10" ]; + # } + # { + # "if".app-id = "com.kagi.kagimacOS"; + # run = [ + # "move-node-to-workspace 10" + # ]; + # } + # # { + # # "if".app-id = "com.openai.chat"; + # # run = [ + # # "move-node-to-workspace 10" + # # ]; + # # } + # # { + # # "if".app-id = "app.mozilla.firefox"; + # # run = [ "move-node-to-workspace 10" ]; + # # } + # # { + # # "if".app-id = "com.google.Chrome"; + # # run = [ "move-node-to-workspace 10" ]; + # # } + # # { + # # "if".app-id = "org.chromium.Chromium"; + # # run = [ "move-node-to-workspace 10" ]; + # # } + # # communications + # { + # "if".app-id = "com.tinyspeck.slackmacgap"; + # run = [ "move-node-to-workspace 9" ]; + # } + # { + # "if".app-id = "com.microsoft.teams2"; + # run = [ "move-node-to-workspace 9" ]; + # } + # # special app's layout + # ## tiling + # { + # "if".app-id = "com.mitchellh.ghostty"; + # run = [ "layout tiling" ]; + # } + # ## floating + # { + # "if".app-id = "com.renfei.SnippetsLab"; + # run = [ "layout floating" ]; + # } + # { + # "if".app-id = "com.colliderli.iina"; + # run = [ "layout tiling" ]; + # } + # { + # "if".app-id = "com.apple.ActivityMonitor"; + # run = [ "layout floating" ]; + # } + # { + # "if".app-id = "com.apple.calculator"; + # run = [ "layout floating" ]; + # } + # { + # "if".app-id = "com.apple.finder"; + # run = [ "layout floating" ]; + # } + # { + # "if".app-id = "com.1password.1password"; + # run = [ "layout floating" ]; + # } + # { + # "if".app-id = "com.chabomakers.Antinote"; + # run = [ "layout floating" ]; + # } + # ]; + # }; + # }; }; } diff --git a/darwin/homebrew.nix b/darwin/homebrew.nix index e564ccb..49a0fcd 100644 --- a/darwin/homebrew.nix +++ b/darwin/homebrew.nix @@ -65,6 +65,7 @@ marta = mkEnableOption "Enable marta"; valgrind = mkEnableOption "Enable valgrind"; hammerspoon = mkEnableOption "Enable hammerspoon"; + aerospace = mkEnableOption "Enable aerospace"; }; config = lib.mkMerge [ @@ -80,10 +81,11 @@ "homebrew/homebrew-createzap" = inputs.homebrew-createzap; "d12frosted/homebrew-emacs-plus" = inputs.homebrew-emacs-plus; "brewsci/homebrew-bio" = inputs.homebrew-brewsci-bio; + "nikitabobko/tap" = inputs.homebrew-nikitabobko; # "LouisBrunner/valgrind" = inputs.homebrew-valgrind; } ]; - mutableTaps = false; # true to enable valgrind + mutableTaps = true; # true to enable valgrind }; homebrew = { enable = true; @@ -201,7 +203,7 @@ }) (lib.mkIf config.custom.brew.ice { homebrew.casks = [ - "jordanbaird-ice" + "jordanbaird-ice@beta" ]; }) (lib.mkIf config.custom.brew.contexts { @@ -382,5 +384,10 @@ "hammerspoon" ]; }) + (lib.mkIf config.custom.brew.aerospace { + homebrew.casks = [ + "aerospace" + ]; + }) ]; } diff --git a/flake.lock b/flake.lock index 6e0f8e6..a522a29 100644 --- a/flake.lock +++ b/flake.lock @@ -1,5 +1,24 @@ { "nodes": { + "aerospace-scratchpad": { + "inputs": { + "nixpkgs": "nixpkgs", + "utils": "utils" + }, + "locked": { + "lastModified": 1764407814, + "narHash": "sha256-IiOWUqodFqzy4PhU6LcziwoJbbFR0AfaOBJDO83/mHM=", + "owner": "cristianoliveira", + "repo": "aerospace-scratchpad", + "rev": "d039cd49e2a15144c9a766509abe1b7f59eb6b04", + "type": "github" + }, + "original": { + "owner": "cristianoliveira", + "repo": "aerospace-scratchpad", + "type": "github" + } + }, "brew-src": { "flake": false, "locked": { @@ -103,7 +122,7 @@ }, "flake-utils": { "inputs": { - "systems": "systems" + "systems": "systems_2" }, "locked": { "lastModified": 1731533236, @@ -141,7 +160,7 @@ }, "flake-utils_3": { "inputs": { - "systems": "systems_3" + "systems": "systems_4" }, "locked": { "lastModified": 1731533236, @@ -161,7 +180,7 @@ "inputs": { "flake-compat": "flake-compat", "flake-utils": "flake-utils", - "nixpkgs": "nixpkgs", + "nixpkgs": "nixpkgs_2", "zig": "zig", "zon2nix": "zon2nix" }, @@ -343,6 +362,22 @@ "type": "github" } }, + "homebrew-nikitabobko": { + "flake": false, + "locked": { + "lastModified": 1764022179, + "narHash": "sha256-OQJ6Wx6Pi61uu46I7xaHpeiTavDQp1ZLVbHJGR1NL20=", + "owner": "nikitabobko", + "repo": "homebrew-tap", + "rev": "80dfd269edca8bc2ec5d83dbd332863cf684f753", + "type": "github" + }, + "original": { + "owner": "nikitabobko", + "repo": "homebrew-tap", + "type": "github" + } + }, "homebrew-valgrind": { "flake": false, "locked": { @@ -364,8 +399,8 @@ "cl-nix-lite": "cl-nix-lite", "flake-compat": "flake-compat_3", "flake-utils": "flake-utils_2", - "nixpkgs": "nixpkgs_3", - "systems": "systems_2", + "nixpkgs": "nixpkgs_4", + "systems": "systems_3", "treefmt-nix": "treefmt-nix" }, "locked": { @@ -459,20 +494,22 @@ }, "nixpkgs": { "locked": { - "lastModified": 315532800, - "narHash": "sha256-sV6pJNzFkiPc6j9Bi9JuHBnWdVhtKB/mHgVmMPvDFlk=", - "rev": "82c2e0d6dde50b17ae366d2aa36f224dc19af469", - "type": "tarball", - "url": "https://releases.nixos.org/nixpkgs/nixpkgs-25.11pre877938.82c2e0d6dde5/nixexprs.tar.xz" + "lastModified": 1747762468, + "narHash": "sha256-I8l6r639PrDpEpAFgY64GmuQ+4NK+nxqAoSUnAEKw9E=", + "owner": "NixOS", + "repo": "nixpkgs", + "rev": "6bd7ba77ef6015853d67a89bd59f01b2880e9050", + "type": "github" }, "original": { - "type": "tarball", - "url": "https://channels.nixos.org/nixpkgs-unstable/nixexprs.tar.xz" + "owner": "NixOS", + "repo": "nixpkgs", + "type": "github" } }, "nixpkgs-firefox-darwin": { "inputs": { - "nixpkgs": "nixpkgs_6" + "nixpkgs": "nixpkgs_7" }, "locked": { "lastModified": 1764291786, @@ -489,6 +526,19 @@ } }, "nixpkgs_2": { + "locked": { + "lastModified": 315532800, + "narHash": "sha256-sV6pJNzFkiPc6j9Bi9JuHBnWdVhtKB/mHgVmMPvDFlk=", + "rev": "82c2e0d6dde50b17ae366d2aa36f224dc19af469", + "type": "tarball", + "url": "https://releases.nixos.org/nixpkgs/nixpkgs-25.11pre877938.82c2e0d6dde5/nixexprs.tar.xz" + }, + "original": { + "type": "tarball", + "url": "https://channels.nixos.org/nixpkgs-unstable/nixexprs.tar.xz" + } + }, + "nixpkgs_3": { "locked": { "lastModified": 1758360447, "narHash": "sha256-XDY3A83bclygHDtesRoaRTafUd80Q30D/Daf9KSG6bs=", @@ -501,7 +551,7 @@ "url": "https://channels.nixos.org/nixos-unstable/nixexprs.tar.xz" } }, - "nixpkgs_3": { + "nixpkgs_4": { "locked": { "lastModified": 1732617236, "narHash": "sha256-PYkz6U0bSEaEB1al7O1XsqVNeSNS+s3NVclJw7YC43w=", @@ -517,7 +567,7 @@ "type": "github" } }, - "nixpkgs_4": { + "nixpkgs_5": { "locked": { "lastModified": 1754340878, "narHash": "sha256-lgmUyVQL9tSnvvIvBp7x1euhkkCho7n3TMzgjdvgPoU=", @@ -533,7 +583,7 @@ "type": "github" } }, - "nixpkgs_5": { + "nixpkgs_6": { "locked": { "lastModified": 1764242076, "narHash": "sha256-sKoIWfnijJ0+9e4wRvIgm/HgE27bzwQxcEmo2J/gNpI=", @@ -549,7 +599,7 @@ "type": "github" } }, - "nixpkgs_6": { + "nixpkgs_7": { "locked": { "lastModified": 1746683680, "narHash": "sha256-+5zk+UbG0+GQlKt+gIKm+OhlYvHmkAHFXvf7hl1HDeM=", @@ -565,7 +615,7 @@ "type": "github" } }, - "nixpkgs_7": { + "nixpkgs_8": { "locked": { "lastModified": 1763806073, "narHash": "sha256-FHsEKDvfWpzdADWj99z7vBk4D716Ujdyveo5+A048aI=", @@ -583,6 +633,7 @@ }, "root": { "inputs": { + "aerospace-scratchpad": "aerospace-scratchpad", "disko": "disko", "ghostty": "ghostty", "git-hooks": "git-hooks", @@ -592,13 +643,14 @@ "homebrew-core": "homebrew-core", "homebrew-createzap": "homebrew-createzap", "homebrew-emacs-plus": "homebrew-emacs-plus", + "homebrew-nikitabobko": "homebrew-nikitabobko", "homebrew-valgrind": "homebrew-valgrind", "mac-app-util": "mac-app-util", "nix-darwin": "nix-darwin", "nix-homebrew": "nix-homebrew", "nix-index-database": "nix-index-database", "nixos-hardware": "nixos-hardware", - "nixpkgs": "nixpkgs_5", + "nixpkgs": "nixpkgs_6", "nixpkgs-firefox-darwin": "nixpkgs-firefox-darwin", "sops-nix": "sops-nix", "treefmt-nix": "treefmt-nix_2", @@ -663,6 +715,21 @@ } }, "systems_2": { + "locked": { + "lastModified": 1681028828, + "narHash": "sha256-Vy1rq5AaRuLzOxct8nz4T6wlgyUR7zLU309k9mBC768=", + "owner": "nix-systems", + "repo": "default", + "rev": "da67096a3b9bf56a91d16901293e51ba5b49a27e", + "type": "github" + }, + "original": { + "owner": "nix-systems", + "repo": "default", + "type": "github" + } + }, + "systems_3": { "locked": { "lastModified": 1689347925, "narHash": "sha256-ozenz5bFe1UUqOn7f60HRmgc01BgTGIKZ4Xl+HbocGQ=", @@ -677,7 +744,7 @@ "type": "github" } }, - "systems_3": { + "systems_4": { "locked": { "lastModified": 1681028828, "narHash": "sha256-Vy1rq5AaRuLzOxct8nz4T6wlgyUR7zLU309k9mBC768=", @@ -694,7 +761,7 @@ }, "treefmt-nix": { "inputs": { - "nixpkgs": "nixpkgs_4" + "nixpkgs": "nixpkgs_5" }, "locked": { "lastModified": 1755934250, @@ -730,10 +797,28 @@ "type": "github" } }, + "utils": { + "inputs": { + "systems": "systems" + }, + "locked": { + "lastModified": 1731533236, + "narHash": "sha256-l0KFg5HjrsfsO/JpG+r7fRrqm12kzFHyUHqHCVpMMbI=", + "owner": "numtide", + "repo": "flake-utils", + "rev": "11707dc2f618dd54ca8739b309ec4fc024de578b", + "type": "github" + }, + "original": { + "owner": "numtide", + "repo": "flake-utils", + "type": "github" + } + }, "yazi": { "inputs": { "flake-utils": "flake-utils_3", - "nixpkgs": "nixpkgs_7", + "nixpkgs": "nixpkgs_8", "rust-overlay": "rust-overlay" }, "locked": { @@ -802,7 +887,7 @@ }, "zon2nix": { "inputs": { - "nixpkgs": "nixpkgs_2" + "nixpkgs": "nixpkgs_3" }, "locked": { "lastModified": 1758405547, diff --git a/flake.nix b/flake.nix index 983b31b..fbe1abd 100644 --- a/flake.nix +++ b/flake.nix @@ -40,8 +40,11 @@ homebrew-brewsci-bio.flake = false; homebrew-valgrind.url = "github:LouisBrunner/homebrew-valgrind"; homebrew-valgrind.flake = false; + homebrew-nikitabobko.url = "github:nikitabobko/homebrew-tap"; + homebrew-nikitabobko.flake = false; # tools + aerospace-scratchpad.url = "github:cristianoliveira/aerospace-scratchpad"; yazi.url = "github:sxyazi/yazi"; }; diff --git a/hosts/dango/default.nix b/hosts/dango/default.nix index 1ff14f3..7e89de2 100644 --- a/hosts/dango/default.nix +++ b/hosts/dango/default.nix @@ -5,10 +5,10 @@ { custom = { gui = { - aerospace.enable = false; + aerospace.enable = true; sketchybar.enable = true; jankyborders.enable = true; - yabai.enable = true; + yabai.enable = false; }; brew = { zen-browser = false; @@ -64,6 +64,7 @@ marta = true; valgrind = true; hammerspoon = true; + aerospace = true; }; };