;;; -*- lexical-binding: t; -*- ;;; ~/.config/emacs/init.el --- Refactored init.el (Intel macOS) ;;; ;;; last updated: 2026/01/02 ;;; Author: HEO SeonMeyong ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;; Tips ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;; emacs -nw -q --batch --eval '(message system-configuration-options)' ; Emacs compile option(Commandline) ;; emacs --batch -f batch-byte-compile init.el ; init.elの文法チェック(init.elcは削除すること) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;; Prefix keys memo ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;; C-? : Control+? ;; M-? : Meta(ESC)+? ;; s-? : Super(command)+? ;; S-? : Shift+? (本当?) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;; コメント定義 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;; セミコロン 3 つは段落コメント ;; セミコロン 2 つはコードブロックコメント ;; セミコロン 1 つは、行コメント ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;; Reference site ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;; https://emacs-jp.github.io ; 日本のEmacsユーザーのためのハブサイト ;; https://emacs-jp.github.io/tips/emacs-in-2020 ; * 2020年代のEmacs入門 ;; https://qiita.com/conao3/items/347d7e472afd0c58fbd7 ; * Emacs入門から始めるleaf.el入門 ;; https://qiita.com/conao3/items/dc88bdadb0523ef95878 ; * leaf.elで「init.el」をクリーンにする ;; https://uwabami.github.io/cc-env/Emacs.html ; Emacs の設定 ;; https://zenn.dev/zenwerk/scraps/b1280f66c8d11a ; Emacs設定記 2021 ;; https://www.gnu.org/software/emacs/manual/html_node/emacs/Find-Init.html ; Emacs Manual ;; https://github.com/purcell/exec-path-from-shell ; Macでshellから環境変数を取り込む ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;; log ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;; 2026/01/02 Refactoring by Microsoft Copilot. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;; Path & package bootstrap ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;; 追加の elisp を load-path に加える(存在チェック付き) (let ((extra-paths '("/usr/local/share/emacs/site-lisp" "~/.config/emacs/elisp/"))) (dolist (p extra-paths) (let ((abs (expand-file-name p))) (when (file-directory-p abs) (add-to-list 'load-path abs))))) ;; Info の追加ディレクトリ(Homebrew等) (dolist (info-dir '("/usr/local/share/info/")) (when (file-directory-p info-dir) (add-to-list 'Info-default-directory-list info-dir))) ;; package.el の初期化(early-init.el で package-enable-at-startup を nil にしている前提) (require 'package) (custom-set-variables '(package-archives '(("gnu" . "https://elpa.gnu.org/packages/") ("melpa" . "https://melpa.org/packages/") ("org" . "https://orgmode.org/elpa/"))) '(package-gnupghome-dir (expand-file-name ".gnupg" (getenv "HOME")))) (package-initialize) ;; leaf を未導入なら取得 (unless (package-installed-p 'leaf) (package-refresh-contents) (package-install 'leaf)) (leaf leaf-keywords :ensure t :config (leaf-keywords-init)) ;; customize の書き込み先を分離 (setq custom-file (expand-file-name "~/.config/emacs/custom.el")) (when (file-exists-p custom-file) (load custom-file)) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;; macOS: シェルの環境変数を取り込む(GUI起動でも PATH 等を揃える) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; (leaf exec-path-from-shell :ensure t :require t :when (memq window-system '(mac ns x)) :config (dolist (var '("PATH" "MANPATH" "LD_LIBRARY_PATH" "LIBRARY_PATH")) (add-to-list 'exec-path-from-shell-variables var)) (exec-path-from-shell-initialize)) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;; 基本設定(UI/操作系) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; (leaf cus-start :doc "Builtins のカスタマイズをまとめる" :bind (("M-%" . replace-regexp) ("C-c M-%" . query-replace-regexp) ("C-%" . replace-string) ("C-c C-%" . query-replace) ("C-z" . undo) ("C-x c" . browse-url-at-point) ("C-h" . delete-backward-char) ("C-c C-l" . toggle-truncate-lines) ("C-c /" . comment-or-uncomment-region) ("C-c l" . display-line-numbers-mode) ("C-s" . isearch-forward) ;; mu4e ランチャー ("C-x m" . mu4e) ;; Tab-bar 操作(mac風) ("s-}" . tab-bar-switch-to-next-tab) ("s-{" . tab-bar-switch-to-prev-tab) ("s-T" . tab-new) ("s-w" . tab-close)) :hook ((minibuffer-setup-hook . shrink-window-if-larger-than-buffer)) :custom '((create-lockfiles . nil) ; lockfile を作らない (debug-on-error . t) ; エラー時 backtrace (frame-resize-pixelwise . t) (enable-recursive-minibuffers . t) (history-length . 1000) (history-delete-duplicates . t) (scroll-preserve-screen-position . t) (scroll-conservatively . 10000) (scroll-step . 1) (scroll-margin . 2) (visible-bell . t) (text-quoting-style . 'straight) (truncate-lines . nil) ; 折り返し表示 (tab-width . 8) (line-number-display-limit-width . 10000) (resize-mini-windows . t) (max-mini-window-height . 0.1) (indicate-empty-lines . t) (indicate-buffer-boundaries . 'left) (gc-cons-percentage . 0.2) (gc-cons-threshold . 134217728) ; 128MB (menu-bar-mode . t) (tool-bar-mode . nil) (scroll-bar-mode . nil) (indent-tabs-mode . nil) (transient-mark-mode . t) (tab-bar-mode . t)) :config ;; yes-or-no を y/n に短縮 (defalias 'yes-or-no-p 'y-or-n-p) ;; 改行のバックスラッシュを非表示 (set-display-table-slot standard-display-table 0 ?\ ) (set-display-table-slot standard-display-table 'wrap ?\ ) ;; macOS 固有 (leaf cus-start-mac :when (eq system-type 'darwin) :custom ((ns-alternate-modifier . 'meta) (ns-use-srgb-colorspace . t))) ;; Frame Transparency (for emacs-plus@31) ;; (set-frame-parameter nil 'ns-alpha-elements nil) ; Not use Transparency (set-frame-parameter nil 'ns-alpha-elements '(ns-alpha-all)) ;; Choose elements: ;; - Full list: ns-alpha-default (default face/background) ;; ns-alpha-fringe (fringes + internal border clears) ;; ns-alpha-box (boxed face outlines) ;; ns-alpha-stipple (stipple mask background clears) ;; ns-alpha-relief (3D relief/shadow lines) ;; ns-alpha-glyphs (glyph background fills like hl-line/region) (set-frame-parameter nil 'ns-alpha-elements '(ns-alpha-default ns-alpha-fringe ns-alpha-glyphs)) (set-frame-parameter nil 'alpha-background 0.8) (set-frame-parameter nil 'ns-background-blur 20) ) ;; dired のショートカット (leaf dired :bind ((:dired-mode-map ("u" . dired-up-directory)))) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;; 多言語環境(mule) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; (leaf mule :config (set-language-environment 'Japanese) (set-terminal-coding-system 'utf-8) (set-keyboard-coding-system 'utf-8) (set-buffer-file-coding-system 'utf-8) (set-file-name-coding-system 'utf-8) (set-clipboard-coding-system 'utf-8) (prefer-coding-system 'utf-8) (set-default-coding-systems 'utf-8) (when (eq system-type 'darwin) (customize-set-variable 'default-input-method "macOS"))) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;; GUI/フォント ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; (when (memq window-system '(x mac ns)) (defvar my-frame-parameters '((height . 45) (width . 188) (top . 20) (left . 20) (line-spacing . 0) (left-fringe . 12) (right-fringe . 12) (cursor-type . box) (alpha . 95) (foreground-color . "#F2F2F2") (background-color . "#000040") (cursor-color . "#C0C000") (mouse-color . "#8D8D8D"))) (setq default-frame-alist my-frame-parameters) (setq frame-title-format '(multiple-frames "%b" ("" invocation-name))) (setq blink-cursor-mode t) (setq frame-inherited-parameters '(font tool-bar-lines)) (setq ns-pop-up-frames nil) ;; mac/ns フォント (when (memq window-system '(mac ns)) (global-set-key [s-mouse-1] 'browse-url-at-mouse) (let* ((size 16) (jpfont "PlemolJP") (asciifont "PlemolJP") (h (* size 10))) (set-face-attribute 'default nil :family asciifont :height h) (set-fontset-font t 'katakana-jisx0201 jpfont) (set-fontset-font t 'japanese-jisx0208 jpfont) (set-fontset-font t 'japanese-jisx0212 jpfont) (set-fontset-font t 'japanese-jisx0213-1 jpfont) (set-fontset-font t 'japanese-jisx0213-2 jpfont) (set-fontset-font t '(#x0080 . #x024F) asciifont)) (setq face-font-rescale-alist '(("^-apple-hiragino.*" . 1.2) (".*-Hiragino Maru Gothic ProN-.*" . 1.2) (".*osaka-bold.*" . 1.2) (".*osaka-medium.*" . 1.2) (".*courier-bold-.*-mac-roman" . 1.0) (".*monaco cy-bold-.*-mac-cyrillic" . 0.9) (".*monaco-bold-.*-mac-roman" . 0.9) ("-cdac$" . 1.3)))) ;; マウス設定 (setq mouse-drag-copy-region t) (setq mouse-wheel-scroll-amount '(1 ((shift) . 2) ((control)))) (setq mouse-wheel-progressive-speed nil)) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;; Builtins: modeline/time 等 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; (leaf which-function :custom '((which-function-mode . t))) (leaf time :hook (emacs-startup-hook . display-time-mode) :custom '((display-time-interval . 1) (display-time-string-forms '((format "%s:%s:%s" 24-hours minutes seconds))) (display-time-day-and-date . t))) (leaf browse-url :custom '((browse-url-browser-function . 'browse-url-generic)) :config (when (eq system-type 'darwin) (customize-set-variable 'browse-url-generic-program "open"))) (leaf time-stamp :hook (before-save-hook . time-stamp) :custom '((time-stamp-active . t) (time-stamp-start . "last updated: ") (time-stamp-format . "%Y/%02m/%02d") (time-stamp-end . " \n$"))) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;; 表示/編集補助 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; (setq-default display-line-numbers nil) ;; 行番号は基本オフ(必要なら C-c l で局所的にトグル) (global-display-line-numbers-mode -1) ;; ← nil ではなく -1 で確実に OFF (setq column-number-mode t) (setq size-indication-mode t) (leaf whitespace :require t :hook (find-file-hook . (lambda () (whitespace-mode 1))) :config (setq whitespace-style '(face trailing tabs empty spaces) ;; 全角スペースのみ可視化 whitespace-space-regexp "\\(\\u3000+\\)") ;; フェイスは一度だけ設定 (set-face-attribute 'whitespace-trailing nil :foreground "DeepPink" :background "Purple4" :underline t) (set-face-attribute 'whitespace-tab nil :foreground "RoyalBlue4" :background "gray20" :underline t) (set-face-attribute 'whitespace-space nil :background "blue3" :foreground "GreenYellow" :weight 'bold :underline t) (set-face-attribute 'whitespace-empty nil :foreground "MediumPurple4" :background "thistle4" :underline t) (global-whitespace-mode t)) (leaf paren :hook (emacs-startup-hook . show-paren-mode) :custom '((show-paren-delay . 0) (show-paren-style . 'mixed))) (leaf simple :custom '((kill-ring-max . 100) (kill-read-only-ok . t) (kill-whole-line . nil) (eval-expression-print-length . nil) (eval-expression-print-level . nil) (indent-tabs-mode . nil) (mail-user-agent . 'mu4e-user-agent))) (leaf files :custom '((make-backup-files . t) (backup-by-copying . t) (version-control . t) (kept-new-versions . 2) (kept-old-versions . 2) (delete-old-versions . t) (auto-save-timeout . 15) (auto-save-interval . 60) (delete-auto-save-files . t))) (leaf startup :config (setq init-file-debug t auto-save-list-file-prefix (locate-user-emacs-file "backup/.saves-") inhibit-startup-screen t inhibit-startup-message t inhibit-startup-echo-area-message t initial-scratch-message "")) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;; 補完: company ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; (leaf company :ensure t :bind (("C-M-i" . company-complete) (:company-active-map ("C-n" . company-select-next) ("C-p" . company-select-previous) ("C-s" . company-filter-candidates) ("C-h" . nil) ("C-S-h" . company-show-doc-buffer) ("" . company-complete-common)) (:company-search-map ("C-n" . company-select-next) ("C-p" . company-select-previous))) :custom '((company-idle-delay . 0.3) (company-minimum-prefix-length . 2) (company-transformers . '(company-sort-by-backend-importance)) (company-auto-expand . t) (company-selection-wrap-around . t) (completion-ignore-case . t) (company-dabbrev-downcase . nil) (company-show-numbers . t))) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;; 言語モード ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; (leaf lua-mode :ensure t :mode ("\\.lua\\'" . lua-mode) :interpreter ("lua" . lua-mode) :custom '((lua-indent-level . 2) (lua-indent-string-contents . nil) (lua-indent-nested-block-content-align . t) (lua-indent-close-paren-align . t) (lua-default-application . "/usr/local/bin/lua") (lua-default-command-switches . "-i") (lua-always-show . t)) :config (add-hook 'lua-mode-hook #'company-mode)) (leaf caddyfile-mode :ensure t :mode (("Caddyfile\\'" . caddyfile-mode) ("caddy\\.conf\\'" . caddyfile-mode)) :hook (caddyfile-mode-hook . (lambda () (setq-local tab-width 4 indent-tabs-mode nil)))) (leaf nginx-mode :ensure t :mode (("nginx\\.conf\\'" . nginx-mode)) :hook (nginx-mode-hook . company-mode)) (leaf w3m :ensure t :custom ((w3m-command . "/usr/local/bin/w3m"))) (leaf vc-fossil :ensure t :init (add-to-list 'vc-handled-backends 'Fossil t)) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;; 翻訳: go-translate (鍵は環境変数/認証ストアから取得推奨) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; (leaf go-translate :ensure t :bind (("C-c t" . gt-do-translate)) :custom '((gt-langs . '(en ja))) :config ;; DeepL API キーは環境変数 DEEPL_API_KEY から取得。未設定なら DeepL を使わず Google/Bing へフォールバック。 (let ((deepl-key (getenv "DEEPL_API_KEY"))) (setq gt-default-translator (gt-translator :taker (gt-taker :text 'buffer :pick 'paragraph) :engines (delq nil (list (gt-deepl-engine :key "d7b2482e-9a53-43a5-885d-bc511b7b0aad:fx" :pro nil) (gt-google-engine) (gt-bing-engine))) :render (gt-buffer-render))))) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;; EasyPG (GPG) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; (leaf epa-file :require t :config (epa-file-enable) ;; pinentry-mode は epg-config の変数 (with-eval-after-load 'epg-config (setq epg-pinentry-mode 'loopback))) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;; mu4e 設定を分離ロード ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; (load (expand-file-name "~/.config/emacs/mu4e-init.el") t) (provide 'init) ;;; init.el ends here