;;; camm3-theme.el --- Custom theme based on user palette -*- lexical-binding: t; -*- (deftheme camm3 "Custom theme with neutrals, syntax highlighting, and UI feedback.") (let ((class '((class color) (min-colors 89))) ;; Neutrals & surfaces (bg-base "#f9fbfb") (bg-panel "#f2f4f4") (bg-surface-2 "#e5e7e7") (bg-surface-3 "#d1d3d3") (border "#bdbfbf") (border-focus "#005fdb") ;; Text scale (text-primary "#0d0d0d") (text-secondary "#111111") (text-tertiary "#242424") (text-muted "#373737") (text-faint "#4a4a4a") (text-faint-2 "#5d5d5d") (text-inverse "#ffffff") ;; Syntax highlighting (code-comment "#b2b6b8") (code-builtin "#40b7bf") (code-keyword "#55b0f6") (code-constant "#ffa200") (code-function "#c42020") (code-string "#a8dc19") (code-type "#8a35b8") (code-variable "#f04ceb") (code-number "#f48925") (code-operator "#4a4a4a") ;; UI & feedback (ui-selection "#005fdb") (ui-selection-bg "#e6eeff") (ui-cursor "#005fdb") (ui-active-line "#f0f4ff") (status-error "#c82829") (status-warning "#f48925") (status-success "#22a653") (status-info "#3b82f6")) (custom-theme-set-faces 'camm3 ;; Basic faces `(default ((,class (:background ,bg-base :foreground ,text-primary)))) `(cursor ((,class (:background ,ui-cursor)))) `(region ((,class (:background ,ui-selection-bg :foreground ,ui-selection)))) `(fringe ((,class (:background ,bg-panel :foreground ,text-faint)))) `(highlight ((,class (:background ,ui-active-line)))) `(hl-line ((,class (:background ,ui-active-line)))) `(vertical-border ((,class (:foreground ,border)))) `(window-divider ((,class (:foreground ,border)))) `(window-divider-first-pixel ((,class (:foreground ,border)))) `(window-divider-last-pixel ((,class (:foreground ,border)))) `(minibuffer-prompt ((,class (:foreground ,status-info :weight bold)))) `(link ((,class (:foreground ,status-info :underline t)))) `(link-visited ((,class (:foreground ,code-type :underline t)))) `(shadow ((,class (:foreground ,text-faint)))) `(success ((,class (:foreground ,status-success :weight bold)))) `(warning ((,class (:foreground ,status-warning :weight bold)))) `(error ((,class (:foreground ,status-error :weight bold)))) ;; Mode line `(mode-line ((,class (:background ,bg-surface-2 :foreground ,text-primary :box (:line-width 1 :color ,border))))) `(mode-line-inactive ((,class (:background ,bg-panel :foreground ,text-faint :box (:line-width 1 :color ,border))))) `(mode-line-buffer-id ((,class (:weight bold :foreground ,ui-selection)))) ;; Line numbers `(line-number ((,class (:background ,bg-base :foreground ,text-faint-2)))) `(line-number-current-line ((,class (:background ,ui-active-line :foreground ,text-primary :weight bold)))) ;; Font lock (syntax highlighting) `(font-lock-builtin-face ((,class (:foreground ,code-builtin)))) `(font-lock-comment-face ((,class (:foreground ,code-comment :slant italic)))) `(font-lock-comment-delimiter-face ((,class (:foreground ,code-comment :slant italic)))) `(font-lock-constant-face ((,class (:foreground ,code-constant)))) `(font-lock-doc-face ((,class (:foreground ,code-comment :slant italic)))) `(font-lock-function-name-face ((,class (:foreground ,code-function)))) `(font-lock-keyword-face ((,class (:foreground ,code-keyword)))) `(font-lock-number-face ((,class (:foreground ,code-number)))) `(font-lock-operator-face ((,class (:foreground ,code-operator)))) `(font-lock-string-face ((,class (:foreground ,code-string)))) `(font-lock-type-face ((,class (:foreground ,code-type)))) `(font-lock-variable-name-face ((,class (:foreground ,code-variable)))) `(font-lock-warning-face ((,class (:foreground ,status-warning :weight bold)))) ;; Search & match `(isearch ((,class (:background ,ui-selection :foreground ,text-inverse)))) `(isearch-fail ((,class (:background ,status-error :foreground ,text-inverse)))) `(lazy-highlight ((,class (:background ,ui-selection-bg :foreground ,ui-selection :underline t)))) `(match ((,class (:background ,ui-selection-bg :foreground ,ui-selection)))) ;; Secondary selection (e.g., multiple-cursors) `(secondary-selection ((,class (:background ,bg-surface-3)))) ;; Trailing whitespace `(trailing-whitespace ((,class (:background ,status-error :foreground ,text-inverse)))) ;; Diff (vc-gutter, magit) `(diff-added ((,class (:foreground ,status-success)))) `(diff-removed ((,class (:foreground ,status-error)))) `(diff-refine-added ((,class (:background ,status-success :foreground ,text-inverse)))) `(diff-refine-removed ((,class (:background ,status-error :foreground ,text-inverse)))) `(diff-header ((,class (:background ,bg-panel :foreground ,text-tertiary)))) `(diff-file-header ((,class (:background ,bg-surface-2 :foreground ,text-primary :weight bold)))) ;; Org mode `(org-level-1 ((,class (:foreground ,ui-selection :weight bold :height 1.2)))) `(org-level-2 ((,class (:foreground ,code-function :weight bold :height 1.1)))) `(org-level-3 ((,class (:foreground ,code-type :weight bold)))) `(org-level-4 ((,class (:foreground ,code-variable :weight bold)))) `(org-level-5 ((,class (:foreground ,code-builtin :weight bold)))) `(org-level-6 ((,class (:foreground ,code-constant :weight bold)))) `(org-level-7 ((,class (:foreground ,code-keyword :weight bold)))) `(org-level-8 ((,class (:foreground ,code-string :weight bold)))) `(org-todo ((,class (:foreground ,status-error :weight bold)))) `(org-done ((,class (:foreground ,status-success :weight bold)))) `(org-date ((,class (:foreground ,code-number :underline t)))) `(org-link ((,class (:foreground ,status-info :underline t)))) `(org-block ((,class (:background ,bg-surface-2 :extend t)))) `(org-block-begin-line ((,class (:background ,bg-panel :foreground ,text-faint)))) `(org-block-end-line ((,class (:background ,bg-panel :foreground ,text-faint)))) ;; Doom modeline specific (if using doom-modeline) `(doom-modeline-bar ((,class (:background ,ui-selection)))) `(doom-modeline-buffer-modified ((,class (:foreground ,status-warning)))) `(doom-modeline-buffer-major-mode ((,class (:foreground ,code-type :weight bold)))) `(doom-modeline-project-root-dir ((,class (:foreground ,code-builtin)))) `(doom-modeline-evil-normal-state ((,class (:background ,ui-selection :foreground ,text-inverse)))) `(doom-modeline-evil-insert-state ((,class (:background ,status-success :foreground ,text-inverse)))) `(doom-modeline-evil-visual-state ((,class (:background ,code-variable :foreground ,text-inverse)))) ;; Tree-sitter (if you use tree-sitter modes) `(tree-sitter-hl-face:function.call ((,class (:foreground ,code-function)))) `(tree-sitter-hl-face:function.builtin ((,class (:foreground ,code-builtin)))) `(tree-sitter-hl-face:function ((,class (:foreground ,code-function)))) `(tree-sitter-hl-face:type ((,class (:foreground ,code-type)))) `(tree-sitter-hl-face:constant ((,class (:foreground ,code-constant)))) `(tree-sitter-hl-face:keyword ((,class (:foreground ,code-keyword)))) `(tree-sitter-hl-face:string ((,class (:foreground ,code-string)))) `(tree-sitter-hl-face:comment ((,class (:foreground ,code-comment :slant italic)))) `(tree-sitter-hl-face:variable ((,class (:foreground ,code-variable)))) `(tree-sitter-hl-face:number ((,class (:foreground ,code-number)))) `(tree-sitter-hl-face:operator ((,class (:foreground ,code-operator)))) `(tree-sitter-hl-face:property ((,class (:foreground ,text-secondary)))) ;; Company / Corfu completion `(company-tooltip ((,class (:background ,bg-panel :foreground ,text-primary)))) `(company-tooltip-selection ((,class (:background ,ui-selection-bg :foreground ,ui-selection)))) `(company-tooltip-common ((,class (:foreground ,code-keyword)))) `(company-tooltip-annotation ((,class (:foreground ,text-faint)))) `(company-scrollbar-bg ((,class (:background ,bg-surface-3)))) `(company-scrollbar-fg ((,class (:background ,border)))) `(corfu-current ((,class (:background ,ui-selection-bg :foreground ,ui-selection)))) ;; LSP / Flycheck `(flycheck-error ((,class (:underline (:style wave :color ,status-error))))) `(flycheck-warning ((,class (:underline (:style wave :color ,status-warning))))) `(flycheck-info ((,class (:underline (:style wave :color ,status-info))))) `(lsp-face-highlight-textual ((,class (:background ,ui-active-line :underline t)))) `(lsp-face-highlight-read ((,class (:background ,ui-selection-bg :underline t)))) `(lsp-face-highlight-write ((,class (:background ,ui-selection-bg :underline t)))) ;; Whitespace mode `(whitespace-space ((,class (:foreground ,bg-surface-3)))) `(whitespace-tab ((,class (:foreground ,bg-surface-3)))) `(whitespace-newline ((,class (:foreground ,bg-surface-3)))) `(whitespace-indentation ((,class (:foreground ,bg-surface-3)))) `(whitespace-line ((,class (:background ,ui-active-line :foreground ,text-primary)))) `(whitespace-empty ((,class (:background ,status-error :foreground ,text-inverse)))) ;; Highlight indentation guides (indent-guides) `(highlight-indent-guides-character-face ((,class (:foreground ,border)))) `(highlight-indent-guides-stack-character-face ((,class (:foreground ,bg-surface-3)))) `(highlight-indent-guides-odd-face ((,class (:background ,bg-panel)))) `(highlight-indent-guides-even-face ((,class (:background ,bg-base)))) ;; IMenu / Outline `(imenu-list-entry-face-0 ((,class (:foreground ,code-keyword)))) `(imenu-list-entry-face-1 ((,class (:foreground ,code-function)))) `(imenu-list-entry-face-2 ((,class (:foreground ,code-type)))) `(imenu-list-entry-face-3 ((,class (:foreground ,code-constant)))) ;; Avy (jump hints) `(avy-lead-face ((,class (:background ,ui-selection :foreground ,text-inverse :weight bold)))) `(avy-lead-face-0 ((,class (:background ,status-success :foreground ,text-inverse :weight bold)))) `(avy-lead-face-1 ((,class (:background ,status-warning :foreground ,text-inverse :weight bold)))) `(avy-lead-face-2 ((,class (:background ,code-variable :foreground ,text-inverse :weight bold)))) `(avy-background-face ((,class (:background ,bg-panel :foreground ,text-faint)))) ;; Denote (notes) `(denote-faces-link ((,class (:foreground ,status-info :underline t)))) `(denote-faces-date ((,class (:foreground ,code-number)))) `(denote-faces-keyword ((,class (:foreground ,code-keyword :weight bold)))) `(denote-faces-title ((,class (:foreground ,text-primary :weight bold :height 1.2)))) ;; Extra: markdown, json, etc. `(markdown-header-face-1 ((,class (:inherit org-level-1)))) `(markdown-header-face-2 ((,class (:inherit org-level-2)))) `(markdown-header-face-3 ((,class (:inherit org-level-3)))) `(markdown-header-face-4 ((,class (:inherit org-level-4)))) `(markdown-header-face-5 ((,class (:inherit org-level-5)))) `(markdown-header-face-6 ((,class (:inherit org-level-6)))) `(markdown-link-face ((,class (:inherit link)))) `(markdown-url-face ((,class (:foreground ,code-number)))) `(json-key-face ((,class (:foreground ,code-keyword)))) `(json-number-face ((,class (:foreground ,code-number)))) `(json-string-face ((,class (:foreground ,code-string)))) `(json-boolean-face ((,class (:foreground ,code-constant)))) `(json-null-face ((,class (:foreground ,code-constant)))) ;; Custom faces used in user config (e.g., my-set-buffer-font buffer-face) `(buffer-face ((,class (:family "Noto Sans" :height 140)))))) ;; Provide the theme (provide-theme 'camm3) ;;; camm3-theme.el ends here