diff --git a/hm/profiles/shell/zsh/default.nix b/hm/profiles/shell/zsh/default.nix index 1d2c7a50..5dc1d38c 100644 --- a/hm/profiles/shell/zsh/default.nix +++ b/hm/profiles/shell/zsh/default.nix @@ -1,27 +1,22 @@ +{ config, lib, pkgs +, osConfig +, ... +}: +let + inherit (lib) getExe concatLines concatStringsSep mapAttrs mapAttrsToList optionalString stringLength; +in { - osConfig, - config, - lib, - pkgs, - ... -}: { - imports = [ - ../common - ./alias.nix - ./completion.nix - ./dirs.nix - ./highlight.nix - ./history.nix - ./init.nix - #./keymaps.nix - #./plugins - ./plugins.nix - #./vte.nix + imports = [ ../common + ./alias.nix ./completion.nix ./dirs.nix ./highlight.nix + ./history.nix ./init.nix ./plugins.nix ]; programs.zsh = { enable = true; - dotDir = ".config/zsh"; # Relative to $HOME. + + # Relative to $HOME. + # TODO: Generate from config.xdg.configHome + dotDir = ".config/zsh"; # --- Keybindings --- # TODO: Create homeManagerModule for global user keymap setting @@ -54,97 +49,101 @@ #${pkgs.neofetch}/bin/neofetch loginExtra = '' - ${lib.getExe pkgs.fastfetch} + ${getExe pkgs.fastfetch} ''; initExtra = let + # TODO: Dynamic path based on this file's path. prefix = '' # +-- programs.zsh.initExtra --------------------------------+ - # | | + # | File Location: | + # | Repo: ./hm/profiles/shell/zsh/default.nix | # +----------------------------------------------------------+ # +-- add-zsh-hook --+ autoload -Uz add-zsh-hook # Attach functions to shell events ''; - cacheHome = '' - mkdir -p "${config.xdg.cacheHome}/zsh" - ''; - dirstack = '' - # +-- dirstack --+ - # Maintain stack of recent directories for quick traversal - if [[ -f "$DIRSTACKFILE" ]] && (( ''${#dirstack} == 0 )); then - dirstack=("''${(@f)"$(< "$DIRSTACKFILE")"}") - [[ -d "''${dirstack[1]}" ]] && cd -- "''${dirstack[1]}" - fi - chpwd_dirstack() { - print -l -- "$PWD" "''${(u)dirstack[@]}" > "$DIRSTACKFILE" - } - add-zsh-hook -Uz chpwd chpwd_dirstack - setopt AUTO_PUSHD PUSHD_SILENT PUSHD_TO_HOME - setopt PUSHD_IGNORE_DUPS # Remove duplicate entries - setopt PUSHD_MINUS # Revert the +/- operators. - ''; - run-help = '' - # --- run-help ----------------------------------------------- - # Show command's manpage using run-help (aliased to 'help') - # Keybinds: '-H' & '-H' - autoload -Uz run-help # Generic - autoload -Uz run-help-ip run-help-openssl # Command-specific - ${lib.optionalString config.programs.git.enable - "autoload -Uz run-help-git"} - ${lib.optionalString - (osConfig.security.sudo.enable || osConfig.security.sudo-rs.enable) - "autoload -Uz run-help-sudo"} - ''; - rehash = '' - # --- rehash completions ------------------------------------- - # Refresh completions when PATH contents change - zstyle ':completion:*' rehash true - ''; - reset = '' - # --- fix terminal garbage ----------------------------------- - function reset_broken_terminal_test () { print '\e(0\e)B' } - function reset_broken_terminal () { - printf '%b' '\e[0m\e(B\e)0\017\e[?5l\e7\e[0;0r\e8' - }; - add-zsh-hook -Uz precmd reset_broken_terminal + suffix = '' + # +-- /end: programs.zsh.initExtra --------------------------+ ''; - repo-info = '' - # --- git repository greeter --- - last_repository= - check_directory_for_new_repository() { - current_repository=$(git rev-parse --show-toplevel 2> /dev/null) - if [ "$current_repository" ] && \ - [ "$current_repository" != "$last_repository" ]; then - ${lib.getExe pkgs.onefetch} + + mkDivider = sect: let chars = (70-5-4)-(stringLength sect); in "\n# +---[${sect}]${lib.strings.replicate chars "-"}+"; + addDivider = n: v: concatLines [(mkDivider n) v]; + mkSections = sections: concatLines ([prefix] ++ (mapAttrsToList addDivider sections) ++ [suffix]); + + # TODO: Impose ordering on items. + # TODO: Add comments to start of snippet. + # TODO: Separate this functionality into lib. + in mkSections { + cacheHome = ''mkdir -p "${config.xdg.cacheHome}/zsh"''; + dirstack = '' + # Maintain stack of recent directories for quick traversal + if [[ -f "$DIRSTACKFILE" ]] && (( ''${#dirstack} == 0 )); then + dirstack=("''${(@f)"$(< "$DIRSTACKFILE")"}") + [[ -d "''${dirstack[1]}" ]] && cd -- "''${dirstack[1]}" fi - last_repository=$current_repository - } - add-zsh-hook -Uz chpwd check_directory_for_new_repository - #cd() { - # builtin cd "$@" - # check_directory_for_new_repository - #} + chpwd_dirstack() { print -l -- "$PWD" "''${(u)dirstack[@]}" > "$DIRSTACKFILE" } + add-zsh-hook -Uz chpwd chpwd_dirstack + setopt AUTO_PUSHD PUSHD_SILENT PUSHD_TO_HOME + setopt PUSHD_IGNORE_DUPS # Remove duplicate entries + setopt PUSHD_MINUS # Revert the +/- operators. + ''; + run-help = '' + # Show command's manpage using run-help (aliased to 'help') + # Keybinds: '-H' & '-H' + autoload -Uz run-help # Generic + autoload -Uz run-help-ip run-help-openssl # Command-specific + ${optionalString config.programs.git.enable "autoload -Uz run-help-git"} + ${optionalString (osConfig.security.sudo.enable || osConfig.security.sudo-rs.enable) "autoload -Uz run-help-sudo"} + ''; + rehash-completions = '' + # Refresh completions when PATH contents change + zstyle ':completion:*' rehash true + ''; + reset-fix-terminal-garbage = '' + function reset_broken_terminal_test () { print '\e(0\e)B' } + function reset_broken_terminal () { + printf '%b' '\e[0m\e(B\e)0\017\e[?5l\e7\e[0;0r\e8' + }; + add-zsh-hook -Uz precmd reset_broken_terminal + ''; + git-repo-greeter-info = '' + last_repository= + check_directory_for_new_repository() { + current_repository=$(git rev-parse --show-toplevel 2> /dev/null) + if [ "$current_repository" ] && \ + [ "$current_repository" != "$last_repository" ]; then + ${getExe pkgs.onefetch} + fi + last_repository=$current_repository + } + add-zsh-hook -Uz chpwd check_directory_for_new_repository + #cd() { + # builtin cd "$@" + # check_directory_for_new_repository + #} - # optional, greet also when opening shell directly in repository directory - # adds time to startup - #check_directory_for_new_repository - ''; - in - lib.strings.concatStringsSep "\n" [ - prefix - cacheHome - dirstack - rehash - reset - run-help - repo-info - ]; - #prefix + dirstack + rehash + reset + run-help + "\n"; + # optional, greet also when opening shell directly in repository directory + # adds time to startup + #check_directory_for_new_repository + ''; + wordchars-improved = '' + # Better word behavior when using + + # Info: 'https://lgug2z.com/articles/sensible-wordchars-for-most-developers' + # Default: WORDCHARS='*?_-.[]~=/&;!#$%^(){}<>' + # Current: WORDCHARS='*?[]~=&;!#$%^(){}<>' + WORDCHARS='*?[]~=&;!#$%^(){}<>' + ''; + }; shellAliases.help = "run-help"; localVariables = { DIRSTACKSIZE = 20; DIRSTACKFILE = "${config.xdg.cacheHome}/zsh/dirs"; + + # Better word handling with: + + # from: https://lgug2z.com/articles/sensible-wordchars-for-most-developers/ + # default: WORDCHARS = "*?_-.[]~=/&;!#$%^(){}<>"; + # WORDCHARS = "*?[]~=&;!#$%^(){}<>"; }; };