;;; ai/agents.el -*- lexical-binding: t; -*- ;;; ============================================================================ ;;; Claude Code Configuration ;;; ============================================================================ (use-package! claude-code :defer t :config ;; Unset CLAUDECODE to allow running Claude Code inside Emacs sub-processes (setenv "CLAUDECODE" nil) (setq claude-code-program "ccr" claude-code-program-switches '("code" "--dangerously-skip-permissions")) ;; Use Eat backend (setq claude-code-terminal-backend 'eat ;; Emacs-style editing in Claude buffer: RET inserts newline, S-RET sends claude-code-newline-keybinding-style 'shift-return-to-send) ;; Enable global mode (claude-code-mode 1) ;; Emacs-style prefix key (works without Doom/Evil leader keys) (global-set-key (kbd "C-c c") claude-code-command-map) ;; Set Doom leader keybindings (map! :leader (:prefix ("C" . "claude-code") :desc "Start Claude" "c" #'claude-code :desc "Start in directory" "d" #'claude-code-start-in-directory :desc "Continue conversation" "C" #'claude-code-continue :desc "Resume session" "R" #'claude-code-resume :desc "New instance" "i" #'claude-code-new-instance :desc "Kill Claude" "k" #'claude-code-kill :desc "Kill all instances" "K" #'claude-code-kill-all :desc "Send command" "s" #'claude-code-send-command :desc "Send command with context" "x" #'claude-code-send-command-with-context :desc "Send region/buffer" "r" #'claude-code-send-region :desc "Send buffer file" "o" #'claude-code-send-buffer-file :desc "Fix error at point" "e" #'claude-code-fix-error-at-point :desc "Toggle window" "t" #'claude-code-toggle :desc "Switch to buffer" "b" #'claude-code-switch-to-buffer :desc "Select buffer" "B" #'claude-code-select-buffer :desc "Toggle read-only" "z" #'claude-code-toggle-read-only-mode :desc "Cycle mode" "M" #'claude-code-cycle-mode :desc "Transient menu" "m" #'claude-code-transient :desc "Slash commands" "/" #'claude-code-slash-commands :desc "Fork conversation" "f" #'claude-code-fork :desc "Send return" "y" #'claude-code-send-return :desc "Send escape" "n" #'claude-code-send-escape :desc "Send 1" "1" #'claude-code-send-1 :desc "Send 2" "2" #'claude-code-send-2 :desc "Send 3" "3" #'claude-code-send-3)) ;; Optional: Configure window display (side window on right) (add-to-list 'display-buffer-alist '("^\\*claude" (display-buffer-in-side-window) (side . right) (window-width . 90))) ;; Optional: Enable auto-revert for files modified by Claude (global-auto-revert-mode 1) ;; Optional: Increase vterm scrollback for long conversations (add-hook 'claude-code-start-hook (lambda () (when (eq claude-code-terminal-backend 'vterm) (setq-local vterm-max-scrollback 100000))))) ;;; ============================================================================ ;;; Gemini CLI Configuration ;;; ============================================================================ (use-package! gemini-cli :defer t :config ;; Set the Gemini executable (setq gemini-cli-program "gemini" gemini-cli-program-switches nil) ;; Use Eat backend (setq gemini-cli-terminal-backend 'eat ;; Emacs-style editing in Gemini buffer: RET inserts newline, S-RET sends gemini-cli-newline-keybinding-style 'shift-return-to-send) ;; Enable global mode (gemini-cli-mode 1) ;; Emacs-style prefix key (global-set-key (kbd "C-c g") gemini-cli-command-map) ;; Set Doom leader keybindings under SPC G (map! :leader (:prefix ("G" . "gemini-cli") :desc "Start Gemini" "c" #'gemini-cli :desc "Start in directory" "d" #'gemini-cli-start-in-directory :desc "Continue conversation" "C" #'gemini-cli-continue :desc "Resume session" "R" #'gemini-cli-resume :desc "New instance" "i" #'gemini-cli-new-instance :desc "Kill Gemini" "k" #'gemini-cli-kill :desc "Kill all instances" "K" #'gemini-cli-kill-all :desc "Send command" "s" #'gemini-cli-send-command :desc "Send command with context" "x" #'gemini-cli-send-command-with-context :desc "Send region/buffer" "r" #'gemini-cli-send-region :desc "Send buffer file" "o" #'gemini-cli-send-buffer-file :desc "Fix error at point" "e" #'gemini-cli-fix-error-at-point :desc "Toggle window" "t" #'gemini-cli-toggle :desc "Switch to buffer" "b" #'gemini-cli-switch-to-buffer :desc "Select buffer" "B" #'gemini-cli-select-buffer :desc "Toggle read-only" "z" #'gemini-cli-toggle-read-only-mode :desc "Cycle mode" "M" #'gemini-cli-cycle-mode :desc "Transient menu" "m" #'gemini-cli-transient :desc "Slash commands" "/" #'gemini-cli-slash-commands :desc "Fork conversation" "f" #'gemini-cli-fork :desc "Send return" "y" #'gemini-cli-send-return :desc "Send escape" "n" #'gemini-cli-send-escape :desc "Send 1" "1" #'gemini-cli-send-1 :desc "Send 2" "2" #'gemini-cli-send-2 :desc "Send 3" "3" #'gemini-cli-send-3)) ;; Optional: Configure window display (side window on right) (add-to-list 'display-buffer-alist '("^\\*gemini" (display-buffer-in-side-window) (side . right) (window-width . 90))) ;; Optional: Increase vterm scrollback for long conversations (add-hook 'gemini-cli-start-hook (lambda () (when (eq gemini-cli-terminal-backend 'vterm) (setq-local vterm-max-scrollback 100000)))))