Files
bankrupt/home-manager/modules/tmux.nix
T
tomatocream 5dc9962fc5 update CLAUDE.md philosophy, set fish as default shell, improve tmux config
CLAUDE.md: add nix-only rule, verify-after-change rule, teach-debugging rule.
darwin: set fish as default user shell.
tmux: configure better-mouse-mode, fix catppuccin status, add extended keys.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-05-25 12:51:04 +08:00

227 lines
7.1 KiB
Nix

# Terminal multiplexer configurations - Batteries-included developer setup
{
inputs,
lib,
config,
pkgs,
...
}: {
home.packages = with pkgs; [
# Required for some tmux plugins
fzf
# Optional multiplexers
# zellij
];
# Tmux configuration - Optimized for developer productivity
programs.tmux = {
enable = true;
terminal = "tmux-256color";
historyLimit = 50000; # Much larger scrollback
baseIndex = 1; # Windows start at 1
keyMode = "vi";
mouse = true;
prefix = "C-a"; # More ergonomic than C-b
escapeTime = 0; # No delay for escape (important for vim)
sensibleOnTop = false; # sensible's reattach-to-user-namespace overrides default-shell on macOS
shell = "${pkgs.fish}/bin/fish";
plugins = with pkgs.tmuxPlugins; [
# Core essentials
sensible
yank # System clipboard integration
vim-tmux-navigator # Seamless vim/tmux pane navigation
{
plugin = better-mouse-mode;
extraConfig = ''
set -g @scroll-without-changing-pane 'on'
set -g @scroll-in-moused-over-pane 'on'
set -g @emulate-scroll-for-no-mouse-alternate-buffer 'on'
set -g @scroll-speed-num-lines-per-scroll '3'
'';
}
# Session persistence - survive reboots
{
plugin = resurrect;
extraConfig = ''
set -g @resurrect-strategy-nvim 'session'
set -g @resurrect-capture-pane-contents 'on'
set -g @resurrect-processes 'ssh nvim vim "~rails server" "~rails console"'
'';
}
{
plugin = continuum;
extraConfig = ''
set -g @continuum-restore 'on'
set -g @continuum-save-interval '10'
'';
}
# Fast copy with hints (like vimium)
tmux-thumbs
# Fuzzy session management
# Note: sessionx is not packaged in nixpkgs, uncomment if you add it as an overlay
# {
# plugin = sessionx;
# extraConfig = ''
# set -g @sessionx-bind 'o'
# set -g @sessionx-zoxide-mode 'on'
# '';
# }
# URL opening
fzf-tmux-url
# Theme - Catppuccin (mocha)
{
plugin = catppuccin;
extraConfig = ''
set -g @catppuccin_flavor 'mocha'
set -g @catppuccin_window_status_style 'rounded'
set -g @catppuccin_status_background 'default'
# Window format
set -g @catppuccin_window_number_position 'right'
set -g @catppuccin_window_default_fill 'number'
set -g @catppuccin_window_default_text '#W'
set -g @catppuccin_window_current_fill 'number'
set -g @catppuccin_window_current_text '#W'
# Status bar modules
set -g @catppuccin_status_modules_right 'session date_time'
set -g @catppuccin_status_modules_left ""
set -g @catppuccin_date_time_text '%H:%M'
'';
}
];
extraConfig = ''
# ============================================
# GENERAL SETTINGS
# ============================================
# Force fish as the shell override sensible plugin's reattach-to-user-namespace
set -g default-command "${pkgs.fish}/bin/fish"
# True color support
set -ag terminal-overrides ",xterm-256color:RGB"
set -ag terminal-overrides ",*256col*:Tc"
# Extended keys lets tmux forward Shift+Enter, Ctrl+Enter, etc.
set -s extended-keys on
set -as terminal-features 'xterm*:extkeys'
# Undercurl support (for spell checking in nvim)
set -as terminal-overrides ',*:Smulx=\E[4::%p1%dm'
set -as terminal-overrides ',*:Setulc=\E[58::2::%p1%{65536}%/%d::%p1%{256}%/%{255}%&%d::%p1%{255}%&%d%;m'
# Renumber windows when one is closed
set -g renumber-windows on
# Enable focus events (for vim autoread)
set -g focus-events on
# Faster command sequences
set -s escape-time 0
# Increase tmux messages display duration
set -g display-time 4000
# Status bar refresh interval
set -g status-interval 5
# Aggressive resize (useful when switching clients)
setw -g aggressive-resize on
# ============================================
# KEY BINDINGS
# ============================================
# Split panes using | and - in current directory
bind | split-window -h -c "#{pane_current_path}"
bind - split-window -v -c "#{pane_current_path}"
bind '"' split-window -v -c "#{pane_current_path}"
bind % split-window -h -c "#{pane_current_path}"
# New window in current directory
bind c new-window -c "#{pane_current_path}"
# Reload config
bind r source-file ~/.config/tmux/tmux.conf \; display-message "Config reloaded!"
# Quick pane switching with Alt+arrow (no prefix needed)
bind -n M-Left select-pane -L
bind -n M-Right select-pane -R
bind -n M-Up select-pane -U
bind -n M-Down select-pane -D
# Quick pane switching with Alt+hjkl (vim style, no prefix)
bind -n M-h select-pane -L
bind -n M-l select-pane -R
bind -n M-k select-pane -U
bind -n M-j select-pane -D
# Resize panes with prefix + HJKL
bind -r H resize-pane -L 5
bind -r J resize-pane -D 5
bind -r K resize-pane -U 5
bind -r L resize-pane -R 5
# Quick window switching with Alt+number
bind -n M-1 select-window -t 1
bind -n M-2 select-window -t 2
bind -n M-3 select-window -t 3
bind -n M-4 select-window -t 4
bind -n M-5 select-window -t 5
bind -n M-6 select-window -t 6
bind -n M-7 select-window -t 7
bind -n M-8 select-window -t 8
bind -n M-9 select-window -t 9
# Switch to last window
bind Space last-window
# Switch to last session
bind -r Tab switch-client -l
# ============================================
# COPY MODE (vi-style)
# ============================================
# Enter copy mode with prefix + v (in addition to [)
bind v copy-mode
# Vi-style selection in copy mode
bind -T copy-mode-vi v send-keys -X begin-selection
bind -T copy-mode-vi C-v send-keys -X rectangle-toggle
bind -T copy-mode-vi y send-keys -X copy-selection-and-cancel
# ============================================
# POPUP WINDOWS (modern tmux feature)
# ============================================
# Quick terminal popup
bind -n M-t display-popup -E -w 80% -h 80%
# Git status popup
bind g display-popup -E -w 80% -h 80% "lazygit || git status"
# ============================================
# SESSION MANAGEMENT
# ============================================
# Create new session
bind S command-prompt -p "New session name:" "new-session -s '%%'"
# Kill session
bind X confirm-before -p "Kill session #S? (y/n)" kill-session
# Detach other clients (claim session)
bind D detach-client -a
'';
};
}