├── .gitignore ├── nvim └── .config │ └── nvim │ ├── .gitignore │ ├── stylua.toml │ ├── .editorconfig │ ├── lua │ └── daneharnett │ │ ├── comment.lua │ │ ├── airline.lua │ │ ├── colorizer.lua │ │ ├── blamer.lua │ │ ├── tests.lua │ │ ├── trouble.lua │ │ ├── autopairs.lua │ │ ├── autosession.lua │ │ ├── buffers.lua │ │ ├── arrowkeys.lua │ │ ├── pre-plugins.lua │ │ ├── catppuccin.lua │ │ ├── lualine.lua │ │ ├── diagnostics.lua │ │ ├── biscuits.lua │ │ ├── bufferline.lua │ │ ├── init.lua │ │ ├── yank.lua │ │ ├── diagnosticls.lua │ │ ├── navigation.lua │ │ ├── editing.lua │ │ ├── panel.lua │ │ ├── efmls.lua │ │ ├── better-ts-errors.lua │ │ ├── options.lua │ │ ├── linting.lua │ │ ├── toggleterm.lua │ │ ├── formatting.lua │ │ ├── utils.lua │ │ ├── gitsigns.lua │ │ ├── treesitter.lua │ │ ├── lspsaga.lua │ │ ├── spectre.lua │ │ ├── nvim-tree.lua │ │ ├── command-palette.lua │ │ ├── null-ls.lua │ │ ├── telescope-fused-layout.lua │ │ ├── lsp.lua │ │ ├── telescope.lua │ │ └── plugins.lua │ ├── .luarc.json │ ├── TODO.md │ ├── init.lua │ └── lazy-lock.json ├── nvm └── .config │ └── nvm │ └── nvm.sh ├── utils ├── measure-zsh-startup └── delete-nvim-user-data-and-cache.sh ├── .editorconfig ├── borders └── .config │ └── borders │ └── bordersrc ├── install ├── uninstall ├── aerospace └── .config │ └── aerospace │ ├── scripts │ └── open-app-in-fullscreen.sh │ └── aerospace.toml ├── nix ├── README.md └── .config │ └── nix │ ├── modules │ ├── fd │ │ └── default.nix │ ├── eza │ │ └── default.nix │ ├── fnm │ │ └── default.nix │ ├── fzf │ │ └── default.nix │ ├── stow │ │ └── default.nix │ ├── wget │ │ └── default.nix │ ├── cargo │ │ └── default.nix │ ├── slack │ │ └── default.nix │ ├── neovim │ │ └── default.nix │ ├── vscode │ │ └── default.nix │ ├── zoxide │ │ └── default.nix │ ├── discord │ │ └── default.nix │ ├── raycast │ │ └── default.nix │ ├── ripgrep │ │ └── default.nix │ ├── antidote │ │ └── default.nix │ ├── carapace │ │ └── default.nix │ ├── obs │ │ └── default.nix │ ├── vlc │ │ └── default.nix │ ├── oh-my-posh │ │ └── default.nix │ ├── util-linux │ │ └── default.nix │ ├── yt-dlp │ │ └── default.nix │ ├── gnu-sed │ │ └── default.nix │ ├── there │ │ └── default.nix │ ├── bitwarden │ │ └── default.nix │ ├── nix-tools │ │ └── default.nix │ ├── leader-key │ │ └── default.nix │ ├── fx-cast-bridge │ │ └── default.nix │ ├── helium-browser │ │ └── default.nix │ ├── wezterm │ │ └── default.nix │ ├── aerospace │ │ └── default.nix │ ├── font-jetbrains-mono-nerd-font │ │ └── default.nix │ ├── borders │ │ └── default.nix │ └── sketchybar │ │ └── default.nix │ ├── hosts │ ├── personal-i9mbp.nix │ └── personal-m4mbp.nix │ ├── home │ └── dane │ │ ├── personal-i9mbp.nix │ │ └── personal-m4mbp.nix │ ├── flake.lock │ └── flake.nix ├── fzf └── .fzf.zsh ├── tmux └── .tmux.conf ├── nix-install.txt ├── zsh ├── .zsh_plugins.txt └── .zshrc ├── wezterm └── .config │ └── wezterm │ └── wezterm.lua ├── README.md ├── leader-key └── .config │ └── leader-key │ └── config.json ├── setup-install ├── scripts └── helium-focus-or-open ├── healthcheck └── oh-my-posh └── .config └── oh-my-posh └── default.toml /.gitignore: -------------------------------------------------------------------------------- 1 | **/.DS_Store 2 | -------------------------------------------------------------------------------- /nvim/.config/nvim/.gitignore: -------------------------------------------------------------------------------- 1 | undodir 2 | -------------------------------------------------------------------------------- /nvim/.config/nvim/stylua.toml: -------------------------------------------------------------------------------- 1 | indent_type = "Spaces" 2 | -------------------------------------------------------------------------------- /nvim/.config/nvim/.editorconfig: -------------------------------------------------------------------------------- 1 | [*] 2 | indent_size = 4 3 | -------------------------------------------------------------------------------- /nvm/.config/nvm/nvm.sh: -------------------------------------------------------------------------------- 1 | #!/bin/zsh 2 | 3 | nvm() { 4 | fnm $@ 5 | } 6 | 7 | -------------------------------------------------------------------------------- /utils/measure-zsh-startup: -------------------------------------------------------------------------------- 1 | #!/bin/zsh 2 | 3 | for run in {1..5}; do 4 | time zsh --interactive -c exit 5 | done 6 | -------------------------------------------------------------------------------- /utils/delete-nvim-user-data-and-cache.sh: -------------------------------------------------------------------------------- 1 | #!/bin/zsh 2 | 3 | rm -rf $HOME/.local/share/nvim/* 4 | rm -rf $HOME/.cache/nvim/* 5 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/comment.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | require("Comment").setup() 5 | end 6 | 7 | return M 8 | -------------------------------------------------------------------------------- /nvim/.config/nvim/.luarc.json: -------------------------------------------------------------------------------- 1 | { 2 | "Lua": { 3 | "runtime.version": "LuaJIT", 4 | "workspace.checkThirdParty": false 5 | } 6 | } 7 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/airline.lua: -------------------------------------------------------------------------------- 1 | vim.g.airline_powerline_fonts = 1 2 | vim.g.airline_section_y = "" 3 | vim.g.airline_skip_empty_sections = 1 4 | -------------------------------------------------------------------------------- /nvim/.config/nvim/TODO.md: -------------------------------------------------------------------------------- 1 | # To do 2 | 3 | [x] Bufferline: Fix colors of icons in background tabs 4 | [x] Project navigation: Learn how to replicate the search panel (Find in folder, list of matches, etc) 5 | -------------------------------------------------------------------------------- /.editorconfig: -------------------------------------------------------------------------------- 1 | root = true 2 | 3 | [*] 4 | end_of_line = LF 5 | charset = utf-8 6 | trim_trailing_whitespace = true 7 | insert_final_newline = true 8 | indent_style = space 9 | indent_size = 2 10 | 11 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/colorizer.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | require("colorizer").setup({ 5 | typescriptreact = { css = true }, 6 | }) 7 | end 8 | 9 | return M 10 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/blamer.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local utils = require("daneharnett.utils") 5 | utils.keymap("n", "bt", "BlamerToggle") 6 | end 7 | 8 | return M 9 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/tests.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local utils = require("daneharnett.utils") 5 | utils.keymap("n", "tf", ":TestFile", "[T]est [f]ile") 6 | end 7 | 8 | return M 9 | -------------------------------------------------------------------------------- /borders/.config/borders/bordersrc: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | options=( 4 | style=round 5 | width=6.0 6 | hidpi=on 7 | active_color=0xffe2e2e3 8 | inactive_color=0xff414550 9 | blacklist="Loom,iPhone Mirroring" 10 | ) 11 | 12 | borders "${options[@]}" 13 | -------------------------------------------------------------------------------- /install: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | stow --target=$HOME aerospace 4 | stow --target=$HOME borders 5 | stow --target=$HOME fzf 6 | stow --target=$HOME nvim 7 | stow --target=$HOME nvm 8 | stow --target=$HOME tmux 9 | stow --target=$HOME wezterm 10 | stow --target=$HOME zsh 11 | -------------------------------------------------------------------------------- /uninstall: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | stow --delete --target=$HOME borders 4 | stow --delete --target=$HOME fzf 5 | stow --delete --target=$HOME nvim 6 | stow --delete --target=$HOME nvm 7 | stow --delete --target=$HOME tmux 8 | stow --delete --target=$HOME wezterm 9 | stow --delete --target=$HOME zsh 10 | -------------------------------------------------------------------------------- /aerospace/.config/aerospace/scripts/open-app-in-fullscreen.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | osascript <gr", "Trouble lsp_references") 10 | end 11 | 12 | return M 13 | -------------------------------------------------------------------------------- /nix/README.md: -------------------------------------------------------------------------------- 1 | # Nix configuration 2 | 3 | ## Usage 4 | 5 | Install nix and nix darwin 6 | TODO: document these commands 7 | 8 | ## How to apply configuration 9 | 10 | Run `darwin-rebuild switch --flake "$(readlink -f ~/.config/nix)#personal-m4mbp"` 11 | 12 | ## How to update 13 | 14 | From repo root: `cd nix/.config/nix` 15 | Run `nix flake update` 16 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/autopairs.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local autopairs_status_ok, autopairs = pcall(require, "nvim-autopairs") 5 | if not autopairs_status_ok then 6 | return 7 | end 8 | autopairs.setup({ 9 | check_ts = true, 10 | fast_wrap = {}, 11 | }) 12 | end 13 | 14 | return M 15 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/fd/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | pkgs, 5 | ... 6 | }: let 7 | cfg = config.fd; 8 | in { 9 | options = { 10 | fd = { 11 | enable = lib.mkEnableOption "Enable fd"; 12 | }; 13 | }; 14 | 15 | config = lib.mkIf cfg.enable { 16 | environment.systemPackages = [ 17 | pkgs.fd 18 | ]; 19 | }; 20 | } 21 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/autosession.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local autosession_status_ok, autosession = pcall(require, "auto-session") 5 | if not autosession_status_ok then 6 | return 7 | end 8 | 9 | autosession.setup({ 10 | pre_save_cmds = { "tabdo NvimTreeClose" }, 11 | }) 12 | end 13 | 14 | return M 15 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/eza/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | pkgs, 5 | ... 6 | }: let 7 | cfg = config.eza; 8 | in { 9 | options = { 10 | eza = { 11 | enable = lib.mkEnableOption "Enable eza"; 12 | }; 13 | }; 14 | 15 | config = lib.mkIf cfg.enable { 16 | environment.systemPackages = [ 17 | pkgs.eza 18 | ]; 19 | }; 20 | } 21 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/fnm/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | pkgs, 5 | ... 6 | }: let 7 | cfg = config.fnm; 8 | in { 9 | options = { 10 | fnm = { 11 | enable = lib.mkEnableOption "Enable fnm"; 12 | }; 13 | }; 14 | 15 | config = lib.mkIf cfg.enable { 16 | environment.systemPackages = [ 17 | pkgs.fnm 18 | ]; 19 | }; 20 | } 21 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/fzf/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | pkgs, 5 | ... 6 | }: let 7 | cfg = config.fzf; 8 | in { 9 | options = { 10 | fzf = { 11 | enable = lib.mkEnableOption "Enable fzf"; 12 | }; 13 | }; 14 | 15 | config = lib.mkIf cfg.enable { 16 | environment.systemPackages = [ 17 | pkgs.fzf 18 | ]; 19 | }; 20 | } 21 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/buffers.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | vim.api.nvim_create_user_command("CopyRelativePath", function() 5 | local path = vim.fn.fnamemodify(vim.fn.expand("%"), ":.") 6 | vim.fn.setreg("+", path) 7 | vim.notify('Copied "' .. path .. '" to the clipboard') 8 | end, {}) 9 | end 10 | 11 | return M 12 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/stow/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | pkgs, 5 | ... 6 | }: let 7 | cfg = config.stow; 8 | in { 9 | options = { 10 | stow = { 11 | enable = lib.mkEnableOption "Enable stow"; 12 | }; 13 | }; 14 | 15 | config = lib.mkIf cfg.enable { 16 | environment.systemPackages = [ 17 | pkgs.stow 18 | ]; 19 | }; 20 | } 21 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/wget/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | pkgs, 5 | ... 6 | }: let 7 | cfg = config.wget; 8 | in { 9 | options = { 10 | wget = { 11 | enable = lib.mkEnableOption "Enable wget"; 12 | }; 13 | }; 14 | 15 | config = lib.mkIf cfg.enable { 16 | environment.systemPackages = [ 17 | pkgs.wget 18 | ]; 19 | }; 20 | } 21 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/arrowkeys.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local utils = require("daneharnett.utils") 5 | 6 | -- disable the arrow keys 7 | utils.keymap("", "", "") 8 | utils.keymap("", "", "") 9 | utils.keymap("", "", "") 10 | utils.keymap("", "", "") 11 | end 12 | 13 | return M 14 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/cargo/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | pkgs, 5 | ... 6 | }: let 7 | cfg = config.cargo; 8 | in { 9 | options = { 10 | cargo = { 11 | enable = lib.mkEnableOption "Enable cargo"; 12 | }; 13 | }; 14 | 15 | config = lib.mkIf cfg.enable { 16 | environment.systemPackages = [ 17 | pkgs.cargo 18 | ]; 19 | }; 20 | } 21 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/slack/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | pkgs, 5 | ... 6 | }: let 7 | cfg = config.slack; 8 | in { 9 | options = { 10 | slack = { 11 | enable = lib.mkEnableOption "Enable slack"; 12 | }; 13 | }; 14 | 15 | config = lib.mkIf cfg.enable { 16 | environment.systemPackages = [ 17 | pkgs.slack 18 | ]; 19 | }; 20 | } 21 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/neovim/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | pkgs, 5 | ... 6 | }: let 7 | cfg = config.neovim; 8 | in { 9 | options = { 10 | neovim = { 11 | enable = lib.mkEnableOption "Enable neovim"; 12 | }; 13 | }; 14 | 15 | config = lib.mkIf cfg.enable { 16 | environment.systemPackages = [ 17 | pkgs.neovim 18 | ]; 19 | }; 20 | } 21 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/vscode/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | pkgs, 5 | ... 6 | }: let 7 | cfg = config.vscode; 8 | in { 9 | options = { 10 | vscode = { 11 | enable = lib.mkEnableOption "Enable vscode"; 12 | }; 13 | }; 14 | 15 | config = lib.mkIf cfg.enable { 16 | environment.systemPackages = [ 17 | pkgs.vscode 18 | ]; 19 | }; 20 | } 21 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/zoxide/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | pkgs, 5 | ... 6 | }: let 7 | cfg = config.zoxide; 8 | in { 9 | options = { 10 | zoxide = { 11 | enable = lib.mkEnableOption "Enable zoxide"; 12 | }; 13 | }; 14 | 15 | config = lib.mkIf cfg.enable { 16 | environment.systemPackages = [ 17 | pkgs.zoxide 18 | ]; 19 | }; 20 | } 21 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/discord/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | pkgs, 5 | ... 6 | }: let 7 | cfg = config.discord; 8 | in { 9 | options = { 10 | discord = { 11 | enable = lib.mkEnableOption "Enable discord"; 12 | }; 13 | }; 14 | 15 | config = lib.mkIf cfg.enable { 16 | environment.systemPackages = [ 17 | pkgs.discord 18 | ]; 19 | }; 20 | } 21 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/raycast/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | pkgs, 5 | ... 6 | }: let 7 | cfg = config.raycast; 8 | in { 9 | options = { 10 | raycast = { 11 | enable = lib.mkEnableOption "Enable raycast"; 12 | }; 13 | }; 14 | 15 | config = lib.mkIf cfg.enable { 16 | environment.systemPackages = [ 17 | pkgs.raycast 18 | ]; 19 | }; 20 | } 21 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/ripgrep/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | pkgs, 5 | ... 6 | }: let 7 | cfg = config.ripgrep; 8 | in { 9 | options = { 10 | ripgrep = { 11 | enable = lib.mkEnableOption "Enable ripgrep"; 12 | }; 13 | }; 14 | 15 | config = lib.mkIf cfg.enable { 16 | environment.systemPackages = [ 17 | pkgs.ripgrep 18 | ]; 19 | }; 20 | } 21 | -------------------------------------------------------------------------------- /fzf/.fzf.zsh: -------------------------------------------------------------------------------- 1 | # Setup fzf 2 | BREW_PREFIX=$(brew --prefix) 3 | # --------- 4 | if [[ ! "$PATH" == *$BREW_PREFIX/opt/fzf/bin* ]]; then 5 | PATH="${PATH:+${PATH}:}$BREW_PREFIX/opt/fzf/bin" 6 | fi 7 | 8 | # Auto-completion 9 | # --------------- 10 | source "$BREW_PREFIX/opt/fzf/shell/completion.zsh" 11 | 12 | # Key bindings 13 | # ------------ 14 | source "$BREW_PREFIX/opt/fzf/shell/key-bindings.zsh" 15 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/antidote/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | pkgs, 5 | ... 6 | }: let 7 | cfg = config.antidote; 8 | in { 9 | options = { 10 | antidote = { 11 | enable = lib.mkEnableOption "Enable antidote"; 12 | }; 13 | }; 14 | 15 | config = lib.mkIf cfg.enable { 16 | environment.systemPackages = [ 17 | pkgs.antidote 18 | ]; 19 | }; 20 | } 21 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/carapace/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | pkgs, 5 | ... 6 | }: let 7 | cfg = config.carapace; 8 | in { 9 | options = { 10 | carapace = { 11 | enable = lib.mkEnableOption "Enable carapace"; 12 | }; 13 | }; 14 | 15 | config = lib.mkIf cfg.enable { 16 | environment.systemPackages = [ 17 | pkgs.carapace 18 | ]; 19 | }; 20 | } 21 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/obs/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | ... 5 | }: let 6 | cfg = config.obs; 7 | in { 8 | options = { 9 | obs = { 10 | enable = lib.mkEnableOption "Enable obs"; 11 | }; 12 | }; 13 | 14 | config = lib.mkIf cfg.enable { 15 | homebrew = { 16 | enable = true; 17 | casks = [ 18 | "obs" 19 | ]; 20 | }; 21 | }; 22 | } 23 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/vlc/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | ... 5 | }: let 6 | cfg = config.vlc; 7 | in { 8 | options = { 9 | vlc = { 10 | enable = lib.mkEnableOption "Enable vlc"; 11 | }; 12 | }; 13 | 14 | config = lib.mkIf cfg.enable { 15 | homebrew = { 16 | enable = true; 17 | casks = [ 18 | "vlc" 19 | ]; 20 | }; 21 | }; 22 | } 23 | -------------------------------------------------------------------------------- /nvim/.config/nvim/init.lua: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------- 2 | -- config inspired by: 3 | -- https://bryankegley.me/posts/nvim-getting-started/ 4 | -- https://www.chrisatmachine.com/ 5 | -- https://www.youtube.com/@teej_dv / https://www.twitch.tv/teej_dv 6 | -- and many others, thank you! 7 | -------------------------------------------------------------- 8 | require("daneharnett") 9 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/pre-plugins.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | -- all of these settings need to be set before the plugins are loaded 5 | 6 | vim.g.mapleader = " " 7 | 8 | -- disable netrw (strongly advised by nvim-tree) 9 | vim.g.loaded_netrw = 1 10 | vim.g.loaded_netrwPlugin = 1 11 | 12 | vim.opt.termguicolors = true 13 | end 14 | 15 | return M 16 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/oh-my-posh/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | pkgs, 5 | ... 6 | }: let 7 | cfg = config.oh-my-posh; 8 | in { 9 | options = { 10 | oh-my-posh = { 11 | enable = lib.mkEnableOption "Enable oh-my-posh"; 12 | }; 13 | }; 14 | 15 | config = lib.mkIf cfg.enable { 16 | environment.systemPackages = [ 17 | pkgs.oh-my-posh 18 | ]; 19 | }; 20 | } 21 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/util-linux/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | pkgs, 5 | ... 6 | }: let 7 | cfg = config.util-linux; 8 | in { 9 | options = { 10 | util-linux = { 11 | enable = lib.mkEnableOption "Enable util-linux"; 12 | }; 13 | }; 14 | 15 | config = lib.mkIf cfg.enable { 16 | environment.systemPackages = [ 17 | pkgs.util-linux 18 | ]; 19 | }; 20 | } 21 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/yt-dlp/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | ... 5 | }: let 6 | cfg = config.yt-dlp; 7 | in { 8 | options = { 9 | yt-dlp = { 10 | enable = lib.mkEnableOption "Enable yt-dlp"; 11 | }; 12 | }; 13 | 14 | config = lib.mkIf cfg.enable { 15 | homebrew = { 16 | enable = true; 17 | brews = [ 18 | "yt-dlp" 19 | ]; 20 | }; 21 | }; 22 | } 23 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/gnu-sed/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | ... 5 | }: let 6 | cfg = config.gnu-sed; 7 | in { 8 | options = { 9 | gnu-sed = { 10 | enable = lib.mkEnableOption "Enable gnu-sed"; 11 | }; 12 | }; 13 | 14 | config = lib.mkIf cfg.enable { 15 | homebrew = { 16 | enable = true; 17 | brews = [ 18 | "gnu-sed" 19 | ]; 20 | }; 21 | }; 22 | } 23 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/there/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | ... 5 | }: 6 | let 7 | cfg = config.there; 8 | in 9 | { 10 | options = { 11 | there = { 12 | enable = lib.mkEnableOption "Enable there"; 13 | }; 14 | }; 15 | 16 | config = lib.mkIf cfg.enable { 17 | homebrew = { 18 | enable = true; 19 | casks = [ 20 | "there" 21 | ]; 22 | }; 23 | }; 24 | } 25 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/catppuccin.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local catppuccin_status_ok, catppuccin = pcall(require, "catppuccin") 5 | if not catppuccin_status_ok then 6 | return 7 | end 8 | 9 | vim.g.catppuccin_flavour = "mocha" -- latte, frappe, macchiato, mocha 10 | catppuccin.setup() 11 | vim.cmd("colorscheme catppuccin") 12 | end 13 | 14 | return M 15 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/lualine.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local lualine_status_ok, lualine = pcall(require, "lualine") 5 | if not lualine_status_ok then 6 | return 7 | end 8 | 9 | lualine.setup({ 10 | options = { 11 | disabled_filetypes = { 12 | "NvimTree", 13 | }, 14 | }, 15 | }) 16 | end 17 | 18 | return M 19 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/bitwarden/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | ... 5 | }: let 6 | cfg = config.bitwarden; 7 | in { 8 | options = { 9 | bitwarden = { 10 | enable = lib.mkEnableOption "Enable bitwarden"; 11 | }; 12 | }; 13 | 14 | config = lib.mkIf cfg.enable { 15 | homebrew = { 16 | enable = true; 17 | casks = [ 18 | "bitwarden" 19 | ]; 20 | }; 21 | }; 22 | } 23 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/nix-tools/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | pkgs, 5 | ... 6 | }: let 7 | cfg = config.nix-tools; 8 | in { 9 | options = { 10 | nix-tools = { 11 | enable = lib.mkEnableOption "Enable nix-tools"; 12 | }; 13 | }; 14 | 15 | config = lib.mkIf cfg.enable { 16 | environment.systemPackages = [ 17 | pkgs.nixfmt 18 | pkgs.nixpkgs-fmt 19 | ]; 20 | }; 21 | } 22 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/leader-key/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | ... 5 | }: 6 | let 7 | cfg = config.leader-key; 8 | in 9 | { 10 | options = { 11 | leader-key = { 12 | enable = lib.mkEnableOption "Enable leader-key"; 13 | }; 14 | }; 15 | 16 | config = lib.mkIf cfg.enable { 17 | homebrew = { 18 | enable = true; 19 | casks = [ 20 | "leader-key" 21 | ]; 22 | }; 23 | }; 24 | } 25 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/fx-cast-bridge/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | ... 5 | }: let 6 | cfg = config.fx-cast-bridge; 7 | in { 8 | options = { 9 | fx-cast-bridge = { 10 | enable = lib.mkEnableOption "Enable fx-cast-bridge"; 11 | }; 12 | }; 13 | 14 | config = lib.mkIf cfg.enable { 15 | homebrew = { 16 | enable = true; 17 | casks = [ 18 | "fx-cast-bridge" 19 | ]; 20 | }; 21 | }; 22 | } 23 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/helium-browser/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | ... 5 | }: 6 | let 7 | cfg = config.helium-browser; 8 | in 9 | { 10 | options = { 11 | helium-browser = { 12 | enable = lib.mkEnableOption "Enable helium-browser"; 13 | }; 14 | }; 15 | 16 | config = lib.mkIf cfg.enable { 17 | homebrew = { 18 | enable = true; 19 | casks = [ 20 | "helium-browser" 21 | ]; 22 | }; 23 | }; 24 | } 25 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/diagnostics.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | -- Exclude this from vscode 5 | if vim.g.vscode then 6 | return 7 | end 8 | 9 | -- configure diagnostics 10 | -- don't try to put this in the lsp on_attach because it causes both folds and 11 | -- blamer virtual text to break. 12 | vim.g.diagnostic_enable_virtual_text = 1 13 | vim.g.diagnostic_insert_delay = 1 14 | end 15 | 16 | return M 17 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/wezterm/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | ... 5 | }: let 6 | cfg = config.wezterm; 7 | in { 8 | options = { 9 | wezterm = { 10 | enable = lib.mkEnableOption "Enable wezterm"; 11 | }; 12 | }; 13 | 14 | config = lib.mkIf cfg.enable { 15 | homebrew = { 16 | enable = true; 17 | casks = [ 18 | "wez/wezterm/wezterm" 19 | ]; 20 | taps = [ 21 | "wez/wezterm" 22 | ]; 23 | }; 24 | }; 25 | } 26 | -------------------------------------------------------------------------------- /tmux/.tmux.conf: -------------------------------------------------------------------------------- 1 | set -g default-terminal "screen.xterm-256color" 2 | 3 | set -g @plugin 'catppuccin/tmux' 4 | set -g @plugin 'tmux-plugins/tpm' 5 | 6 | # vim-like pane switching 7 | bind -r k select-pane -U 8 | bind -r j select-pane -D 9 | bind -r h select-pane -L 10 | bind -r l select-pane -R 11 | 12 | #set -g status-style fg=black,bg=#89ddff 13 | #set -g status-right "" 14 | 15 | # Initialize TMUX plugin manager (keep this line at the very bottom of tmux.conf) 16 | run '~/.tmux/plugins/tpm/tpm' 17 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/aerospace/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | ... 5 | }: let 6 | cfg = config.aerospace; 7 | in { 8 | options = { 9 | aerospace = { 10 | enable = lib.mkEnableOption "Enable aerospace"; 11 | }; 12 | }; 13 | 14 | config = lib.mkIf cfg.enable { 15 | homebrew = { 16 | enable = true; 17 | casks = [ 18 | "nikitabobko/tap/aerospace" 19 | ]; 20 | taps = [ 21 | "nikitabobko/tap" 22 | ]; 23 | }; 24 | }; 25 | } 26 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/font-jetbrains-mono-nerd-font/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | ... 5 | }: let 6 | cfg = config.font-jetbrains-mono-nerd-font; 7 | in { 8 | options = { 9 | font-jetbrains-mono-nerd-font = { 10 | enable = lib.mkEnableOption "Enable font-jetbrains-mono-nerd-font"; 11 | }; 12 | }; 13 | 14 | config = lib.mkIf cfg.enable { 15 | homebrew = { 16 | enable = true; 17 | casks = [ 18 | "font-jetbrains-mono-nerd-font" 19 | ]; 20 | }; 21 | }; 22 | } 23 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/borders/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | ... 5 | }: let 6 | cfg = config.borders; 7 | in { 8 | options = { 9 | borders = { 10 | enable = lib.mkEnableOption "Enable borders"; 11 | }; 12 | }; 13 | 14 | config = lib.mkIf cfg.enable { 15 | homebrew = { 16 | enable = true; 17 | brews = [ 18 | { 19 | name = "FelixKratz/formulae/borders"; 20 | restart_service = true; 21 | } 22 | ]; 23 | taps = [ 24 | "FelixKratz/formulae" 25 | ]; 26 | }; 27 | }; 28 | } 29 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/biscuits.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local biscuits_status_ok, biscuits = pcall(require, "nvim-biscuits") 5 | if not biscuits_status_ok then 6 | return 7 | end 8 | biscuits.setup({ 9 | cursor_line_only = true, 10 | on_events = { 11 | "CursorHold", 12 | "CursorHoldI", 13 | "InsertLeave", 14 | }, 15 | language_config = { 16 | vimdoc = { 17 | disabled = true, 18 | }, 19 | }, 20 | }) 21 | end 22 | 23 | return M 24 | -------------------------------------------------------------------------------- /nix-install.txt: -------------------------------------------------------------------------------- 1 | How to setup computer to use nix+nix-darwin 2 | 3 | Install nix 4 | 5 | sh <(curl -L https://nixos.org/nix/install) 6 | 7 | 8 | 9 | 10 | Command to initialise a new flake 11 | 12 | nix flake init -t nix-darwin --extra-experimental-features "nix-command flakes" 13 | 14 | 15 | 16 | 17 | 18 | First time building flake 19 | 20 | nix run nix-darwin --extra-experimental-features "nix-command flakes" -- switch --flake "$(readlink -f ~/.config/nix)#personal-m4mbp" 21 | 22 | 23 | 24 | Rebuilding flake 25 | 26 | darwin-rebuild switch --flake "$(readlink -f ~/.config/nix)#personal-m4mbp" 27 | 28 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/bufferline.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local status_ok, bufferline = pcall(require, "bufferline") 5 | if not status_ok then 6 | return 7 | end 8 | 9 | bufferline.setup({ 10 | options = { 11 | max_name_length = 30, 12 | max_prefix_length = 30, 13 | tab_size = 21, 14 | offsets = { { filetype = "NvimTree", text = "", padding = 1 } }, 15 | show_buffer_close_icons = false, 16 | show_close_icon = false, 17 | enforce_regular_tabs = true, 18 | }, 19 | }) 20 | end 21 | 22 | return M 23 | -------------------------------------------------------------------------------- /zsh/.zsh_plugins.txt: -------------------------------------------------------------------------------- 1 | # .zsh_plugins.txt 2 | 3 | # INSTRUCTIONS 4 | # After changing this file run: 5 | # antidote bundle <~/.zsh_plugins.txt >~/.zsh_plugins.zsh 6 | 7 | # prompts: 8 | # with prompt plugins, remember to add this to your .zshrc: 9 | # `autoload -Uz promptinit && promptinit && prompt powerlevel10k` 10 | romkatv/powerlevel10k kind:fpath 11 | 12 | # other plugins: 13 | jimhester/per-directory-history 14 | mattmc3/zephyr path:plugins/completion 15 | zdharma-continuum/fast-syntax-highlighting kind:defer 16 | zsh-users/zsh-autosuggestions 17 | zsh-users/zsh-history-substring-search 18 | chrisands/zsh-yarn-completions 19 | chitoku-k/fzf-zsh-completions 20 | -------------------------------------------------------------------------------- /nix/.config/nix/modules/sketchybar/default.nix: -------------------------------------------------------------------------------- 1 | { 2 | config, 3 | lib, 4 | ... 5 | }: let 6 | cfg = config.sketchybar; 7 | in { 8 | options = { 9 | sketchybar = { 10 | enable = lib.mkEnableOption "Enable sketchybar"; 11 | }; 12 | }; 13 | 14 | config = lib.mkIf cfg.enable { 15 | homebrew = { 16 | enable = true; 17 | brews = [ 18 | { 19 | name = "FelixKratz/formulae/sketchybar"; 20 | restart_service = true; 21 | } 22 | ]; 23 | casks = [ 24 | "font-hasklug-nerd-font" 25 | ]; 26 | taps = [ 27 | "FelixKratz/formulae" 28 | ]; 29 | }; 30 | }; 31 | } 32 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/init.lua: -------------------------------------------------------------------------------- 1 | -- these settings need to be set before the plugins are loaded 2 | require("daneharnett.pre-plugins").init() 3 | 4 | -- Exclude these plugins from vscode 5 | if not vim.g.vscode then 6 | require("daneharnett.plugins") 7 | end 8 | 9 | -- load these settings after the plugins 10 | require("daneharnett.options").init() 11 | require("daneharnett.yank").init() 12 | require("daneharnett.arrowkeys").init() 13 | require("daneharnett.editing").init() 14 | require("daneharnett.buffers").init() 15 | require("daneharnett.diagnostics").init() 16 | require("daneharnett.navigation").init() 17 | require("daneharnett.command-palette").init() 18 | require("daneharnett.panel").init() 19 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/yank.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local utils = require("daneharnett.utils") 5 | 6 | if not vim.g.vscode then 7 | -- Make it so that yanking also places the selection into the system clipboard -- 8 | vim.opt.clipboard:append("unnamedplus") 9 | end 10 | 11 | -- When in visual mode, after yanking keep the cursor in the last selected 12 | -- position. 13 | utils.keymap("v", "y", "ygv") 14 | 15 | -- Exclude these yank keymaps from vscode 16 | if not vim.g.vscode then 17 | -- Yank into system clipboard 18 | utils.keymap("v", "y", '"+ygv') 19 | utils.keymap("n", "y", '"+y') 20 | end 21 | end 22 | 23 | return M 24 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/diagnosticls.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local status_ok, diagnosticls = pcall(require, "diagnosticls-configs") 5 | if not status_ok then 6 | return 7 | end 8 | local eslint_status_ok, eslint = pcall(require, "diagnosticls-configs.linters.eslint") 9 | if not eslint_status_ok then 10 | return 11 | end 12 | local prettier_status_ok, prettier = pcall(require, "diagnosticls-configs.formatters.prettier") 13 | if not prettier_status_ok then 14 | return 15 | end 16 | 17 | diagnosticls.init({}) 18 | 19 | diagnosticls.setup({ 20 | javascript = { 21 | linter = eslint, 22 | }, 23 | typescript = { 24 | linter = eslint, 25 | }, 26 | typescriptreact = { 27 | linter = eslint, 28 | }, 29 | }) 30 | end 31 | 32 | return M 33 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/navigation.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | -- Exclude this from vscode 5 | if vim.g.vscode then 6 | return 7 | end 8 | 9 | local utils = require("daneharnett.utils") 10 | -- Normal -- 11 | -- Better window navigation 12 | utils.keymap("n", "", "h") 13 | utils.keymap("n", "", "j") 14 | utils.keymap("n", "", "k") 15 | utils.keymap("n", "", "l") 16 | 17 | -- Resize with arrows 18 | utils.keymap("n", "", ":resize -2") 19 | utils.keymap("n", "", ":resize +2") 20 | utils.keymap("n", "", ":vertical resize -2") 21 | utils.keymap("n", "", ":vertical resize +2") 22 | 23 | -- Navigate buffers 24 | utils.keymap("n", "", ":bnext") 25 | utils.keymap("n", "", ":bprevious") 26 | end 27 | 28 | return M 29 | -------------------------------------------------------------------------------- /wezterm/.config/wezterm/wezterm.lua: -------------------------------------------------------------------------------- 1 | local wezterm = require("wezterm") 2 | local config = wezterm.config_builder() 3 | 4 | config.color_scheme = "Catppuccin Mocha" 5 | config.font = wezterm.font_with_fallback({ "JetBrainsMono Nerd Font" }) 6 | config.font_rules = { 7 | { 8 | italic = true, 9 | font = wezterm.font_with_fallback({ "JetBrains Mono" }), 10 | }, 11 | } 12 | config.font_size = 16.0 13 | -- If you want to disable ligatures in most fonts, then you may want to use a setting like this: 14 | config.harfbuzz_features = { "calt=0", "clig=0", "liga=0" } 15 | config.keys = { 16 | { 17 | key = "-", 18 | mods = "CTRL", 19 | action = wezterm.action.DisableDefaultAssignment, 20 | }, 21 | { 22 | key = "=", 23 | mods = "CTRL", 24 | action = wezterm.action.DisableDefaultAssignment, 25 | }, 26 | } 27 | config.use_fancy_tab_bar = false 28 | config.window_decorations = "RESIZE" 29 | 30 | return config 31 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/editing.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local utils = require("daneharnett.utils") 5 | -- In normal mode... 6 | -- Move current line down one line 7 | utils.keymap("n", "", ":m .+1") 8 | -- Move current line up one line 9 | utils.keymap("n", "", ":m .-2") 10 | 11 | -- In visual/visual-line mode... 12 | -- Stay in visual/visual-line mode after deindenting 13 | utils.keymap("v", "<", "", ">gv") 16 | 17 | -- Move selected line(s) down one line 18 | utils.keymap("v", "", ":m .+1==") 19 | -- Move selected line(s) up one line 20 | utils.keymap("v", "", ":m .-2==") 21 | -- what is this? 22 | utils.keymap("v", "p", '"_dP') 23 | 24 | -- In visual-block mode... 25 | -- Move selected block down one line 26 | utils.keymap("x", "J", ":move '>+1gv-gv") 27 | utils.keymap("x", "", ":move '>+1gv-gv") 28 | -- Move selected block up one line 29 | utils.keymap("x", "K", ":move '<-2gv-gv") 30 | utils.keymap("x", "", ":move '<-2gv-gv") 31 | end 32 | 33 | return M 34 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/panel.lua: -------------------------------------------------------------------------------- 1 | -- Treat plugins that open in a split on the right (nvim-tree, spectre) like 2 | -- a side-panel. This module adds a keymap to close all "panels". 3 | -- See nvim-tree and spectre files for more of this implementation like 4 | -- switching between plugins, opening and focusing. 5 | local M = {} 6 | 7 | function M.init() 8 | local utils = require("daneharnett.utils") 9 | 10 | utils.keymap("n", "pc", M.close_panel, "[P]anel [c]lose") 11 | end 12 | 13 | function M.close_panel() 14 | M.close_nvim_tree() 15 | M.close_spectre() 16 | end 17 | 18 | function M.close_nvim_tree() 19 | local status_ok, nvim_tree_api = pcall(require, "nvim-tree.api") 20 | if not status_ok then 21 | return 22 | end 23 | nvim_tree_api.tree.close_in_all_tabs() 24 | end 25 | 26 | function M.close_spectre() 27 | local spectre_status_ok, spectre = pcall(require, "spectre") 28 | if not spectre_status_ok then 29 | return 30 | end 31 | local spectre_state_status_ok, spectre_state = pcall(require, "spectre.state") 32 | if not spectre_state_status_ok then 33 | return 34 | end 35 | 36 | if spectre_state.is_open then 37 | spectre.toggle() 38 | end 39 | end 40 | 41 | return M 42 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/efmls.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local status_ok, efmls = pcall(require, "efmls-configs") 5 | if not status_ok then 6 | return 7 | end 8 | local eslint_status_ok, eslint = pcall(require, "efmls-configs.linters.eslint") 9 | if not eslint_status_ok then 10 | return 11 | end 12 | local prettier_status_ok, prettier = pcall(require, "efmls-configs.formatters.prettier") 13 | if not prettier_status_ok then 14 | return 15 | end 16 | 17 | local function on_attach(_, bufnr) 18 | local utils = require("daneharnett.utils") 19 | -- Set the timeout to 10s as it kept timing out for me. 20 | utils.create_format_on_save_autocmd("Efmls", bufnr, 10000) 21 | end 22 | 23 | efmls.init({ 24 | on_attach = on_attach, 25 | init_options = { 26 | documentFormatting = true, 27 | }, 28 | }) 29 | 30 | efmls.setup({ 31 | javascript = { 32 | linter = eslint, 33 | formatter = prettier, 34 | }, 35 | typescript = { 36 | linter = eslint, 37 | formatter = prettier, 38 | }, 39 | typescriptreact = { 40 | linter = eslint, 41 | formatter = prettier, 42 | }, 43 | }) 44 | end 45 | 46 | return M 47 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/better-ts-errors.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local bte_status_ok, bte = pcall(require, "better-ts-errors") 5 | if not bte_status_ok then 6 | return 7 | end 8 | 9 | bte.setup() 10 | end 11 | 12 | function M.attach_keymaps_to_buffer(bufnr) 13 | local utils = require("daneharnett.utils") 14 | utils.buffer_keymap(bufnr, "n", "]a", M.next) 15 | utils.buffer_keymap(bufnr, "n", "[a", M.previous) 16 | end 17 | 18 | function M.next() 19 | local bte_status_ok, bte = pcall(require, "better-ts-errors") 20 | if not bte_status_ok then 21 | return 22 | end 23 | 24 | bte.disable() 25 | local target = vim.diagnostic.get_next() 26 | if not target then 27 | return 28 | end 29 | M.focus_target(target) 30 | bte.enable() 31 | end 32 | 33 | function M.previous() 34 | local bte_status_ok, bte = pcall(require, "better-ts-errors") 35 | if not bte_status_ok then 36 | return 37 | end 38 | 39 | bte.disable() 40 | local target = vim.diagnostic.get_prev() 41 | if not target then 42 | return 43 | end 44 | M.focus_target(target) 45 | bte.enable() 46 | end 47 | 48 | function M.focus_target(target) 49 | local winid = vim.api.nvim_get_current_win() 50 | vim.api.nvim_win_set_cursor(winid, { target.lnum + 1, (target.col or 1) }) 51 | end 52 | 53 | return M 54 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # dotfiles 2 | 3 | Welcome to my dotfiles repository. This is where I keep the configuration 4 | for my personal computer setup. 5 | I use or have used the following software: 6 | 7 | ## Package management 8 | 9 | brew 10 | 11 | ## Configuration management 12 | 13 | I use `stow` to install the configuration from this repository into my home directory. 14 | 15 | ## Terminal emulator 16 | 17 | I currently use wezterm but have used alacritty and iterm2 in the past. 18 | 19 | ## Terminal multiplexer 20 | 21 | I use tmux. tmux is a terminal multiplexer: it enables a number of terminals to be created, accessed, and controlled from a single screen. 22 | 23 | ## Shell environment 24 | 25 | zsh is my preferred shell environment. I use the antidote plugin manager for zsh. 26 | 27 | ## Text editor 28 | 29 | I use neovim. 30 | 31 | ## Shell utilities 32 | 33 | ### eza 34 | 35 | A better `ls` 36 | 37 | ### fzf 38 | 39 | A fuzzy-finder. 40 | 41 | ### zoxide 42 | 43 | A better `cd` 44 | 45 | ### gnu-sed 46 | 47 | Used for text replacement in nvim-spectre 48 | 49 | ## Node.js version management 50 | 51 | I use both Fast Node Manager (`fnm`) and Node Version Manager (`nvm`) (for reasons). 52 | 53 | # Install 54 | 55 | Clone this repository somewhere on the machine you want to be configured. 56 | 57 | Run the `./setup-install` script to install all the required software. 58 | Run the `./install` script to apply the configuration. 59 | 60 | # Uninstall 61 | 62 | Run the `./uninstall` script to remove the configuration. 63 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/options.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local o = vim.o 5 | local bo = vim.bo 6 | local wo = vim.wo 7 | local opt = vim.opt 8 | 9 | -- global options -- 10 | -- do i want to keep these settings? 11 | -- o.errorbells = false 12 | -- o.smartcase = true 13 | -- o.showmode = false 14 | o.backup = false 15 | o.completeopt = "menuone,noinsert,noselect" 16 | o.expandtab = true 17 | o.filetype = "on" 18 | 19 | -- folds 20 | -- customize chars and start open 21 | o.fillchars = "foldopen:,foldclose:" 22 | o.foldcolumn = "auto" 23 | o.foldlevelstart = 99 24 | o.foldnestmax = 3 25 | o.foldminlines = 1 26 | 27 | o.hidden = true 28 | o.incsearch = true 29 | o.listchars = [[tab:▸ ,trail:·,space:·]] 30 | o.scrolloff = 8 31 | o.shiftwidth = 2 32 | o.softtabstop = 2 33 | o.syntax = "on" 34 | o.tabstop = 2 35 | o.undodir = vim.fn.stdpath("data") .. "/undodir" 36 | o.undofile = true 37 | 38 | -- buffer options -- 39 | bo.autoindent = true 40 | bo.smartindent = true 41 | bo.swapfile = false 42 | 43 | -- window options -- 44 | wo.colorcolumn = "80,100,120" 45 | wo.cursorcolumn = true 46 | wo.cursorline = true 47 | wo.list = true 48 | wo.number = true 49 | wo.numberwidth = 5 50 | wo.relativenumber = true 51 | wo.signcolumn = "yes" 52 | wo.wrap = false 53 | 54 | -- split options -- 55 | opt.splitright = true 56 | opt.splitbelow = true 57 | end 58 | 59 | return M 60 | -------------------------------------------------------------------------------- /nix/.config/nix/hosts/personal-i9mbp.nix: -------------------------------------------------------------------------------- 1 | { pkgs, inputs, self, ...}: { 2 | programs.zsh.enable = true; 3 | programs.zsh.enableCompletion = true; 4 | 5 | system.defaults = { 6 | NSGlobalDomain.AppleInterfaceStyle = "Dark"; 7 | NSGlobalDomain._HIHideMenuBar = true; 8 | 9 | dock.autohide = true; 10 | 11 | finder.AppleShowAllExtensions = true; 12 | finder.AppleShowAllFiles = true; 13 | finder.FXPreferredViewStyle = "clmv"; 14 | 15 | spaces.spans-displays = true; 16 | }; 17 | 18 | system.keyboard.enableKeyMapping = true; 19 | 20 | system.keyboard.remapCapsLockToEscape = true; 21 | 22 | homebrew = { 23 | enable = true; 24 | onActivation.cleanup = "zap"; 25 | }; 26 | 27 | home-manager.backupFileExtension = "backup"; 28 | 29 | users.users.dane.home = "/Users/dane"; 30 | # home.homeDirectory = "/Users/${userSettings.userName}"; 31 | aerospace.enable = true; 32 | antidote.enable = true; 33 | arc-browser.enable = true; 34 | bitwarden.enable = true; 35 | borders.enable = true; 36 | discord.enable = true; 37 | eza.enable = true; 38 | fd.enable = true; 39 | fnm.enable = true; 40 | font-jetbrains-mono-nerd-font.enable = true; 41 | fzf.enable = true; 42 | gnu-sed.enable = true; 43 | neovim.enable = true; 44 | nix-tools.enable = true; 45 | oh-my-posh.enable = true; 46 | raycast.enable = true; 47 | ripgrep.enable = true; 48 | slack.enable = true; 49 | stow.enable = true; 50 | util-linux.enable = true; 51 | vscode.enable = true; 52 | wezterm.enable = true; 53 | wget.enable = true; 54 | zoxide.enable = true; 55 | } 56 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/linting.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local utils = require("daneharnett.utils") 5 | local lint_status_ok, lint = pcall(require, "lint") 6 | if not lint_status_ok then 7 | return 8 | end 9 | 10 | lint.linters_by_ft = { 11 | javascript = { "eslint_d" }, 12 | typescript = { "eslint_d" }, 13 | javascriptreact = { "eslint_d" }, 14 | typescriptreact = { "eslint_d" }, 15 | svelte = { "eslint_d" }, 16 | python = { "pylint" }, 17 | } 18 | 19 | local mason_nvim_lint_status_ok, mason_nvim_lint = pcall(require, "mason-nvim-lint") 20 | if mason_nvim_lint_status_ok then 21 | mason_nvim_lint.setup() 22 | end 23 | 24 | local lint_augroup = vim.api.nvim_create_augroup("lint", { clear = true }) 25 | 26 | local js_filetypes = { "typescript", "javascript", "typescriptreact", "javascriptreact" } 27 | 28 | vim.api.nvim_create_autocmd({ "BufEnter", "BufWritePost", "InsertLeave" }, { 29 | group = lint_augroup, 30 | callback = function(args) 31 | local filetype = vim.api.nvim_get_option_value("filetype", { buf = args.buf }) 32 | 33 | if vim.tbl_contains(js_filetypes, filetype) then 34 | if not utils.has_eslint_config(args.buf) then 35 | return 36 | end 37 | end 38 | 39 | lint.try_lint() 40 | end, 41 | }) 42 | 43 | vim.keymap.set("n", "l", function() 44 | lint.try_lint() 45 | end, { desc = "Trigger linting for current file" }) 46 | end 47 | 48 | return M 49 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/toggleterm.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local status_ok, toggleterm = pcall(require, "toggleterm") 5 | if not status_ok then 6 | return 7 | end 8 | 9 | local utils = require("daneharnett.utils") 10 | 11 | toggleterm.setup({ 12 | size = 20, 13 | open_mapping = [[]], 14 | hide_numbers = true, 15 | shade_filetypes = {}, 16 | shade_terminals = true, 17 | shading_factor = 2, 18 | start_in_insert = true, 19 | insert_mappings = true, 20 | persist_size = true, 21 | direction = "horizontal", 22 | close_on_exit = true, 23 | shell = vim.o.shell, 24 | float_opts = { 25 | border = "curved", 26 | winblend = 0, 27 | highlights = { 28 | border = "Normal", 29 | background = "Normal", 30 | }, 31 | }, 32 | }) 33 | 34 | local function set_terminal_keymaps(event) 35 | local bufnr = event.buf 36 | utils.buffer_keymap(bufnr, "t", "", [[]]) 37 | utils.buffer_keymap(bufnr, "t", "jk", [[]]) 38 | utils.buffer_keymap(bufnr, "t", "", [[h]]) 39 | utils.buffer_keymap(bufnr, "t", "", [[j]]) 40 | utils.buffer_keymap(bufnr, "t", "", [[k]]) 41 | utils.buffer_keymap(bufnr, "t", "", [[l]]) 42 | end 43 | 44 | local group = vim.api.nvim_create_augroup("ToggleTerm", { clear = true }) 45 | vim.api.nvim_create_autocmd("TermOpen", { 46 | callback = set_terminal_keymaps, 47 | group = group, 48 | pattern = "term://*", 49 | }) 50 | end 51 | 52 | return M 53 | -------------------------------------------------------------------------------- /nix/.config/nix/hosts/personal-m4mbp.nix: -------------------------------------------------------------------------------- 1 | { 2 | pkgs, 3 | inputs, 4 | self, 5 | ... 6 | }: 7 | { 8 | system.primaryUser = "dane"; 9 | 10 | programs.zsh.enable = true; 11 | programs.zsh.enableCompletion = true; 12 | 13 | system.defaults = { 14 | NSGlobalDomain.AppleInterfaceStyle = "Dark"; 15 | NSGlobalDomain._HIHideMenuBar = false; 16 | 17 | dock.autohide = true; 18 | 19 | finder.AppleShowAllExtensions = true; 20 | finder.AppleShowAllFiles = true; 21 | finder.FXPreferredViewStyle = "clmv"; 22 | 23 | spaces.spans-displays = true; 24 | }; 25 | 26 | system.keyboard.enableKeyMapping = true; 27 | 28 | system.keyboard.remapCapsLockToEscape = true; 29 | 30 | homebrew = { 31 | enable = true; 32 | onActivation = { 33 | autoUpdate = true; 34 | cleanup = "uninstall"; 35 | upgrade = true; 36 | }; 37 | }; 38 | 39 | home-manager.backupFileExtension = "backup"; 40 | 41 | users.users.dane.home = "/Users/dane"; 42 | # home.homeDirectory = "/Users/${userSettings.userName}"; 43 | aerospace.enable = true; 44 | antidote.enable = true; 45 | bitwarden.enable = true; 46 | borders.enable = true; 47 | carapace.enable = true; 48 | cargo.enable = true; 49 | discord.enable = true; 50 | eza.enable = true; 51 | fd.enable = true; 52 | fnm.enable = true; 53 | font-jetbrains-mono-nerd-font.enable = true; 54 | fx-cast-bridge.enable = true; 55 | fzf.enable = true; 56 | gnu-sed.enable = true; 57 | leader-key.enable = true; 58 | helium-browser.enable = true; 59 | neovim.enable = true; 60 | nix-tools.enable = true; 61 | obs.enable = true; 62 | oh-my-posh.enable = true; 63 | raycast.enable = false; 64 | ripgrep.enable = true; 65 | slack.enable = true; 66 | stow.enable = true; 67 | there.enable = true; 68 | util-linux.enable = true; 69 | vlc.enable = true; 70 | vscode.enable = true; 71 | wezterm.enable = true; 72 | wget.enable = true; 73 | yt-dlp.enable = true; 74 | zoxide.enable = true; 75 | } 76 | -------------------------------------------------------------------------------- /leader-key/.config/leader-key/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "group", 3 | "actions": [ 4 | { 5 | "key": "t", 6 | "type": "application", 7 | "value": "/Applications/WezTerm.app" 8 | }, 9 | { 10 | "key": "o", 11 | "type": "group", 12 | "actions": [ 13 | { 14 | "key": "s", 15 | "type": "application", 16 | "value": "/Applications/Safari.app" 17 | }, 18 | { 19 | "key": "e", 20 | "type": "application", 21 | "value": "/Applications/Mail.app" 22 | }, 23 | { 24 | "key": "i", 25 | "type": "application", 26 | "value": "/System/Applications/Music.app" 27 | }, 28 | { 29 | "key": "m", 30 | "type": "application", 31 | "value": "/Applications/Messages.app" 32 | } 33 | ] 34 | }, 35 | { 36 | "key": "r", 37 | "type": "group", 38 | "actions": [ 39 | { 40 | "key": "e", 41 | "type": "url", 42 | "value": "raycast://extensions/raycast/emoji-symbols/search-emoji-symbols" 43 | }, 44 | { "key": "p", "type": "url", "value": "raycast://confetti" }, 45 | { 46 | "key": "c", 47 | "type": "url", 48 | "value": "raycast://extensions/raycast/system/open-camera" 49 | } 50 | ] 51 | }, 52 | { 53 | "key": "b", 54 | "type": "group", 55 | "actions": [ 56 | { 57 | "key": "m", 58 | "label": "Open Mail in Browser", 59 | "type": "command", 60 | "value": "~/projects/personal/dotfiles/scripts/helium-focus-or-open 'https://mail.google.com/mail/u/0/#inbox'" 61 | }, 62 | { 63 | "key": "y", 64 | "label": "Open YouTube in Browser", 65 | "type": "command", 66 | "value": "~/projects/personal/dotfiles/scripts/helium-focus-or-open 'https://www.youtube.com/'" 67 | } 68 | ] 69 | } 70 | ] 71 | } 72 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/formatting.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local conform_status_ok, conform = pcall(require, "conform") 5 | if not conform_status_ok then 6 | return 7 | end 8 | local conform_util_status_ok, conform_util = pcall(require, "conform.util") 9 | if not conform_util_status_ok then 10 | return 11 | end 12 | local conform_eslint_d_status_ok, conform_eslint_d = pcall(require, "conform.formatters.eslint_d") 13 | if not conform_eslint_d_status_ok then 14 | return 15 | end 16 | local conform_prettierd_status_ok, conform_prettierd = pcall(require, "conform.formatters.prettierd") 17 | if not conform_prettierd_status_ok then 18 | return 19 | end 20 | 21 | conform_eslint_d.cwd = conform_util.root_file({ 22 | "yarn.lock", 23 | "package-lock.json", 24 | }) 25 | conform_prettierd.cwd = conform_util.root_file({ 26 | "yarn.lock", 27 | "package-lock.json", 28 | }) 29 | 30 | conform.setup({ 31 | formatters_by_ft = { 32 | javascript = { "prettierd", "eslint_d" }, 33 | typescript = { "prettierd", "eslint_d" }, 34 | javascriptreact = { "prettierd", "eslint_d" }, 35 | typescriptreact = { "prettierd", "eslint_d" }, 36 | svelte = { "prettierd" }, 37 | css = { "prettierd" }, 38 | html = { "prettierd" }, 39 | json = { "prettierd" }, 40 | yaml = { "prettierd" }, 41 | markdown = { "prettierd" }, 42 | graphql = { "prettierd" }, 43 | lua = { "stylua" }, 44 | python = { "isort", "black" }, 45 | }, 46 | format_on_save = { 47 | lsp_fallback = true, 48 | async = false, 49 | timeout_ms = 10000, 50 | }, 51 | }) 52 | 53 | vim.keymap.set({ "n", "v" }, "mp", function() 54 | conform.format({ 55 | lsp_fallback = true, 56 | async = false, 57 | timeout_ms = 10000, 58 | }) 59 | end, { desc = "Format file or range (in visual mode)" }) 60 | end 61 | 62 | return M 63 | -------------------------------------------------------------------------------- /nix/.config/nix/home/dane/personal-i9mbp.nix: -------------------------------------------------------------------------------- 1 | # home.nix 2 | # home-manager switch 3 | 4 | { config, pkgs, ... }: 5 | 6 | { 7 | home.username = "dane"; 8 | home.homeDirectory = "/Users/dane"; 9 | home.stateVersion = "24.05"; 10 | 11 | # Makes sense for user specific applications that shouldn't be available system-wide 12 | home.packages = [ 13 | ]; 14 | 15 | # Home Manager is pretty good at managing dotfiles. The primary way to manage 16 | # plain files is through 'home.file'. 17 | home.file = { 18 | ".config/aerospace".source = ../../../../../aerospace/.config/aerospace; 19 | ".config/borders".source = ../../../../../borders/.config/borders; 20 | ".config/nvim".source = ../../../../../nvim/.config/nvim; 21 | ".config/nvm".source = ../../../../../nvm/.config/nvm; 22 | ".wezterm.lua".source = ../../../../../wezterm/.wezterm.lua; 23 | }; 24 | 25 | home.sessionVariables = { 26 | }; 27 | 28 | home.sessionPath = [ 29 | "/run/current-system/sw/bin" 30 | "$HOME/.nix-profile/bin" 31 | ]; 32 | programs.home-manager.enable = true; 33 | programs.fzf.enable = true; 34 | programs.oh-my-posh = { 35 | enable = true; 36 | settings = builtins.fromTOML (builtins.unsafeDiscardStringContext (builtins.readFile ../../../../../oh-my-posh/.config/oh-my-posh/default.toml)); 37 | }; 38 | programs.zsh = { 39 | enable = true; 40 | initContent = builtins.readFile ../../../../../zsh/.zshrc; 41 | antidote = { 42 | enable = true; 43 | plugins = [ 44 | "jimhester/per-directory-history" 45 | "mattmc3/zephyr path:plugins/completion" 46 | "zdharma-continuum/fast-syntax-highlighting kind:defer" 47 | "chrisands/zsh-yarn-completions" 48 | "chitoku-k/fzf-zsh-completions" 49 | ]; 50 | }; 51 | autosuggestion.enable = true; 52 | defaultKeymap = "viins"; 53 | historySubstringSearch = { 54 | enable = true; 55 | }; 56 | shellAliases = { 57 | ll = "ls -lah"; 58 | ls = "eza"; 59 | cd = "z"; 60 | zz = "z -"; 61 | }; 62 | }; 63 | 64 | programs.zoxide = { 65 | enable = true; 66 | enableZshIntegration = true; 67 | }; 68 | } 69 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/utils.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | M.keymap = function(mode, key, result, desc) 4 | desc = desc or "" 5 | vim.keymap.set(mode, key, result, { 6 | desc = desc, 7 | noremap = true, 8 | silent = true, 9 | }) 10 | end 11 | 12 | M.buffer_keymap = function(bufnr, mode, key, result) 13 | vim.keymap.set(mode, key, result, { buffer = bufnr, noremap = true, silent = true }) 14 | end 15 | 16 | M.create_format_on_save_autocmd = function(augroup_name, bufnr, timeout_ms) 17 | timeout_ms = timeout_ms or 1000 18 | 19 | local group = vim.api.nvim_create_augroup(augroup_name .. "FormatOnSave", { clear = false }) 20 | vim.api.nvim_create_autocmd("BufWritePre", { 21 | buffer = bufnr, 22 | callback = function() 23 | vim.lsp.buf.format({ timeout_ms = timeout_ms }) 24 | end, 25 | group = group, 26 | }) 27 | end 28 | 29 | M.get_typescript_filetypes = function() 30 | return { "typescript", "typescriptreact", "typescript.tsx" } 31 | end 32 | 33 | M.has_deno_config = function(fname) 34 | local lspconfig_util_status_ok, lspconfig_util = pcall(require, "lspconfig.util") 35 | if not lspconfig_util_status_ok then 36 | return false 37 | end 38 | return lspconfig_util.root_pattern("deno.json", "deno.jsonc")(fname) 39 | end 40 | 41 | M.has_eslint_config = function(fname) 42 | local lspconfig_util_status_ok, lspconfig_util = pcall(require, "lspconfig.util") 43 | if not lspconfig_util_status_ok then 44 | return false 45 | end 46 | return lspconfig_util.root_pattern("eslintrc.js", "eslint.config.js", "eslint.config.mjs")(fname) 47 | end 48 | 49 | M.has_tsconfig = function(fname) 50 | local lspconfig_util_status_ok, lspconfig_util = pcall(require, "lspconfig.util") 51 | if not lspconfig_util_status_ok then 52 | return false 53 | end 54 | return lspconfig_util.root_pattern("tsconfig.json")(fname) 55 | end 56 | 57 | M.is_git_repo = function(fname) 58 | local git_ancestor = vim.fs.dirname(vim.fs.find(".git", { path = fname, upward = true })[1]) 59 | if git_ancestor then 60 | return git_ancestor 61 | end 62 | return false 63 | end 64 | 65 | return M 66 | -------------------------------------------------------------------------------- /setup-install: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | # This script is currently a work-in-progress and has not yet been tested. 4 | 5 | # install brew if its not already available 6 | if [[ ! $(command -v "brew") ]]; then 7 | /bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh)" 8 | fi 9 | 10 | # install stow via brew if its not already available 11 | if [[ ! $(command -v "stow") ]]; then 12 | brew install stow 13 | fi 14 | 15 | # install eza via brew if its not already available 16 | if [[ ! $(command -v "eza") ]]; then 17 | brew install eza 18 | fi 19 | 20 | # install zoxide via brew if its not already available 21 | if [[ ! $(command -v "zoxide") ]]; then 22 | brew install zoxide 23 | fi 24 | 25 | # install fd via brew if its not already available 26 | if [[ ! $(command -v "fd") ]]; then 27 | brew install fd 28 | fi 29 | 30 | # install rg via brew if its not already available 31 | if [[ ! $(command -v "rg") ]]; then 32 | brew install ripgrep 33 | fi 34 | 35 | # install fzf via brew if its not already available 36 | if [[ ! $(command -v "fzf") ]]; then 37 | brew install fzf 38 | fi 39 | 40 | # install fnm via brew if its not already available 41 | if [[ ! $(command -v "fnm") ]]; then 42 | brew install fnm 43 | fi 44 | 45 | if [[ ! $(command -v "nvim") ]]; then 46 | brew install neovim 47 | fi 48 | 49 | if [[ ! $(command -v "tmux") ]]; then 50 | brew install tmux 51 | fi 52 | 53 | # check for tmux plugin manager (tpm) 54 | if [[ ! -f ~/.tmux/plugins/tpm/README.md ]]; then 55 | git clone https://github.com/tmux-plugins/tpm ~/.tmux/plugins/tpm 56 | fi 57 | 58 | if [[ ! $(command -v "wezterm") ]]; then 59 | brew install --cask wez/wezterm/wezterm 60 | fi 61 | 62 | if [[ ! $(command -v "node") ]]; then 63 | fnm install v16.19.0 64 | fi 65 | 66 | if [[ ! $(command -v "aerospace") ]]; then 67 | brew install --cask nikitabobko/tap/aerospace 68 | fi 69 | 70 | if [[ ! $(command -v "borders") ]]; then 71 | # install borders 72 | brew install FelixKratz/formulae/borders 73 | # run automatically at startup 74 | brew services start borders 75 | fi 76 | 77 | if [[ ! $(command -v "gsed") ]]; then 78 | brew install gnu-sed 79 | fi 80 | 81 | echo -e "Setup complete. Now run ./install to apply the config" 82 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/gitsigns.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local status_ok, gitsigns = pcall(require, "gitsigns") 5 | if not status_ok then 6 | return 7 | end 8 | 9 | gitsigns.setup({ 10 | signs = { 11 | add = { text = "┃" }, 12 | change = { text = "┃" }, 13 | delete = { text = "_" }, 14 | topdelete = { text = "‾" }, 15 | changedelete = { text = "~" }, 16 | untracked = { text = "┆" }, 17 | }, 18 | signs_staged = { 19 | add = { text = "┃" }, 20 | change = { text = "┃" }, 21 | delete = { text = "_" }, 22 | topdelete = { text = "‾" }, 23 | changedelete = { text = "~" }, 24 | untracked = { text = "┆" }, 25 | }, 26 | signs_staged_enable = true, 27 | signcolumn = true, -- Toggle with `:Gitsigns toggle_signs` 28 | numhl = false, -- Toggle with `:Gitsigns toggle_numhl` 29 | linehl = false, -- Toggle with `:Gitsigns toggle_linehl` 30 | word_diff = false, -- Toggle with `:Gitsigns toggle_word_diff` 31 | watch_gitdir = { 32 | follow_files = true, 33 | }, 34 | auto_attach = true, 35 | attach_to_untracked = false, 36 | current_line_blame = false, -- Toggle with `:Gitsigns toggle_current_line_blame` 37 | current_line_blame_opts = { 38 | virt_text = true, 39 | virt_text_pos = "eol", -- 'eol' | 'overlay' | 'right_align' 40 | delay = 1000, 41 | ignore_whitespace = false, 42 | virt_text_priority = 100, 43 | }, 44 | current_line_blame_formatter = ", - ", 45 | sign_priority = 6, 46 | update_debounce = 100, 47 | status_formatter = nil, -- Use default 48 | max_file_length = 40000, -- Disable if file is longer than this (in lines) 49 | preview_config = { 50 | -- Options passed to nvim_open_win 51 | border = "single", 52 | style = "minimal", 53 | relative = "cursor", 54 | row = 0, 55 | col = 1, 56 | }, 57 | }) 58 | end 59 | 60 | return M 61 | -------------------------------------------------------------------------------- /scripts/helium-focus-or-open: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env bash 2 | # helium-open: focus existing Helium tab for URL, else open new. 3 | # Usage: 4 | # helium-open "https://example.com" # quiet mode 5 | # DEBUG=1 helium-open "https://example.com" # debug mode -> /tmp/helium-open-debug.log 6 | set -euo pipefail 7 | if [[ $# -lt 1 ]]; then 8 | echo "Usage: helium-open " >&2 9 | exit 1 10 | fi 11 | 12 | url="$1" 13 | 14 | apple_script=' 15 | on run argv 16 | set theURL to item 1 of argv 17 | log "[AppleScript] Starting Helium check for URL: " & theURL 18 | tell application "Helium" 19 | activate 20 | set foundTab to false 21 | set windowIndex to 0 22 | repeat with w in windows 23 | set windowIndex to windowIndex + 1 24 | log "[AppleScript] Checking window " & windowIndex 25 | set tabIndex to 0 26 | repeat with t in tabs of w 27 | set tabIndex to tabIndex + 1 28 | try 29 | set thisURL to URL of t as text 30 | log "[AppleScript] Tab " & tabIndex & " has URL: " & thisURL 31 | if thisURL is theURL then 32 | log "[AppleScript] ✅ Found matching tab: window " & windowIndex & ", tab " & tabIndex 33 | set active tab index of w to tabIndex 34 | set index of w to 1 35 | set foundTab to true 36 | exit repeat 37 | end if 38 | on error errMsg 39 | log "[AppleScript] ⚠️ Error reading tab " & tabIndex & ": " & errMsg 40 | end try 41 | end repeat 42 | if foundTab then exit repeat 43 | end repeat 44 | 45 | if not foundTab then 46 | log "[AppleScript] No matching tab found, opening new one..." 47 | if (count of windows) is 0 then 48 | make new window 49 | end if 50 | tell window 1 to make new tab with properties {URL:theURL} 51 | set index of window 1 to 1 52 | end if 53 | end tell 54 | log "[AppleScript] Done." 55 | end run 56 | ' 57 | 58 | if [[ "${DEBUG:-0}" == "1" ]]; then 59 | echo "[bash] Target URL: $url" 60 | osascript -e "$apple_script" "$url" 2>&1 | tee /tmp/helium-open-debug.log 61 | echo "[bash] Debug log: /tmp/helium-open-debug.log" 62 | else 63 | # Keep the *same* AppleScript (and thus the working behavior), 64 | # but suppress its noisy stderr output. 65 | osascript -e "$apple_script" "$url" 2>/dev/null 66 | fi 67 | 68 | -------------------------------------------------------------------------------- /zsh/.zshrc: -------------------------------------------------------------------------------- 1 | export PATH=$HOME/bin:/usr/local/bin:$PATH 2 | export PATH=$HOME/.composer/vendor/bin:$PATH 3 | export PATH=$HOME/.deno/bin:$PATH 4 | export XDG_CONFIG_HOME=$HOME/.config 5 | 6 | # Ensure terminal colors work inside tmux 7 | if [ ! "$TMUX" = "" ]; then export TERM=xterm-256color; fi 8 | 9 | # Make vi mode transitions faster (KEYTIMEOUT is in hundredths of a second) 10 | export KEYTIMEOUT=1 11 | 12 | # Conditionally prepare environment variables for cargo/rust 13 | [[ -f "$HOME/.cargo/env" ]] && source "$HOME/.cargo/env" 14 | 15 | # Conditionally add cabal and .ghcup to the path for haskell 16 | [[ -f "$HOME/.ghcup/env" ]] && source "$HOME/.ghcup/env" 17 | 18 | # My custom configuration 19 | 20 | # Ctrl+space accepts the auto-suggestion 21 | bindkey '^ ' autosuggest-accept 22 | 23 | bindkey -M vicmd 'k' history-substring-search-up 24 | bindkey -M vicmd 'j' history-substring-search-down 25 | 26 | # copy current input on command-prompt to clipboard: 27 | copy-prompt-to-clipboard() { 28 | zle kill-buffer 29 | print -rn -- "$CUTBUFFER" | pbcopy 30 | } 31 | 32 | zle -N copy-prompt-to-clipboard 33 | bindkey -M viins '^]' copy-prompt-to-clipboard 34 | 35 | # If my personal github ssh key exists then configure ssh-agent to use it 36 | if [ -f "$HOME/.ssh/github" ]; then 37 | ssh-agent | source /dev/stdin > /dev/null 38 | ssh-add -q --apple-use-keychain ~/.ssh/github 39 | fi 40 | 41 | # Initialize fast node manager (fnm) 42 | [[ $(command -v "fnm") ]] && eval "$(fnm env --use-on-cd --log-level=quiet)" 43 | # load my nvm to fnm shim 44 | export NVM_DIR="$([ -z "${XDG_CONFIG_HOME-}" ] && printf %s "${HOME}/.nvm" || printf %s "${XDG_CONFIG_HOME}/nvm")" 45 | [ -s "$NVM_DIR/nvm.sh" ] && \. "$NVM_DIR/nvm.sh" 46 | 47 | # These additions to PATH cannot be in zshenv due to order of execution. 48 | # export PATH="$(brew --prefix)/opt/util-linux/sbin:$(brew --prefix)/opt/util-linux/bin:$PATH" 49 | export PATH="$HOME/.jenv/bin:$PATH" 50 | if [[ $(command -v "jenv") ]]; then 51 | function jenv() { 52 | unset -f jenv 53 | eval "$(command jenv init -)" 54 | jenv "$@" 55 | } 56 | fi 57 | 58 | # Disable that annoying beep. 59 | unsetopt BEEP 60 | 61 | # pyenv 62 | export PYENV_ROOT="$HOME/.pyenv" 63 | command -v pyenv >/dev/null || export PATH="$PYENV_ROOT/bin:$PATH" 64 | if [[ $(command -v "pyenv") ]]; then 65 | eval "$(pyenv init -)" 66 | fi 67 | 68 | if [[ $(command -v "carapace") ]]; then 69 | # export CARAPACE_BRIDGES='zsh,fish,bash,inshellisense' # optional 70 | zstyle ':completion:*' format $'\e[2;37mCompleting %d\e[m' 71 | source <(carapace _carapace) 72 | fi 73 | 74 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/treesitter.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local ts_configs_setup_status_ok = M.setup_treesitter_configs() 5 | if not ts_configs_setup_status_ok then 6 | return 7 | end 8 | 9 | M.setup_treesitter_context() 10 | M.setup_treesitter_folds() 11 | end 12 | 13 | M.setup_treesitter_configs = function() 14 | local ts_configs_status_ok, ts_configs = pcall(require, "nvim-treesitter.configs") 15 | if not ts_configs_status_ok then 16 | return false 17 | end 18 | 19 | ts_configs.setup({ 20 | ensure_installed = { 21 | "bash", 22 | "css", 23 | "html", 24 | "java", 25 | "javascript", 26 | "json", 27 | "lua", 28 | "markdown", 29 | "markdown_inline", 30 | "tsx", 31 | "typescript", 32 | "vimdoc", 33 | }, 34 | modules = {}, 35 | sync_install = false, 36 | auto_install = false, 37 | ignore_install = {}, 38 | highlight = { 39 | enable = true, 40 | }, 41 | indent = { 42 | enable = true, 43 | }, 44 | playground = { 45 | enable = true, 46 | updatetime = 25, 47 | }, 48 | }) 49 | 50 | return true 51 | end 52 | 53 | M.setup_treesitter_context = function() 54 | local context_status_ok, tscontext = pcall(require, "treesitter-context") 55 | if context_status_ok then 56 | tscontext.setup({ 57 | max_lines = 3, 58 | }) 59 | end 60 | end 61 | 62 | M.setup_treesitter_folds = function() 63 | local ts_parsers_status_ok, ts_parsers = pcall(require, "nvim-treesitter.parsers") 64 | if not ts_parsers_status_ok then 65 | return 66 | end 67 | 68 | local group = vim.api.nvim_create_augroup("FoldsWithTreesitter", { clear = true }) 69 | local additional_file_types = { 70 | "typescriptreact", 71 | } 72 | local all_file_types = {} 73 | 74 | local parsers = ts_parsers.available_parsers() 75 | for _, filetype in ipairs(parsers) do 76 | table.insert(all_file_types, filetype) 77 | end 78 | for _, filetype in ipairs(additional_file_types) do 79 | table.insert(all_file_types, filetype) 80 | end 81 | 82 | for _, filetype in ipairs(all_file_types) do 83 | vim.api.nvim_create_autocmd("FileType", { 84 | pattern = filetype, 85 | callback = function() 86 | vim.wo.foldmethod = "expr" 87 | vim.wo.foldexpr = "nvim_treesitter#foldexpr()" 88 | end, 89 | group = group, 90 | }) 91 | end 92 | end 93 | 94 | return M 95 | -------------------------------------------------------------------------------- /nix/.config/nix/home/dane/personal-m4mbp.nix: -------------------------------------------------------------------------------- 1 | # home.nix 2 | # home-manager switch 3 | 4 | { config, pkgs, ... }: 5 | 6 | { 7 | home.username = "dane"; 8 | home.homeDirectory = "/Users/dane"; 9 | home.stateVersion = "24.05"; 10 | 11 | # Makes sense for user specific applications that shouldn't be available system-wide 12 | home.packages = [ 13 | ]; 14 | 15 | # Home Manager is pretty good at managing dotfiles. The primary way to manage 16 | # plain files is through 'home.file'. 17 | home.file = { 18 | ".config/aerospace".source = 19 | config.lib.file.mkOutOfStoreSymlink "${config.home.homeDirectory}/projects/personal/dotfiles/aerospace/.config/aerospace"; 20 | ".config/borders".source = ../../../../../borders/.config/borders; 21 | ".config/leader-key".source = 22 | config.lib.file.mkOutOfStoreSymlink "${config.home.homeDirectory}/projects/personal/dotfiles/leader-key/.config/leader-key"; 23 | ".config/nvim".source = 24 | config.lib.file.mkOutOfStoreSymlink "${config.home.homeDirectory}/projects/personal/dotfiles/nvim/.config/nvim"; 25 | ".config/nvm".source = ../../../../../nvm/.config/nvm; 26 | ".config/wezterm".source = ../../../../../wezterm/.config/wezterm; 27 | }; 28 | 29 | home.sessionVariables = { 30 | }; 31 | 32 | home.sessionPath = [ 33 | "/run/current-system/sw/bin" 34 | "$HOME/.nix-profile/bin" 35 | ]; 36 | programs.home-manager.enable = true; 37 | programs.fzf.enable = true; 38 | programs.git = { 39 | enable = true; 40 | lfs.enable = true; 41 | settings = { 42 | alias = { 43 | co = "checkout"; 44 | st = "status"; 45 | }; 46 | user = { 47 | email = "2585257+dane-harnett@users.noreply.github.com"; 48 | name = "Dane Harnett"; 49 | }; 50 | }; 51 | }; 52 | programs.oh-my-posh = { 53 | enable = true; 54 | settings = builtins.fromTOML ( 55 | builtins.unsafeDiscardStringContext ( 56 | builtins.readFile ../../../../../oh-my-posh/.config/oh-my-posh/default.toml 57 | ) 58 | ); 59 | }; 60 | programs.zsh = { 61 | enable = true; 62 | initContent = builtins.readFile ../../../../../zsh/.zshrc; 63 | antidote = { 64 | enable = true; 65 | plugins = [ 66 | "jimhester/per-directory-history" 67 | "zdharma-continuum/fast-syntax-highlighting kind:defer" 68 | ]; 69 | }; 70 | autosuggestion.enable = true; 71 | defaultKeymap = "viins"; 72 | historySubstringSearch = { 73 | enable = true; 74 | }; 75 | shellAliases = { 76 | ll = "ls -lah"; 77 | ls = "eza"; 78 | cd = "z"; 79 | zz = "z -"; 80 | }; 81 | }; 82 | 83 | programs.zoxide = { 84 | enable = true; 85 | enableZshIntegration = true; 86 | }; 87 | } 88 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/lspsaga.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local status_ok, lspsaga = pcall(require, "lspsaga") 5 | if not status_ok then 6 | return 7 | end 8 | 9 | lspsaga.setup({}) 10 | end 11 | 12 | function M.attach_keymaps_to_buffer(bufnr) 13 | local utils = require("daneharnett.utils") 14 | 15 | -- lsp provider to find the cursor word definition and reference 16 | utils.buffer_keymap(bufnr, "n", "gh", "Lspsaga lsp_finder") 17 | 18 | -- code action 19 | utils.buffer_keymap(bufnr, { "n", "v" }, "ca", "Lspsaga code_action") 20 | 21 | -- show hover doc 22 | utils.buffer_keymap(bufnr, "n", "K", "Lspsaga hover_doc") 23 | 24 | -- Call hierarchy 25 | utils.buffer_keymap(bufnr, "n", "ci", "Lspsaga incoming_calls") 26 | utils.buffer_keymap(bufnr, "n", "co", "Lspsaga outgoing_calls") 27 | 28 | -- scroll down hover doc or scroll in definition preview 29 | utils.buffer_keymap(bufnr, "n", "", ':lua require"lspsaga.action".smart_scroll_with_saga(1)') 30 | 31 | -- scroll up hover doc 32 | utils.buffer_keymap(bufnr, "n", "", ':lua require"lspsaga.action".smart_scroll_with_saga(-1)') 33 | 34 | -- show signature help 35 | -- utils.("n", "gs", ':lua require"lspsaga.signaturehelp".signature_help()') 36 | 37 | -- rename 38 | utils.buffer_keymap(bufnr, "n", "gr", "Lspsaga rename") 39 | 40 | -- peek definition 41 | utils.buffer_keymap(bufnr, "n", "gp", "Lspsaga peek_definition") 42 | 43 | -- go to definition 44 | utils.buffer_keymap(bufnr, "n", "gd", "Lspsaga goto_definition") 45 | 46 | -- show line diagnostics 47 | utils.buffer_keymap(bufnr, "n", "sl", "Lspsaga show_line_diagnostics") 48 | 49 | -- show cursor diagnostics 50 | utils.buffer_keymap(bufnr, "n", "sc", "Lspsaga show_cursor_diagnostics") 51 | 52 | -- Show buffer diagnostics 53 | utils.buffer_keymap(bufnr, "n", "sb", "Lspsaga show_buf_diagnostics") 54 | 55 | -- jump to diagnostic 56 | utils.buffer_keymap(bufnr, "n", "[e", "Lspsaga diagnostic_jump_prev") 57 | utils.buffer_keymap(bufnr, "n", "]e", "Lspsaga diagnostic_jump_next") 58 | 59 | -- Diagnostic jump with filter like Only jump to error 60 | utils.buffer_keymap(bufnr, "n", "[E", function() 61 | require("lspsaga.diagnostic").goto_prev({ severity = vim.diagnostic.severity.ERROR }) 62 | end) 63 | utils.buffer_keymap(bufnr, "n", "]E", function() 64 | require("lspsaga.diagnostic").goto_next({ severity = vim.diagnostic.severity.ERROR }) 65 | end) 66 | 67 | -- floating terminal 68 | utils.buffer_keymap(bufnr, { "n", "t" }, "", "Lspsaga term_toggle") 69 | end 70 | 71 | return M 72 | -------------------------------------------------------------------------------- /nix/.config/nix/flake.lock: -------------------------------------------------------------------------------- 1 | { 2 | "nodes": { 3 | "brew-src": { 4 | "flake": false, 5 | "locked": { 6 | "lastModified": 1763638478, 7 | "narHash": "sha256-n/IMowE9S23ovmTkKX7KhxXC2Yq41EAVFR2FBIXPcT8=", 8 | "owner": "Homebrew", 9 | "repo": "brew", 10 | "rev": "fbfdbaba008189499958a7aeb1e2c36ab10c067d", 11 | "type": "github" 12 | }, 13 | "original": { 14 | "owner": "Homebrew", 15 | "ref": "5.0.3", 16 | "repo": "brew", 17 | "type": "github" 18 | } 19 | }, 20 | "home-manager": { 21 | "inputs": { 22 | "nixpkgs": [ 23 | "nixpkgs" 24 | ] 25 | }, 26 | "locked": { 27 | "lastModified": 1764361670, 28 | "narHash": "sha256-jgWzgpIaHbL3USIq0gihZeuy1lLf2YSfwvWEwnfAJUw=", 29 | "owner": "nix-community", 30 | "repo": "home-manager", 31 | "rev": "780be8ef503a28939cf9dc7996b48ffb1a3e04c6", 32 | "type": "github" 33 | }, 34 | "original": { 35 | "owner": "nix-community", 36 | "repo": "home-manager", 37 | "type": "github" 38 | } 39 | }, 40 | "nix-darwin": { 41 | "inputs": { 42 | "nixpkgs": [ 43 | "nixpkgs" 44 | ] 45 | }, 46 | "locked": { 47 | "lastModified": 1764161084, 48 | "narHash": "sha256-HN84sByg9FhJnojkGGDSrcjcbeioFWoNXfuyYfJ1kBE=", 49 | "owner": "LnL7", 50 | "repo": "nix-darwin", 51 | "rev": "e95de00a471d07435e0527ff4db092c84998698e", 52 | "type": "github" 53 | }, 54 | "original": { 55 | "owner": "LnL7", 56 | "repo": "nix-darwin", 57 | "type": "github" 58 | } 59 | }, 60 | "nix-homebrew": { 61 | "inputs": { 62 | "brew-src": "brew-src" 63 | }, 64 | "locked": { 65 | "lastModified": 1764473698, 66 | "narHash": "sha256-C91gPgv6udN5WuIZWNehp8qdLqlrzX6iF/YyboOj6XI=", 67 | "owner": "zhaofengli-wip", 68 | "repo": "nix-homebrew", 69 | "rev": "6a8ab60bfd66154feeaa1021fc3b32684814a62a", 70 | "type": "github" 71 | }, 72 | "original": { 73 | "owner": "zhaofengli-wip", 74 | "repo": "nix-homebrew", 75 | "type": "github" 76 | } 77 | }, 78 | "nixpkgs": { 79 | "locked": { 80 | "lastModified": 1764445028, 81 | "narHash": "sha256-ik6H/0Zl+qHYDKTXFPpzuVHSZE+uvVz2XQuQd1IVXzo=", 82 | "owner": "NixOS", 83 | "repo": "nixpkgs", 84 | "rev": "a09378c0108815dbf3961a0e085936f4146ec415", 85 | "type": "github" 86 | }, 87 | "original": { 88 | "owner": "NixOS", 89 | "ref": "nixpkgs-unstable", 90 | "repo": "nixpkgs", 91 | "type": "github" 92 | } 93 | }, 94 | "root": { 95 | "inputs": { 96 | "home-manager": "home-manager", 97 | "nix-darwin": "nix-darwin", 98 | "nix-homebrew": "nix-homebrew", 99 | "nixpkgs": "nixpkgs" 100 | } 101 | } 102 | }, 103 | "root": "root", 104 | "version": 7 105 | } 106 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/spectre.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local utils = require("daneharnett.utils") 5 | local spectre_status_ok, spectre = pcall(require, "spectre") 6 | if not spectre_status_ok then 7 | return 8 | end 9 | 10 | spectre.setup({ 11 | result_padding = "", 12 | find_engine = { 13 | -- rg is map with finder_cmd 14 | ["rg"] = { 15 | cmd = "rg", 16 | -- default args 17 | args = { 18 | "--color=never", 19 | "--no-heading", 20 | "--with-filename", 21 | "--line-number", 22 | "--column", 23 | "--glob=!.git/", 24 | }, 25 | options = { 26 | ["ignore-case"] = { 27 | value = "--ignore-case", 28 | icon = "[I]", 29 | desc = "ignore case", 30 | }, 31 | ["hidden"] = { 32 | value = "--hidden", 33 | desc = "hidden file", 34 | icon = "[H]", 35 | }, 36 | -- you can put any rg search option you want here it can toggle with 37 | -- show_option function 38 | }, 39 | }, 40 | }, 41 | }) 42 | 43 | utils.keymap("n", "ss", M.toggle, "Toggle [s]pectre [s]earch") 44 | utils.keymap( 45 | "n", 46 | "sw", 47 | 'lua require("spectre").open_visual({select_word=true})', 48 | "[S]pectre search [w]ord" 49 | ) 50 | utils.keymap( 51 | "v", 52 | "sw", 53 | 'lua require("spectre").open_visual()', 54 | "[S]pectre search [w]ord (visual)" 55 | ) 56 | utils.keymap( 57 | "n", 58 | "scf", 59 | 'lua require("spectre").open_file_search({select_word=true})', 60 | "[S]pectre [c]urrent [f]ile" 61 | ) 62 | end 63 | 64 | local function is_empty(s) 65 | return s == nil or s == "" 66 | end 67 | 68 | local function is_query_empty(query) 69 | if query == nil then 70 | return true 71 | end 72 | return is_empty(query.search_query) and is_empty(query.replace_query) and is_empty(query.path) 73 | end 74 | 75 | function M.toggle() 76 | local spectre_status_ok, spectre = pcall(require, "spectre") 77 | if not spectre_status_ok then 78 | return 79 | end 80 | local spectre_state_status_ok, spectre_state = pcall(require, "spectre.state") 81 | if not spectre_state_status_ok then 82 | return 83 | end 84 | 85 | M.ensure_nvim_tree_is_closed() 86 | 87 | spectre.toggle() 88 | if spectre_state.is_open and not is_query_empty(spectre_state.query_backup) then 89 | spectre.resume_last_search() 90 | end 91 | end 92 | 93 | function M.ensure_nvim_tree_is_closed() 94 | local status_ok, nvim_tree_api = pcall(require, "nvim-tree.api") 95 | if not status_ok then 96 | return 97 | end 98 | 99 | nvim_tree_api.tree.close_in_all_tabs() 100 | end 101 | 102 | return M 103 | -------------------------------------------------------------------------------- /nix/.config/nix/flake.nix: -------------------------------------------------------------------------------- 1 | { 2 | description = "Dane Harnett Darwin system flake"; 3 | 4 | inputs = { 5 | nixpkgs.url = "github:NixOS/nixpkgs/nixpkgs-unstable"; 6 | 7 | nix-darwin.url = "github:LnL7/nix-darwin"; 8 | nix-darwin.inputs.nixpkgs.follows = "nixpkgs"; 9 | 10 | nix-homebrew.url = "github:zhaofengli-wip/nix-homebrew"; 11 | 12 | home-manager = { 13 | url = "github:nix-community/home-manager"; 14 | inputs.nixpkgs.follows = "nixpkgs"; 15 | }; 16 | }; 17 | 18 | outputs = 19 | inputs@{ 20 | self, 21 | nix-darwin, 22 | nixpkgs, 23 | nix-homebrew, 24 | home-manager, 25 | }: 26 | let 27 | configuration = 28 | { pkgs, ... }: 29 | { 30 | # Set Git commit hash for darwin-version. 31 | system.configurationRevision = self.rev or self.dirtyRev or null; 32 | 33 | # nix.package = pkgs.nix; 34 | 35 | # Necessary for using flakes on this system. 36 | nix.settings.experimental-features = "nix-command flakes"; 37 | 38 | nixpkgs.config.allowUnfree = true; 39 | 40 | system.stateVersion = 5; 41 | }; 42 | mkDarwinConfig = 43 | host: system: username: 44 | let 45 | pkgs = import inputs.nixpkgs { inherit system; }; 46 | madeConfig = { 47 | nixpkgs.hostPlatform = "${system}"; 48 | }; 49 | in 50 | nix-darwin.lib.darwinSystem { 51 | modules = [ 52 | madeConfig 53 | configuration 54 | 55 | ./hosts/${host}.nix 56 | 57 | ./modules/aerospace 58 | ./modules/antidote 59 | ./modules/bitwarden 60 | ./modules/borders 61 | ./modules/carapace 62 | ./modules/cargo 63 | ./modules/discord 64 | ./modules/eza 65 | ./modules/fd 66 | ./modules/fnm 67 | ./modules/font-jetbrains-mono-nerd-font 68 | ./modules/fx-cast-bridge 69 | ./modules/fzf 70 | ./modules/gnu-sed 71 | ./modules/helium-browser 72 | ./modules/leader-key 73 | ./modules/neovim 74 | ./modules/nix-tools 75 | ./modules/obs 76 | ./modules/oh-my-posh 77 | ./modules/raycast 78 | ./modules/ripgrep 79 | ./modules/sketchybar 80 | ./modules/slack 81 | ./modules/stow 82 | ./modules/there 83 | ./modules/util-linux 84 | ./modules/vlc 85 | ./modules/vscode 86 | ./modules/wezterm 87 | ./modules/wget 88 | ./modules/yt-dlp 89 | ./modules/zoxide 90 | 91 | nix-homebrew.darwinModules.nix-homebrew 92 | { 93 | nix-homebrew = { 94 | enable = true; 95 | user = "${username}"; 96 | }; 97 | } 98 | 99 | home-manager.darwinModules.home-manager 100 | { 101 | home-manager.useGlobalPkgs = true; 102 | home-manager.useUserPackages = true; 103 | home-manager.users.${username} = import ./home/${username}/${host}.nix; 104 | } 105 | ]; 106 | }; 107 | in 108 | { 109 | darwinConfigurations = { 110 | "personal-m4mbp" = mkDarwinConfig "personal-m4mbp" "aarch64-darwin" "dane"; 111 | }; 112 | }; 113 | } 114 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/nvim-tree.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local status_ok, nvim_tree = pcall(require, "nvim-tree") 5 | if not status_ok then 6 | return 7 | end 8 | 9 | local default_width = 60 10 | 11 | nvim_tree.setup({ 12 | diagnostics = { 13 | enable = true, 14 | }, 15 | filters = { 16 | custom = { 17 | "^\\.git$", 18 | "node_modules", 19 | }, 20 | }, 21 | git = { 22 | enable = false, 23 | }, 24 | on_attach = M.on_attach, 25 | renderer = { 26 | indent_markers = { 27 | enable = true, 28 | }, 29 | }, 30 | view = { 31 | centralize_selection = true, 32 | side = "right", 33 | width = default_width, 34 | }, 35 | }) 36 | 37 | local utils = require("daneharnett.utils") 38 | utils.keymap("n", "e", M.toggle) 39 | utils.keymap("n", "", "NvimTreeResize " .. default_width .. "") 40 | utils.keymap("n", "", "NvimTreeResize 100") 41 | utils.keymap("n", "", "NvimTreeResize +5") 42 | utils.keymap("n", "", "NvimTreeResize -5") 43 | end 44 | 45 | function M.on_attach(bufnr) 46 | local status_ok, nvim_tree_api = pcall(require, "nvim-tree.api") 47 | if not status_ok then 48 | return 49 | end 50 | nvim_tree_api.config.mappings.default_on_attach(bufnr) 51 | 52 | -- the following keymaps should only be attached to buffers of 53 | -- `NvimTree` filetype. 54 | local file_type = vim.api.nvim_get_option_value("filetype", { buf = bufnr }) 55 | if not file_type == "NvimTree" then 56 | return 57 | end 58 | local utils = require("daneharnett.utils") 59 | utils.keymap("n", "sf", M.spectre_find_in_folder) 60 | end 61 | 62 | function M.toggle() 63 | local status_ok, nvim_tree_api = pcall(require, "nvim-tree.api") 64 | if not status_ok then 65 | return 66 | end 67 | 68 | M.ensure_spectre_is_closed() 69 | 70 | nvim_tree_api.tree.toggle({ 71 | find_file = true, 72 | }) 73 | end 74 | 75 | function M.ensure_spectre_is_closed() 76 | local spectre_status_ok, spectre = pcall(require, "spectre") 77 | if not spectre_status_ok then 78 | return 79 | end 80 | local spectre_state_status_ok, spectre_state = pcall(require, "spectre.state") 81 | if not spectre_state_status_ok then 82 | return 83 | end 84 | 85 | if spectre_state.is_open then 86 | spectre.toggle() 87 | end 88 | end 89 | 90 | function M.spectre_find_in_folder() 91 | local status_ok, nvim_tree_api = pcall(require, "nvim-tree.api") 92 | if not status_ok then 93 | return 94 | end 95 | local spectre_status_ok, spectre = pcall(require, "spectre") 96 | if not spectre_status_ok then 97 | return 98 | end 99 | local plenary_status_ok, plenary = pcall(require, "plenary") 100 | if not plenary_status_ok then 101 | return 102 | end 103 | 104 | local node = nvim_tree_api.tree.get_node_under_cursor() 105 | if node.type == "directory" then 106 | node = node 107 | else 108 | node = node.parent 109 | end 110 | 111 | local relative_path = plenary.path:new(node.absolute_path):make_relative() 112 | local path = relative_path .. "/**" 113 | 114 | nvim_tree_api.tree.toggle() 115 | 116 | spectre.toggle({ 117 | path = path, 118 | }) 119 | end 120 | 121 | return M 122 | -------------------------------------------------------------------------------- /healthcheck: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | # This script is used to check if a new computer has all the desired programs 4 | # installed, if not it helps instruct how to install them. 5 | 6 | # check for brew 7 | if [[ ! $(command -v "brew") ]]; then 8 | echo -e "brew not installed. go to https://brew.sh/" 9 | else 10 | echo -e "brew installed." 11 | fi 12 | 13 | # check for stow 14 | if [[ ! $(command -v "stow") ]]; then 15 | echo -e "stow not installed. run brew install stow" 16 | else 17 | echo -e "stow installed." 18 | fi 19 | 20 | # check for eza 21 | if [[ ! $(command -v "eza") ]]; then 22 | echo -e "eza not installed. run brew install eza" 23 | else 24 | echo -e "eza installed." 25 | fi 26 | 27 | # check for zoxide 28 | if [[ ! $(command -v "zoxide") ]]; then 29 | echo -e "zoxide not installed. run brew install zoxide" 30 | else 31 | echo -e "zoxide installed." 32 | fi 33 | 34 | # check for fd 35 | if [[ ! $(command -v "fd") ]]; then 36 | echo -e "fd not installed. run brew install fd" 37 | else 38 | echo -e "fd installed." 39 | fi 40 | 41 | # check for ripgrep 42 | if [[ ! $(command -v "rg") ]]; then 43 | echo -e "rg not installed. run brew install ripgrep" 44 | else 45 | echo -e "rg installed." 46 | fi 47 | 48 | # check for fzf 49 | if [[ ! $(command -v "fzf") ]]; then 50 | echo -e "fzf not installed. run brew install fzf" 51 | else 52 | echo -e "fzf installed." 53 | fi 54 | 55 | # check for fast node manager (fnm) 56 | if [[ ! $(command -v "fnm") ]]; then 57 | echo -e "fnm not installed. run brew install fnm" 58 | else 59 | echo -e "fnm installed." 60 | fi 61 | # check for node (and npm) 62 | if [[ ! $(command -v "node") ]]; then 63 | echo -e "node not installed. run fnm install " 64 | else 65 | echo -e "node installed." 66 | fi 67 | 68 | # check for neovim 69 | if [[ ! $(command -v "nvim") ]]; then 70 | echo -e "neovim not installed. run brew install neovim" 71 | else 72 | echo -e "neovim installed." 73 | fi 74 | 75 | # check for tmux 76 | if [[ ! $(command -v "tmux") ]]; then 77 | echo -e "tmux not installed. run: brew install tmux" 78 | else 79 | echo -e "tmux installed." 80 | fi 81 | 82 | # check for efm-langserver 83 | if [[ ! $(command -v "efm-langserver") ]]; then 84 | echo -e "efm-langserver not installed. run: brew install efm-langserver" 85 | else 86 | echo -e "efm-langserver installed." 87 | fi 88 | 89 | # check for diagnostic-languageserver 90 | if [[ ! $(command -v "diagnostic-languageserver") ]]; then 91 | echo -e "diagnostic-languageserver not installed. run: npm i -g diagnostic-languageserver" 92 | else 93 | echo -e "diagnostic-languageserver installed." 94 | fi 95 | 96 | # check for tmux plugin manager (tpm) 97 | if [[ ! -f ~/.tmux/plugins/tpm/README.md ]]; then 98 | echo -e "tmux plugin manager not installed. go to https://github.com/tmux-plugins/tpm" 99 | else 100 | echo -e "tmux plugin manager installed." 101 | fi 102 | 103 | # check for zsh 104 | if [[ ! $(command -v "zsh") ]]; then 105 | echo -e "zsh not installed. wut." 106 | else 107 | echo -e "zsh installed." 108 | fi 109 | 110 | # check for antidote 111 | if [[ ! -f "$(brew --prefix)/opt/antidote/share/antidote/antidote.zsh" ]]; then 112 | echo -e "antidote not installed. run: brew install antidote" 113 | else 114 | echo -e "antidote installed." 115 | fi 116 | 117 | # check that the antidote plugins have been bundled. 118 | if [[ ! -f ~/.zsh_plugins.zsh ]]; then 119 | echo -e "antidote plugins not bundled. run: antidote bundle <~/.zsh_plugins.txt >~/.zsh_plugins.zsh" 120 | else 121 | echo -e "antidote plugins bundled." 122 | fi 123 | 124 | # check for aerospace 125 | if [[ ! $(command -v "aerospace") ]]; then 126 | echo -e "aerospace not installed. run: brew install --cask nikitabobko/tap/aerospace" 127 | else 128 | echo -e "aerospace installed." 129 | fi 130 | 131 | # check for borders 132 | if [[ ! $(command -v "borders") ]]; then 133 | echo -e "borders not installed. run: brew install FelixKratz/formulae/borders" 134 | else 135 | echo -e "borders installed." 136 | fi 137 | 138 | # check for gnu-sed 139 | if [[ ! $(command -v "gsed") ]]; then 140 | echo -e "gnu-sed not installed. run: brew install gnu-sed" 141 | else 142 | echo -e "gnu-sed installed." 143 | fi 144 | 145 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/command-palette.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | -- Exclude this from vscode 5 | if vim.g.vscode then 6 | return 7 | end 8 | 9 | local pickers = require("telescope.pickers") 10 | local finders = require("telescope.finders") 11 | local conf = require("telescope.config").values 12 | local actions = require("telescope.actions") 13 | local action_state = require("telescope.actions.state") 14 | 15 | local commands = { 16 | { 17 | title = "Find in project", 18 | command = "TelescopeCustomLiveGrep", 19 | }, 20 | { 21 | title = "Find files including hidden", 22 | command = "TelescopeFindFilesIncludingHidden", 23 | }, 24 | { 25 | title = "Live grep with globs", 26 | command = "TelescopeLiveGrepWithGlobs", 27 | }, 28 | { 29 | title = "Lsp references", 30 | command = "Telescope lsp_references", 31 | }, 32 | { 33 | title = "Toggle terminal", 34 | command = "ToggleTerm", 35 | }, 36 | { 37 | title = "Git changed files", 38 | command = "Telescope git_status", 39 | }, 40 | { 41 | title = "Git commit history", 42 | command = "Telescope git_commits", 43 | }, 44 | { 45 | title = "List diagnostics for workspace", 46 | command = "Telescope diagnostics", 47 | }, 48 | { 49 | title = "List diagnostics for current file", 50 | command = "Telescope diagnostics bufnr=0", 51 | }, 52 | { 53 | title = "Harpoon: mark add file", 54 | command = "lua require('harpoon.mark').add_file()", 55 | }, 56 | { 57 | title = "Harpoon: open marks in telescope", 58 | command = "Telescope harpoon marks", 59 | }, 60 | { 61 | title = "Blamer: toggle", 62 | command = "BlamerToggle", 63 | }, 64 | { 65 | title = "Resume last cached telescope picker", 66 | command = "Telescope resume", 67 | }, 68 | { 69 | title = "LSP: rename", 70 | command = vim.lsp.buf.rename, 71 | }, 72 | } 73 | 74 | local function open_command_palette() 75 | local opts = {} 76 | pickers 77 | .new(opts, { 78 | -- This option ensures that the command palette is not cahhed 79 | -- therefore ensuring that it does not get resumed when triggering 80 | -- Telescope resume, meaning I can trigger resume from the command 81 | -- palette itself. 82 | cache_picker = false, 83 | prompt_title = "Command palette", 84 | finder = finders.new_table({ 85 | results = commands, 86 | entry_maker = function(entry) 87 | return { 88 | value = entry, 89 | display = entry.title, 90 | ordinal = entry.title, 91 | } 92 | end, 93 | }), 94 | sorter = conf.generic_sorter(opts), 95 | attach_mappings = function(prompt_bufnr) 96 | actions.select_default:replace(function() 97 | actions.close(prompt_bufnr) 98 | local selection = action_state.get_selected_entry() 99 | vim.schedule(function() 100 | if type(selection.value.command) == "function" then 101 | selection.value.command() 102 | else 103 | vim.cmd(selection.value.command) 104 | end 105 | end) 106 | end) 107 | return true 108 | end, 109 | }) 110 | :find() 111 | end 112 | 113 | local utils = require("daneharnett.utils") 114 | utils.keymap("n", "cp", open_command_palette) 115 | end 116 | 117 | return M 118 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lazy-lock.json: -------------------------------------------------------------------------------- 1 | { 2 | "Comment.nvim": { "branch": "master", "commit": "e30b7f2008e52442154b66f7c519bfd2f1e32acb" }, 3 | "LuaSnip": { "branch": "master", "commit": "458560534a73f7f8d7a11a146c801db00b081df0" }, 4 | "better-ts-errors.nvim": { "branch": "main", "commit": "d57a7794b271e1a0010d0328e5d3f18e20f1face" }, 5 | "blamer.nvim": { "branch": "master", "commit": "e0d43c11697300eb68f00d69df8b87deb0bf52dc" }, 6 | "blink.cmp": { "branch": "main", "commit": "327fff91fe6af358e990be7be1ec8b78037d2138" }, 7 | "bufferline.nvim": { "branch": "main", "commit": "655133c3b4c3e5e05ec549b9f8cc2894ac6f51b3" }, 8 | "catppuccin": { "branch": "main", "commit": "30fa4d122d9b22ad8b2e0ab1b533c8c26c4dde86" }, 9 | "completion-treesitter": { "branch": "master", "commit": "45c9b2faff4785539a0d0c655440c2465fed985a" }, 10 | "conform.nvim": { "branch": "master", "commit": "b4aab989db276993ea5dcb78872be494ce546521" }, 11 | "diffview.nvim": { "branch": "main", "commit": "4516612fe98ff56ae0415a259ff6361a89419b0a" }, 12 | "editorconfig-vim": { "branch": "master", "commit": "6a58b7c11f79c0e1d0f20533b3f42f2a11490cf8" }, 13 | "fidget.nvim": { "branch": "main", "commit": "0ba1e16d07627532b6cae915cc992ecac249fb97" }, 14 | "fzf-lua": { "branch": "main", "commit": "52b8199b9bf185720389d5ca99350ae26a724a2d" }, 15 | "gitsigns.nvim": { "branch": "main", "commit": "f780609807eca1f783a36a8a31c30a48fbe150c5" }, 16 | "harpoon": { "branch": "master", "commit": "1bc17e3e42ea3c46b33c0bbad6a880792692a1b3" }, 17 | "lazy.nvim": { "branch": "main", "commit": "6c3bda4aca61a13a9c63f1c1d1b16b9d3be90d7a" }, 18 | "lazydev.nvim": { "branch": "main", "commit": "258d2a5ef4a3e3d6d9ba9da72c9725c53e9afcbd" }, 19 | "lspsaga.nvim": { "branch": "main", "commit": "8efe00d6aed9db6449969f889170f1a7e43101a1" }, 20 | "lualine.nvim": { "branch": "master", "commit": "b8c23159c0161f4b89196f74ee3a6d02cdc3a955" }, 21 | "mason-lspconfig.nvim": { "branch": "main", "commit": "7f9a39fcd2ac6e979001f857727d606888f5909c" }, 22 | "mason-nvim-lint": { "branch": "main", "commit": "767b8ccdddaa977bec8987fd7507b9865a279235" }, 23 | "mason-tool-installer.nvim": { "branch": "main", "commit": "517ef5994ef9d6b738322664d5fdd948f0fdeb46" }, 24 | "mason.nvim": { "branch": "main", "commit": "7dc4facca9702f95353d5a1f87daf23d78e31c2a" }, 25 | "nui.nvim": { "branch": "main", "commit": "de740991c12411b663994b2860f1a4fd0937c130" }, 26 | "nvim-autopairs": { "branch": "master", "commit": "23320e75953ac82e559c610bec5a90d9c6dfa743" }, 27 | "nvim-biscuits": { "branch": "main", "commit": "dae2323054b9ff3a1f6300847dee29c00cdabdde" }, 28 | "nvim-colorizer.lua": { "branch": "master", "commit": "a065833f35a3a7cc3ef137ac88b5381da2ba302e" }, 29 | "nvim-lint": { "branch": "master", "commit": "0864f81c681e15d9bdc1156fe3a17bd07db5a3ed" }, 30 | "nvim-lspconfig": { "branch": "master", "commit": "1f7fbc34e6420476142b5cc85e9bee52717540fb" }, 31 | "nvim-notify": { "branch": "master", "commit": "8701bece920b38ea289b457f902e2ad184131a5d" }, 32 | "nvim-spectre": { "branch": "master", "commit": "72f56f7585903cd7bf92c665351aa585e150af0f" }, 33 | "nvim-tree.lua": { "branch": "master", "commit": "e179ad2f83b5955ab0af653069a493a1828c2697" }, 34 | "nvim-treesitter": { "branch": "master", "commit": "42fc28ba918343ebfd5565147a42a26580579482" }, 35 | "nvim-treesitter-context": { "branch": "master", "commit": "41847d3dafb5004464708a3db06b14f12bde548a" }, 36 | "nvim-web-devicons": { "branch": "master", "commit": "6e51ca170563330e063720449c21f43e27ca0bc1" }, 37 | "playground": { "branch": "master", "commit": "ba48c6a62a280eefb7c85725b0915e021a1a0749" }, 38 | "plenary.nvim": { "branch": "master", "commit": "b9fd5226c2f76c951fc8ed5923d85e4de065e509" }, 39 | "popup.nvim": { "branch": "master", "commit": "b7404d35d5d3548a82149238289fa71f7f6de4ac" }, 40 | "schemastore.nvim": { "branch": "main", "commit": "8ebf58bd467f353d18cfa71776b33b28a68130de" }, 41 | "telescope-fzf-native.nvim": { "branch": "main", "commit": "1f08ed60cafc8f6168b72b80be2b2ea149813e55" }, 42 | "telescope-ui-select.nvim": { "branch": "master", "commit": "6e51d7da30bd139a6950adf2a47fda6df9fa06d2" }, 43 | "telescope.nvim": { "branch": "master", "commit": "b4da76be54691e854d3e0e02c36b0245f945c2c7" }, 44 | "todo-comments.nvim": { "branch": "main", "commit": "304a8d204ee787d2544d8bc23cd38d2f929e7cc5" }, 45 | "toggleterm.nvim": { "branch": "main", "commit": "9a88eae817ef395952e08650b3283726786fb5fb" }, 46 | "trouble.nvim": { "branch": "main", "commit": "f176232e7759c4f8abd923c21e3e5a5c76cd6837" }, 47 | "vim-fugitive": { "branch": "master", "commit": "61b51c09b7c9ce04e821f6cf76ea4f6f903e3cf4" }, 48 | "vim-polyglot": { "branch": "master", "commit": "f061eddb7cdcc614c8406847b2bfb53099832a4e" }, 49 | "vim-smoothie": { "branch": "master", "commit": "df1e324e9f3395c630c1c523d0555a01d2eb1b7e" }, 50 | "vim-test": { "branch": "master", "commit": "5ee3c0b3734eab612b9f70bbc8a4f69f17f8e8ef" } 51 | } 52 | -------------------------------------------------------------------------------- /oh-my-posh/.config/oh-my-posh/default.toml: -------------------------------------------------------------------------------- 1 | "$schema" = "https://raw.githubusercontent.com/JanDeDobbeleer/oh-my-posh/main/themes/schema.json" 2 | console_title_template = '{{ .Shell }} in {{ .Folder }}' 3 | final_space = true 4 | version = 3 5 | 6 | [[blocks]] 7 | type = 'prompt' 8 | alignment = 'left' 9 | 10 | [[blocks.segments]] 11 | type = 'session' 12 | style = 'diamond' 13 | leading_diamond = '' 14 | trailing_diamond = '' 15 | template = ' {{ if .SSHSession }} {{ end }}{{ .UserName }} ' 16 | background = 'p:yellow' 17 | foreground = 'p:black' 18 | 19 | [[blocks.segments]] 20 | type = 'path' 21 | style = 'powerline' 22 | powerline_symbol = '' 23 | template = '  {{ path .Path .Location }} ' 24 | background = 'p:orange' 25 | foreground = 'p:black' 26 | 27 | [blocks.segments.properties] 28 | style = 'folder' 29 | 30 | # [[blocks.segments]] 31 | # type = 'git' 32 | # style = 'powerline' 33 | # powerline_symbol = '' 34 | # foreground_templates = ['{{ if or (.Working.Changed) (.Staging.Changed) }}p:black{{ end }}', '{{ if and (gt .Ahead 0) (gt .Behind 0) }}p:white{{ end }}', '{{ if gt .Ahead 0 }}p:white{{ end }}'] 35 | # background_templates = ['{{ if or (.Working.Changed) (.Staging.Changed) }}p:yellow{{ end }}', '{{ if and (gt .Ahead 0) (gt .Behind 0) }}p:red{{ end }}', '{{ if gt .Ahead 0 }}#49416D{{ end }}', '{{ if gt .Behind 0 }}#7A306C{{ end }}'] 36 | # template = ' {{ if .UpstreamURL }}{{ url .UpstreamIcon .UpstreamURL }} {{ end }}{{ .HEAD }}{{if .BranchStatus }} {{ .BranchStatus }}{{ end }}{{ if .Working.Changed }}  {{ .Working.String }}{{ end }}{{ if .Staging.Changed }}  {{ .Staging.String }}{{ end }} ' 37 | # background = 'p:green' 38 | # foreground = 'p:black' 39 | # 40 | # [blocks.segments.properties] 41 | # branch_max_length = 25.0 42 | # fetch_status = true 43 | # fetch_upstream_icon = true 44 | 45 | [[blocks.segments]] 46 | type = 'root' 47 | style = 'powerline' 48 | powerline_symbol = '' 49 | template = '  ' 50 | background = 'p:yellow' 51 | foreground = 'p:black' 52 | 53 | [[blocks.segments]] 54 | type = 'status' 55 | style = 'diamond' 56 | background_templates = ['{{ if gt .Code 0 }}p:red{{ end }}'] 57 | leading_diamond = '' 58 | trailing_diamond = '' 59 | template = ' {{ if gt .Code 0 }}{{ else }}{{ end }} ' 60 | background = 'p:blue' 61 | foreground = 'p:black' 62 | 63 | [blocks.segments.properties] 64 | always_enabled = true 65 | 66 | [[blocks]] 67 | type = 'rprompt' 68 | 69 | [[blocks.segments]] 70 | type = 'node' 71 | style = 'plain' 72 | template = ' ' 73 | background = 'transparent' 74 | foreground = 'p:green' 75 | 76 | [blocks.segments.properties] 77 | display_mode = 'files' 78 | fetch_package_manager = false 79 | home_enabled = false 80 | 81 | [[blocks.segments]] 82 | type = 'go' 83 | style = 'plain' 84 | template = ' ' 85 | background = 'transparent' 86 | foreground = 'p:blue' 87 | 88 | [blocks.segments.properties] 89 | fetch_version = false 90 | 91 | [[blocks.segments]] 92 | type = 'python' 93 | style = 'plain' 94 | template = ' ' 95 | background = 'transparent' 96 | foreground = 'p:yellow' 97 | 98 | [blocks.segments.properties] 99 | display_mode = 'files' 100 | fetch_version = false 101 | fetch_virtual_env = false 102 | 103 | [[blocks.segments]] 104 | type = 'shell' 105 | style = 'plain' 106 | template = 'in {{ .Name }} ' 107 | background = 'transparent' 108 | foreground = 'p:white' 109 | 110 | [[blocks.segments]] 111 | type = 'time' 112 | style = 'plain' 113 | template = 'at {{ .CurrentDate | date "15:04:05" }}' 114 | background = 'transparent' 115 | foreground = 'p:white' 116 | 117 | [[tooltips]] 118 | type = 'aws' 119 | tips = ['aws'] 120 | style = 'diamond' 121 | leading_diamond = '' 122 | trailing_diamond = '' 123 | template = '  {{ .Profile }}{{ if .Region }}@{{ .Region }}{{ end }} ' 124 | background = 'p:orange' 125 | foreground = 'p:black' 126 | 127 | [tooltips.properties] 128 | display_default = true 129 | 130 | [[tooltips]] 131 | type = 'az' 132 | tips = ['az'] 133 | style = 'diamond' 134 | leading_diamond = '' 135 | trailing_diamond = '' 136 | template = '  {{ .Name }} ' 137 | background = 'p:blue' 138 | foreground = 'p:black' 139 | 140 | [tooltips.properties] 141 | display_default = true 142 | 143 | [transient_prompt] 144 | template = '<,p:yellow> {{ .Folder }}  ' 145 | background = 'transparent' 146 | foreground = 'p:black' 147 | 148 | [secondary_prompt] 149 | template = '<,p:yellow> >  ' 150 | background = 'transparent' 151 | foreground = 'p:black' 152 | 153 | [palette] 154 | black = '#11111b' 155 | blue = '#89B4FA' 156 | green = '#a6e3a1' 157 | orange = '#fab387' 158 | red = '#f38ba8' 159 | white = '#cdd6f4' 160 | yellow = '#f9e2af' 161 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/null-ls.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local status_ok, null_ls = pcall(require, "null-ls") 5 | if not status_ok then 6 | return 7 | end 8 | local null_ls_utils_status_ok, null_ls_utils = pcall(require, "null-ls.utils") 9 | if not null_ls_utils_status_ok then 10 | return 11 | end 12 | local mason_null_ls_status_ok, mason_null_ls = pcall(require, "mason-null-ls") 13 | if not mason_null_ls_status_ok then 14 | return 15 | end 16 | 17 | local formatting = null_ls.builtins.formatting 18 | local diagnostics = null_ls.builtins.diagnostics 19 | 20 | local get_match_count = function(filepath, needle) 21 | local grep_cmd = "cat " .. filepath .. " | grep -c --max-count=1 " .. needle 22 | local grep_cmd_handle = io.popen(grep_cmd) 23 | if grep_cmd_handle then 24 | local grep_result = grep_cmd_handle:read("*a") 25 | grep_cmd_handle:close() 26 | -- trim whitespace 27 | local count_matches = string.gsub(grep_result, "^%s*(.-)%s*$", "%1") 28 | return tonumber(count_matches) 29 | end 30 | return 0 31 | end 32 | -- this var is used to cache the result of this function so we don't run 33 | -- the grep command over and over. 34 | local is_eslint_project_result = nil 35 | local is_eslint_project = function(utils) 36 | if type(is_eslint_project_result) == "boolean" then 37 | return is_eslint_project_result 38 | end 39 | 40 | local has_eslintrc_js = utils.root_has_file({ ".eslintrc.js", ".eslintrc.json" }) 41 | if has_eslintrc_js then 42 | is_eslint_project_result = true 43 | return true 44 | end 45 | 46 | local has_package_json = utils.root_has_file({ "package.json" }) 47 | local package_json_has_eslint_config = false 48 | if has_package_json then 49 | local filepath = null_ls_utils.path.join({ null_ls_utils.get_root(), "package.json" }) 50 | 51 | local count_matches = get_match_count(filepath, "eslintConfig") 52 | if count_matches >= 1 then 53 | package_json_has_eslint_config = true 54 | end 55 | end 56 | 57 | is_eslint_project_result = package_json_has_eslint_config 58 | return is_eslint_project_result 59 | end 60 | 61 | -- A project is an `eslint prettier` project if it's package.json includes 62 | -- `eslint-plugin-prettier` 63 | local is_eslint_prettier_project_result = nil 64 | local is_eslint_prettier_project = function(utils) 65 | if type(is_eslint_prettier_project_result) == "boolean" then 66 | return is_eslint_prettier_project_result 67 | end 68 | 69 | local has_package_json = utils.root_has_file({ "package.json" }) 70 | if has_package_json then 71 | local filepath = null_ls_utils.path.join({ null_ls_utils.get_root(), "package.json" }) 72 | 73 | local count_matches = get_match_count(filepath, "eslint-plugin-prettier") 74 | if count_matches >= 1 then 75 | is_eslint_prettier_project_result = true 76 | return is_eslint_prettier_project_result 77 | end 78 | end 79 | is_eslint_prettier_project_result = false 80 | return is_eslint_prettier_project_result 81 | end 82 | 83 | local is_prettier_project_result = nil 84 | local is_prettier_project = function(utils) 85 | if type(is_prettier_project_result) == "boolean" then 86 | return is_prettier_project_result 87 | end 88 | 89 | if utils.root_has_file({ ".prettierrc" }) then 90 | is_prettier_project_result = true 91 | return is_prettier_project_result 92 | end 93 | 94 | is_prettier_project_result = false 95 | return is_prettier_project_result 96 | end 97 | 98 | local is_deno_project = function(utils) 99 | return utils.root_has_file({ "deno.json" }) 100 | end 101 | 102 | local should_format_with_prettier = function(utils) 103 | if not is_prettier_project(utils) then 104 | return false 105 | end 106 | if is_eslint_project(utils) and is_eslint_prettier_project(utils) then 107 | return false 108 | end 109 | return true 110 | end 111 | 112 | null_ls.setup({ 113 | diagnostics_format = "[#{c}] #{m} (#{s})", 114 | debug = true, 115 | on_attach = function(_, bufnr) 116 | local utils = require("daneharnett.utils") 117 | -- Set the timeout to 10s as it kept timing out for me. 118 | utils.create_format_on_save_autocmd("NullLs", bufnr, 10000) 119 | end, 120 | -- Support monorepos where a lock file exists in a subfolder. 121 | root_dir = null_ls_utils.root_pattern("package-lock.json", "yarn.lock", ".null-ls-root", "Makefile", ".git"), 122 | sources = { 123 | -- diagnostic sources 124 | diagnostics.eslint_d.with({ 125 | -- We only want this source to apply when the project uses eslint. 126 | condition = is_eslint_project, 127 | timeout = -1, 128 | }), 129 | -- formatting sources 130 | formatting.deno_fmt.with({ 131 | condition = is_deno_project, 132 | timeout = -1, 133 | }), 134 | formatting.prettierd.with({ 135 | -- We only want this source to apply when the project uses prettier 136 | -- and doesn't use eslint, if eslint is used it should be configured 137 | -- with eslint-plugin-prettier. 138 | condition = should_format_with_prettier, 139 | timeout = -1, 140 | }), 141 | formatting.eslint_d.with({ 142 | -- We only want this source to apply when the project uses eslint. 143 | condition = is_eslint_project, 144 | timeout = -1, 145 | }), 146 | formatting.stylua, 147 | }, 148 | }) 149 | 150 | mason_null_ls.setup({ 151 | ensure_installed = nil, 152 | automatic_installation = true, 153 | automatic_setup = false, 154 | }) 155 | end 156 | 157 | return M 158 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/telescope-fused-layout.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | M.get_create_layout = function() 4 | local Layout = require("nui.layout") 5 | local Popup = require("nui.popup") 6 | 7 | local TSLayout = require("telescope.pickers.layout") 8 | 9 | local function make_popup(options) 10 | local popup = Popup(options) 11 | function popup.border:change_title(title) 12 | popup.border.set_text(popup.border, "top", title) 13 | end 14 | return TSLayout.Window(popup) 15 | end 16 | 17 | return function(picker) 18 | local border = { 19 | results = { 20 | top_left = "┌", 21 | top = "─", 22 | top_right = "┬", 23 | right = "│", 24 | bottom_right = "", 25 | bottom = "", 26 | bottom_left = "", 27 | left = "│", 28 | }, 29 | results_patch = { 30 | minimal = { 31 | top_left = "┌", 32 | top_right = "┐", 33 | }, 34 | horizontal = { 35 | top_left = "┌", 36 | top_right = "┬", 37 | }, 38 | vertical = { 39 | top_left = "├", 40 | top_right = "┤", 41 | }, 42 | }, 43 | prompt = { 44 | top_left = "├", 45 | top = "─", 46 | top_right = "┤", 47 | right = "│", 48 | bottom_right = "┘", 49 | bottom = "─", 50 | bottom_left = "└", 51 | left = "│", 52 | }, 53 | prompt_patch = { 54 | minimal = { 55 | bottom_right = "┘", 56 | }, 57 | horizontal = { 58 | bottom_right = "┴", 59 | }, 60 | vertical = { 61 | bottom_right = "┘", 62 | }, 63 | }, 64 | preview = { 65 | top_left = "┌", 66 | top = "─", 67 | top_right = "┐", 68 | right = "│", 69 | bottom_right = "┘", 70 | bottom = "─", 71 | bottom_left = "└", 72 | left = "│", 73 | }, 74 | preview_patch = { 75 | minimal = {}, 76 | horizontal = { 77 | bottom = "─", 78 | bottom_left = "", 79 | bottom_right = "┘", 80 | left = "", 81 | top_left = "", 82 | }, 83 | vertical = { 84 | bottom = "", 85 | bottom_left = "", 86 | bottom_right = "", 87 | left = "│", 88 | top_left = "┌", 89 | }, 90 | }, 91 | } 92 | 93 | local results = make_popup({ 94 | focusable = false, 95 | border = { 96 | style = border.results, 97 | text = { 98 | top = picker.results_title, 99 | top_align = "center", 100 | }, 101 | }, 102 | win_options = { 103 | winhighlight = "Normal:Normal", 104 | }, 105 | }) 106 | 107 | local prompt = make_popup({ 108 | enter = true, 109 | border = { 110 | style = border.prompt, 111 | text = { 112 | top = picker.prompt_title, 113 | top_align = "center", 114 | }, 115 | }, 116 | win_options = { 117 | winhighlight = "Normal:Normal", 118 | }, 119 | }) 120 | 121 | local preview = make_popup({ 122 | focusable = false, 123 | border = { 124 | style = border.preview, 125 | text = { 126 | top = picker.preview_title, 127 | top_align = "center", 128 | }, 129 | }, 130 | }) 131 | 132 | local box_by_kind = { 133 | vertical = Layout.Box({ 134 | Layout.Box(preview, { grow = 1 }), 135 | Layout.Box(results, { grow = 1 }), 136 | Layout.Box(prompt, { size = 3 }), 137 | }, { dir = "col" }), 138 | horizontal = Layout.Box({ 139 | Layout.Box({ 140 | Layout.Box(results, { grow = 1 }), 141 | Layout.Box(prompt, { size = 3 }), 142 | }, { dir = "col", size = "50%" }), 143 | Layout.Box(preview, { size = "50%" }), 144 | }, { dir = "row" }), 145 | minimal = Layout.Box({ 146 | Layout.Box(results, { grow = 1 }), 147 | Layout.Box(prompt, { size = 3 }), 148 | }, { dir = "col" }), 149 | } 150 | 151 | local function get_box() 152 | if picker.previewer == false then 153 | return box_by_kind.minimal, "minimal" 154 | end 155 | 156 | local layout_config = picker.layout_config 157 | local strategy = picker.layout_strategy 158 | if strategy == "vertical" or strategy == "horizontal" then 159 | if layout_config[strategy].preview_width == 0 then 160 | return box_by_kind.minimal, "minimal" 161 | end 162 | return box_by_kind[strategy], strategy 163 | end 164 | 165 | local height, width = vim.o.lines, vim.o.columns 166 | local box_kind = "horizontal" 167 | if width < 100 then 168 | box_kind = "vertical" 169 | if height < 40 then 170 | box_kind = "minimal" 171 | end 172 | end 173 | return box_by_kind[box_kind], box_kind 174 | end 175 | 176 | local function prepare_layout_parts(layout, box_type) 177 | layout.results = results 178 | results.border:set_style(border.results_patch[box_type]) 179 | 180 | layout.prompt = prompt 181 | prompt.border:set_style(border.prompt_patch[box_type]) 182 | 183 | if box_type == "minimal" then 184 | layout.preview = nil 185 | else 186 | layout.preview = preview 187 | preview.border:set_style(border.preview_patch[box_type]) 188 | end 189 | end 190 | 191 | local function get_layout_size(box_kind) 192 | return picker.layout_config[box_kind == "minimal" and "vertical" or box_kind].size 193 | end 194 | 195 | local box, box_kind = get_box() 196 | local layout = Layout({ 197 | relative = "editor", 198 | position = "50%", 199 | size = get_layout_size(box_kind), 200 | }, box) 201 | 202 | layout.picker = picker 203 | prepare_layout_parts(layout, box_kind) 204 | 205 | local layout_update = layout.update 206 | function layout:update() 207 | local box, box_kind = get_box() 208 | prepare_layout_parts(layout, box_kind) 209 | layout_update(self, { size = get_layout_size(box_kind) }, box) 210 | end 211 | 212 | return TSLayout(layout) 213 | end 214 | end 215 | 216 | return M 217 | -------------------------------------------------------------------------------- /aerospace/.config/aerospace/aerospace.toml: -------------------------------------------------------------------------------- 1 | # Place a copy of this config to ~/.aerospace.toml 2 | # After that, you can edit ~/.aerospace.toml to your liking 3 | 4 | # It's not necessary to copy all keys to your config. 5 | # If the key is missing in your config, "default-config.toml" will serve as a fallback 6 | 7 | # You can use it to add commands that run after login to macOS user session. 8 | # 'start-at-login' needs to be 'true' for 'after-login-command' to work 9 | # Available commands: https://nikitabobko.github.io/AeroSpace/commands 10 | after-login-command = [] 11 | 12 | # You can use it to add commands that run after AeroSpace startup. 13 | # 'after-startup-command' is run after 'after-login-command' 14 | # Available commands : https://nikitabobko.github.io/AeroSpace/commands 15 | after-startup-command = [] 16 | 17 | # Start AeroSpace at login 18 | start-at-login = true 19 | 20 | # Normalizations. See: https://nikitabobko.github.io/AeroSpace/guide#normalization 21 | enable-normalization-flatten-containers = true 22 | enable-normalization-opposite-orientation-for-nested-containers = true 23 | 24 | # See: https://nikitabobko.github.io/AeroSpace/guide#layouts 25 | # The 'accordion-padding' specifies the size of accordion padding 26 | # You can set 0 to disable the padding feature 27 | accordion-padding = 30 28 | 29 | # Possible values: tiles|accordion 30 | default-root-container-layout = 'tiles' 31 | 32 | # Possible values: horizontal|vertical|auto 33 | # 'auto' means: wide monitor (anything wider than high) gets horizontal orientation, 34 | # tall monitor (anything higher than wide) gets vertical orientation 35 | default-root-container-orientation = 'auto' 36 | 37 | # Possible values: (qwerty|dvorak) 38 | # See https://nikitabobko.github.io/AeroSpace/guide#key-mapping 39 | key-mapping.preset = 'qwerty' 40 | 41 | # Mouse follows focus when focused monitor changes 42 | # Drop it from your config, if you don't like this behavior 43 | # See https://nikitabobko.github.io/AeroSpace/guide#on-focus-changed-callbacks 44 | # See https://nikitabobko.github.io/AeroSpace/commands#move-mouse 45 | # on-focused-monitor-changed = ['move-mouse monitor-lazy-center'] 46 | 47 | # Gaps between windows (inner-*) and between monitor edges (outer-*). 48 | # Possible values: 49 | # - Constant: gaps.outer.top = 8 50 | # - Per monitor: gaps.outer.top = [{ monitor.main = 16 }, { monitor."some-pattern" = 32 }, 24] 51 | # In this example, 24 is a default value when there is no match. 52 | # Monitor pattern is the same as for 'workspace-to-monitor-force-assignment'. 53 | # See: https://nikitabobko.github.io/AeroSpace/guide#assign-workspaces-to-monitors 54 | [gaps] 55 | inner.horizontal = 6 56 | inner.vertical = 6 57 | outer.left = 3 58 | outer.bottom = 3 59 | outer.top = 3 60 | outer.right = 3 61 | 62 | [workspace-to-monitor-force-assignment] 63 | 1 = 'main' 64 | 10 = 'secondary' 65 | 66 | # 'main' binding mode declaration 67 | # See: https://nikitabobko.github.io/AeroSpace/guide#binding-modes 68 | # 'main' binding mode must be always presented 69 | [mode.main.binding] 70 | 71 | # All possible keys: 72 | # - Letters. a, b, c, ..., z 73 | # - Numbers. 0, 1, 2, ..., 9 74 | # - Keypad numbers. keypad0, keypad1, keypad2, ..., keypad9 75 | # - F-keys. f1, f2, ..., f20 76 | # - Special keys. minus, equal, period, comma, slash, backslash, quote, semicolon, backtick, 77 | # leftSquareBracket, rightSquareBracket, space, enter, esc, backspace, tab 78 | # - Keypad special. keypadClear, keypadDecimalMark, keypadDivide, keypadEnter, keypadEqual, 79 | # keypadMinus, keypadMultiply, keypadPlus 80 | # - Arrows. left, down, up, right 81 | 82 | # All possible modifiers: cmd, alt, ctrl, shift 83 | 84 | # All possible commands: https://nikitabobko.github.io/AeroSpace/commands 85 | 86 | # You can uncomment this line to open up terminal with alt + enter shortcut 87 | # See: https://nikitabobko.github.io/AeroSpace/commands#exec-and-forget 88 | # alt-enter = 'exec-and-forget open -n /System/Applications/Utilities/Terminal.app' 89 | 90 | # See: https://nikitabobko.github.io/AeroSpace/commands#layout 91 | alt-slash = 'layout tiles horizontal vertical' 92 | alt-comma = 'layout accordion horizontal vertical' 93 | 94 | # See: https://nikitabobko.github.io/AeroSpace/commands#focus 95 | alt-h = 'focus left' 96 | alt-j = 'focus down' 97 | alt-k = 'focus up' 98 | alt-l = 'focus right' 99 | 100 | # See: https://nikitabobko.github.io/AeroSpace/commands#move 101 | alt-shift-h = 'move left' 102 | alt-shift-j = 'move down' 103 | alt-shift-k = 'move up' 104 | alt-shift-l = 'move right' 105 | 106 | # See: https://nikitabobko.github.io/AeroSpace/commands#resize 107 | alt-shift-minus = 'resize smart -50' 108 | alt-shift-equal = 'resize smart +50' 109 | 110 | # e for equalize 111 | alt-cmd-ctrl-shift-e = 'balance-sizes' 112 | 113 | # See: https://nikitabobko.github.io/AeroSpace/commands#workspace 114 | alt-cmd-ctrl-shift-1 = 'workspace 1' 115 | alt-cmd-ctrl-shift-2 = 'workspace 10' 116 | alt-3 = 'workspace 3' 117 | alt-4 = 'workspace 4' 118 | alt-5 = 'workspace 5' 119 | alt-6 = 'workspace 6' 120 | alt-7 = 'workspace 7' 121 | alt-8 = 'workspace 8' 122 | alt-9 = 'workspace 9' 123 | alt-cmd-ctrl-shift-a = 'workspace A' # In your config, you can drop workspace bindings that you don't need 124 | alt-cmd-ctrl-shift-b = 'workspace B' 125 | alt-c = 'workspace C' 126 | alt-d = 'workspace D' 127 | 128 | # See: https://nikitabobko.github.io/AeroSpace/commands#move-node-to-workspace 129 | alt-shift-1 = 'move-node-to-workspace 1' 130 | alt-shift-2 = 'move-node-to-workspace 10' 131 | alt-shift-3 = 'move-node-to-workspace 3' 132 | alt-shift-4 = 'move-node-to-workspace 4' 133 | alt-shift-5 = 'move-node-to-workspace 5' 134 | alt-shift-6 = 'move-node-to-workspace 6' 135 | alt-shift-7 = 'move-node-to-workspace 7' 136 | alt-shift-8 = 'move-node-to-workspace 8' 137 | alt-shift-9 = 'move-node-to-workspace 9' 138 | alt-shift-a = 'move-node-to-workspace A' 139 | alt-shift-b = 'move-node-to-workspace B' 140 | alt-shift-c = 'move-node-to-workspace C' 141 | alt-shift-d = 'move-node-to-workspace D' 142 | 143 | # See: https://nikitabobko.github.io/AeroSpace/commands#workspace-back-and-forth 144 | alt-tab = 'workspace-back-and-forth' 145 | # See: https://nikitabobko.github.io/AeroSpace/commands#move-workspace-to-monitor 146 | alt-shift-tab = 'move-workspace-to-monitor --wrap-around next' 147 | 148 | alt-cmd-ctrl-shift-f = 'fullscreen' 149 | 150 | # See: https://nikitabobko.github.io/AeroSpace/commands#mode 151 | alt-cmd-ctrl-shift-semicolon = 'mode service' 152 | 153 | alt-cmd-ctrl-shift-r = 'mode resize' 154 | alt-cmd-ctrl-shift-m = 'mode move' 155 | alt-cmd-ctrl-shift-j = 'mode appswitcher' 156 | 157 | # 'service' binding mode declaration. 158 | # See: https://nikitabobko.github.io/AeroSpace/guide#binding-modes 159 | [mode.service.binding] 160 | esc = ['reload-config', 'mode main'] 161 | r = ['flatten-workspace-tree', 'mode main'] # reset layout 162 | #s = ['layout sticky tiling', 'mode main'] # sticky is not yet supported https://github.com/nikitabobko/AeroSpace/issues/2 163 | f = ['layout floating tiling', 'mode main'] # Toggle between floating and tiling layout 164 | backspace = ['close-all-windows-but-current', 'mode main'] 165 | 166 | h = ['join-with left', 'mode main'] 167 | j = ['join-with down', 'mode main'] 168 | k = ['join-with up', 'mode main'] 169 | l = ['join-with right', 'mode main'] 170 | 171 | [mode.resize.binding] 172 | h = 'resize width -50' 173 | j = 'resize height +50' 174 | k = 'resize height -50' 175 | l = 'resize width +50' 176 | b = 'balance-sizes' 177 | 178 | minus = 'resize smart -50' 179 | equal = 'resize smart +50' 180 | 181 | enter = 'mode main' 182 | esc = 'mode main' 183 | 184 | [mode.move.binding] 185 | 1 = ['move-node-to-workspace 1', 'workspace 1', 'mode main'] 186 | 2 = ['move-node-to-workspace 10', 'workspace 10', 'mode main'] 187 | a = ['move-node-to-workspace A', 'workspace A', 'mode main'] 188 | b = ['move-node-to-workspace B', 'workspace B', 'mode main'] 189 | enter = 'mode main' 190 | esc = 'mode main' 191 | 192 | [mode.appswitcher.binding] 193 | b = [ 194 | 'exec-and-forget ~/.config/aerospace/scripts/open-app-in-fullscreen.sh "Zen Browser"', 195 | 'mode main' 196 | ] 197 | t = [ 198 | 'exec-and-forget ~/.config/aerospace/scripts/open-app-in-fullscreen.sh "WezTerm"', 199 | 'mode main' 200 | ] 201 | enter = 'mode main' 202 | esc = 'mode main' 203 | 204 | # float finder 205 | [[on-window-detected]] 206 | if.app-id = 'com.apple.finder' 207 | check-further-callbacks = true 208 | run = ['layout floating'] 209 | 210 | # float Preview 211 | [[on-window-detected]] 212 | if.app-id = 'com.apple.Preview' 213 | check-further-callbacks = true 214 | run = ['layout floating'] 215 | 216 | # float QuickTime 217 | [[on-window-detected]] 218 | if.app-id = 'com.apple.QuickTimePlayerX' 219 | check-further-callbacks = true 220 | run = ['layout floating'] 221 | 222 | # float Slack huddles 223 | [[on-window-detected]] 224 | if.app-id = 'com.tinyspeck.slackmacgap' 225 | if.window-title-regex-substring = 'Huddle' 226 | check-further-callbacks = true 227 | run = ['layout floating'] 228 | 229 | # float zoom 230 | [[on-window-detected]] 231 | if.app-id = 'us.zoom.xos' 232 | check-further-callbacks = true 233 | run = ['layout floating'] 234 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/lsp.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | local server_configs = { 4 | denols = function() 5 | local utils = require("daneharnett.utils") 6 | 7 | return { 8 | filetypes = utils.get_typescript_filetypes(), 9 | root_dir = function(bufnr, on_dir) 10 | local fname = vim.api.nvim_buf_get_name(bufnr) 11 | local matchesRootPattern = utils.has_deno_config(fname) 12 | if matchesRootPattern then 13 | on_dir(matchesRootPattern) 14 | end 15 | end, 16 | } 17 | end, 18 | eslint = function() 19 | local utils = require("daneharnett.utils") 20 | 21 | return { 22 | filetypes = utils.get_typescript_filetypes(), 23 | root_dir = function(bufnr, on_dir) 24 | local fname = vim.api.nvim_buf_get_name(bufnr) 25 | local matchesRootPattern = utils.has_eslint_config(fname) 26 | if matchesRootPattern then 27 | on_dir(matchesRootPattern) 28 | end 29 | end, 30 | } 31 | end, 32 | jsonls = function() 33 | local schemastore_status_ok, schemastore = pcall(require, "schemastore") 34 | if not schemastore_status_ok then 35 | return 36 | end 37 | 38 | return { 39 | settings = { 40 | json = { 41 | schemas = schemastore.json.schemas(), 42 | validate = { enable = true }, 43 | }, 44 | }, 45 | } 46 | end, 47 | lua_ls = function() 48 | local runtime_path = vim.split(package.path, ";") 49 | table.insert(runtime_path, "lua/?.lua") 50 | table.insert(runtime_path, "lua/?/init.lua") 51 | 52 | return { 53 | settings = { 54 | Lua = { 55 | runtime = { 56 | version = "LuaJIT", 57 | path = runtime_path, 58 | }, 59 | diagnostics = { 60 | globals = { "vim" }, 61 | }, 62 | hint = { 63 | enable = true, 64 | }, 65 | workspace = { 66 | library = vim.api.nvim_get_runtime_file("", true), 67 | }, 68 | telemetry = { 69 | enable = false, 70 | }, 71 | }, 72 | }, 73 | } 74 | end, 75 | rust_analyzer = function() 76 | return {} 77 | end, 78 | nil_ls = function() 79 | return {} 80 | end, 81 | ts_ls = function() 82 | local utils = require("daneharnett.utils") 83 | 84 | return { 85 | filetypes = utils.get_typescript_filetypes(), 86 | init_options = { 87 | maxTsServerMemory = 12288, 88 | preferences = { 89 | importModuleSpecifierPreference = "relative", 90 | }, 91 | }, 92 | -- if the project is a typescript project (has a tsconfig.json) 93 | -- configure for use in monorepos, spawn one process at the root of 94 | -- the project (the directory with `.git`). 95 | -- otherwise, fallback to the location where the tsconfig.json lives 96 | -- otherwise, it's not a typescript project we want to use this lsp 97 | -- with. 98 | root_dir = function(bufnr, on_dir) 99 | local fname = vim.api.nvim_buf_get_name(bufnr) 100 | 101 | local tsconfig_ancestor = utils.has_tsconfig(fname) 102 | if not tsconfig_ancestor then 103 | return nil 104 | end 105 | 106 | local git_ancestor = utils.is_git_repo(fname) 107 | if not git_ancestor then 108 | on_dir(tsconfig_ancestor) 109 | end 110 | 111 | on_dir(git_ancestor) 112 | end, 113 | single_file_support = false, 114 | typescript = { 115 | inlayHints = { 116 | includeInlayEnumMemberValueHints = true, 117 | includeInlayFunctionLikeReturnTypeHints = true, 118 | includeInlayFunctionParameterTypeHints = true, 119 | includeInlayParameterNameHints = "all", 120 | includeInlayParameterNameHintsWhenArgumentMatchesName = true, 121 | includeInlayPropertyDeclarationTypeHints = true, 122 | includeInlayVariableTypeHints = true, 123 | }, 124 | }, 125 | } 126 | end, 127 | } 128 | 129 | local client_on_attach_config = { 130 | rust_analyzer = function(event) 131 | local utils = require("daneharnett.utils") 132 | utils.create_format_on_save_autocmd("Rust", event.buf) 133 | end, 134 | ts_ls = function(event) 135 | local client = vim.lsp.get_client_by_id(event.data.client_id) 136 | -- Need to disable formatting because we will use eslint or prettier instead 137 | client.server_capabilities.documentFormattingProvider = false 138 | client.server_capabilities.documentRangeFormattingProvider = false 139 | 140 | local bte = require("daneharnett.better-ts-errors") 141 | bte.attach_keymaps_to_buffer(event.buf) 142 | end, 143 | } 144 | 145 | function M.init() 146 | local lspconfig_status_ok, lspconfig = pcall(require, "lspconfig") 147 | if not lspconfig_status_ok then 148 | return 149 | end 150 | local mason_status_ok, mason = pcall(require, "mason") 151 | if not mason_status_ok then 152 | return 153 | end 154 | local mason_lspconfig_status_ok, mason_lspconfig = pcall(require, "mason-lspconfig") 155 | if not mason_lspconfig_status_ok then 156 | return 157 | end 158 | local mason_tool_installer_status_ok, mason_tool_installer = pcall(require, "mason-tool-installer") 159 | if not mason_tool_installer_status_ok then 160 | return 161 | end 162 | local blink_cmp_status_ok, blink_cmp = pcall(require, "blink.cmp") 163 | if not blink_cmp_status_ok then 164 | return 165 | end 166 | 167 | local client_capabilities = vim.lsp.protocol.make_client_capabilities() 168 | local blink_cmp_capabilities = blink_cmp.get_lsp_capabilities() 169 | local capabilities = {} 170 | capabilities = vim.tbl_extend("force", {}, client_capabilities) 171 | capabilities = vim.tbl_extend("force", capabilities, blink_cmp_capabilities) 172 | 173 | local servers = {} 174 | for server_name, make_server_config in pairs(server_configs) do 175 | local server_config = make_server_config() 176 | if server_config then 177 | local server_config_built = {} 178 | server_config_built = vim.tbl_extend("force", server_config_built, server_config) 179 | server_config_built = vim.tbl_extend("force", server_config_built, { 180 | capabilities = capabilities, 181 | }) 182 | vim.lsp.config(server_name, server_config_built) 183 | servers[server_name] = server_config_built 184 | end 185 | end 186 | 187 | mason.setup() 188 | mason_lspconfig.setup({ 189 | automatic_installation = false, 190 | ensure_installed = vim.tbl_keys(servers), 191 | }) 192 | mason_tool_installer.setup({ 193 | ensure_installed = { 194 | "prettierd", 195 | "stylua", 196 | "isort", 197 | "black", 198 | "pylint", 199 | }, 200 | }) 201 | 202 | local fidget_status_ok, fidget = pcall(require, "fidget") 203 | if not fidget_status_ok then 204 | return 205 | end 206 | fidget.setup({}) 207 | 208 | M.create_lspattach_autocmd() 209 | end 210 | M.create_lspattach_autocmd = function() 211 | local group = vim.api.nvim_create_augroup("daneharnett-lsp-attach", { clear = true }) 212 | vim.api.nvim_create_autocmd("LspAttach", { 213 | callback = function(event) 214 | local client = vim.lsp.get_client_by_id(event.data.client_id) 215 | local bufnr = event.buf 216 | M.setup_diagnostics() 217 | M.attach_keymaps_to_buffer(bufnr) 218 | 219 | if client and client_on_attach_config[client.name] then 220 | client_on_attach_config[client.name](event) 221 | end 222 | end, 223 | group = group, 224 | }) 225 | end 226 | M.setup_diagnostics = function() 227 | local config = { 228 | -- disable virtual text 229 | virtual_text = false, 230 | -- show signs 231 | signs = { 232 | text = { 233 | [vim.diagnostic.severity.ERROR] = "", 234 | [vim.diagnostic.severity.WARN] = "", 235 | [vim.diagnostic.severity.HINT] = "", 236 | [vim.diagnostic.severity.INFO] = "", 237 | }, 238 | texthl = { 239 | [vim.diagnostic.severity.ERROR] = "DiagnosticSignError", 240 | [vim.diagnostic.severity.WARN] = "DiagnosticSignWarn", 241 | [vim.diagnostic.severity.HINT] = "DiagnosticSignHint", 242 | [vim.diagnostic.severity.INFO] = "DiagnosticSignInfo", 243 | }, 244 | numhl = { 245 | [vim.diagnostic.severity.ERROR] = "", 246 | [vim.diagnostic.severity.WARN] = "", 247 | [vim.diagnostic.severity.HINT] = "", 248 | [vim.diagnostic.severity.INFO] = "", 249 | }, 250 | }, 251 | update_in_insert = true, 252 | underline = true, 253 | severity_sort = true, 254 | float = { 255 | focusable = false, 256 | style = "minimal", 257 | border = "rounded", 258 | source = "always", 259 | header = "", 260 | prefix = "", 261 | }, 262 | } 263 | vim.diagnostic.config(config) 264 | end 265 | 266 | M.attach_keymaps_to_buffer = function(bufnr) 267 | local utils = require("daneharnett.utils") 268 | local my_lspsaga = require("daneharnett.lspsaga") 269 | local my_trouble = require("daneharnett.trouble") 270 | my_lspsaga.attach_keymaps_to_buffer(bufnr) 271 | my_trouble.attach_keymaps_to_buffer(bufnr) 272 | 273 | utils.buffer_keymap(bufnr, { "n", "v" }, "ca", "") 274 | 275 | if vim.lsp.inlay_hint then 276 | utils.buffer_keymap(bufnr, "n", "uh", function() 277 | vim.lsp.inlay_hint(bufnr, nil) 278 | end) 279 | end 280 | end 281 | 282 | return M 283 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/telescope.lua: -------------------------------------------------------------------------------- 1 | local M = {} 2 | 3 | function M.init() 4 | local telescope = require("telescope") 5 | 6 | telescope.setup({ 7 | defaults = M.get_defaults(), 8 | extensions = M.get_extensions(), 9 | pickers = M.get_pickers(), 10 | }) 11 | 12 | M.load_extensions() 13 | M.create_user_commands() 14 | M.attach_keymaps() 15 | end 16 | 17 | M.get_defaults = function() 18 | local actions = require("telescope.actions") 19 | local previewers = require("telescope.previewers") 20 | local sorters = require("telescope.sorters") 21 | local fused_layout = require("daneharnett.telescope-fused-layout") 22 | 23 | return { 24 | file_sorter = sorters.get_fzy_sorter, 25 | path_display = { 26 | truncate = true, 27 | }, 28 | prompt_prefix = " >", 29 | color_devicons = true, 30 | mappings = { 31 | i = { 32 | [""] = actions.cycle_history_next, 33 | [""] = actions.cycle_history_prev, 34 | }, 35 | }, 36 | file_previewer = previewers.vim_buffer_cat.new, 37 | grep_previewer = previewers.vim_buffer_vimgrep.new, 38 | qflist_previewer = previewers.vim_buffer_qflist.new, 39 | layout_strategy = "flex", 40 | layout_config = { 41 | horizontal = { 42 | size = { 43 | width = "90%", 44 | height = "60%", 45 | }, 46 | }, 47 | vertical = { 48 | size = { 49 | width = "90%", 50 | height = "90%", 51 | }, 52 | }, 53 | }, 54 | create_layout = fused_layout.get_create_layout(), 55 | } 56 | end 57 | 58 | M.get_extensions = function() 59 | local themes = require("telescope.themes") 60 | return { 61 | fzf = { 62 | fuzzy = true, 63 | override_generic_sorter = true, 64 | override_file_sorter = true, 65 | case_mode = "smart_case", 66 | }, 67 | ["ui-select"] = { 68 | themes.get_dropdown(), 69 | }, 70 | } 71 | end 72 | 73 | M.get_pickers = function() 74 | return { 75 | buffers = { preview = true }, 76 | find_files = M.get_find_files(), 77 | git_files = {}, 78 | grep_string = { preview = true }, 79 | live_grep = { 80 | additional_args = function() 81 | return { "--hidden" } 82 | end, 83 | }, 84 | oldfiles = {}, 85 | } 86 | end 87 | 88 | M.load_extensions = function() 89 | local telescope = require("telescope") 90 | pcall(telescope.load_extension, "fzf") 91 | pcall(telescope.load_extension, "harpoon") 92 | pcall(telescope.load_extension, "ui-select") 93 | end 94 | 95 | M.create_user_commands = function() 96 | vim.api.nvim_create_user_command("TelescopeFindFilesIncludingHidden", M.find_files_including_hidden, {}) 97 | vim.api.nvim_create_user_command("TelescopeCustomLiveGrep", M.live_grep_with_globs, {}) 98 | vim.api.nvim_create_user_command("TelescopeLiveGrepWithGlobs", M.live_grep_with_globs, {}) 99 | vim.api.nvim_create_user_command("TelescopeInsertPathToDirectory", M.insert_path_to_directory, {}) 100 | end 101 | 102 | M.attach_keymaps = function() 103 | local utils = require("daneharnett.utils") 104 | utils.keymap("n", "", "Telescope find_files") 105 | utils.keymap("n", "dl", "Telescope diagnostics") 106 | utils.keymap("n", "fb", "Telescope file_browser") 107 | utils.keymap("n", "fg", "Telescope git_files") 108 | utils.keymap("n", "fh", "Telescope help_tags") 109 | utils.keymap("n", "fs", "Telescope grep_string") 110 | utils.keymap("n", "lb", "Telescope buffers") 111 | utils.keymap("n", "lg", "Telescope live_grep") 112 | utils.keymap("n", "tr", "Telescope resume") 113 | utils.keymap("n", "ff", "TelescopeLiveGrepWithGlobs") 114 | utils.keymap("n", "fdp", "TelescopeInsertPathToDirectory") 115 | end 116 | 117 | M.live_grep_with_globs = function() 118 | local conf = require("telescope.config").values 119 | local finders = require("telescope.finders") 120 | local make_entry = require("telescope.make_entry") 121 | local pickers = require("telescope.pickers") 122 | 123 | local live_grep_with_globs = finders.new_async_job({ 124 | command_generator = function(prompt) 125 | if not prompt or prompt == "" then 126 | return nil 127 | end 128 | 129 | local prompt_split = vim.split(prompt, " ") 130 | 131 | if not prompt_split[1] or not prompt_split[2] or prompt_split[2] == "" then 132 | return nil 133 | end 134 | 135 | local args = { "rg" } 136 | 137 | -- apply the globs 138 | local pattern = prompt_split[1] 139 | local split_pattern = vim.split(pattern, ",") 140 | 141 | for _, patt in pairs(split_pattern) do 142 | patt = string.gsub(patt, "^%s*(.-)%s*$", "%1") 143 | if patt ~= "" then 144 | table.insert(args, string.format("--glob=%s", patt)) 145 | end 146 | end 147 | 148 | -- apply the search query 149 | local query = prompt_split[2] 150 | 151 | -- a prompt is "regex" if it begins and ends with `/` 152 | local is_regex_query = string.sub(query, 1, 1) == "/" 153 | and string.sub(query, string.len(query), string.len(query)) == "/" 154 | 155 | if is_regex_query then 156 | local query_without_slashes = string.sub(query, 2, string.len(query) - 1) 157 | table.insert(args, string.format("--regexp=%s", query_without_slashes)) 158 | else 159 | table.insert(args, "--fixed-strings") 160 | end 161 | 162 | local command = vim.tbl_flatten({ 163 | args, 164 | { 165 | "--color=never", 166 | "--no-heading", 167 | "--with-filename", 168 | "--line-number", 169 | "--column", 170 | "--smart-case", 171 | "--hidden", 172 | }, 173 | }) 174 | 175 | if not is_regex_query then 176 | table.insert(command, query) 177 | end 178 | 179 | return command 180 | end, 181 | entry_maker = make_entry.gen_from_vimgrep(), 182 | }) 183 | 184 | pickers 185 | .new({ 186 | file_ignore_patterns = { ".git/" }, 187 | }, { 188 | debounce = 100, 189 | prompt_title = "Live grep with globs", 190 | finder = live_grep_with_globs, 191 | previewer = conf.grep_previewer({}), 192 | sorter = require("telescope.sorters").highlighter_only(), 193 | }) 194 | :find() 195 | end 196 | 197 | M.custom_live_grep = function() 198 | local conf = require("telescope.config").values 199 | local finders = require("telescope.finders") 200 | local make_entry = require("telescope.make_entry") 201 | local pickers = require("telescope.pickers") 202 | 203 | local custom_live_grep = finders.new_async_job({ 204 | command_generator = function(prompt) 205 | if not prompt or prompt == "" then 206 | return nil 207 | end 208 | 209 | local query = prompt 210 | 211 | local args = { "rg" } 212 | 213 | -- is "regex" if it begins and ends with `/` 214 | local is_regex_query = string.sub(query, 1, 1) == "/" 215 | and string.sub(query, string.len(query), string.len(query)) == "/" 216 | 217 | if is_regex_query then 218 | local query_without_slashes = string.sub(query, 2, string.len(query) - 1) 219 | table.insert(args, string.format("--regexp=%s", query_without_slashes)) 220 | else 221 | table.insert(args, "--fixed-strings") 222 | end 223 | 224 | local command = vim.tbl_flatten({ 225 | args, 226 | { 227 | "--color=never", 228 | "--no-heading", 229 | "--with-filename", 230 | "--line-number", 231 | "--column", 232 | "--smart-case", 233 | "--hidden", 234 | }, 235 | }) 236 | 237 | if not is_regex_query then 238 | table.insert(command, query) 239 | end 240 | 241 | return command 242 | end, 243 | entry_maker = make_entry.gen_from_vimgrep(), 244 | }) 245 | 246 | pickers 247 | .new({ 248 | file_ignore_patterns = { ".git/" }, 249 | }, { 250 | debounce = 100, 251 | prompt_title = "Live grep", 252 | finder = custom_live_grep, 253 | previewer = conf.grep_previewer({}), 254 | sorter = require("telescope.sorters").highlighter_only(), 255 | }) 256 | :find() 257 | end 258 | 259 | M.insert_path_to_directory = function() 260 | local opts = { 261 | attach_mappings = M.insert_selected_entry, 262 | find_command = { 263 | "fd", 264 | "--type=d", 265 | "--hidden", 266 | "--exclude=.git", 267 | "--exclude=node_modules", 268 | }, 269 | } 270 | require("telescope.builtin").find_files(opts) 271 | end 272 | 273 | M.insert_selected_entry = function(prompt_bufnr) 274 | local actions = require("telescope.actions") 275 | local action_state = require("telescope.actions.state") 276 | 277 | actions.select_default:replace(function() 278 | actions.close(prompt_bufnr) 279 | local selection = action_state.get_selected_entry() 280 | vim.api.nvim_put({ selection[1] }, "c", true, true) 281 | end) 282 | return true 283 | end 284 | 285 | M.get_base_find_command = function() 286 | return { 287 | "rg", 288 | "--files", 289 | "--color=never", 290 | "--no-heading", 291 | "--with-filename", 292 | "--line-number", 293 | "--column", 294 | "--smart-case", 295 | } 296 | end 297 | 298 | M.get_base_find_layout_config = function() 299 | return { 300 | horizontal = { 301 | preview_width = 0, 302 | }, 303 | } 304 | end 305 | 306 | M.get_find_files = function() 307 | return { 308 | attach_mappings = function(_, map) 309 | -- press ctrl+h to toggle hidden files 310 | map("i", "", function(_prompt_bufnr) 311 | local state = require("telescope.actions.state") 312 | M.find_files_including_hidden(state.get_current_line()) 313 | end) 314 | return true 315 | end, 316 | find_command = M.get_base_find_command(), 317 | layout_strategy = "horizontal", 318 | layout_config = M.get_base_find_layout_config(), 319 | } 320 | end 321 | 322 | M.find_files_including_hidden = function(default_text_arg) 323 | local default_text = default_text_arg or "" 324 | local base_find_command = M.get_base_find_command() 325 | local find_command_with_hidden = vim.list_extend({}, base_find_command) 326 | vim.list_extend(find_command_with_hidden, { "--hidden", "--glob=!.git/" }) 327 | local find_files_including_hidden = { 328 | attach_mappings = function(_, map) 329 | -- press ctrl+h to toggle hidden files 330 | map("i", "", function(_prompt_bufnr) 331 | local state = require("telescope.actions.state") 332 | require("telescope.builtin").find_files({ 333 | default_text = state.get_current_line(), 334 | }) 335 | end) 336 | return true 337 | end, 338 | find_command = find_command_with_hidden, 339 | layout_strategy = "horizontal", 340 | layout_config = M.get_base_find_layout_config(), 341 | prompt_title = "Find Files (including hidden)", 342 | default_text = default_text, 343 | } 344 | require("telescope.builtin").find_files(find_files_including_hidden) 345 | end 346 | 347 | return M 348 | -------------------------------------------------------------------------------- /nvim/.config/nvim/lua/daneharnett/plugins.lua: -------------------------------------------------------------------------------- 1 | local plugins = { 2 | -- theme 3 | { 4 | "catppuccin/nvim", 5 | cond = not vim.g.vscode, 6 | config = function() 7 | require("daneharnett.catppuccin").init() 8 | end, 9 | lazy = false, 10 | name = "catppuccin", 11 | -- colorschemes need high priority 12 | priority = 1000, 13 | }, 14 | -- enhanced vim.notify ui 15 | { "rcarriga/nvim-notify" }, 16 | -- treesitter 17 | { 18 | "nvim-treesitter/nvim-treesitter", 19 | config = function() 20 | require("daneharnett.treesitter").init() 21 | end, 22 | }, 23 | { 24 | "nvim-treesitter/completion-treesitter", 25 | }, 26 | { 27 | "nvim-treesitter/nvim-treesitter-context", 28 | }, 29 | { 30 | "nvim-treesitter/playground", 31 | }, 32 | -- nvim-biscuits 33 | { 34 | "code-biscuits/nvim-biscuits", 35 | cond = not vim.g.vscode, 36 | config = function() 37 | require("daneharnett.biscuits").init() 38 | end, 39 | }, 40 | -- A collection of language packs for Vim. 41 | { 42 | "sheerun/vim-polyglot", 43 | }, 44 | -- buffer line (top of buffer) 45 | { 46 | "akinsho/bufferline.nvim", 47 | config = function() 48 | require("daneharnett.bufferline").init() 49 | end, 50 | dependencies = { 51 | { 52 | "nvim-tree/nvim-web-devicons", 53 | }, 54 | }, 55 | }, 56 | -- status line (bottom of buffer) 57 | { 58 | "nvim-lualine/lualine.nvim", 59 | cond = not vim.g.vscode, 60 | config = function() 61 | require("daneharnett.lualine").init() 62 | end, 63 | dependencies = { 64 | { 65 | "nvim-tree/nvim-web-devicons", 66 | }, 67 | }, 68 | }, 69 | -- lsp 70 | { 71 | "folke/lazydev.nvim", 72 | ft = "lua", 73 | opts = { 74 | library = { 75 | { path = "${3rd}/luv/library", words = { "vim%.uv" } }, 76 | }, 77 | }, 78 | }, 79 | { 80 | "neovim/nvim-lspconfig", 81 | config = function() 82 | require("daneharnett.lsp").init() 83 | end, 84 | dependencies = { 85 | { 86 | "williamboman/mason.nvim", 87 | }, 88 | { 89 | "williamboman/mason-lspconfig.nvim", 90 | }, 91 | { "WhoIsSethDaniel/mason-tool-installer.nvim" }, 92 | { 93 | "j-hui/fidget.nvim", 94 | tag = "legacy", 95 | }, 96 | { 97 | "b0o/schemastore.nvim", 98 | }, 99 | { 100 | "saghen/blink.cmp", 101 | }, 102 | }, 103 | }, 104 | { -- Autocompletion 105 | "saghen/blink.cmp", 106 | event = "VimEnter", 107 | version = "1.*", 108 | dependencies = { 109 | -- Snippet Engine 110 | { 111 | "L3MON4D3/LuaSnip", 112 | version = "2.*", 113 | build = (function() 114 | -- Build Step is needed for regex support in snippets. 115 | -- This step is not supported in many windows environments. 116 | -- Remove the below condition to re-enable on windows. 117 | if vim.fn.has("win32") == 1 or vim.fn.executable("make") == 0 then 118 | return 119 | end 120 | return "make install_jsregexp" 121 | end)(), 122 | dependencies = { 123 | -- `friendly-snippets` contains a variety of premade snippets. 124 | -- See the README about individual language/framework/plugin snippets: 125 | -- https://github.com/rafamadriz/friendly-snippets 126 | -- { 127 | -- 'rafamadriz/friendly-snippets', 128 | -- config = function() 129 | -- require('luasnip.loaders.from_vscode').lazy_load() 130 | -- end, 131 | -- }, 132 | }, 133 | opts = {}, 134 | }, 135 | "folke/lazydev.nvim", 136 | }, 137 | --- @module 'blink.cmp' 138 | --- @type blink.cmp.Config 139 | opts = { 140 | keymap = { 141 | -- 'default' (recommended) for mappings similar to built-in completions 142 | -- to accept ([y]es) the completion. 143 | -- This will auto-import if your LSP supports it. 144 | -- This will expand snippets if the LSP sent a snippet. 145 | -- 'super-tab' for tab to accept 146 | -- 'enter' for enter to accept 147 | -- 'none' for no mappings 148 | -- 149 | -- For an understanding of why the 'default' preset is recommended, 150 | -- you will need to read `:help ins-completion` 151 | -- 152 | -- No, but seriously. Please read `:help ins-completion`, it is really good! 153 | -- 154 | -- All presets have the following mappings: 155 | -- /: move to right/left of your snippet expansion 156 | -- : Open menu or open docs if already open 157 | -- / or /: Select next/previous item 158 | -- : Hide menu 159 | -- : Toggle signature help 160 | -- 161 | -- See :h blink-cmp-config-keymap for defining your own keymap 162 | preset = "default", 163 | 164 | -- For more advanced Luasnip keymaps (e.g. selecting choice nodes, expansion) see: 165 | -- https://github.com/L3MON4D3/LuaSnip?tab=readme-ov-file#keymaps 166 | }, 167 | 168 | appearance = { 169 | -- 'mono' (default) for 'Nerd Font Mono' or 'normal' for 'Nerd Font' 170 | -- Adjusts spacing to ensure icons are aligned 171 | nerd_font_variant = "mono", 172 | }, 173 | 174 | completion = { 175 | -- By default, you may press `` to show the documentation. 176 | -- Optionally, set `auto_show = true` to show the documentation after a delay. 177 | documentation = { auto_show = false, auto_show_delay_ms = 500 }, 178 | }, 179 | 180 | sources = { 181 | default = { "lsp", "path", "snippets", "lazydev" }, 182 | providers = { 183 | lazydev = { module = "lazydev.integrations.blink", score_offset = 100 }, 184 | }, 185 | }, 186 | 187 | snippets = { preset = "luasnip" }, 188 | 189 | -- Blink.cmp includes an optional, recommended rust fuzzy matcher, 190 | -- which automatically downloads a prebuilt binary when enabled. 191 | -- 192 | -- By default, we use the Lua implementation instead, but you may enable 193 | -- the rust implementation via `'prefer_rust_with_warning'` 194 | -- 195 | -- See :h blink-cmp-config-fuzzy for more information 196 | fuzzy = { implementation = "prefer_rust" }, 197 | 198 | -- Shows a signature help window while you type arguments for a function 199 | signature = { enabled = true }, 200 | }, 201 | }, 202 | { 203 | "stevearc/conform.nvim", 204 | config = function() 205 | require("daneharnett.formatting").init() 206 | end, 207 | event = { "BufReadPre", "BufNewFile" }, -- to disable, comment this out 208 | }, 209 | { 210 | "mfussenegger/nvim-lint", 211 | config = function() 212 | require("daneharnett.linting").init() 213 | end, 214 | event = { "BufReadPre", "BufNewFile" }, -- to disable, comment this out 215 | }, 216 | { 217 | "rshkarin/mason-nvim-lint", 218 | }, 219 | -- Disabling via commenting this for now as it doesn't quite meet my needs, 220 | -- more tinkering required. 221 | -- { 222 | -- "creativenull/diagnosticls-configs-nvim", 223 | -- dependencies = { 224 | -- { 225 | -- "neovim/nvim-lspconfig", 226 | -- }, 227 | -- }, 228 | -- config = function() 229 | -- require("daneharnett.diagnosticls").init() 230 | -- end, 231 | -- }, 232 | -- { 233 | -- "creativenull/efmls-configs-nvim", 234 | -- dependencies = { 235 | -- { 236 | -- "neovim/nvim-lspconfig", 237 | -- }, 238 | -- }, 239 | -- config = function() 240 | -- require("daneharnett.efmls").init() 241 | -- end, 242 | -- }, 243 | { 244 | "nvimdev/lspsaga.nvim", 245 | config = function() 246 | require("daneharnett.lspsaga").init() 247 | end, 248 | dependencies = { 249 | "nvim-treesitter/nvim-treesitter", 250 | "nvim-tree/nvim-web-devicons", 251 | }, 252 | event = "LspAttach", 253 | }, 254 | -- file-tree sidebar explorer 255 | { 256 | "nvim-tree/nvim-tree.lua", 257 | config = function() 258 | require("daneharnett.nvim-tree").init() 259 | end, 260 | }, 261 | -- harpoon 262 | { 263 | "ThePrimeagen/harpoon", 264 | dependencies = { 265 | { 266 | "nvim-lua/plenary.nvim", 267 | }, 268 | }, 269 | }, 270 | -- telescope 271 | { 272 | "nvim-telescope/telescope.nvim", 273 | config = function() 274 | require("daneharnett.telescope").init() 275 | end, 276 | dependencies = { 277 | { 278 | "nvim-lua/popup.nvim", 279 | }, 280 | { 281 | "nvim-lua/plenary.nvim", 282 | }, 283 | { 284 | "nvim-telescope/telescope-fzf-native.nvim", 285 | build = "make", 286 | }, 287 | { "nvim-telescope/telescope-ui-select.nvim" }, 288 | }, 289 | event = "VeryLazy", 290 | }, 291 | -- trouble 292 | { 293 | "folke/trouble.nvim", 294 | config = function() 295 | require("daneharnett.trouble").init() 296 | end, 297 | dependencies = { 298 | { 299 | "nvim-tree/nvim-web-devicons", 300 | }, 301 | }, 302 | }, 303 | -- editorconfig 304 | { 305 | "editorconfig/editorconfig-vim", 306 | }, 307 | -- vim-smoothie for smooth scrolling 308 | { 309 | "psliwka/vim-smoothie", 310 | }, 311 | -- comments 312 | { 313 | "numToStr/Comment.nvim", 314 | config = function() 315 | require("daneharnett.comment").init() 316 | end, 317 | }, 318 | -- autopairs 319 | { 320 | "windwp/nvim-autopairs", 321 | config = function() 322 | require("daneharnett.autopairs").init() 323 | end, 324 | }, 325 | -- terminal 326 | { 327 | "akinsho/toggleterm.nvim", 328 | config = function() 329 | require("daneharnett.toggleterm").init() 330 | end, 331 | }, 332 | -- run tests 333 | { 334 | "vim-test/vim-test", 335 | config = function() 336 | require("daneharnett.tests").init() 337 | end, 338 | }, 339 | -- show colors visually 340 | { 341 | "norcalli/nvim-colorizer.lua", 342 | config = function() 343 | require("daneharnett.colorizer").init() 344 | end, 345 | }, 346 | -- git 347 | { 348 | "lewis6991/gitsigns.nvim", 349 | config = function() 350 | require("daneharnett.gitsigns").init() 351 | end, 352 | }, 353 | { 354 | "tpope/vim-fugitive", 355 | }, 356 | { 357 | "APZelos/blamer.nvim", 358 | config = function() 359 | require("daneharnett.blamer").init() 360 | end, 361 | }, 362 | { 363 | "nvim-pack/nvim-spectre", 364 | config = function() 365 | require("daneharnett.spectre").init() 366 | end, 367 | dependencies = { 368 | { 369 | "nvim-tree/nvim-web-devicons", 370 | "nvim-lua/plenary.nvim", 371 | }, 372 | }, 373 | }, 374 | -- NOTE: this plugin highlights these types of comments. 375 | { 376 | "folke/todo-comments.nvim", 377 | dependencies = { "nvim-lua/plenary.nvim" }, 378 | opts = {}, 379 | }, 380 | { 381 | "OlegGulevskyy/better-ts-errors.nvim", 382 | dependencies = { "MunifTanjim/nui.nvim" }, 383 | config = function() 384 | require("daneharnett.better-ts-errors").init() 385 | end, 386 | }, 387 | -- { 388 | -- "rmagatti/auto-session", 389 | -- config = function() 390 | -- require("daneharnett.autosession").init() 391 | -- end, 392 | -- }, 393 | -- trialling fzf-lua because telescope can be slow for my large repos 394 | { 395 | "ibhagwan/fzf-lua", 396 | dependencies = { "nvim-tree/nvim-web-devicons" }, 397 | config = function() 398 | require("fzf-lua").setup({}) 399 | 400 | vim.keymap.set({ "n", "v", "i" }, "", function() 401 | require("fzf-lua").complete_path() 402 | end, { silent = true, desc = "Fuzzy complete path" }) 403 | 404 | vim.keymap.set({ "n", "v", "i" }, "", function() 405 | require("fzf-lua").complete_path({ 406 | cmd = "fd --type=d --hidden --exclude=.git --exclude=node_modules", 407 | }) 408 | end, { silent = true, desc = "Fuzzy complete directory path" }) 409 | end, 410 | }, 411 | { 412 | "sindrets/diffview.nvim", 413 | }, 414 | } 415 | 416 | local lazypath = vim.fn.stdpath("data") .. "/lazy/lazy.nvim" 417 | if not (vim.uv or vim.loop).fs_stat(lazypath) then 418 | local lazyrepo = "https://github.com/folke/lazy.nvim.git" 419 | local out = vim.fn.system({ "git", "clone", "--filter=blob:none", "--branch=stable", lazyrepo, lazypath }) 420 | if vim.v.shell_error ~= 0 then 421 | vim.api.nvim_echo({ 422 | { "Failed to clone lazy.nvim:\n", "ErrorMsg" }, 423 | { out, "WarningMsg" }, 424 | { "\nPress any key to exit..." }, 425 | }, true, {}) 426 | vim.fn.getchar() 427 | os.exit(1) 428 | end 429 | end 430 | vim.opt.rtp:prepend(lazypath) 431 | 432 | require("lazy").setup(plugins) 433 | --------------------------------------------------------------------------------