Emacs Configuration

Table of Contents


A Straightforward Emacs Configuration Bundle.

This is my Emacs configuration in literate form, and it is towards macOS. I am not sure if it would work well well on Linux or Windows.

My Blog
Complete Literate Configuration


  • Use straight.el to manage packages.
  • For macOS GUI.
  • Now only tested with GNU Emacs 26.2/27.0.50 of macOS 10.14.






  • Emacs
  • git
  • make


To install, clone this repo to ~/.emacs.d :

git clone https://github.com/nasyxx/emacs.d.git ~/.emacs.d
make generate

Upon the first time staring up emacs, other third-party packages will be automatically clone to the straight: folder and installed. If you encounter any errors at that stage, try restarting Emacs, and maybe running make clean-build before doing so.

You can regenerate init.el by make generate.


Update this config with running make update or git pull after a make clean-build and restart Emacs.

And I guess you'll need to update third-party packages regularly too if you have not modificated the straight-check-for-modifications in config/nasy-config.el:

  • M-x straight-pull-all RET
  • M-x straight-rebuild-all RET

If you encounter any errors while updating, you may need to kill Emacs and run make clean. If you still meet errors after doing that, you probably need to run make clean-all and restart Emacs.

Custom Configuration

Example Custom Configuration

To add your own customization, use M-x customize etc. and/or create a file custom/user-config.el which looks like this (when you make or make generate, below will generate to custom/user-config-example.el ):

 ;;calendar-latitude        24.8801
 ;;calendar-longitude       102.8329
 ;;user-mail-address        "[email protected]"
 ;;initial-buffer-choice    #'(lambda () (get-buffer "*dashboard*"))
 cnfonts-profiles         '("nasy-profile" "profile1" "profile2" "profile3")
 gcmh-high-cons-threshold #x40000000
 *theme*                  'doom-vibrant
 *debug*                  t
 *struct-hs*              nil
 ;;*vterm*                  "/Users/Nasy/src/emacs-libvterm"
 *risky-var*              nil
 *dvorak*                 nil
 *font-cjk*               "Kaiti SC"
 *font-weight-cjk*        'normal)
(provide 'user-config-example)


If you want to start with dashboard, you need to set

(setq initial-buffer-choice #'(lambda () (get-buffer "*dashboard*"))

in your custom/user-config.el.

Launching emacs from command line with a file name causes errors. Please refer to the issue here. Hope someone could fix it.


  • Functions added to nasy/config-before-hook will be run before loading custom.el.
  • Functions added to nasy/config-after-hook will be run after init.



Package Manager
straight.el with –depth=1
  • lsp-mode/lsp-dap
  • Haskell
  • Python
  • Lisp
  • HTML/CSS/JavaScript/TypeScript
  • Rust
  • Doom Themes
  • Darktooth
  • Soothe

The Configuration

See the complete literate config here:



One thing to note is that this file generates a file named init.el. You should not edit that file directly and make any changes here and regenerate it from Emacs org-mode using C-c C-v t .


File Header

This includes some necessary headers.

;;; init.el --- Nasy's emacs.d init file.            -*- lexical-binding: t; -*-
;; Copyright (C) 2018  Nasy

;; Author: Nasy <[email protected]>

;;; Commentary:

;; Nasy's emacs.d init file.  For macOS and Emacs 26, Emacs 27.

Lexical Binding

This makes it so that the file that is produced from tangling this file uses lexical scoping.

(setq-default lexical-binding t)

Some Default Settings

Some default settings are here, including debug-on-error, message-log-max, load-prefer-newer and ad-redefinition-action.

(setq-default debug-on-error         t
              message-log-max        t
              load-prefer-newer      t
              ad-redefinition-action 'accept
              gc-cons-threshold      most-positive-fixnum)

Macros & Alias

Useful Macros and Alias.

(defmacro λ! (&rest body)
  "A shortcut for inline interactive lambdas."
  (declare (doc-string 1))
  `(lambda () (interactive) ,@body))

(defalias 'lambda! 'λ!)

(defmacro after! (package &rest body)
  "Evaluate BODY after PACKAGE have loaded.
PACKAGE is a symbol or list of them. These are package names, not modes,
functions or variables. It can be:
- An unquoted package symbol (the name of a package)
    (after! helm BODY...)
- An unquoted list of package symbols (i.e. BODY is evaluated once both magit
  and git-gutter have loaded)
    (after! (magit git-gutter) BODY...)
- An unquoted, nested list of compound package lists, using any combination of
  :or/:any and :and/:all
    (after! (:or package-a package-b ...)  BODY...)
    (after! (:and package-a package-b ...) BODY...)
    (after! (:and package-a (:or package-b package-c) ...) BODY...)
  Without :or/:any/:and/:all, :and/:all are implied.
This is a wrapper around `eval-after-load' that:
1. Suppresses warnings for disabled packages at compile-time
2. No-ops for package that are disabled by the user (via `package!')
3. Supports compound package statements (see below)
4. Prevents eager expansion pulling in autoloaded macros all at once"
  (declare (indent defun) (debug t))
  (if (symbolp package)
      (list (if (or (not (bound-and-true-p byte-compile-current-file))
                    (require package nil 'noerror))
            (let ((body (macroexp-progn body)))
              `(if (featurep ',package)
                 ;; We intentionally avoid `with-eval-after-load' to prevent
                 ;; eager macro expansion from pulling (or failing to pull) in
                 ;; autoloaded macros/packages.
                 (eval-after-load ',package ',body))))
    (let ((p (car package)))
      (cond ((not (keywordp p))
             `(after! (:and ,@package) ,@body))
            ((memq p '(:or :any))
              (cl-loop for next in (cdr package)
                       collect `(after! ,next ,@body))))
            ((memq p '(:and :all))
             (dolist (next (cdr package))
               (setq body `((after! ,next ,@body))))
             (car body))))))

Is A Mac?

If this os is macOS?

(defconst *is-a-mac* (eq system-type 'darwin))

Packages Manager

I use straight.el as my packages manager.


(setq straight-recipes-gnu-elpa-use-mirror    t
      straight-repository-branch              "develop"
      straight-vc-git-default-clone-depth     1
      straight-enable-use-package-integration nil
      straight-check-for-modifications        '(find-when-checking))

(defvar bootstrap-version)

(let ((bootstrap-file
       (expand-file-name "straight/repos/straight.el/bootstrap.el" user-emacs-directory))
      (bootstrap-version 5))
  (unless (file-exists-p bootstrap-file)
         'silent 'inhibit-cookies)
      (goto-char (point-max))
  (load bootstrap-file nil 'nomessage))

At the same time, I use use-package to manage packages' loading.

(straight-use-package 'use-package)

Garbage Collection

Use GCMH – the Garbage Collector Magic Hack – to adjust garbage collection.


(straight-use-package 'gcmh)
(use-package gcmh
  :demand t
  (setq gcmh-verbose             t
        gcmh-lows-cons-threshold #x800000
        gcmh-high-cons-threshold most-positive-fixnum
        gcmh-idle-delay          3600)


(straight-use-package 'benchmark-init)
(use-package benchmark-init
  :demand t
  :hook ((after-init . benchmark-init/deactivate)))

No Littering


(straight-use-package 'no-littering)
(require 'no-littering)

Define Nasy Custom

Here includes all of the customizable variables of my configuration.

You can custom it in custom/user-config.el

Custom Config Hooks
(defvar nasy/config-before-hook nil
  "Hooks to run config functions before load custom.el.")

(defvar nasy/config-after-hook nil
  "Hooks to run config functions after.")

(add-hook 'nasy/config-after-hook
          #'(lambda () (message "Hi~ Hope you have fun with this config.")))
(defgroup nasy nil
  "Nasy Emacs Custom Configurations."
  :group 'emacs)

(defcustom lisp-modes-hooks '(cider-repl-mode-hook
  "List of lisp-related modes hooks."
  :type '(repeat symbol)
  :group 'nasy)

(defcustom *clangd* (executable-find "clangd")
  "Clangd path.  If nil, will not use clangd."
  :group 'nasy
  :type 'string)

(defcustom *ccls* (executable-find "ccls")  ;; macOS
  "Ccls path.  If nil, will not use ccls."
  :group 'nasy
  :type 'string)

(defcustom *eldoc-box* nil
  "Whether to use eloc-box or not."
  :group 'nasy
  :type 'boolean)

(defcustom *nix* nil
  "Nix path.  If nil, will not use nix."
  :group 'nasy
  :type 'string)

(defcustom *rust* (or (executable-find "rustc")
                      (executable-find "cargo")
                      (executable-find "rustup"))
  "The Rust path.  If nil, will not use Rust."
  :group 'nasy
  :type 'string)

(defcustom *rls* (executable-find "rls")
  "The rls path.  If nil, will not use rls."
  :group 'nasy
  :type 'string)

(defcustom *highlight-indent-guides* t
  "Whether to use highlight-indent-guides or not."
  :group 'nasy
  :type 'boolean)

(defcustom *debug* t
  "Whether to use debug or not."
  :group 'nasy
  :type 'boolean)

(defcustom *server* t
  "Whether to use server or not."
  :group 'nasy
  :type 'boolean)

(defcustom *intero* t
  "Whether to use intero or not."
  :group 'nasy
  :type 'boolean)

(defcustom *struct-hs* (executable-find "structured-haskell-mode")
  "The structured-haskell-mode path.  If nil, will not use structured-haskell-mode."
  :group 'nasy
  :type 'string)

(defcustom *blacken* nil
  "Whether to use blacken or not."
  :group 'nasy
  :type 'boolean)

(defcustom *c-box* t
  "Whether to use company box or not."
  :group 'nasy
  :type 'boolean)

(defcustom *ivy-posframe* nil
  "Whether to use ivy-posframe or not."
  :group 'nasy
  :type 'boolean)

(defcustom *vterm* nil
  "Whether to use vterm or not."
  :group 'nasy
  :type 'boolean)

(defcustom *org-headline-rescale* t
  "Whether to rescale org-headline or not."
  :group 'nasy
  :type 'boolean)

(defcustom *ispell* (executable-find "aspell")
  "The Ispell.  If nil, will not use Ispell."
  :group 'nasy
  :type 'string)

(defcustom *theme* 'doom-dracula
  "The Theme."
  :group 'nasy
  :type 'symbol)

(defcustom *dvorak* nil
  "Whether to use dvorak or not."
  :group 'nasy
  :type 'boolean)

(defcustom *mouse-color* "black"
  "Mouse color."
  :group 'nasy
  :type 'string)

(defcustom *font* "OperatorMonoSSmLig Nerd Font"
 "The main font.  After change it, run `M-x nasy/set-font' to see the effect."
 :group 'nasy
 :type 'string)

(defcustom *font-size* 12.0
 "The main font.  After change it, run `M-x nasy/set-font' to see the effect."
 :group 'nasy
 :type 'float)

(defcustom *font-weight* 'normal
 "The main font.  After change it, run `M-x nasy/set-font' to see the effect."
 :group 'nasy
 :type 'symbol)

(defcustom *font-cjk* "Xingkai SC"
 "The cjk font.  After change it, run `M-x nasy/set-font' to see the effect."
 :group 'nasy
 :type 'string)

(defcustom *font-size-cjk* 16.0
 "The cjk font.  After change it, run `M-x nasy/set-font' to see the effect."
 :group 'nasy
 :type 'float)

(defcustom *font-weight-cjk* 'light
 "The cjk font.  After change it, run `M-x nasy/set-font' to see the effect."
 :group 'nasy
 :type 'symbol)
Default Settings
 company-idle-delay .5)
  blink-cursor-interval .6
  blink-matching-paren  t
  cursor-in-non-selected-windows t)

(blink-cursor-mode 0)

(add-hook 'nasy/config-after-hook
          #'(lambda ()
              (when (fboundp 'set-mouse-color)
                (set-mouse-color *mouse-color*))))
 haskell-stylish-on-save nil
 blacken-line-length     80
 lsp-rust-rls-command    '("rls"))
 org-pandoc-options-for-context     '((template . "~/.emacs.d/nasy-context.tex"))  ;; I have no idea why I cannot set it as a variable.
 org-pandoc-options-for-context-pdf '((template . "~/.emacs.d/nasy-context.tex")))
 show-paren-style                                'parenthesis
 sp-autoinsert-quote-if-followed-by-closing-pair t
 sp-base-key-bindings                            'paredit
 sp-show-pair-from-inside                        t)
(setq hscroll-margin                  7
      scroll-margin                   7
      hscroll-step                    7
      scroll-step                     7
      scroll-conservatively           100000
      scroll-preserve-screen-position 'always
      mac-mouse-wheel-smooth-scroll    nil)
 shell-file-name "/bin/zsh")
 initial-scratch-message     (concat ";; Happy hacking, " user-login-name " - Emacs ♥ you!\n\n")
 dashboard-banner-logo-title (concat ";; Happy hacking, " user-login-name " - Emacs ♥ you!\n\n")
 ;; initial-buffer-choice       #'(lambda () (get-buffer "*dashboard*"))  ;; It will cause error if you start emacs from Command line with file name
                                                                          ;; https://github.com/rakanalh/emacs-dashboard/issues/69
 fill-column                    80
 visual-fill-column-width       100
 word-wrap                      t
 highlight-indent-guides-method 'column
 tab-width                      8
 tooltip-delay                  1.5)
 whitespace-line-column 80
 whitespace-style       '(face spaces tabs newline
                          space-mark tab-mark newline-mark
                          lines-tail empty))
   bookmark-default-file (no-littering-expand-var-file-name ".bookmarks.el")
   buffers-menu-max-size 30
   case-fold-search      t
   column-number-mode    t
   dired-dwim-target     t
   ediff-split-window-function 'split-window-horizontally
   ediff-window-setup-function 'ediff-setup-windows-plain
   indent-tabs-mode      nil
   line-move-visual      t
   make-backup-files     nil
   mouse-yank-at-point   t
   require-final-newline t
   save-interprogram-paste-before-kill t
   set-mark-command-repeat-pop    t
   tab-always-indent              'complete
   truncate-lines                 nil
   truncate-partial-width-windows nil)

(when *is-a-mac*
  (setq line-move-visual nil))

(fset 'yes-or-no-p 'y-or-n-p)

(global-auto-revert-mode t)

(delete-selection-mode t)
Config After initialization
(defun nasy/config-after ()
  "Set configuration need to be set after init."
   ;; helm-allow-mouse                  t
   ;; helm-follow-mode-persistent       t
   ;; helm-move-to-line-cycle-in-source nil
   ;; helm-source-names-using-follow    '("Buffers" "kill-buffer" "Occur")
   debug-on-error *debug*))

(add-hook 'nasy/config-after-hook  #'nasy/config-after)
Custom Faces
(defun nasy/set-face ()
  "Set custom face."
  (after! org
    (set-face-attribute 'org-meta-line               nil                                             :slant   'italic)
    (set-face-attribute 'org-block-begin-line        nil                                             :slant   'italic)
    (set-face-attribute 'org-block-end-line          nil                                             :slant   'italic)
    (when *org-headline-rescale*
      (set-face-attribute 'org-level-1 nil :height 1.6 :inherit 'outline-1)
      (set-face-attribute 'org-level-2 nil :height 1.4 :inherit 'outline-2)
      (set-face-attribute 'org-level-3 nil :height 1.2 :inherit 'outline-3)
      (set-face-attribute 'org-level-4 nil :height 1.1 :inherit 'outline-4)))
  (set-face-attribute 'font-lock-comment-face      nil                                             :slant   'italic)
  (set-face-attribute 'font-lock-keyword-face      nil                                             :slant   'italic)
  (set-face-attribute 'show-paren-match            nil :background "#a1de93" :foreground "#705772" :weight  'ultra-bold)
  (after! smartparens-config
    (set-face-attribute 'sp-show-pair-match-face     nil :background "#a1de93" :foreground "#705772" :weight  'ultra-bold)))
(add-hook 'nasy/config-after-hook #'nasy/set-face)

Expand load-path and load user custom

(add-to-list 'load-path (expand-file-name "custom" user-emacs-directory))
(require 'user-config-example)
(require 'user-config nil t)

Key Definition



(straight-use-package 'general)
(use-package general
  (defalias 'gsetq #'general-setq)
  (defalias 'gsetq-local #'general-setq-local)
  (defalias 'gsetq-default #'general-setq-default))
macOS Key Bindings
(when *is-a-mac*
  (gsetq mac-option-modifier        'meta
         mac-command-modifier       'hyper
         mac-right-command-modifier 'super
         mac-function-modifier      'super)

   "C-z" 'stop-minimizing-window

   ;; cursor Movement
   "H-<up>"   'beginning-of-buffer
   "H-<down>" 'end-of-buffer
   "H-l"      'goto-line

   ;; text Operations
   "H-a" 'mark-whole-buffer
   "H-v" 'yank
   "H-c" 'kill-ring-save
   "H-s" 'save-buffer
   "H-z" 'undo
   "H-w" (lambda! (delete-window))
   "M-¥" (lambda! (insert "\\"))
   "H-<backspace>" (lambda! (kill-line 0)))

  ;; unset
  (global-unset-key (kbd "<magnify-down>"))
  (global-unset-key (kbd "<magnify-up>")))
Dvorak Key Bindings
(add-hook #'nasy/config-after-hook
          #'(lambda ()
              (when *dvorak*
                 :keymaps 'key-translation-map
                 "C-," "C-x"
                 "C-x" "C-,"
                 "M-," "M-x"
                 "M-x" "M-,"
                 "C-c" "C-."
                 "C-." "C-c"
                 "M-c" "M-."
                 "M-." "M-c"))))
Toogle Dvorak Key Bindings
(defun nasy/toogle-dvorak ()
  "Toogle dvorak key bindings."
  (if (not *dvorak*)
         :keymaps 'key-translation-map
         "C-," "C-x"
         "C-x" "C-,"
         "M-," "M-x"
         "M-x" "M-,"
         "C-c" "C-."
         "C-." "C-c"
         "M-c" "M-."
         "M-." "M-c")
        (gsetq *dvorak* t)
        (message "Use Dvorak key bindings."))
         :keymaps 'key-translation-map
         "C-," nil
         "C-x" nil
         "M-," nil
         "M-x" nil
         "C-c" nil
         "C-." nil
         "M-c" nil
         "M-." nil)
      (gsetq *dvorak* nil)
      (message "Use normal key bindings."))))
Mouse Key Bindings
 "<mouse-4>" (lambda! (scroll-down 1))
 "<mouse-5>" (lambda! (scroll-up 1)))

Load Org

When using straight.el, the org version is needed to custom set.

(straight-use-package 'org-plus-contrib)


Core Functions
;;; Borrow from doom emacs.
(define-error 'n-error "Error in Nasy Emacs core")
(define-error 'n-hook-error "Error in a Nasy startup hook" 'Nasy-error)

(defun nasy-enlist (exp)
 "Return EXP wrapped in a list, or as-is if already a list."
 (declare (pure t) (side-effect-free t))
 (if (listp exp) exp (list exp)))

(defun nasy/try-run-hook (hook)
  "Run HOOK (a hook function), but handle errors better, to make debugging
issues easier.
Meant to be used with `run-hook-wrapped'."
  (message "Running hook: %s" hook)
  (condition-case e
      (funcall hook)
    ((debug error)
     (signal 'n-hook-error (list hook e))))
  ;; return nil so `run-hook-wrapped' won't short circuit

;; File+dir local variables are initialized after the major mode and its hooks
;; have run. If you want hook functions to be aware of these customizations, add
;; them to MODE-local-vars-hook instead.
(defun nasy/run-local-var-hooks-h ()
  "Run MODE-local-vars-hook after local variables are initialized."
  (run-hook-wrapped (intern-soft (format "%s-local-vars-hook" major-mode))
(add-hook 'hack-local-variables-hook #'nasy/run-local-var-hooks-h)

;; If the user has disabled `enable-local-variables', then
;; `hack-local-variables-hook' is never triggered, so we trigger it at the end
;; of `after-change-major-mode-hook':
(defun nasy/run-local-var-hooks-if-necessary-h ()
  "Run `nasy/run-local-var-hooks-h' if `enable-local-variables' is disabled."
  (unless enable-local-variables
(add-hook 'after-change-major-mode-hook
macOS Frame
(when *is-a-mac*
  (add-to-list 'default-frame-alist
               '(ns-transparent-titlebar . t))

  (add-to-list 'default-frame-alist
               '(ns-appearance . dark))

  (add-to-list 'default-frame-alist
               '(alpha . (80 . 75)))

  (defun stop-minimizing-window ()
    "Stop minimizing window under macOS."
    (unless (and *is-a-mac*
Disable Some Features
(setq use-file-dialog        nil
      use-dialog-box         nil
      inhibit-startup-screen t)

(when (fboundp 'tool-bar-mode)
  (tool-bar-mode -1))

(when (fboundp 'set-scroll-bar-mode)
  (set-scroll-bar-mode nil))
;; https://github.com/jwiegley/emacs-async
(straight-use-package 'async)
(use-package dired-async
  :commands dired-async-mode)
(use-package async-bytecomp
  (gsetq async-bytecomp-allowed-packages '(all))

;; (straight-use-package 'auto-compile)
;; (require 'auto-compile)
;; (auto-compile-on-load-mode)
;; (auto-compile-on-save-mode)

(setq-default compilation-scroll-output t)

;; https://github.com/jwiegley/alert
(straight-use-package 'alert)
(use-package alert
  :defer    t
  (defun alert-after-compilation-finish (buf result)
    "Use `alert' to report compilation RESULT if BUF is hidden."
    (when (buffer-live-p buf)
      (unless (catch 'is-visible
                (walk-windows (lambda (w)
                                (when (eq (window-buffer w) buf)
                                  (throw 'is-visible t))))
        (alert (concat "Compilation " result)
               :buffer buf
               :category 'compilation)))))

(use-package compile
  :defer t
  (defvar nasy/last-compilation-buffer nil
    "The last buffer in which compilation took place.")

  (defun nasy/save-compilation-buffer (&rest _)
    "Save the compilation buffer to find it later."
    (setq nasy/last-compilation-buffer next-error-last-buffer))
  (advice-add 'compilation-start :after 'nasy/save-compilation-buffer)

  (defun nasy/find-prev-compilation (orig &rest args)
    "Find the previous compilation buffer, if present, and recompile there."
    (if (and (null edit-command)
             (not (derived-mode-p 'compilation-mode))
             (buffer-live-p (get-buffer nasy/last-compilation-buffer)))
        (with-current-buffer nasy/last-compilation-buffer
          (apply orig args))
      (apply orig args)))
  :bind (([f6] . recompile))
  :hook ((compilation-finish-functions . alert-after-compilation-finish)))

(use-package ansi-color
  :defer    t
  (defun colourise-compilation-buffer ()
    (when (eq major-mode 'compilation-mode)
      (ansi-cOLOR-APPLY-on-region compilation-filter-start (point-max))))
  :hook ((compilation-filter . colourise-compilation-buffer)))
Auto Compression
(require 'jka-compr)
History, Saving and Session
(gsetq desktop-path              (list user-emacs-directory no-littering-var-directory)
       desktop-dirname           (list user-emacs-directory no-littering-var-directory)
       desktop-auto-save-timeout 600)
(desktop-save-mode t)
(gsetq desktop-save 'if-exists)

(defun nasy/desktop-time-restore (orig &rest args)
  (let ((start-time (current-time)))
        (apply orig args)
      (message "Desktop restored in %.2fms"
               (benchmark-init/time-subtract-millis (current-time)
(advice-add 'desktop-read :around 'nasy/desktop-time-restore)

(defun nasy/desktop-time-buffer-create (orig ver filename &rest args)
  (let ((start-time (current-time)))
        (apply orig ver filename args)
      (message "Desktop: %.2fms to restore %s"
               (benchmark-init/time-subtract-millis (current-time)
               (when filename
                 (abbreviate-file-name filename))))))
(advice-add 'desktop-create-buffer :around 'nasy/desktop-time-buffer-create)

(gsetq kill-ring-max 300)

(gsetq history-length 3000
       history-delete-duplicates t
       savehist-autosave-interval 60)

(add-hook #'after-init-hook #'savehist-mode)

(straight-use-package 'session)
(use-package session
  :defer    t
  :hook ((after-init . session-initialize))
  (gsetq session-save-file (no-littering-expand-var-file-name ".session")
         session-name-disable-regexp "\\(?:\\`'/tmp\\|\\.git/[A-Z_]+\\'\\)"
         session-save-file-coding-system 'utf-8
         (append '((comint-input-ring        . 50)
                   (compile-history          . 30)
                   (dired-regexp-history     . 20)
                   (extended-command-history . 30)
                   (face-name-history        . 20)
                   (file-name-history        . 100)
                   (grep-find-history        . 30)
                   (grep-history             . 30)
                   (ivy-history              . 100)
                   (magit-revision-history   . 50)
                   (minibuffer-history       . 50)
                   (org-clock-history        . 50)
                   (org-refile-history       . 50)
                   (org-tags-history         . 50)
                   (query-replace-history    . 60)
                   (read-expression-history  . 60)
                   (regexp-history           . 60)
                   (regexp-search-ring       . 20)
                   (search-ring              . 20)
                   (shell-command-history    . 50)
Auto Save (Super Save)

I use super save to auto save files.

(straight-use-package 'super-save)
(use-package super-save
  :ghook 'after-init-hook
  :gfhook '(lambda () (remove-hook #'mouse-leave-buffer-hook #'super-save-command))
  :init (gsetq super-save-auto-save-when-idle nil
               super-save-remote-files        nil
               super-save-hook-triggers       nil
               '(ibuffer other-window windmove-up windmove-down windmove-left windmove-right next-buffer previous-buffer)))
Text Scale
(straight-use-package 'default-text-scale)
(use-package default-text-scale
  :commands default-text-scale-mode
  :ghook 'after-init-hook)

Custom Functions

Reload the init-file
(defun radian-reload-init ()
  "Reload init.el."
    (message "Reloading init.el...")
    (load user-init-file nil 'nomessage)
    (message "Reloading init.el... done.")))

(defun radian-eval-buffer ()
  "Evaluate the current buffer as Elisp code."
  (message "Evaluating %s..." (buffer-name))
    (if (null buffer-file-name)
      (when (string= buffer-file-name user-init-file)
      (load-file buffer-file-name)))
  (message "Evaluating %s... done." (buffer-name)))
Insert Date
(defun nasy:insert-current-date ()
  "Insert current date."
  (insert (shell-command-to-string "echo -n $(date +'%b %d, %Y')")))

(defun nasy:insert-current-filename ()
  "Insert current buffer filename."
  (insert (file-relative-name buffer-file-name)))
Posframe Helper
(defun posframe-poshandler-frame-top-center (info)
  (cons (/ (- (plist-get info :parent-frame-width)
              (plist-get info :posframe-width))
        (round (* 0.02 (x-display-pixel-height)))))


Ace Window
(straight-use-package 'ace-window)
(use-package ace-window
  :bind (("M-o" . ace-window))
   'aw-leading-char-face nil
   :foreground "deep sky blue"
   :weight 'bold
   :height 3.0)
   'aw-mode-line-face nil
   :inherit 'mode-line-buffer-id
   :foreground "lawn green")
  (gsetq-default cursor-in-non-selected-windows 'hollow)
  (gsetq aw-reverse-frame-list t
         aw-keys '(?a ?s ?d ?f ?j ?k ?l)
         aw-dispatch-always t
         '((?w hydra-window-size/body)
           (?o hydra-window-scroll/body)
           (?\; hydra-frame-window/body)
           (?0 delete-frame)
           (?1 delete-other-frames)
           (?2 make-frame)
           (?x aw-delete-window "Ace - Delete Window")
           (?c aw-swap-window "Ace - Swap Window")
           (?n aw-flip-window)
           (?v aw-split-window-vert "Ace - Split Vert Window")
           (?h aw-split-window-horz "Ace - Split Horz Window")
           (?\- aw-split-window-vert "Ace - Split Vert Window")
           (?\| aw-split-window-horz "Ace - Split Horz Window")
           (?m delete-other-windows "Ace - Maximize Window")
           (?g delete-other-windows)
           (?b balance-windows)
           (?u (lambda ()
                   (setq this-command 'winner-undo)))
               (?r winner-redo))))
  (after! hydra
    (defhydra hydra-window-size (:color violet)
      "Windows size"
      ("h" shrink-window-horizontally "shrink horizontal")
      ("j" shrink-window "shrink vertical")
      ("k" enlarge-window "enlarge vertical")
      ("l" enlarge-window-horizontally "enlarge horizontal"))
    (defhydra hydra-window-scroll (:color violet)
      "Scroll other window"
      ("n" joe-scroll-other-window "scroll")
      ("p" joe-scroll-other-window-down "scroll down"))
    (defhydra hydra-frame-window (:color violet :hint nil)
^Delete^                       ^Frame resize^             ^Window^                Window Size^^^^^^   ^Text^                         (__)
_0_: delete-frame              _g_: resize-frame-right    _t_: toggle               ^ ^ _k_ ^ ^        _K_                           (oo)
_1_: delete-other-frames       _H_: resize-frame-left     _e_: ace-swap-win         _h_ ^+^ _l_        ^+^                     /------\\/
_2_: make-frame                _F_: fullscreen            ^ ^                       ^ ^ _j_ ^ ^        _J_                    / |    ||
_d_: kill-and-delete-frame     _n_: new-frame-right       _w_: ace-delete-window    _b_alance^^^^      ^ ^                   *  /\\---/\\  ~~  C-x f ;
      ("0" delete-frame :exit t)
      ("1" delete-other-frames :exit t)
      ("2" make-frame  :exit t)
      ("b" balance-windows)
      ("d" kill-and-delete-frame :exit t)
      ("e" ace-swap-window)
      ("F" toggle-frame-fullscreen)   ;; is <f11>
      ("g" resize-frame-right :exit t)
      ("H" resize-frame-left :exit t)  ;; aw-dispatch-alist uses h, I rebind here so hjkl can be used for size
      ("n" new-frame-right :exit t)
      ("r" reverse-windows)
      ("t" toggle-window-spilt)
      ("w" ace-delete-window :exit t)
      ("x" delete-frame :exit t)
      ("K" text-scale-decrease)
      ("J" text-scale-increase)
      ("h" shrink-window-horizontally)
      ("k" shrink-window)
      ("j" enlarge-window)
      ("l" enlarge-window-horizontally)))
  (ace-window-display-mode t))
(straight-use-package 'switch-window)
(use-package switch-window
  :init (gsetq-default switch-window-shortcut-style 'alphabet
                       switch-window-timeout nil)
  ;; When splitting window, show (other-buffer) in the new window
  (defun split-window-func-with-other-buffer (split-function)
    "Split window with `SPLIT-FUNCTION'."
    (lambda (&optional arg)
      "Split this window and switch to the new window unless ARG is provided."
      (interactive "P")
      (funcall split-function)
      (let ((target-window (next-window)))
        (set-window-buffer target-window (other-buffer))
        (unless arg
          (select-window target-window)))))

  (defun toggle-delete-other-windows ()
    "Delete other windows in frame if any, or restore previous window config."
    (if (and winner-mode
             (equal (selected-window) (next-window)))

  (defun split-window-horizontally-instead ()
    "Kill any other windows and re-split such that the current window is on the top half of the frame."
    (let ((other-buffer (and (next-window) (window-buffer (next-window)))))
      (when other-buffer
        (set-window-buffer (next-window) other-buffer))))

  (defun split-window-vertically-instead ()
    "Kill any other windows and re-split such that the current window is on the left half of the frame."
    (let ((other-buffer (and (next-window) (window-buffer (next-window)))))
      (when other-buffer
        (set-window-buffer (next-window) other-buffer))))

  ;; Borrowed from http://postmomentum.ch/blog/201304/blog-on-emacs
  (defun nasy/split-window()
    "Split the window to see the most recent buffer in the other window.
  Call a second time to restore the original window configuration."
    (if (eq last-command 'nasy-split-window)
          (jump-to-register :nasy-split-window)
          (setq this-command 'nasy-unsplit-window))
      (window-configuration-to-register :nasy/split-window)
      (switch-to-buffer-other-window nil)))

   :prefix "C-x"
   "1" 'toggle-delete-other-windows
   "2" (split-window-func-with-other-buffer 'split-window-vertically)
   "3" (split-window-func-with-other-buffer 'split-window-horizontally)
   "|" 'split-window-horizontally-instead
   "_" 'split-window-vertically-instead
   "x" 'nasy/split-window
   "o" 'switch-window))


Disable Mouse
(straight-use-package 'disable-mouse)
(setq enable-recursive-minibuffers t)


;; https://www.reddit.com/r/emacs/comments/4d8gvt/how_do_i_automatically_close_the_minibuffer_after/
(defun helper/kill-minibuffer ()
  "Exit the minibuffer if it is active."
  (when (and (>= (recursion-depth) 1)

(add-hook #'mouse-leave-buffer-hook #'helper/kill-minibuffer)
Scratch Message
(straight-use-package 'scratch)
Shell & Term
(straight-use-package 'shell)

(straight-use-package 'cmd-to-echo)

(straight-use-package 'command-log-mode)

(defun nasy:shell-command-in-view-mode (start end command &optional output-buffer replace &rest other-args)
  "Put \"*Shell Command Output*\" buffers into view-mode."
  (unless (or output-buffer replace)
    (with-current-buffer "*Shell Command Output*"
      (view-mode 1))))
(advice-add 'shell-command-on-region :after 'nasy:shell-command-in-view-mode)

(straight-use-package 'exec-path-from-shell)
(use-package exec-path-from-shell
  :demand   *is-a-mac*
  ;; Non-Forking Shell Command To String
  ;; https://github.com/bbatsov/projectile/issues/1044

  (defun call-process-to-string (program &rest args)
      (apply 'call-process program nil (current-buffer) nil args)

  (defun get-call-process-args-from-shell-command (command)
        (the-command . args) (split-string command " ")
      (let ((binary-path (executable-find the-command)))
        (when binary-path
          (cons binary-path args)))))

  (defun shell-command-to-string (command)
    (let ((call-process-args
           (get-call-process-args-from-shell-command command)))
      (if call-process-args
          (apply 'call-process-to-string call-process-args)
        (shell-command-to-string command))))

  (defun try-call-process (command)
    (let ((call-process-args
           (get-call-process-args-from-shell-command command)))
      (if call-process-args
          (apply 'call-process-to-string call-process-args))))

  (advice-add 'shell-command-to-string :before-until 'try-call-process)

  (straight-use-package 'noflet)

  (defun call-with-quick-shell-command (fn &rest args)
    (noflet ((shell-command-to-string
              (&rest args)
              (or (apply 'try-call-process args) (apply this-fn args))))
            (apply fn args)))

  (advice-add 'projectile-find-file :around 'call-with-quick-shell-command)
  :init (gsetq shell-command-switch "-ic")
  (when nil (message "PATH: %s, INFO: %s" (getenv "PATH")
                     (getenv "ENVIRONMENT_SETUP_DONE"))
        (setq exec-path-from-shell-debug t))
  (gsetq exec-path-from-shell-arguments (list "-l")
         exec-path-from-shell-check-startup-files nil)
  (add-to-list 'exec-path-from-shell-variables "SHELL")
  (add-to-list 'exec-path-from-shell-variables "GOPATH")
  (add-to-list 'exec-path-from-shell-variables "ENVIRONMENT_SETUP_DONE")
  (add-to-list 'exec-path-from-shell-variables "PYTHONPATH")
  (add-to-list 'exec-path-from-shell-variables "PKG_CONFIG_PATH")
  (add-to-list 'exec-path "~/.pyenv/shims/"))

Emacs libvterm intergration


(when *vterm*
    (add-to-list 'load-path *vterm*)
    (let (vterm-install)
      (require 'vterm))))


Here is the editor config, including some features and functions.

;; Editor


(straight-use-package 'diminish)


(straight-use-package 'flx)

Advance Words Count

(straight-use-package '(advance-words-count :type git :host github :repo "LdBeth/advance-words-count.el"))


(straight-use-package 'anzu)
(use-package anzu
  :defer    t
  :hook ((after-init . global-anzu-mode))
  :bind ([remap query-replace] . anzu-query-replace-regexp))

Auto Insert

(use-package autoinsert
    '("\\.py" . "Python Language")
    '("Python Language"
      "#!/usr/bin/env python3\n"
      "# -*- coding: utf-8 -*-\n\n"
      "Life's pathetic, have fun (\"▔□▔)/hi~♡ Nasy.\n\n"
      "Excited without bugs::\n\n"
      "    |             *         *\n"
      "    |                  .                .\n"
      "    |           .\n"
      "    |     *                      ,\n"
      "    |                   .\n"
      "    |\n"
      "    |                               *\n"
      "    |          |\\___/|\n"
      "    |          )    -(             .              ·\n"
      "    |         =\\ -   /=\n"
      "    |           )===(       *\n"
      "    |          /   - \\\n"
      "    |          |-    |\n"
      "    |         /   -   \\     0.|.0\n"
      "    |  NASY___\\__( (__/_____(\\=/)__+1s____________\n"
      "    |  ______|____) )______|______|______|______|_\n"
      "    |  ___|______( (____|______|______|______|____\n"
      "    |  ______|____\\_|______|______|______|______|_\n"
      "    |  ___|______|______|______|______|______|____\n"
      "    |  ______|______|______|______|______|______|_\n"
      "    |  ___|______|______|______|______|______|____\n\n"
      "author   : Nasy https://nasy.moe\n"
      "date     : " (format-time-string "%b %e, %Y") \n
      "email    : Nasy <[email protected]>" \n
      "filename : " (file-name-nondirectory (buffer-file-name)) \n
      "project  : " (file-name-nondirectory (directory-file-name (or projectile-project-root default-directory))) \n
      "license  : GPL-3.0+\n\n"
      "At pick'd leisure\n"
      "  Which shall be shortly, single I'll resolve you,\n"
      "Which to you shall seem probable, of every\n"
      "  These happen'd accidents\n"
      "                          -- The Tempest\n"

    '("\\.hs" . "Haskell Language")
    '("Haskell Language"
      " Excited without bugs, have fun (\"▔□▔)/hi~♡ Nasy.\n"
      " ------------------------------------------------\n"
      " |             *         *\n"
      " |                  .                .\n"
      " |           .\n"
      " |     *                      ,\n"
      " |                   .\n"
      " |\n"
      " |                               *\n"
      " |          |\\___/|\n"
      " |          )    -(             .              ·\n"
      " |         =\\ -   /=\n"
      " |           )===(       *\n"
      " |          /   - \\\n"
      " |          |-    |\n"
      " |         /   -   \\     0.|.0\n"
      " |  NASY___\\__( (__/_____(\\=/)__+1s____________\n"
      " |  ______|____) )______|______|______|______|_\n"
      " |  ___|______( (____|______|______|______|____\n"
      " |  ______|____\\_|______|______|______|______|_\n"
      " |  ___|______|______|______|______|______|____\n"
      " |  ______|______|______|______|______|______|_\n"
      " |  ___|______|______|______|______|______|____\n\n"
      " At pick'd leisure\n"
      "   Which shall be shortly, single I'll resolve you,\n"
      " Which to you shall seem probable, of every\n"
      "   These happen'd accidents\n"
      "                           -- The Tempest\n"
      "--------------------------------------------------------------------------------\n-- |\n"
      "-- Filename   : " (file-name-nondirectory (buffer-file-name)) \n
      "-- Project    : " (file-name-nondirectory (directory-file-name (or projectile-project-root default-directory))) \n
      "-- Author     : Nasy\n"
      "-- License    : GPL-3.0+\n--\n"
      "-- Maintainer : Nasy <[email protected]>\n"

Beacon (Disabled)

(use-package beacon
  :disabled t
  :straight t
  :init (setq beacon-size  7
              beacon-color "#f85e9f")
  :hook ((after-init . beacon-mode)))


(straight-use-package 'beginend)
(use-package beginend
  :hook ((after-init . beginend-global-mode)))

Carbon Now sh

Emacs to carbon.now.sh integration.


Try: M-x carbon-now-sh RET

;; Emacs to carbon.now.sh integration
;; https://github.com/veelenga/carbon-now-sh.el
;; (carbon-now-sh)
(straight-use-package 'carbon-now-sh)

Cheat Sh

(straight-use-package 'cheat-sh)


Preface Functions
;; Borrow from doom emacs.
(defvar nasy/company-backend-alist
 '((text-mode company-dabbrev company-yasnippet company-ispell company-files)
   (prog-mode company-capf company-yasnippet company-files)
   (conf-mode company-capf company-dabbrev-code company-yasnippet company-files))
 "An alist matching modes to company backends. The backends for any mode is
built from this.")

(defun nasy/add-company-backend (modes &rest backends)
 "Prepends BACKENDS (in order) to `company-backends' in MODES.
MODES should be one symbol or a list of them, representing major or minor modes.
This will overwrite backends for MODES on consecutive uses.
If the car of BACKENDS is nil, unset the backends for MODES.
 (nasy/add-company-backend 'js2-mode
   'company-tide 'company-yasnippet)
 (nasy/add-company-backend 'sh-mode
   '(company-shell :with company-yasnippet))
 (nasy/add-company-backend '(c-mode c++-mode)
   '(:separate company-irony-c-headers company-irony))
 (nasy/add-company-backend 'sh-mode nil)  ; unsets backends for sh-mode"
 (declare (indent defun))
 (dolist (mode (nasy-enlist modes))
   (if (null (car backends))
       (setq nasy/company-backend-alist
             (delq (assq mode nasy/company-backend-alist)
     (setf (alist-get mode nasy/company-backend-alist)

(defun nasy/company-backends ()
 (let (backends)
   (let ((mode major-mode)
         (modes (list major-mode)))
     (while (setq mode (get mode 'derived-mode-parent))
       (push mode modes))
     (dolist (mode modes)
       (dolist (backend (append (cdr (assq mode nasy/company-backend-alist))
                                (default-value 'company-backends)))
         (push backend backends)))
      (append (cl-loop for (mode . backends) in nasy/company-backend-alist
                       if (or (eq major-mode mode)  ; major modes
                              (and (boundp mode)
                                   (symbol-value mode))) ; minor modes
                       append backends)
              (nreverse backends))))))

(defun nasy/company-init-backends-h ()
 "Set `company-backends' for the current buffer."
 (if (not company-mode)
     (remove-hook 'change-major-mode-after-body-hook #'nasy/company-init-backends-h 'local)
   (unless (eq major-mode 'fundamental-mode)
     (setq-local company-backends (nasy/company-backends)))
   (add-hook 'change-major-mode-after-body-hook #'nasy/company-init-backends-h nil 'local)))

(put 'nasy/company-init-backends-h 'permanent-local-hook t)
Company Mode
(straight-use-package 'company)
(use-package company
  :commands (nasy/company-backends
  (defun nasy/company-has-completion-p ()
    "Return non-nil if a completion candidate exists at point."
    (and (company-manual-begin)
         (= company-candidates-length 1)))

  (defun nasy/company-toggle-auto-completion ()
    "Toggle as-you-type code completion."
    (require 'company)
    (setq company-idle-delay (unless company-idle-delay 0.2))
    (message "Auto completion %s"
             (if company-idle-delay "enabled" "disabled")))

  (defun nasy/company-complete ()
    "Bring up the completion popup. If only one result, complete it."
    (require 'company)
    (when (ignore-errors
            (/= (point)
                (cdr (bounds-of-thing-at-point 'symbol))))
      (save-excursion (insert " ")))
    (when (and (company-manual-begin)
               (= company-candidates-length 1))

  (defun nasy/company-dabbrev ()
    "Invokes `company-dabbrev-code' in prog-mode buffers and `company-dabbrev'
  everywhere else."
     (if (derived-mode-p 'prog-mode)

  (defun nasy/company-whole-lines (command &optional arg &rest ignored)
    "`company-mode' completion backend that completes whole-lines, akin to vim's
  C-x C-l."
    (interactive (list 'interactive))
    (require 'company)
    (pcase command
      (`interactive (company-begin-backend 'nasy/company-whole-lines))
      (`prefix      (company-grab-line "^[\t\s]*\\(.+\\)" 1))
           "^[\t\s]+" ""
           (concat (buffer-substring-no-properties (point-min) (line-beginning-position))
                   (buffer-substring-no-properties (line-end-position) (point-max))))
          "\\(\r\n\\|[\n\r]\\)" t))))))

  (defun nasy/company-dict-or-keywords ()
    "`company-mode' completion combining `company-dict' and `company-keywords'."
    (require 'company-dict)
    (require 'company-keywords)
    (let ((company-backends '((company-keywords company-dict))))
      (call-interactively #'company-complete)))

  (defun nasy/company-dabbrev-code-previous ()
    (require 'company-dabbrev)
    (let ((company-selection-wrap-around t))
      (call-interactively #'nasy/company-dabbrev)

  (add-to-list 'completion-styles 'initials t)
  (gsetq company-tooltip-limit             10
         company-dabbrev-downcase          nil
         company-dabbrev-ignore-case       t
         '(not erc-mode message-mode help-mode gud-mode eshell-mode)
         company-backends                  '(company-capf)
         company-dabbrev-other-buffers     'all
         company-tooltip-align-annotations t
         company-minimum-prefix-length     2
         company-idle-delay                .2
         company-tooltip-idle-delay        .2
         company-require-match             'never)
  :hook ((company-mode . nasy/company-init-backends-h))
  :bind (("M-/"     . company-files)
         ("M-C-/"   . nasy/company-complete)
         ("C-<tab>" . nasy/company-complete)
         :map company-mode-map
         ("M-/" . nasy/company-complete)
         :map company-active-map
         ("M-/" . company-other-backend)
         ("C-n" . company-select-next)
         ("C-p" . company-select-previous))
  (global-company-mode +1)
  (defvar nasy/prev-whitespace-mode nil)
  (make-variable-buffer-local 'nasy/prev-whitespace-mode)
  (defvar nasy/show-trailing-whitespace nil)
  (make-variable-buffer-local 'nasy/show-trailing-whitespace)
  (defun pre-popup-draw ()
    "Turn off whitespace mode before showing company complete tooltip"
    (if whitespace-mode
          (gsetq my-prev-whitespace-mode t)
          (whitespace-mode -1)))
    (gsetq nasy/show-trailing-whitespace show-trailing-whitespace)
    (gsetq show-trailing-whitespace nil))
  (defun post-popup-draw ()
    "Restore previous whitespace mode after showing company tooltip"
    (if nasy/prev-whitespace-mode
          (whitespace-mode 1)
          (gsetq nasy/prev-whitespace-mode nil)))
    (gsetq show-trailing-whitespace nasy/show-trailing-whitespace))
  (advice-add 'company-pseudo-tooltip-unhide :before #'pre-popup-draw)
  (advice-add 'company-pseudo-tooltip-hide :after #'post-popup-draw)

  (defun company-backend-with-yas (backends)
    "Add :with company-yasnippet to company BACKENDS.
  Taken from https://github.com/syl20bnr/spacemacs/pull/179."
    (if (and (listp backends) (memq 'company-yasnippet backends))
      (append (if (consp backends)
                (list backends))
              '(:with company-yasnippet))))
  ;; add yasnippet to all backends
  ;; (gsetq company-backends
  ;;        (mapcar #'company-backend-with-yas company-backends))
  :diminish company-mode)
Company Try Hard
(straight-use-package 'company-try-hard)
(use-package company-try-hard
  :bind (:map company-active-map
         ("C-z" . company-try-hard)))
Company Quickhelp
(straight-use-package 'company-quickhelp)
(use-package company-quickhelp
  :bind (:map company-active-map
              ("C-c h" . company-quickhelp-manual-begin))
  :ghook #'after-init-hook
  :init (gsetq pos-tip-use-relative-coordinates t))
Company Tabnine
(straight-use-package 'company-tabnine)
(gsetq company-tabnine-log-file-path
       (concat company-tabnine-binaries-folder "/log"))
Company Math
(straight-use-package 'company-math)
Company Dict
(straight-use-package 'company-dict)
Company Flx
(straight-use-package 'company-flx)
(use-package company-flx
  :ghook #'after-init-hook)
Company Box
(when *c-box*
  (straight-use-package 'company-box)
  (use-package company-box
    :defer    t
    :after (all-the-icons company)
    (defun nasy/company-box-icons--yasnippet-fn (candidate)
      (when (get-text-property 0 'yas-annotation candidate)

    (defun nasy/company-box-icons--elisp-fn (candidate)
      (when (derived-mode-p 'emacs-lisp-mode)
        (let ((sym (intern candidate)))
          (cond ((fboundp sym)  'ElispFunction)
                ((boundp sym)   'ElispVariable)
                ((featurep sym) 'ElispFeature)
                ((facep sym)    'ElispFace)))))
    (setq company-box-icons-alist 'company-box-icons-all-the-icons)
    :ghook 'company-mode-hook
    (gsetq company-box-show-single-candidate t
           company-box-backends-colors       nil
           company-box-max-candidates        50
           company-box-icons-alist           'company-box-icons-all-the-icons
           `((Unknown       . ,(all-the-icons-material "find_in_page"             :height 0.8 :face 'all-the-icons-purple))
             (Text          . ,(all-the-icons-material "text_fields"              :height 0.8 :face 'all-the-icons-green))
             (Method        . ,(all-the-icons-material "functions"                :height 0.8 :face 'all-the-icons-yellow))
             (Function      . ,(all-the-icons-material "functions"                :height 0.8 :face 'all-the-icons-yellow))
             (Constructor   . ,(all-the-icons-material "functions"                :height 0.8 :face 'all-the-icons-yellow))
             (Field         . ,(all-the-icons-material "functions"                :height 0.8 :face 'all-the-icons-yellow))
             (Variable      . ,(all-the-icons-material "adjust"                   :height 0.8 :face 'all-the-icons-blue))
             (Class         . ,(all-the-icons-material "class"                    :height 0.8 :face 'all-the-icons-cyan))
             (Interface     . ,(all-the-icons-material "settings_input_component" :height 0.8 :face 'all-the-icons-cyan))
             (Module        . ,(all-the-icons-material "view_module"              :height 0.8 :face 'all-the-icons-cyan))
             (Property      . ,(all-the-icons-material "settings"                 :height 0.8 :face 'all-the-icons-lorange))
             (Unit          . ,(all-the-icons-material "straighten"               :height 0.8 :face 'all-the-icons-red))
             (Value         . ,(all-the-icons-material "filter_1"                 :height 0.8 :face 'all-the-icons-red))
             (Enum          . ,(all-the-icons-material "plus_one"                 :height 0.8 :face 'all-the-icons-lorange))
             (Keyword       . ,(all-the-icons-material "filter_center_focus"      :height 0.8 :face 'all-the-icons-lgreen))
             (Snippet       . ,(all-the-icons-material "short_text"               :height 0.8 :face 'all-the-icons-lblue))
             (Color         . ,(all-the-icons-material "color_lens"               :height 0.8 :face 'all-the-icons-green))
             (File          . ,(all-the-icons-material "insert_drive_file"        :height 0.8 :face 'all-the-icons-green))
             (Reference     . ,(all-the-icons-material "collections_bookmark"     :height 0.8 :face 'all-the-icons-silver))
             (Folder        . ,(all-the-icons-material "folder"                   :height 0.8 :face 'all-the-icons-green))
             (EnumMember    . ,(all-the-icons-material "people"                   :height 0.8 :face 'all-the-icons-lorange))
             (Constant      . ,(all-the-icons-material "pause_circle_filled"      :height 0.8 :face 'all-the-icons-blue))
             (Struct        . ,(all-the-icons-material "streetview"               :height 0.8 :face 'all-the-icons-blue))
             (Event         . ,(all-the-icons-material "event"                    :height 0.8 :face 'all-the-icons-yellow))
             (Operator      . ,(all-the-icons-material "control_point"            :height 0.8 :face 'all-the-icons-red))
             (TypeParameter . ,(all-the-icons-material "class"                    :height 0.8 :face 'all-the-icons-red))
             ;; (Template   . ,(company-box-icons-image "Template.png"))))
             (Yasnippet     . ,(all-the-icons-material "short_text"               :height 0.8 :face 'all-the-icons-green))
             (ElispFunction . ,(all-the-icons-material "functions"                :height 0.8 :face 'all-the-icons-red))
             (ElispVariable . ,(all-the-icons-material "check_circle"             :height 0.8 :face 'all-the-icons-blue))
             (ElispFeature  . ,(all-the-icons-material "stars"                    :height 0.8 :face 'all-the-icons-orange))
             (ElispFace     . ,(all-the-icons-material "format_paint"             :height 0.8 :face 'all-the-icons-pink))))))


(straight-use-package 'dash)

Dash Functional

(straight-use-package 'dash-functional)


(use-package dired
  (let ((gls (executable-find "gls")))
    (when gls (setq insert-directory-program gls)))
  (setq dired-recursive-deletes 'top)
  :bind (:map dired-mode-map
              ([mouse-2] . dired-find-file             )
              ("C-c C-p" . wdired-change-to-wdired-mode)))
(straight-use-package 'diredfl)
(use-package diredfl
  :after dired
  :hook ((after-init . diredfl-global-mode)))
(use-package uniquify
  :init  ;; nicer naming of buffers for files with identical names
  (gsetq uniquify-buffer-name-style   'reverse
         uniquify-separator           " • "
         uniquify-after-kill-buffer-p t
         uniquify-ignore-buffers-re   "^\\*"))
Diff-hl (only for dired)
(straight-use-package 'diff-hl)
(use-package diff-hl
  :after dired
  :hook ((dired-mode . diff-hl-dired-mode)
         (magit-post-refresh . diff-hl-magit-post-refresh)))
Dired Hacks Utils
(straight-use-package 'dired-hacks-utils)
Dired Filter
(straight-use-package 'dired-filter)
(use-package dired-filter
  :after    dired
  :bind (:map dired-mode-map
              ("/" . dired-filter-map))
  :hook ((dired-mode . dired-filter-mode)
         (dired-mode . dired-filter-group-mode))
  :init (gsetq dired-filter-revert 'never
                   (directory . ".git")
                   (file . ".gitignore"))
                   (extension . "pdf"))
                   (extension "tex" "bib"))
                   (extension "c" "cpp" "hs" "rb" "py" "r" "cs" "el" "lisp" "html" "js" "css"))
                   (extension "md" "rst" "txt"))
                   (extension . "org"))
                   (extension "zip" "rar" "gz" "bz2" "tar"))
                   (extension "jpg" "JPG" "webp" "png" "PNG" "jpeg" "JPEG" "bmp" "BMP" "TIFF" "tiff" "gif" "GIF"))))))
Dired avfs
(when (executable-find "avfsd")
  (straight-use-package 'dired-avfs))
Dired Rainbow
(straight-use-package 'dired-rainbow)
(use-package dired-rainbow
  :after dired
  (dired-rainbow-define-chmod directory "#6cb2eb" "d.*")
  (dired-rainbow-define html        "#eb5286" ("css" "less" "sass" "scss" "htm" "html" "jhtm" "mht" "eml" "mustache" "xhtml"))
  (dired-rainbow-define xml         "#f2d024" ("xml" "xsd" "xsl" "xslt" "wsdl" "bib" "json" "msg" "pgn" "rss" "yaml" "yml" "rdata"))
  (dired-rainbow-define document    "#9561e2" ("docm" "doc" "docx" "odb" "odt" "pdb" "pdf" "ps" "rtf" "djvu" "epub" "odp" "ppt" "pptx"))
  (dired-rainbow-define markdown    "#ffed4a" ("org" "etx" "info" "markdown" "md" "mkd" "nfo" "pod" "rst" "tex" "textfile" "txt"))
  (dired-rainbow-define database    "#6574cd" ("xlsx" "xls" "csv" "accdb" "db" "mdb" "sqlite" "nc"))
  (dired-rainbow-define media       "#de751f" ("mp3" "mp4" "MP3" "MP4" "avi" "mpeg" "mpg" "flv" "ogg" "mov" "mid" "midi" "wav" "aiff" "flac"))
  (dired-rainbow-define image       "#f66d9b" ("tiff" "tif" "cdr" "gif" "ico" "jpeg" "jpg" "png" "psd" "eps" "svg"))
  (dired-rainbow-define log         "#c17d11" ("log"))
  (dired-rainbow-define shell       "#f6993f" ("awk" "bash" "bat" "sed" "sh" "zsh" "vim"))
  (dired-rainbow-define interpreted "#38c172" ("py" "ipynb" "rb" "pl" "t" "msql" "mysql" "pgsql" "sql" "r" "clj" "cljs" "scala" "js"))
  (dired-rainbow-define compiled    "#4dc0b5" ("asm" "cl" "lisp" "el" "c" "h" "c++" "h++" "hpp" "hxx" "m" "cc" "cs" "cp" "cpp" "go" "f" "for" "ftn" "f90" "f95" "f03" "f08" "s" "rs" "hi" "hs" "pyc" ".java"))
  (dired-rainbow-define executable  "#8cc4ff" ("exe" "msi"))
  (dired-rainbow-define compressed  "#51d88a" ("7z" "zip" "bz2" "tgz" "txz" "gz" "xz" "z" "Z" "jar" "war" "ear" "rar" "sar" "xpi" "apk" "xz" "tar"))
  (dired-rainbow-define packaged    "#faad63" ("deb" "rpm" "apk" "jad" "jar" "cab" "pak" "pk3" "vdf" "vpk" "bsp"))
  (dired-rainbow-define encrypted   "#ffed4a" ("gpg" "pgp" "asc" "bfe" "enc" "signature" "sig" "p12" "pem"))
  (dired-rainbow-define fonts       "#6cb2eb" ("afm" "fon" "fnt" "pfb" "pfm" "ttf" "otf"))
  (dired-rainbow-define partition   "#e3342f" ("dmg" "iso" "bin" "nrg" "qcow" "toast" "vcd" "vmdk" "bak"))
  (dired-rainbow-define vc          "#0074d9" ("git" "gitignore" "gitattributes" "gitmodules"))
  (dired-rainbow-define-chmod executable-unix "#38c172" "-.*x.*"))
Dired Subtree/ranger
(straight-use-package 'dired-subtree)

(straight-use-package 'dired-ranger)
Dired Narrow
(straight-use-package 'dired-narrow)
(use-package dired-narrow
  :after    dired
  :bind (:map dired-narrow-map
              ("<down>"  . dired-narrow-next-file)
              ("<up>"    . dired-narrow-previous-file)
              ("<right>" . dired-narrow-enter-directory)))
Dired Collapse
(straight-use-package 'dired-collapse)
(use-package dired-collapse
  :ghook 'dired-mode-hook)

Easy Kill

(straight-use-package 'easy-kill)
(use-package easy-kill
  :bind (([remap kill-ring-save] . easy-kill)
         ([remap mark-sexp]      . easy-mark)))
(straight-use-package 'thingopt)

Eldoc Box

Disabled by default due to it causes lots of cpu.

(when *eldoc-box*
  (straight-use-package 'eldoc-box)
  (use-package eldoc-box
    :hook ((eldoc-mode . eldoc-box-hover-mode)
           (eldoc-mode . eldoc-box-hover-at-point-mode))))

Fill Column

(straight-use-package 'unfill)
(use-package unfill
  :bind (("M-q" . unfill-toggle)))
(straight-use-package 'visual-fill-column)
(use-package visual-fill-column
  (defun maybe-adjust-visual-fill-column ()
    "Readjust visual fill column when the global font size is modified.
This is helpful for writeroom-mode, in particular."
    (if visual-fill-column-mode
        (add-hook 'after-setting-font-hook 'visual-fill-column--adjust-window nil t)
      (remove-hook 'after-setting-font-hook 'visual-fill-column--adjust-window t)))
  :hook ((visual-line-mode        . visual-fill-column-mode        )
         (visual-fill-column-mode . maybe-adjust-visual-fill-column)))

Find File in Project

(straight-use-package 'find-file-in-project)
(gsetq ffip-use-rust-fd t)


(straight-use-package 'flycheck)
(straight-use-package 'flycheck-package)

(use-package flycheck
  (defun save-buffer-maybe-show-errors ()
    "Save buffer and show errors if any."
    (when (not flycheck-current-errors)
  :commands (flycheck-mode
  ;; :bind (("C-x C-s" . save-buffer-maybe-show-errors))
  :hook ((after-init . global-flycheck-mode))
  :init (gsetq flycheck-display-errors-function
               flycheck-check-syntax-automatically '(save mode-enabled)
               flycheck-display-errors-delay       0.25)
  :bind (:map flycheck-error-list-mode-map
              ("C-n"    . flycheck-error-list-next-error)
              ("C-p"    . flycheck-error-list-previous-error)
              ("RET"    . flycheck-error-list-goto-error)
              ([return] . flycheck-error-list-goto-error))
  :config (defalias 'show-error-at-point-soon
  (add-to-list 'flycheck-emacs-lisp-checkdoc-variables 'sentence-end-double-space))

(use-package flycheck-package
  :after flycheck
  (after! elisp-mode


Fast and precise fuzzy scoring/matching utils for Emacs, powered by rust


(straight-use-package 'fuz)
(straight-use-package 'helm-fuz)
(use-package fuz
  :defer t
  (defun load-fuz ()
    "Load fuz.el."
    (require 'fuz)
    (unless (require 'fuz-core nil t)
  :hook ((after-init . load-fuz))
  (after! helm
    (require 'helm-fuz)

Grab Mac Link

(straight-use-package 'grab-mac-link)


(gsetq-default grep-highlight-matches t
               grep-scroll-output t)

(when *is-a-mac*
  (gsetq-default locate-command "mdfind"))


(straight-use-package 'cl-lib-highlight)
(after! emacs-lisp-mode
  (use-package cl-lib-highlight
Color Identifiers Mode
(straight-use-package 'color-identifiers-mode)
(use-package color-identifiers-mode
  :defer t
  :hook ((prog-mode . color-identifiers-mode)))
(straight-use-package 'hl-line)
(use-package hl-line
  :defer t
  :hook ((after-init . global-hl-line-mode)))
Highlight Indent Guides
(when *highlight-indent-guides*
  (straight-use-package 'highlight-indent-guides)
  (use-package highlight-indent-guides
    :init (gsetq highlight-indent-guides-responsive nil
                 highlight-indent-guides-delay      0.5)
    :ghook '(prog-mode-hook text-mode-hook org-mode-hook)))
(straight-use-package 'rainbow-mode)
(use-package rainbow-mode
  :hook (((after-init
           prog-mode). rainbow-mode))
  :diminish rainbow-mode)



(straight-use-package 'helpful)
(use-package helpful
  :bind (("C-c C-d" . helpful-at-point))
  :init (general-define-key
         :prefix "C-h"
         "f" 'helpful-callable
         "v" 'helpful-variable
         "k" 'helpful-key
         "F" 'helpful-function
         "C" 'helpful-command))


(straight-use-package 'helm)

(defun nasy/helm ()
    (let ((helm-ff-transformer-show-only-basename nil)
      (unless helm-source-buffers-list
        (setq helm-source-buffers-list
              (helm-make-source "Buffers" 'helm-source-buffers)))
      (cond (
             ;; Just add helm-source-projectile-* in list when current place in project.
             (setq helm-source-list
                     ;; helm-source-awesome-tab-group

             (setq helm-source-list
                     ;; helm-source-awesome-tab-group
      (helm-other-buffer helm-source-list "*helm search*")))

(use-package helm-mode
  :ghook 'pre-command-hook
  :defer t
     [remap execute-extended-command]    #'helm-M-x
     [remap noop-show-kill-ring]         #'helm-show-kill-ring
     [remap find-library]                #'helm-locate-library
     [remap bookmark-jump]               #'helm-bookmarks
     [remap find-file]                   #'helm-find-files
     [remap locate]                      #'helm-locate
     [remap imenu]                       #'helm-semantic-or-imenu
     [remap noop-show-kill-ring]         #'helm-show-kill-ring
     [remap persp-switch-to-buffer]      #'+helm/workspace-mini
     [remap switch-to-buffer]            #'helm-buffers-list
     [remap projectile-find-file]        #'+helm/projectile-find-file
     [remap projectile-recentf]          #'helm-projectile-recentf
     [remap projectile-switch-project]   #'helm-projectile-switch-project
     [remap projectile-switch-to-buffer] #'helm-projectile-switch-to-buffer
     [remap recentf-open-files]          #'helm-recentf
     [remap yank-pop]                    #'helm-show-kill-ring
     "M-b"     'nasy/helm
     "C-o"     'helm-occur
     "C-x C-f" 'helm-find-files)
   :prefix "C-x c"
   "x"   'helm-register
   "g"   'helm-google-suggest
   "M-:" 'helm-eval-expression-with-eldoc)
   :keymaps 'helm-map
   "<tab>" 'helm-execute-persistent-action ; rebind tab to run persistent action
   "C-i"   'helm-execute-persistent-action ; make TAB works in terminal
   "C-z"   'helm-select-action) ; list actions using C-z
   :keymaps 'shell-mode-map
   "C-c C-l" 'helm-comint-input-ring)
   :keymaps 'minibuffer-local-map
   "C-c C-l" 'helm-minibuffer-history)
  (helm-mode +1))

(use-package helm
  :after helm-mode
  :hook ((helm-mode . helm-autoresize-mode))
  (gsetq helm-M-x-fuzzy-match        t
         helm-buffers-fuzzy-matching t
         helm-recentf-fuzzy-match    t
         helm-imenu-fuzzy-match      t
         helm-locate-fuzzy-match     t
         helm-apropos-fuzzy-match    t
         helm-lisp-fuzzy-completion  t
         helm-allow-mouse            t
         helm-follow-mode-persistent t
         helm-ff-lynx-style-map      t
         helm-bookmark-show-location t)

  (when (executable-find "curl")
    (gsetq helm-google-suggest-use-curl-p t))

  (gsetq helm-split-window-in-side-p           t
         helm-move-to-line-cycle-in-source     nil
         helm-ff-search-library-in-sexp        t
         helm-scroll-amount                    8
         helm-ff-file-name-history-use-recentf t
         helm-echo-input-in-header-line        t
         helm-source-names-using-follow        '("Buffers" "kill-buffer" "Occur"))
  (add-to-list 'helm-sources-using-default-as-input 'helm-source-man-pages))

(defvar helm-generic-files-map (make-sparse-keymap))

(after! helm-locate
 (when (and *is-a-mac*
          (null helm-locate-command)
          (executable-find "mdfind"))
   (gsetq helm-locate-command "mdfind -name %s"))
 (set-keymap-parent helm-generic-files-map helm-map))
Helm Org
(use-package helm-org
  :defer t
  (cl-defun helm-org-headings-in-buffer ()
    (helm :sources (helm-source-org-headings-for-files
                    (list (projectile-completing-read
                           "File to look at headings from: "
          :candidate-number-limit 99999
          :buffer "*helm org inbuffer*")))
Helm Descbings
(straight-use-package 'helm-descbinds)
(use-package helm-descbinds
  :defer t
  :hook ((helm-mode . helm-descbinds-mode)))
Helm Projectile
(straight-use-package 'helm-projectile)
(use-package helm-projectile
  :defer t
  :commands (helm-projectile-find-file
  (gsetq projectile-completion-system 'helm)
  (defvar helm-projectile-find-file-map (make-sparse-keymap))
  (after! helm
    (require 'helm-for-files)
    (set-keymap-parent helm-projectile-find-file-map helm-map)))
Helm rg
(straight-use-package 'helm-rg)
(use-package helm-rg
  :defer t
   :keymaps 'helm-rg-map
   "C-c C-e" #'helm-rg--bounce)
   :keymaps 'helm-rg--bounce-mode-map
   "q" #'kill-current-buffer
   "C-c C-c" (lambda! (helm-rg--bounce-dump) (kill-current-buffer))
   "C-x C-c" #'helm-rg--bounce-dump-current-file
   "C-c C-k" #'kill-current-buffer))
Helm Dash
(straight-use-package 'helm-dash)
(use-package helm-dash
  :defer t
  :init (gsetq helm-dash-docsets-path "~/.docsets"))


(straight-use-package 'htmlize)
(use-package htmlize
  :defer t
  :init (gsetq htmlize-pre-style t))


(straight-use-package 'hydra)
(use-package hydra
  :defer t
   :prefix "C-x"
   "9" 'hydra-unicode/body)
   :keymaps 'dired-mode-map
   "." 'hydra-dired/body)
  ;; insert unicode
  (defun nasy:insert-unicode (unicode-name)
    "Same as C-x 8 enter UNICODE-NAME."
    (insert-char (gethash unicode-name (ucs-names))))
  (defhydra hydra-unicode (:hint nil)
    Unicode  _e_ €  _s_ ZERO WIDTH SPACE
             _f_ ♀  _o_ °   _m_ µ
             _r_ ♂  _a_ →   _l_ λ
    ("e" (nasy:insert-unicode "EURO SIGN"))
    ("r" (nasy:insert-unicode "MALE SIGN"))
    ("f" (nasy:insert-unicode "FEMALE SIGN"))
    ("s" (nasy:insert-unicode "ZERO WIDTH SPACE"))
    ("o" (nasy:insert-unicode "DEGREE SIGN"))
    ("a" (nasy:insert-unicode "RIGHTWARDS ARROW"))
    ("m" (nasy:insert-unicode "MICRO SIGN"))
    ("l" (nasy:insert-unicode "GREEK SMALL LETTER LAMBDA")))

  (defhydra hydra-dired (:hint nil :color pink)
  _+_ mkdir          _v_iew           _m_ark             _(_ details        _i_nsert-subdir    wdired
  _C_opy             _O_ view other   _U_nmark all       _)_ omit-mode      _$_ hide-subdir    C-x C-q : edit
  _D_elete           _o_pen other     _u_nmark           _l_ redisplay      _w_ kill-subdir    C-c C-c : commit
  _R_ename           _M_ chmod        _t_oggle           _g_ revert buf     _e_ ediff          C-c ESC : abort
  _Y_ rel symlink    _G_ chgrp        _E_xtension mark   _s_ort             _=_ pdiff
  _S_ymlink          ^ ^              _F_ind marked      _._ toggle hydra   \\ flyspell
  _r_sync            ^ ^              ^ ^                ^ ^                _?_ summary
  _z_ compress-file  _A_ find regexp
  _Z_ compress       _Q_ repl regexp

  T - tag prefix
    ("\\" dired-do-ispell)
    ("(" dired-hide-details-mode)
    (")" dired-omit-mode)
    ("+" dired-create-directory)
    ("=" diredp-ediff)         ;; smart diff
    ("?" dired-summary)
    ("$" diredp-hide-subdir-nomove)
    ("A" dired-do-find-regexp)
    ("C" dired-do-copy)        ;; Copy all marked files
    ("D" dired-do-delete)
    ("E" dired-mark-extension)
    ("e" dired-ediff-files)
    ("F" dired-do-find-marked-files)
    ("G" dired-do-chgrp)
    ("g" revert-buffer)        ;; read all directories again (refresh)
    ("i" dired-maybe-insert-subdir)
    ("l" dired-do-redisplay)   ;; relist the marked or singel directory
    ("M" dired-do-chmod)
    ("m" dired-mark)
    ("O" dired-display-file)
    ("o" dired-find-file-other-window)
    ("Q" dired-do-find-regexp-and-replace)
    ("R" dired-do-rename)
    ("r" dired-do-rsynch)
    ("S" dired-do-symlink)
    ("s" dired-sort-toggle-or-edit)
    ("t" dired-toggle-marks)
    ("U" dired-unmark-all-marks)
    ("u" dired-unmark)
    ("v" dired-view-file)      ;; q to exit, s to search, = gets line #
    ("w" dired-kill-subdir)
    ("Y" dired-do-relsymlink)
    ("z" diredp-compress-this-file)
    ("Z" dired-do-compress)
    ("q" nil)
    ("." nil :color blue)))


(use-package ibuffer
  :bind (("C-x C-b" . ibuffer))
  (defun ibuffer-switch-to-normal ()
    "ibuffer swith to normal filter groups."
    (ibuffer-switch-to-saved-filter-groups "Normal"))
  (gsetq ibuffer-saved-filter-groups
            ("Dired"      (mode . dired-mode))
            ("Emacs"     (or
                          (name . "^\\*dashboard\\*$" )
                          (name . "^\\*scratch\\*$"   )
                          (name . "^\\*Messages\\*$"  )
                          (name . "^\\*Backtrace\\*$" )))
            ("Term"       (mode . vterm-mode))
            ("Text"      (or
                          (mode . org-mode)
                          (mode . markdown)
                          (mode . rst-mode)
                          (mode . text-mode)))
            ("TeX"        (mode . tex-mode))
            ("Languages" (or
                          (mode . emacs-lisp-mode)
                          (mode . haskell-mode)
                          (mode . javascript-mode)
                          (mode . lisp-mode)
                          (mode . python-mode)
                          (mode . ruby-mode)
                          (mode . rust-mode)
                          (mode . html-mode)
                          (mode . css-mode)
                          (mode . prog-mode)))
            ("GNUs"      (or
                          (mode . message-mode)
                          (mode . bbdb-mode)
                          (mode . mail-mode)
                          (mode . gnus-group-mode)
                          (mode . gnus-summary-mode)
                          (mode . gnus-article-mode)
                          (name . "^\\.bbdb$")
                          (name . "^\\.newsrc-dribble")))
            ("Magit"      (name . "^magit"))
            ("Help"      (or
                          (name . "^\\*Help\\*$")
                          (name . "^\\*Apropos\\*$")
                          (name . "^\\*info\\*$")
                          (name . "^\\*helpful")))
            ("Custom"    (or
                          (mode . custom-mode)
                          (name . "^\\*Customize")))
            ("Helm"       (mode . helm-major-mode))
         ibuffer-show-empty-filter-groups nil
         ibuffer-default-sorting-mode     'filename/process)
  :hook ((ibuffer-mode . ibuffer-switch-to-normal)))
ibuffer vc
(straight-use-package 'ibuffer-vc)
Other settings
(use-package ibuffer
  :defer t
  (define-ibuffer-column size-h
    (:name "Size" :inline t)
    (file-size-human-readable (buffer-size)))
   '((mark modified read-only vc-status-mini " "
           (name 22 22 :left :elide)
           " "
           (size-h 9 -1 :right)
           " "
           (mode 12 12 :left :elide)
           " "
     (mark modified read-only vc-status-mini " "
           (name 22 22 :left :elide)
           " "
           (size-h 9 -1 :right)
           " "
           (mode 14 14 :left :elide)
           " "
           (vc-status 12 12 :left)
           " "

imenu list

(straight-use-package 'imenu-list)
(use-package imenu-list
  :bind (("C-." . imenu-list-smart-toggle))
  :init (setq imenu-list-auto-resize t))


(straight-use-package 'indent-tools)
(use-package indent-tools
  :bind (("C-c TAB" . indent-tools-hydra/body)))


I only use rg to search, so I disabled the key-map of isearch.

(use-package isearch
  ;; Search back/forth for the symbol at point
  ;; See http://www.emacswiki.org/emacs/SearchAtPoint
  (defun isearch-yank-symbol ()
    "*Put symbol at current point into search string."
    (let ((sym (thing-at-point 'symbol)))
      (if sym
            (setq isearch-regexp t
                  isearch-string (concat "\\_<" (regexp-quote sym) "\\_>")
                  isearch-message (mapconcat 'isearch-text-char-description isearch-string "")
                  isearch-yank-flag t))

  ;; http://www.emacswiki.org/emacs/ZapToISearch
  (defun isearch-exit-other-end (rbeg rend)
    "Exit isearch, but at the other end of the search string.
This is useful when followed by an immediate kill."
    (interactive "r")
    (goto-char isearch-other-end))

  :bind (:map isearch-mode-map
              ([remap isearch-delete-char] . isearch-del-char)
              ("C-M-w"                     . isearch-yank-symbol)
              ([(control return)]              . isearch-exit-other-end)
              ("C-c C-o"                   . isearch-occur)))

Ivy, Counsel and Swiper

Now disabled.

Large File

(straight-use-package 'vlf)
(use-package vlf
  (defun ffap-vlf ()
    "Find file at point with VLF."
    (let ((file (ffap-file-at-point)))
      (unless (file-exists-p file)
        (error "File does not exist: %s" file))
      (vlf file))))

Link Hint

(straight-use-package 'link-hint)
(use-package link-hint
  :bind (("C-c l o" . link-hint-open-link)
         ("C-c l c" . link-hint-copy-link))
   :prefix "C-c l")
  "o" 'link-hint-open-link
  "c" 'link-hint-copy-link)

List Unicode Display

(straight-use-package 'list-unicode-display)


(straight-use-package 'mmm-mode)
(use-package mmm-auto
  :init (gsetq
         mmm-submode-decoration-level 2))

Multiple Cursors

(straight-use-package 'multiple-cursors)
(use-package multiple-cursors
  :bind (("C-<"     . mc/mark-previous-like-this)
         ("C->"     . mc/mark-next-like-this)
         ("C-+"     . mc/mark-next-like-this)
         ("C-c C-<" . mc/mark-all-like-this))
  ;; From active region to multiple cursors:
   :preface "C-c m"
   "r" 'set=rectangular-region-anchor
   "c" 'mc/edit-lines
   "e" 'mc/edit-ends-of-lines
   "a" 'mc/edit-beginnings-of-lines))

Pangu Spacing

(straight-use-package 'pangu-spacing)
(use-package pangu-spacing
  :init (gsetq pangu-spacing-real-insert-separtor t)
  :hook ((after-init . global-pangu-spacing-mode)))

Paper Break Lines

(straight-use-package 'page-break-lines)
(use-package page-break-lines
  :hook ((after-init . global-page-break-lines-mode))
  :diminish page-break-lines-mode)


I use smartparens, parinfer with rainbow-delimiters instead of paredit.

(add-hook 'after-init-hook 'show-paren-mode)
(straight-use-package 'smartparens)
(use-package smartparens-config
  :hook ((after-init . smartparens-global-mode))
  :init (gsetq sp-hybrid-kill-entire-symbol nil))
(straight-use-package 'parinfer)
(use-package parinfer
  :bind (("C-," . parinfer-toggle-mode))
  :init (gsetq parinfer-auto-switch-indent-mode              t
               parinfer-auto-switch-indent-mode-when-closing t
               '(defaults       ;; should be included.
                 pretty-parens  ;; different paren styles for different modes.
                 ;; evil           ;; If you use Evil.
                 ;; lispy          ;; If you use Lispy. With this extension, you should install Lispy and do not enable lispy-mode directly.
                 ;; paredit        ;; Introduce some paredit commands.
                 smart-tab      ;; C-b & C-f jump positions and smart shift with tab & S-tab.
                 smart-yank))   ;; Yank behavior depend on mode.
  :ghook lisp-modes-hooks)
Rainbow Delimiters
(straight-use-package 'rainbow-delimiters)
(use-package rainbow-delimiters
  :defer t
  :ghook '(prog-mode-hook text-mode-hook org-src-mode-hook))

PDF Tools

(straight-use-package 'pdf-tools)
(use-package pdf-tools
  :defer t
  (gsetq-default pdf-view-display-size 'fit-width)
  (bind-keys :map pdf-view-mode-map
             ("\\" . hydra-pdftools/body)
             ("<s-spc>" .  pdf-view-scroll-down-or-next-page)
             ("g"  . pdf-view-first-page)
             ("G"  . pdf-view-last-page)
             ("l"  . image-forward-hscroll)
             ("h"  . image-backward-hscroll)
             ("j"  . pdf-view-next-page)
             ("k"  . pdf-view-previous-page)
             ("e"  . pdf-view-goto-page)
             ("u"  . pdf-view-revert-buffer)
             ("al" . pdf-annot-list-annotations)
             ("ad" . pdf-annot-delete)
             ("aa" . pdf-annot-attachment-dired)
             ("am" . pdf-annot-add-markup-annotation)
             ("at" . pdf-annot-add-text-annotation)
             ("y"  . pdf-view-kill-ring-save)
             ("i"  . pdf-misc-display-metadata)
             ("s"  . pdf-occur)
             ("b"  . pdf-view-set-slice-from-bounding-box)
             ("r"  . pdf-view-reset-slice)))


Pretty Mode
(straight-use-package 'pretty-mode)
(use-package pretty-mode
  :commands (turn-on-pretty-mode global-prettify-symbols-mode)
  :hook (((text-mode
           org-mode)  . turn-on-pretty-mode)
         (after-init  . global-prettify-symbols-mode)
         (prog-mode . (lambda () (mapc (lambda (pair) (push pair prettify-symbols-alist))
                                  '(;; Data Type             P N
                                    ("Float"  . #x211d)  ;; ℝxxxx
                                    ("float"  . #x211d)  ;; ℝxxx
                                    ("Int"    . #x2124)  ;; ℤxxx
                                    ("int"    . #x2124)  ;; 𝕫xxx
                                    ;; ("String" . #x1d57e)  ;; 𝕊 𝕾
                                    ;; ("string" . #x1d598)  ;; 𝕤 𝖘
                                    ;; ("str"    . #x1d598)  ;; 𝕤 𝖘
                                    ("String" . (#x1d54a (Br . Bl) #x2006))  ;; 𝕊 xxxxxx
                                    ("string" . (#x1d564 (Br . Bl) #x2006))  ;; 𝕤 xxxxxx
                                    ("str"    . (#x1d564 (Br . Bl) #x2006))  ;; 𝕤 xxxx
                                    ("Char"   . #x2102)   ;; ℂx
                                    ("char"   . (#x1d554 (Br . Bl) #x2006))  ;; 𝕔 x

                                    ("False"  . #x1d53d)  ;; 𝕱 𝔽
                                    ("True"   . #x1d54b)  ;; 𝕿 𝕋

                                    ("Any"    . #x2203)  ;; 
                                    ("any"    . #x2203)  ;; 
                                    ("any_"   . #x2203)  ;; 
                                    ("And"    . #x22c0)  ;; 
                                    ("and"    . #x22cf)  ;; 
                                    ("Or"     . #x22c1)  ;; 
                                    ("or"     . #x22cE)  ;; 
                                    ("not"    . #x00ac)  ;; ¬
                                    ("not_"   . #x00ac)  ;; ¬

                                    ("All"    . #x2200)  ;; 
                                    ("all"    . #x2200)  ;; 
                                    ("all_"   . #x2200)  ;; 
                                    ("for"    . #x2200)  ;; 
                                    ("forall" . #x2200)  ;; 
                                    ("forM"   . #x2200)  ;; 

                                    ("pi"     . #x03c0)  ;; π

                                    ("sum"    . #x2211)  ;; 
                                    ("Sum"    . #x2211)  ;; 
                                    ("Product" . #x220F) ;; 
                                    ("product" . #x220F) ;; 

                                    ("None"   . #x2205)  ;; 
                                    ("none"   . #x2205)  ;; 

                                    ("in"     . #x2286)  ;; 
                                    ("`elem`" . #x2286)  ;; 
                                    ("not in"    . #x2288)  ;; 
                                    ("`notElem`" . #x2288)  ;; 

                                    ("return" . (#x21d2 (Br . Bl) #x2006 (Br . Bl) #x2004))  ;; ⇒  x
                                    ("yield"  . (#x21d4 (Br . Bl) #x2004))  ;; ⇔ x
                                    ("pure"   . (#x21f0 (Br . Bl)))))))          ;; ⇰ x

           org-mode) . (lambda () (mapc (lambda (pair) (push pair prettify-symbols-alist))
                                   '(;; Global
                                     ;; Pipes
                                     ("<|"  . (?\s (Br . Bl) #Xe14d))
                                     ("<>"  . (?\s (Br . Bl) #Xe15b))
                                     ("<|>" . (?\s (Br . Bl) ?\s (Br . Bl) #Xe14e))
                                     ("|>"  . (?\s (Br . Bl) #Xe135))

                                     ;; Brackets
                                     ("<*"  . (?\s (Br . Bl) #Xe14b))
                                     ("<*>" . (?\s (Br . Bl) ?\s (Br . Bl) #Xe14c))
                                     ("*>"  . (?\s (Br . Bl) #Xe104))
                                     ("<$"  . (?\s (Br . Bl) #Xe14f))
                                     ("<$>" . (?\s (Br . Bl) ?\s (Br . Bl) #Xe150))
                                     ("$>"  . (?\s (Br . Bl) #Xe137))
                                     ("<+"  . (?\s (Br . Bl) #Xe155))
                                     ("<+>" . (?\s (Br . Bl) ?\s (Br . Bl) #Xe156))
                                     ("+>"  . (?\s (Br . Bl) #Xe13a))
                                     ("[]"  . (#x2005 (Br . Bl) #x1d731 (Br . Bl) #x2005))

                                     ;; Equality
                                     ("=/="  . (?\s (Br . Bl) ?\s (Br . Bl) #Xe143))
                                     ("/="   . (?\s (Br . Bl) #Xe12c))
                                     ("/=="  . (?\s (Br . Bl) ?\s (Br . Bl) #Xe12d))
                                     ("/==>" . (?\s (Br . Bl) ?\s (Br . Bl) ?\s (Br . Bl) #Xe13c))
                                     ("!==>" . (?\s (Br . Bl) ?\s (Br . Bl) ?\s (Br . Bl) #Xe13c))
                                     ;; Special
                                     ("||="  . (?\s (Br . Bl) ?\s (Br . Bl) #Xe133))
                                     ("|="   . (?\s (Br . Bl) #Xe134))
                                     ("~="   . (?\s (Br . Bl) #Xe166))
                                     ("^="   . (?\s (Br . Bl) #Xe136))
                                     ("=:="  . (?\s (Br . Bl) ?\s (Br . Bl) #Xe13b))

                                     ;; Comparisons
                                     ("</"   . (?\s (Br . Bl) #Xe162))
                                     ("</>"  . (?\s (Br . Bl) ?\s (Br . Bl) #Xe163))

                                     ;; Shifts
                                     ("=>>"  . (?\s (Br . Bl) ?\s (Br . Bl) #Xe147))
                                     ("->>"  . (?\s (Br . Bl) ?\s (Br . Bl) #Xe147))
                                     (">>>"  . (?\s (Br . Bl) ?\s (Br . Bl) #Xe14a))
                                     (">>>"  . (?\s (Br . Bl) ?\s (Br . Bl) #Xe14a))
                                     ("=<<"  . (?\s (Br . Bl) ?\s (Br . Bl) #Xe15c))
                                     ("-<<"  . (?\s (Br . Bl) ?\s (Br . Bl) #Xe15c))
                                     ("<<<"  . (?\s (Br . Bl) ?\s (Br . Bl) #Xe15f))

                                     ;; Dots
                                     (".-"   . (?\s (Br . Bl) #Xe122))
                                     (".="   . (?\s (Br . Bl) #Xe123))
                                     ("..<"  . (?\s (Br . Bl) ?\s (Br . Bl) #Xe125))

                                     ;; Hashes
                                     ("#{"   . (?\s (Br . Bl) #Xe119))
                                     ("#("   . (?\s (Br . Bl) #Xe11e))
                                     ("#_"   . (?\s (Br . Bl) #Xe120))
                                     ("#_("  . (?\s (Br . Bl) #Xe121))
                                     ("#?"   . (?\s (Br . Bl) #Xe11f))
                                     ("#["   . (?\s (Br . Bl) #Xe11a))

                                     ;; REPEATED CHARACTERS
                                     ;; 2-Repeats
                                     ("!!"   . (?\s (Br . Bl) #Xe10d))
                                     ("%%"   . (?\s (Br . Bl) #Xe16a))

                                     ;; 2+3-Repeats
                                     ("##"   . (?\s (Br . Bl) #Xe11b))
                                     ("###"  . (?\s (Br . Bl) ?\s (Br . Bl) #Xe11c))
                                     ("####" . (?\s (Br . Bl) ?\s (Br . Bl) #Xe11d))
                                     ("---"  . (?\s (Br . Bl) ?\s (Br . Bl) #Xe112))
                                     ("{-"   . (?\s (Br . Bl) #Xe108))
                                     ("-}"   . (?\s (Br . Bl) #Xe110))
                                     ("\\\\" . (?\s (Br . Bl) #Xe106))
                                     ("\\\\\\" . (?\s (Br . Bl) ?\s (Br . Bl) #Xe107))
                                     (".."   . (?\s (Br . Bl) #Xe124))
                                     ("..."  . (?\s (Br . Bl) ?\s (Br . Bl) #Xe126))
                                     ("+++"  . (?\s (Br . Bl) ?\s (Br . Bl) #Xe139))
                                     ("//"   . (?\s (Br . Bl) #Xe12f))
                                     ("///"  . (?\s (Br . Bl) ?\s (Br . Bl) #Xe130))
                                     ("::"   . (?\s (Br . Bl) #Xe10a))  ;; 
                                     (":::"  . (?\s (Br . Bl) ?\s (Br . Bl) #Xe10b))

                                     ;; Arrows
                                     ;; Direct
                                     ;; ("->"  . (?\s (Br . Bl) #Xe114))  ;; 
                                     ;; ("=>"  . (?\s (Br . Bl) #Xe13f))
                                     ("->>" . (?\s (Br . Bl) ?\s (Br . Bl) #Xe115))
                                     ("=>>" . (?\s (Br . Bl) ?\s (Br . Bl) #Xe140))
                                     ("<<-" . (?\s (Br . Bl) ?\s (Br . Bl) #Xe15d))
                                     ("<<=" . (?\s (Br . Bl) ?\s (Br . Bl) #Xe15e))
                                     ("<->" . (?\s (Br . Bl) ?\s (Br . Bl) #Xe154))
                                     ("<=>" . (?\s (Br . Bl) ?\s (Br . Bl) #Xe159))
                                     ;; Branches
                                     ("-<"  . (?\s (Br . Bl) #Xe116))
                                     ("-<<" . (?\s (Br . Bl) ?\s (Br . Bl) #Xe117))
                                     (">-"  . (?\s (Br . Bl) #Xe144))
                                     (">>-" . (?\s (Br . Bl) ?\s (Br . Bl) #Xe148))
                                     ("=<<" . (?\s (Br . Bl) ?\s (Br . Bl) #Xe142))
                                     (">=>" . (?\s (Br . Bl) ?\s (Br . Bl) #Xe146))
                                     (">>=" . (?\s (Br . Bl) ?\s (Br . Bl) #Xe149))
                                     ("<=<" . (?\s (Br . Bl) ?\s (Br . Bl) #Xe15a))
                                     ;; Squiggly
                                     ("<~"  . (?\s (Br . Bl) #Xe160))
                                     ("<~~" . (?\s (Br . Bl) ?\s (Br . Bl) #Xe161))
                                     ("~>"  . (?\s (Br . Bl) #Xe167))
                                     ("~~>" . (?\s (Br . Bl) ?\s (Br . Bl) #Xe169))
                                     ("-~"  . (?\s (Br . Bl) #Xe118))
                                     ("~-"  . (?\s (Br . Bl) #Xe165))

                                     ;; MISC
                                     ("www" . (?\s (Br . Bl) ?\s (Br . Bl) #Xe100))
                                     ("[email protected]"  . (?\s (Br . Bl) #Xe164))
                                     ("~~"  . (?\s (Br . Bl) #Xe168))
                                     ("?="  . (?\s (Br . Bl) #Xe127))
                                     (":="  . (?\s (Br . Bl) #Xe10c))
                                     ("/>"  . (?\s (Br . Bl) #Xe12e))
                                     ("+"   . #Xe16d)
                                     ("(:"  . (?\s (Br . Bl) #Xe16c))))))

         (python-mode . (lambda ()
                          (mapc (lambda (pair) (push pair prettify-symbols-alist))
                                '(;; Syntax
                                  ;;("def"    . (#x1d521 (Br . Bl) #x1d522 (Br . Bl) #x1d523))
                                  ("def"    . #x1D487)  ;; 𝒇 1 111
                                  ("List"   . #x1d543)  ;; 𝕃 𝕷
                                  ("list"   . (#x1d55d (Br . Bl) #x2006 (Br . Bl) #x2005))  ;; 𝕝   𝖑
                                  ("Dict"   . #x1d53B)  ;; 𝔻 𝕯
                                  ("dict"   . #x1d555)  ;; 𝕕 𝖉
                                  ("Set"    . #x1d61a)  ;; 𝔖 𝘚
                                  ("set"    . #x1d634)  ;; 𝔰 𝘴
                                  ("Tuple"  . #x1d61b)  ;; 𝕋 𝕿 𝘛
                                  ("tuple"  . #x1d635)  ;; 𝕥 𝖙 𝘵

                                  ("Union"  . #x22c3)  ;; 
                                  ("union"  . #x22c3)))))  ;; 

         (haskell-mode . (lambda ()
                           (mapc (lambda (pair) (push pair prettify-symbols-alist))
                                 '(;; Syntax
                                   ("pure" . (#x21f0 (Br . Bl) #x2006))))))) ;; ⇰  x
                                   ;; (" . "  . (?\s (Br . Bl) #x2218 (Br . Bl) ?\s (Br . Bl) #x2006)) ;; ∘

   '(:sub-and-superscripts :greek :arithmetic))

   '(:equality :ordering :ordering-double :ordering-triple
               :arrows :arrows-twoheaded :punctuation
               :logic :sets :arithmetic-double :arithmetic-triple)))
(straight-use-package 'ipretty)
(use-package ipretty
  :defer    t
  :ghook 'after-init-hook)
Pretty Font
;; https://github.com/tonsky/FiraCode/wiki/Emacs-instructions
;; This works when using emacs --daemon + emacsclient
(add-hook 'after-make-frame-functions (lambda (frame) (set-fontset-font t '(#Xe100 . #Xe16f) "Fira Code Symbol")))
;; This works when using emacs without server/client
(set-fontset-font t '(#Xe100 . #Xe16f) "Fira Code Symbol")
;; I haven't found one statement that makes both of the above situations work, so I use both for now

(defun pretty-fonts-set-fontsets (CODE-FONT-ALIST)
  "Utility to associate many unicode points with specified `CODE-FONT-ALIST'."
    (-let (((font . codes) it))
      (--each codes
        (set-fontset-font nil `(,it . ,it) font)
        (set-fontset-font t `(,it . ,it) font)))))

(defun pretty-fonts--add-kwds (FONT-LOCK-ALIST)
  "Exploits `font-lock-add-keywords'(`FONT-LOCK-ALIST') to apply regex-unicode replacements."
   nil (--map (-let (((rgx uni-point) it))
               `(,rgx (0 (progn
                            (match-beginning 1) (match-end 1)
                            ,(concat "\t" (list uni-point)))

(defmacro pretty-fonts-set-kwds (FONT-LOCK-HOOKS-ALIST)
  "Set regex-unicode replacements to many modes(`FONT-LOCK-HOOKS-ALIST')."
     (-let (((font-locks . mode-hooks) it))
       (--each mode-hooks
         (add-hook it (-partial 'pretty-fonts--add-kwds
                                (symbol-value font-locks)))))))

(defconst pretty-fonts-fira-font
    ;; Pipes
    ("\\(<|\\)" #Xe14d) ("\\(<>\\)" #Xe15b) ("\\(<|>\\)" #Xe14e) ("\\(|>\\)" #Xe135)

    ;; Brackets
    ("\\(<\\*\\)" #Xe14b) ("\\(<\\*>\\)" #Xe14c) ("\\(\\*>\\)" #Xe104)
    ("\\(<\\$\\)" #Xe14f) ("\\(<\\$>\\)" #Xe150) ("\\(\\$>\\)" #Xe137)
    ("\\(<\\+\\)" #Xe155) ("\\(<\\+>\\)" #Xe156) ("\\(\\+>\\)" #Xe13a)

    ;; Equality
    ("\\(!=\\)" #Xe10e) ("\\(!==\\)"         #Xe10f) ("\\(=/=\\)" #Xe143)
    ("\\(/=\\)" #Xe12c) ("\\(/==\\)"         #Xe12d)
    ("\\(===\\)" #Xe13d) ("[^!/]\\(==\\)[^>]" #Xe13c)

    ;; Equality Special
    ("\\(||=\\)"  #Xe133) ("[^|]\\(|=\\)" #Xe134)
    ("\\(~=\\)"   #Xe166)
    ("\\(\\^=\\)" #Xe136)
    ("\\(=:=\\)"  #Xe13b)

    ;; Comparisons
    ("\\(<=\\)" #Xe141) ("\\(>=\\)" #Xe145)
    ("\\(</\\)" #Xe162) ("\\(</>\\)" #Xe163)

    ;; Shifts
    ("[^-=]\\(>>\\)" #Xe147) ("\\(>>>\\)" #Xe14a)
    ("[^-=]\\(<<\\)" #Xe15c) ("\\(<<<\\)" #Xe15f)

    ;; Dots
    ("\\(\\.-\\)"    #Xe122) ("\\(\\.=\\)" #Xe123)
    ("\\(\\.\\.<\\)" #Xe125)

    ;; Hashes
    ("\\(#{\\)"  #Xe119) ("\\(#(\\)"   #Xe11e) ("\\(#_\\)"   #Xe120)
    ("\\(#_(\\)" #Xe121) ("\\(#\\?\\)" #Xe11f) ("\\(#\\[\\)" #Xe11a)

    ;; 2-Repeats
    ("\\(||\\)" #Xe132)
    ("\\(!!\\)" #Xe10d)
    ("\\(%%\\)" #Xe16a)
    ("\\(&&\\)" #Xe131)

    ;; 2+3-Repeats
    ("\\(##\\)"       #Xe11b) ("\\(###\\)"          #Xe11c) ("\\(####\\)" #Xe11d)
    ("\\(--\\)"       #Xe111) ("\\(---\\)"          #Xe112)
    ("\\({-\\)"       #Xe108) ("\\(-}\\)"           #Xe110)
    ("\\(\\\\\\\\\\)" #Xe106) ("\\(\\\\\\\\\\\\\\)" #Xe107)
    ("\\(\\.\\.\\)"   #Xe124) ("\\(\\.\\.\\.\\)"    #Xe126)
    ("\\(\\+\\+\\)"   #Xe138) ("\\(\\+\\+\\+\\)"    #Xe139)
    ("\\(//\\)"       #Xe12f) ("\\(///\\)"          #Xe130)
    ("\\(::\\)"       #Xe10a) ("\\(:::\\)"          #Xe10b)

    ;; ARROWS
    ;; Direct
    ("[^-]\\(->\\)" #Xe114) ("[^=]\\(=>\\)" #Xe13f)
    ("\\(<-\\)"     #Xe152)
    ("\\(-->\\)"    #Xe113) ("\\(->>\\)"    #Xe115)
    ("\\(==>\\)"    #Xe13e) ("\\(=>>\\)"    #Xe140)
    ("\\(<--\\)"    #Xe153) ("\\(<<-\\)"    #Xe15d)
    ("\\(<==\\)"    #Xe158) ("\\(<<=\\)"    #Xe15e)
    ("\\(<->\\)"    #Xe154) ("\\(<=>\\)"    #Xe159)

    ;; Branches
    ("\\(-<\\)"  #Xe116) ("\\(-<<\\)" #Xe117)
    ("\\(>-\\)"  #Xe144) ("\\(>>-\\)" #Xe148)
    ("\\(=<<\\)" #Xe142) ("\\(>>=\\)" #Xe149)
    ("\\(>=>\\)" #Xe146) ("\\(<=<\\)" #Xe15a)

    ;; Squiggly
    ("\\(<~\\)" #Xe160) ("\\(<~~\\)" #Xe161)
    ("\\(~>\\)" #Xe167) ("\\(~~>\\)" #Xe169)
    ("\\(-~\\)" #Xe118) ("\\(~-\\)"  #Xe165)

    ;; MISC
    ("\\(www\\)"                   #Xe100)
    ("\\(<!--\\)"                  #Xe151)
    ("\\([email protected]\\)"                    #Xe164)
    ("[^<]\\(~~\\)"                #Xe168)
    ("\\(\\?=\\)"                  #Xe127)
    ("[^=]\\(:=\\)"                #Xe10c)
    ("\\(/>\\)"                    #Xe12e)
    ("[^\\+<>]\\(\\+\\)[^\\+<>]"   #Xe16d)
    ("[^:=]\\(:\\)[^:=]"           #Xe16c)
    ("\\(<=\\)"                    #Xe157))
  "Fira font ligatures and their regexes.")

(if (fboundp 'mac-auto-operator-composition-mode)
   '((pretty-fonts-fira-font prog-mode-hook org-mode-hook))))


(straight-use-package 'prescient)
;; (straight-use-package 'ivy-prescient)
(straight-use-package 'company-prescient)

(use-package prescient
  :hook ((after-init . prescient-persist-mode)))

(use-package ivy-prescient
  :disabled t
  :ghook 'after-init-hook)

(use-package company-prescient
  :hook ((company-mode . company-prescient-mode)))


(straight-use-package 'projectile)
(use-package projectile
  :defer t
  :commands (projectile-project-root
  :bind-keymap ("C-c C-p" . projectile-command-map)
  :ghook '(after-find-file dired-before-readin-hook minibuffer-setup-hook)
  (gsetq projectile-indexing-method      'hybrid
         projectile-require-project-root 'prompt)
   [remap find-tag] #'projectile-find-tag)
  (gsetq projectile-project-root-files-top-down-recurring
         (append '("compile_commands.json"
  (projectile-mode +1))


(use-package recentf
  :init (gsetq
         recentf-save-file       "~/.emacs.d/var/recentf"
         recentf-max-saved-items 100
         recentf-exclude         '("/tmp/" "/ssh:"))
  (add-to-list 'recentf-exclude no-littering-var-directory)
  (add-to-list 'recentf-exclude no-littering-etc-directory))


Now use amx instead of smex.

It's for ivy.


A modern, easy-to-expand fuzzy search framework


Not work now.


(use-package subword
  :defer t
  :diminish (subword-mode))

Symbol Overlay

(straight-use-package 'symbol-overlay)
(use-package symbol-overlay
  :bind (("M-i"  . symbol-overlay-put)
         ("M-n"  . symbol-overlay-switch-forward)
         ("M-p"  . symbol-overlay-switch-backward)
         ("<f8>" . symbol-overlay-remove-all)
         ("<f7>" . symbol-overlay-mode)))


(straight-use-package 'treemacs)
(use-package treemacs
  :defer t
  (after! winum
    (define-key winum-keymap (kbd "M-0") #'treemacs-select-window))
  (gsetq treemacs-collapse-dirs                 (if treemacs-python-executable 3 0)
         treemacs-deferred-git-apply-delay      0.5
         treemacs-display-in-side-window        t
         treemacs-eldoc-display                 t
         treemacs-file-event-delay              5000
         treemacs-file-follow-delay             0.2
         treemacs-follow-after-init             t
         treemacs-git-command-pipe              ""
         treemacs-goto-tag-strategy             'refetch-index
         treemacs-indentation                   2
         treemacs-indentation-string            " "
         treemacs-is-never-other-window         nil
         treemacs-max-git-entries               5000
         treemacs-missing-project-action        'ask
         treemacs-no-png-images                 nil
         treemacs-no-delete-other-windows       t
         treemacs-project-follow-cleanup        nil
         (no-littering-expand-var-file-name "treemacs-persist")
         treemacs-position                      'left
         treemacs-recenter-distance             0.1
         treemacs-recenter-after-file-follow    nil
         treemacs-recenter-after-tag-follow     nil
         treemacs-recenter-after-project-jump   'always
         treemacs-recenter-after-project-expand 'on-distance
         treemacs-show-cursor                   nil
         treemacs-show-hidden-files             t
         treemacs-silent-filewatch              nil
         treemacs-silent-refresh                nil
         treemacs-sorting                       'alphabetic-desc
         treemacs-space-between-root-nodes      t
         treemacs-tag-follow-cleanup            t
         treemacs-tag-follow-delay              1.5
         treemacs-width                         35)

  ;; The default width and height of the icons is 22 pixels. If you are
  ;; using a Hi-DPI display, uncomment this to double the icon size.
  ;; (treemacs-resize-icons 44)
  (treemacs-follow-mode t)
  (treemacs-filewatch-mode t)
  (treemacs-fringe-indicator-mode t)
  (pcase (cons (not (null (executable-find "git")))
               (not (null treemacs-python-executable)))
    (`(t . t)
     (treemacs-git-mode 'deferred))
    (`(t . _)
     (treemacs-git-mode 'simple)))
   :keymaps 'global-map
   "M-0" 'treemacs-select-window)
   :prefix "C-x t"
   :keymaps 'global-map
   "1"   'treemacs-delete-other-windows
   "t"   'treemacs
   "B"   'treemacs-bookmark
   "C-t" 'treemacs-find-file
   "M-t" 'treemacs-find-tag))

(straight-use-package 'treemacs-projectile)
(straight-use-package 'treemacs-icons-dired)
(straight-use-package 'treemacs-magit)

(use-package treemacs-projectile
  :after treemacs projectile)

(use-package treemacs-icons-dired
  :after treemacs dired
  :config (treemacs-icons-dired-mode))

(use-package treemacs-magit
  :after treemacs magit)


Point History
(straight-use-package '(point-history :type git :host github :repo "blue0513/point-history"))
(use-package point-history
  :ghook 'after-init-hook
  :bind (("C-c C-/" . point-history-show))
  :init (gsetq point-history-ignore-buffer "^ \\*Minibuf\\|^ \\*point-history-show*"))
Undo Propose
(straight-use-package 'undo-propose)
(use-package undo-propose
  :config (undo-propose-wrap redo))

Version Control

Useful Simple Packages
(dolist (package '(git-blamed
  (straight-use-package package))
Git Modes
(straight-use-package 'git-modes)
(straight-use-package 'magit)
(use-package magit
  :defer t
  :commands magit-status
  :hook ((magit-popup-mode-hook . no-trailing-whitespace)
         (git-commit-mode . goto-address-mode))
  :init (gsetq magit-diff-refine-hunk t)
  :bind (([(meta f12)] . magit-status)  ;; Hint: customize `magit-repository-directories' so that you can use C-u M-F12 to
         ("C-x g"      . magit-status)
         ("C-x M-g"    . magit-dispatch-popup)
         :map magit-status-mode-map
         ("C-M-<up>"   . magit-section-up)
         :map vc-prefix-map
         ("f"          . vc-git-grep))
  (gsetq vc-handled-backends nil)
  (when *is-a-mac* (add-hook 'magit-mode-hook (lambda () (local-unset-key [(meta h)])))))

(straight-use-package 'magit-todos)
(use-package magit-todos
  :defer t
  :hook ((magit-status-mode . magit-todos-mode)))
Magit Org Todos
(straight-use-package 'magit-org-todos)
(use-package magit-org-todos
  :defer t
  :config (magit-org-todos-autoinsert))
(straight-use-package 'forge)
(straight-use-package 'transient)
(gsetq transient-default-level 5)
Git Messenger
(straight-use-package 'git-messenger)
(use-package git-messenger
  :init (gsetq git-messenger:show-detail t)
  :bind (:map vc-prefix-map
         ("p" . git-messenger:popup-message)))
Git Gutter
(straight-use-package 'git-gutter)
(use-package git-gutter
  :hook (after-init . global-git-gutter-mode)
  :init (gsetq git-gutter:visual-line t
               git-gutter:disabled-modes '(asm-mode image-mode)
               git-gutter:modified-sign "❚"
               git-gutter:added-sign "✚"
               git-gutter:deleted-sign "✘")

  :config (general-define-key
           :prefix "C-x"
           "v =" 'git-gutter:popup-hunk
           "p"   'git-gutter:previous-hunk
           "n"   'git-gutter:next-hunk))
Github Gist
(straight-use-package 'gist)

Which Function

(use-package which-func
  :defer t
  :ghook 'after-init-hook)

Which Key

(straight-use-package 'which-key)
(use-package which-key
  :ghook 'after-init-hook)


(use-package whitespace
  (defun no-trailing-whitespace ()
    "Turn off display of trailing whitespace in this buffer."
    (setq show-trailing-whitespace nil))
  ;; But don't show trailing whitespace in SQLi, inf-ruby etc.
  (dolist (hook '(artist-mode-hook
    (add-hook hook #'no-trailing-whitespace))
  :diminish whitespace-mode)

(straight-use-package 'whitespace-cleanup-mode)
(use-package whitespace-cleanup-mode
  (gsetq whitespace-cleanup-mode-only-if-initially-clean nil)
  (gsetq-default whitespace-style
                 '(face tabs spaces trailing space-before-tab
                        newline indentation empty space-after-tab
                        space-mark tab-mark newline-mark))
  :hook ((after-init . global-whitespace-cleanup-mode))
  :diminish (whitespace-cleanup-mode)
  :bind (("<remap> <just-one-space>" . cycle-spacing)))

Writeroom Mode

(straight-use-package 'writeroom-mode)
(use-package writeroom-mode
  :defer t
  (define-minor-mode prose-mode
    "Set up a buffer for prose editing.
This enables or modifies a number of settings so that the
experience of editing prose is a little more like that of a
typical word processor."
    nil " Prose" nil
    (if prose-mode
          (when (fboundp 'writeroom-mode)
            (writeroom-mode 1))
          (setq truncate-lines nil)
          (setq word-wrap t)
          (setq cursor-type 'bar)
          (when (eq major-mode 'org)
            (kill-local-variable 'buffer-face-mode-face))
          (buffer-face-mode 1)
          ;;(delete-selection-mode 1)
          (set (make-local-variable 'blink-cursor-interval) 0.6)
          (set (make-local-variable 'show-trailing-whitespace) nil)
          (set (make-local-variable 'line-spacing) 0.2)
          (set (make-local-variable 'electric-pair-mode) nil)
          (ignore-errors (flyspell-mode 1))
          (visual-line-mode 1))
      (kill-local-variable 'truncate-lines)
      (kill-local-variable 'word-wrap)
      (kill-local-variable 'cursor-type)
      (kill-local-variable 'show-trailing-whitespace)
      (kill-local-variable 'line-spacing)
      (kill-local-variable 'electric-pair-mode)
      (buffer-face-mode -1)
      ;; (delete-selection-mode -1)
      (flyspell-mode -1)
      (visual-line-mode -1)
      (when (fboundp 'writeroom-mode)
        (writeroom-mode 0)))))


(straight-use-package 'yasnippet)
(straight-use-package 'yasnippet-snippets)

(use-package yasnippet
  :defer t
  :bind (:map yas-minor-mode-map
              ("C-'" . yas-expand))
  :commands (yas-minor-mode)
  :hook ((prog-mode      . yas-minor-mode)
         (yas-minor-mode . (lambda ()
                              (concat user-emacs-directory "snippets")))))
  :config (yas-reload-all))



(straight-use-package 'bing-dict)
(use-package bing-dict
  :bind (("C-c d" . bing-dict-brief))
  :init (gsetq bing-dict-show-thesaurus  'both
               bing-dict-vocabulary-save t
               bing-dict-cache-auto-save t
               (no-littering-expand-var-file-name "bing-dict/vocabulary.org")
               (no-littering-expand-var-file-name "bing-dict/bing-dict-save.el")))
(use-package ispell
  :if *ispell*
  (gsetq-default ispell-program-name   *ispell*
                 ispell-silently-savep t
                 ispell-dictionary     "english"
                 (no-littering-expand-var-file-name "ispell/dictionary"))
  (when (string-suffix-p "aspell" *ispell*)
    (gsetq-default ispell-extra-args '("--reverse"))))

(unless *ispell*
  (message "if you want to use ispell, try\n brew install aspell\n brew install ispell"))

Simple Supported Languages

(let ((languages '(elvish-mode
      (extras    '(fish-completion
  (dolist (language languages)
    (straight-use-package language))
  (dolist (extra extras)
    (straight-use-package extra)))

Language Server Protocol & Debug Adapter Protocol

(straight-use-package 'lsp-mode)
(use-package lsp
  :commands (lsp lsp-deferred)
  (defun delete-company-lsp ()
    "Delete company-lsp added by lsp-mode from company-backends"
    (when 'company-backends
      (gsetq company-backends (delete 'company-lsp company-backends)
             company-backends (delete 'intero-company company-backends))))
  :hook ((lsp-after-open . lsp-enable-imenu))
  :init (gsetq lsp-log-io                       *debug*
               lsp-print-performance            *debug*
               lsp-inhibit-message              t
               lsp-report-if-no-buffer          *debug*
               lsp-keep-workspace-alive         t
               lsp-enable-snippet               t
               lsp-restart                      'interactive
               lsp-auto-configure               nil
               lsp-document-sync-method         nil
               lsp-auto-execute-action          nil
               lsp-eldoc-render-all             t
               lsp-enable-completion-at-point   nil
               lsp-enable-xref                  t
               lsp-enable-indentation           t
               lsp-prefer-flymake               nil
               lsp-enable-on-type-formatting    t
               lsp-signature-auto-activate      t
               lsp-enable-semantic-highlighting t))
(straight-use-package 'lsp-ui)
(use-package lsp-ui
  :commands lsp-ui-mode
  :bind (:map lsp-ui-mode-map
              ("M-,"  . lsp-ui-peek-find-definitions)
              ("M-?"  . lsp-ui-peek-find-references)
              ("C-c u"   . lsp-ui-imenu)
              ("C-c C-a" . lsp-ui-sideline-apply-code-actions))
  :hook ((lsp-after-open . lsp-ui-mode))
  (gsetq lsp-ui-doc-position              'at-point
         lsp-ui-doc-header                nil
         lsp-ui-doc-border                "violet"
         lsp-ui-doc-include-signature     t
         lsp-ui-sideline-update-mode      'point
         lsp-ui-sideline-delay            1
         lsp-ui-sideline-ignore-duplicate t
         lsp-ui-peek-always-show          t
         lsp-ui-flycheck-enable           t))
(straight-use-package 'company-lsp)
(use-package company-lsp
  :after company
  :defer t
  :commands company-lsp
  (defun push-company-lsp-backends ()
   "Push company-lsp to the backends."
       (company-dabbrev company-dabbrev-code)
  (defun company-lsp-init-h ()
    "Make sure that `company-capf' is disabled since it is incompatible with
`company-lsp' (see lsp-mode#884)."
    (if (not (bound-and-true-p company-mode))
        (add-hook 'company-mode-hook #'company-lsp-init-h t t)
      (setq-local company-backends
                  (cons 'company-lsp
                        (remq 'company-capf company-backends)))
      (remove-hook 'company-mode-hook #'company-lsp-init-h t)))
  :hook ((lsp-mode . company-lsp-init-h))
  (gsetq company-lsp-async               t
         company-lsp-enable-recompletion t
         company-lsp-enable-snippet      t
         company-lsp-cache-candidates    'auto))
Dap Mode
(straight-use-package 'dap-mode)
(straight-use-package 'lsp-treemacs)
(use-package lsp-treemacs
  :commands lsp-treemacs-errors-list
  (lsp-metals-treeview-enable t)
  (gsetq lsp-metals-treeview-show-when-views-received t))

C/C++/Object-C (Clangd or ccls)

Clangd or ccls.

(use-package lsp-mode
  :if *clangd*
  :hook (((c-mode c++-mode objc-mode) . lsp-deferred))
  :init (setq-default lsp-clients-clangd-executable *clangd*))
(when *ccls*
  (straight-use-package 'ccls)
  (use-package ccls
    (defun ccls/load ()
      (require 'ccls)
    :hook (((c-mode c++-mode objc-mode) . ccls/load))
    :init (gsetq ccls-executable *ccls*
                 '(:clang (:extraArgs
                 ccls-sem-highlight-method 'font-lock)
    (defun ccls/callee ()
      (lsp-ui-peek-find-custom "$ccls/call" '(:callee t)))
    (defun ccls/caller ()
      (lsp-ui-peek-find-custom "$ccls/call"))
    (defun ccls/vars (kind)
      (lsp-ui-peek-find-custom "$ccls/vars" `(:kind ,kind)))
    (defun ccls/base (levels)
      (lsp-ui-peek-find-custom "$ccls/inheritance" `(:levels ,levels)))
    (defun ccls/derived (levels)
      (lsp-ui-peek-find-custom "$ccls/inheritance" `(:levels ,levels :derived t)))
    (defun ccls/member (kind)
      (lsp-ui-peek-find-custom "$ccls/member" `(:kind ,kind)))

    ;; The meaning of :role corresponds to https://github.com/maskray/ccls/blob/master/src/symbol.h

    ;; References w/ Role::Address bit (e.g. variables explicitly being taken addresses)
    (defun ccls/references-address ()
      (lsp-ui-peek-find-custom "textDocument/references"
       (plist-put (lsp--text-document-position-params) :role 128)))

    ;; References w/ Role::Dynamic bit (macro expansions)
    (defun ccls/references-macro ()
      (lsp-ui-peek-find-custom "textDocument/references"
       (plist-put (lsp--text-document-position-params) :role 64)))

    ;; References w/o Role::Call bit (e.g. where functions are taken addresses)
    (defun ccls/references-not-call ()
      (lsp-ui-peek-find-custom "textDocument/references"
       (plist-put (lsp--text-document-position-params) :excludeRole 32)))

    ;; References w/ Role::Read
    (defun ccls/references-read ()
      (lsp-ui-peek-find-custom "textDocument/references"
       (plist-put (lsp--text-document-position-params) :role 8)))

    ;; References w/ Role::Write
    (defun ccls/references-write ()
      (lsp-ui-peek-find-custom "textDocument/references"
       (plist-put (lsp--text-document-position-params) :role 16)))

    ;; xref-find-apropos (workspace/symbol)

    (defun my/highlight-pattern-in-text (pattern line)
      (when (> (length pattern) 0)
        (let ((i 0))
         (while (string-match pattern line i)
           (setq i (match-end 0))
           (add-face-text-property (match-beginning 0) (match-end 0) 'isearch t line))


    (after! lsp-methods
      ;;; Override
      ;; This deviated from the original in that it highlights pattern appeared in symbol
      (defun lsp--symbol-information-to-xref (pattern symbol)
       "Return a `xref-item' from SYMBOL information."
       (let* ((location (gethash "location" symbol))
              (uri (gethash "uri" location))
              (range (gethash "range" location))
              (start (gethash "start" range))
              (name (gethash "name" symbol)))
         (xref-make (format "[%s] %s"
                            (alist-get (gethash "kind" symbol) lsp--symbol-kind)
                            (my/highlight-pattern-in-text (regexp-quote pattern) name))
                    (xref-make-file-location (string-remove-prefix "file://" uri)
                                             (1+ (gethash "line" start))
                                             (gethash "character" start)))))

      (cl-defmethod xref-backend-apropos ((_backend (eql xref-lsp)) pattern)
        (let ((symbols (lsp--send-request (lsp--make-request
                                           `(:query ,pattern)))))
          (mapcar (lambda (x) (lsp--symbol-information-to-xref pattern x)) symbols))))))


Include haskell-mode, lsp-haskell, intero and structured haskell mode. Also inlcude haskell-snippets.

(straight-use-package 'haskell-mode)
(use-package haskell-mode
  (define-minor-mode stack-exec-path-mode
    "If this is a stack project, set `exec-path' to the path \"stack exec\" would use."
    :lighter ""
    :global nil
    (if stack-exec-path-mode
        (when (and (executable-find "stack")
                   (locate-dominating-file default-directory "stack.yaml"))
            (append (list (concat (string-trim-right (shell-command-to-string "stack path --local-install-root")) "/bin"))
                     (replace-regexp-in-string "[\r\n]+\\'" ""
                                               (shell-command-to-string "stack path --bin-path"))))
      (kill-local-variable 'exec-path)))

  :gfhook '(subword-mode
            (lambda () (gsetq-local tab-width 4)))
  :bind (("C-x a a" . align)
         :map haskell-mode-map
         ("C-c h" . hoogle)
         ("C-o"   . open-line))
  (gsetq haskell-mode-stylish-haskell-path            "stylish-haskell"
         haskell-indentation-layout-offset            4
         haskell-indentation-left-offset              4
         haskell-process-suggest-haskell-docs-imports t
         haskell-process-suggest-remove-import-lines  t
         haskell-process-auto-import-loaded-modules   t
         haskell-process-log                          t
         haskell-process-suggest-hayoo-imports        t
         haskell-process-suggest-hoogle-imports       t
         haskell-process-suggest-remove-import-lines  t
         haskell-tags-on-save                         t
         haskell-completing-read-function             'helm--completing-read-default
         haskell-doc-show-global-types                t
         haskell-svg-render-images                    t
         haskell-doc-chop-off-context                 nil)

  (unless *struct-hs*
    (add-hook #'haskell-mode-hook #'haskell-indentation-mode))

  (unless (fboundp 'align-rules-list)
    (defvar align-rules-list nil))

  (add-to-list 'align-rules-list
                 (regexp . "\\(\\s-+\\)\\(::\\|\\)\\s-+")
                 (modes quote (haskell-mode literate-haskell-mode))))
  (add-to-list 'align-rules-list
                 (regexp . "\\(\\s-+\\)=\\s-+")
                 (modes quote (haskell-mode literate-haskell-mode))))
  (add-to-list 'align-rules-list
                 (regexp . "\\(\\s-+\\)\\(->\\|\\)\\s-+")
                 (modes quote (haskell-mode literate-haskell-mode))))
  (add-to-list 'align-rules-list
                 (regexp . "\\(\\s-+\\)\\(<-\\|\\)\\s-+")
                 (modes quote (haskell-mode literate-haskell-mode))))

  (after! page-break-lines
    (push 'haskell-mode page-break-lines-modes))
  (defun haskell-mode-generate-tags (&optional and-then-find-this-tag)
    "Generate tags using Hasktags.  This is synchronous function.

  If optional AND-THEN-FIND-THIS-TAG argument is present it is used
  with function `xref-find-definitions' after new table was
    (let* ((dir (haskell-cabal--find-tags-dir))
           (command (haskell-cabal--compose-hasktags-command dir)))
      (if (not command)
          (error "Unable to compose hasktags command")
        ;; I disabled the noisy shell command output.
        ;; The original is (shell-command command)
        (call-process-shell-command command nil "*Shell Command Output*" t)
        (haskell-mode-message-line "Tags generated.")
        (when and-then-find-this-tag
          (let ((tags-file-name dir))
            (xref-find-definitions and-then-find-this-tag)))))))
LSP Haskell
(straight-use-package 'lsp-haskell)
(use-package lsp-haskell
  (defun start-lsp-haskell ()
    (require 'lsp)
    (require 'lsp-haskell)
  :defer t
  :hook ((haskell-mode . start-lsp-haskell))
  ;; :init
  ;; (gsetq lsp-haskell-process-path-hie "hie-8.6.5")
  ;; You can set the lsp-haskell settings here
  ;; (lsp-haskell-set-hlint-on)                    ;; default on
  ;; (lsp-haskell-set-max-number-of-problems 100)  ;; default 100
  ;; (lsp-haskell-set-liquid-on)                   ;; default off
  ;; (lsp-haskell-set-completion-snippets-on)      ;; default on
  ;; (gsetq lsp-haskell-process-path-hie "ghcide")
  ;; (gsetq lsp-haskell-process-args-hie '())
(when *intero*
  (straight-use-package 'intero)
  (use-package intero
    :hook ((haskell-mode . intero-mode))
    (define-key intero-mode-map (kbd "M-?") nil)
    (define-key intero-mode-map (kbd "C-c C-r") nil)))
Structured Haskell Mode
(if *struct-hs*
      (add-to-list 'load-path *struct-hs-path*)
      (require 'shm)
      (setq shm-program-name *struct-hs*)
      (add-hook #'haskell-mode-hook #'structured-haskell-mode))
    (when *struct-hs*
      (message (concat "*NOTE* about structured-haskell-mode:\n"
                       "No structured-haskell-mode elisp find.\n"
                       "If you want to use it, \n"
                       "please install it and config its variables *struct-hs-path* in user-config.el\n")))))
haskell snippets
(straight-use-package 'haskell-snippets)


(use-package lsp-html
  :hook ((html-mode . lsp-deferred)))

JavaScript & TypeScript

(use-package lsp-mode
  :disabled t
  :hook ((javascript-mode . lsp-deferred)))


(use-package lisp-mode
  (defun eval-last-sexp-or-region (prefix)
    "Eval region from BEG to END if active, otherwise the last sexp."
    (interactive "P")
    (if (and (mark) (use-region-p))
        (eval-region (min (point) (mark)) (max (point) (mark)))
      (pp-eval-last-sexp prefix)))
  :bind (:map emacs-lisp-mode-map
         ("<remap> <eval-expression>" . pp-eval-expression)
         ("C-x C-e" . eval-last-sexp-or-region)))
(straight-use-package 'highlight-quoted)
(use-package highlight-quoted
  :defer t
  :hook ((emacs-lisp-mode . highlight-quoted-mode)))
(straight-use-package 'elisp-def)
(use-package elisp-def
  :defer t
  :hook (((emacs-lisp-mode ielm-mode) . elisp-def-mode)))


(straight-use-package 'markdown-mode)
(use-package markdown-mode
  :defer t
  :mode ("INSTALL\\'"


(straight-use-package 'pandoc-mode)


Include python-mode, black, py-isort, python-docstring and sphinx-doc.

Python Mode
(straight-use-package 'python-mode)
(use-package python-mode
  :commands python-mode
  :mode ("\\.py\\'" . python-mode)
  :interpreter (("python"  . python-mode)
                ("python3" . python-mode))
  (defcustom nasy*python-buffer "vterm"
    "Nasy Python Buffer"
    :group 'python-mode
    :type 'string)

  (defun nasy/python-send-buffer ()
    "Send current buffer to the running python process."
    (let ((proc (get-buffer-process nasy*python-buffer)))
      (unless proc
        (error "No process found"))
      (comint-simple-send proc
                          (concat "%run " (format "%s" (buffer-file-name))))
      (pop-to-buffer nasy*python-buffer)))

  (defun nasy/python-send-region (begin end)
    "Evaluate the code in region from BEGIN to END in the python repl.
if the region is unset, the current line will be used."
    (interactive "r")
    (unless (use-region-p)
      (setq begin (line-beginning-position)
            end (line-end-position)))
    (let* ((text (buffer-substring-no-properties begin end))
           (proc (get-buffer-process nasy*python-buffer)))
      (unless proc
        (error "No process found"))
      (comint-simple-send proc text)
      (display-buffer nasy*python-buffer)))

  (defun nasy/python-send-defun (&optional arg)
    "Send the current defun to inferior Python process.
When ARG is non-nil do not include decorators."
    (interactive (list current-prefix-arg t))
       (end-of-line 1)
       (while (and (or (python-nav-beginning-of-defun)
                    (beginning-of-line 1))
                 (> (current-indentation) 0)))
       (when (not arg)
         (while (and (forward-line -1)
                   (looking-at (python-rx decorator))))
         (forward-line 1))
         (or (python-nav-end-of-defun)
            (end-of-line 1))

  (defun nasy/python-switch-to-shell ()
    "Switch to inferior Python process buffer."
    (interactive "p")
    (let ((proc (get-buffer-process nasy:python-buffer)))
      (unless proc
        (error "No process found"))
      (pop-to-buffer nasy*python-buffer)))

  (defun python-flycheck-setup ()
    "Add python checker for lsp-ui."
    (after! lsp-ui
      (flycheck-add-next-checker 'lsp-ui             'python-pytype)
      (flycheck-add-next-checker 'python-pytype      'python-flake8)))

  (defun start-lsp-pyls ()
    "Start lsp-python-ms."
    (require 'lsp-pyls)

   :prefix "C-c"
   :keymaps 'python-mode-map
   "C-b" 'nasy/python-send-buffer
   "C-r" 'nasy/python-send-region
   "C-c" 'nasy/python-send-defun
   "C-z" 'nasy/python-switch-to-shell)
   :keymaps 'python-mode-map
   "<S-return>" 'nasy/python-send-region)
  (gsetq python-indent-offset                  4
         indent-tabs-mode                      nil
         python-indent-guess-indent-offset     nil
         python-shell-completion-native-enable nil
         py-set-fill-column-p                  t
         py-shell-name                         nasy*python-buffer)

  (nasy/add-company-backend 'python-mode '(company-lsp company-files :with company-tabnine company-yasnippet))

  ;; A list here https://github.com/palantir/python-language-server/blob/develop/vscode-client/package.json#L23-L230
  ;; I prefer pydocstyle and black, so disabled yapf, though, pydocstyle still cannot be abled.
  ;; pip install black pyls-black -U
  ;; The default line-length is 88 when using black, you can add a file named "pyproject.yaml" that contains
  ;; [tool.black]
  ;; line-length = 79
  (after! lsp-pyls
    (gsetq lsp-pyls-configuration-sources                          ["flake8"]
           lsp-pyls-plugins-pydocstyle-enabled                     t
           lsp-pyls-plugins-yapf-enabled                           nil
           lsp-pyls-plugins-jedi-definition-follow-imports         t
           lsp-pyls-plugins-jedi-definition-follow-builtin-imports t
           lsp-pyls-plugins-jedi-signature-help-enabled            t
           lsp-pyls-plugins-jedi-symbols-enabled                   t
           lsp-pyls-plugins-flake8-enabled                         t
           lsp-pyls-plugins-pyls_mypy-live-mode                    nil))
  :hook ((after-init  . python-flycheck-setup))
         ;; (python-mode . start-lsp-pyls))
  (unless *blacken*
    (add-hook #'python-mode-hook
              #'(lambda () (add-hook #'before-save-hook #'lsp-format-buffer nil t)))))
(straight-use-package 'lsp-python-ms)
(use-package lsp-python-ms
  :defer t
  (defun start-lsp-mspyls ()
    "Start lsp-python-ms."
    (require 'lsp-python-ms)
  :init (gsetq lsp-python-ms-nupkg-channel "daily"
               lsp-python-ms-executable    "~/.local/bin/Microsoft.Python.LanguageServer"
               lsp-python-ms-errors        ["inherit-non-class"
               lsp-python-ms-warnings      ["no-cls-argument"
  :hook ((python-mode . start-lsp-mspyls)))

Flycheck Mypy
;; (straight-use-package 'flycheck-mypy)
(gsetq flycheck-python-mypy-ini "~/config/mypy/config")
(after! flycheck
  (flycheck-def-args-var flycheck-python-pytype-args python-pytype)

  (flycheck-define-checker python-pytype
    "Pytype syntax checker.

    See url `https://github.com/google/pytype`."
    :command ("pytype"
              (eval flycheck-python-pytype-args)
    ((warning line-start "File \"" (file-name) "\", line " line ", " (message (one-or-more (not (any "[")))) "[" (id (one-or-more not-newline)) "]"))
    :modes python-mode
    :predicate flycheck-buffer-saved-p)
    ;; :next-checkers (python-flake8))

  (add-to-list 'flycheck-checkers 'python-pytype t))
;; Now you can use it in lsp.
;; NOTICE you have to config black though pyproject.toml.
(when *blacken*
  (straight-use-package 'blacken)
  (use-package blacken
    :hook ((python-mode . blacken-mode))
    :init (gsetq blacken-allow-py36  t)))
(straight-use-package 'py-isort)
(use-package py-isort
  :hook ((before-save . py-isort-before-save)))
Python Docstring
(straight-use-package 'python-docstring)
(use-package python-docstring
  :hook ((python-mode . python-docstring-mode)))
Sphinx Doc
(straight-use-package 'sphinx-doc)
(use-package sphinx-doc
  :hook ((python-mode . sphinx-doc-mode)))
(straight-use-package 'pyimport)
(use-package pyimport
  :bind (:map python-mode-map
              ("C-c C-i" . pyimport-insert-missing)))


Include rust-mode, rls and Cargo.

(when *rust*
  (straight-use-package 'rust-mode)
  (straight-use-package 'cargo)
  (use-package rust-mode
    :defer t
    :hook ((rust-mode . (lambda () (setq-local tab-width 4)))
           (rust-mode . lsp-deferred))
    (when *rls*
      (add-hook #'rust-mode-hook #'(lambda () (add-to-list 'flycheck-disabled-checkers 'rust-cargo)))))

  (use-package cargo
    :after rust-mode
    :hook ((toml-mode . cargo-minor-mode)
           (rust-mode . cargo-minor-mode))))


(use-package lsp-yaml
  :defer t
  :hook ((yaml-mode . lsp-deferred)))

Org Mode


I use org with org-plus-contrib

(straight-use-package 'org-plus-contrib)

Basic Configs

(use-package org
  (advice-add 'org-refile :after (lambda (&rest _) (org-save-all-org-buffers)))

  ;; Exclude DONE state tasks from refile targets
  (defun verify-refile-target ()
    "Exclude todo keywords with a done state from refile targets."
    (not (member (nth 2 (org-heading-components)) org-done-keywords)))
  (setq org-refile-target-verify-function 'verify-refile-target)

  (defun org-refile-anywhere (&optional goto default-buffer rfloc msg)
    "A version of `org-refile' which allows refiling to any subtree."
    (interactive "P")
    (let ((org-refile-target-verify-function))
      (org-refile goto default-buffer rfloc msg)))

  (defun org-agenda-refile-anywhere (&optional goto rfloc no-update)
    "A version of `org-agenda-refile' which allows refiling to any subtree."
    (interactive "P")
    (let ((org-refile-target-verify-function))
      (org-agenda-refile goto rfloc no-update)))

  ;; The original from spacemacs chinese layer shows as follow.
  ;;   (defadvice org-html-paragraph (before org-html-paragraph-advice
  ;;                                         (paragraph contents info) activate)
  ;;     "Join consecutive Chinese lines into a single long line without
  ;; unwanted space when exporting org-mode to html."
  ;;     (let* ((origin-contents (ad-get-arg 1))
  ;;            (fix-regexp "[[:multibyte:]]")
  ;;            (fixed-contents
  ;;             (replace-regexp-in-string
  ;;              (concat
  ;;               "\\(" fix-regexp "\\) *\n *\\(" fix-regexp "\\)") "\\1\\2" origin-contents)))
  ;;       (ad-set-arg 1 fixed-contents)))

  (defun nasy/org-html-paragraph-advice (orig paragraph contents &rest args)
    "Join consecutive Chinese lines into a single long line without
unwanted space when exporting org-mode to html."
    (let* ((fix-regexp "[[:multibyte:]]")
              "\\(" fix-regexp "\\) *\n *\\(" fix-regexp "\\)") "\\1\\2" contents)))
      (apply orig paragraph fixed-contents args)))
  (advice-add #'org-html-paragraph :around #'nasy/org-html-paragraph-advice)

  (defun nasy/org-fix-saveplace ()
    "Fix a problem with saveplace.el putting you back in a folded position"
    (when (outline-invisible-p)
        (outline-previous-visible-heading 1)

  (defvar-local nasy/org-at-src-begin -1
    "Variable that holds whether last position was a ")

  (defvar nasy/ob-header-symbol ?☰
    "Symbol used for babel headers")

  (defun nasy/org-prettify-src--update ()
    (let ((case-fold-search t)
          (re "^[ \t]*#\\+begin_src[ \t]+[^ \f\t\n\r\v]+[ \t]*")
        (goto-char (point-min))
        (while (re-search-forward re nil t)
          (goto-char (match-end 0))
          (let ((args (org-trim
                       (buffer-substring-no-properties (point)
            (when (org-string-nw-p args)
              (let ((new-cell (cons args nasy/ob-header-symbol)))
                (cl-pushnew new-cell prettify-symbols-alist :test #'equal)
                (cl-pushnew new-cell found :test #'equal)))))
        (setq prettify-symbols-alist
              (cl-set-difference prettify-symbols-alist
                                   (lambda (elm)
                                     (eq (cdr elm) nasy/ob-header-symbol))
                                  found :test #'equal)))
        ;; Clean up old font-lock-keywords.
        (font-lock-remove-keywords nil prettify-symbols--keywords)
        (setq prettify-symbols--keywords (prettify-symbols--make-keywords))
        (font-lock-add-keywords nil prettify-symbols--keywords)
        (while (re-search-forward re nil t)
          (font-lock-flush (line-beginning-position) (line-end-position))))))

  (defun nasy/org-prettify-src ()
    "Hide src options via `prettify-symbols-mode'.

  `prettify-symbols-mode' is used because it has uncollpasing. It's
  may not be efficient."
    (let* ((case-fold-search t)
           (at-src-block (save-excursion
                           (looking-at "^[ \t]*#\\+begin_src[ \t]+[^ \f\t\n\r\v]+[ \t]*"))))
      ;; Test if we moved out of a block.
      (when (or (and nasy/org-at-src-begin
                     (not at-src-block))
                ;; File was just opened.
                (eq nasy/org-at-src-begin -1))
      ;; Remove composition if at line; doesn't work properly.
      ;; (when at-src-block
      ;;   (with-silent-modifications
      ;;     (remove-text-properties (match-end 0)
      ;;                             (1+ (line-end-position))
      ;;                             '(composition))))
      (setq nasy/org-at-src-begin at-src-block)))

  (defun nasy/org-prettify-symbols ()
    (mapc (apply-partially 'add-to-list 'prettify-symbols-alist)
          (cl-reduce 'append
                     (mapcar (lambda (x) (list x (cons (upcase (car x)) (cdr x))))
                             `(("#+begin_src" . ?λ)
                               ("#+end_src"   . ?⌞)
                               ("#+header:" . ,nasy/ob-header-symbol)
                               ("#+begin_quote" . ?✎)
                               ("#+end_quote" . ?⌞)))))
    (add-hook 'post-command-hook 'nasy/org-prettify-src t t))

  :bind (("C-c l" . org-store-link)
         ("C-c a" . org-agenda)
         ("C-c c" . org-capture)
         :map org-mode-map
         ("C-M-<up>" . org-up-element)
         ("M-h"      . nil)
         ("C-c g"    . org-mac-grab-link)
         ("C-c _"    . org-edit-special)
         :map org-src-mode-map
         ("C-c _"    . org-edit-src-exit))
  :hook ((org-mode . auto-fill-mode)
         (org-mode . nasy/org-fix-saveplace)
         (org-mode . nasy/org-prettify-symbols))
   org-archive-mark-done nil
   org-archive-location  "%s_archive::* Archive"
   org-archive-mark-done nil

   org-catch-invisible-edits 'smart

   org-default-notes-file "~/notes/default.org"

   org-edit-timestamp-down-means-later t

   org-ellipsis " ﹅"

   org-emphasis-regexp-components ;; markup chinesee without space
      (list (concat " \t('\"{"            "[:nonascii:]")
            (concat "- \t.,:!?;'\")}\\["  "[:nonascii:]")
            " \t\r\n,\"'"

   org-export-backends                           '(ascii html latex md)
   org-export-coding-system                      'utf-8
   org-export-kill-product-buffer-when-displayed t
   org-export-with-broken-links                  'mark
   org-export-with-sub-superscripts              '{}
   org-use-sub-superscripts                      '{}

   org-fast-tag-selection-single-key 'expert

   org-highlight-latex-and-related: '(native latex script entities)

   org-hide-emphasis-markers t
   org-hide-leading-stars    nil

   org-html-checkbox-type       'uncode
   org-html-doctype             "html5"
   org-html-html5-fancy         t
   org-html-htmlize-output-type 'inline-css
   org-html-klipsify-src        t
   org-html-mathjax-options     '((path          "https://cdnjs.cloudflare.com/ajax/libs/mathjax/2.7.5/latest.js?config=TeX-AMS-MML_HTMLorMML")
                                  (scale         "100")
                                  (align         "center")
                                  (font          "Neo-Euler")
                                  (linebreaks    "false")
                                  (autonumber    "AMS")
                                  (indent        "0em")
                                  (multlinewidth "85%")
                                  (tagindent     ".8em")
                                  (tagside       "right"))
   org-html-with-latex          'mathjax
   org-html-validation-link     nil

   org-indent-mode-turns-on-hiding-stars nil

   org-pretty-entities t

   ;; org time
   ;; org-display-custom-times         t  ;; should setq-default
   org-time-stamp-custom-formats    '("<%a %b %d, %Y>" . "<%a %b %d %H:%M:%S %Y>")
   org-export-date-timestamp-format "%b %d, %Y"

   ;; org latex
   org-latex-compiler "lualatex"
    (("AUTO" "inputenc"  t   ("pdflatex"))
     ("T1"   "fontenc"   t   ("pdflatex"))
     (""     "graphicx"  t   nil)
     (""     "grffile"   t   nil)
     (""     "longtable" t   nil)
     (""     "booktabs"  t   nil)
     (""     "wrapfig"   nil nil)
     (""     "rotating"  nil nil)
     ("normalem" "ulem"  t   nil)
     (""     "amsmath"   t   nil)
     (""     "textcomp"  t   nil)
     (""     "amssymb"   t   nil)
     (""     "capt-of"   nil nil)
      "hyperref" t nil)
     (""            "luatexja-fontspec" t nil)
     (""            "listings"          t nil)
     (""            "algpseudocode" t nil)
     ("cache=false" "minted"            t nil)))
   org-latex-default-table-environment "longtable"
   org-latex-listings 'minted
    ((emacs-lisp   "Lisp")
     (lisp         "Lisp")
     (clojure      "Lisp")
     (c            "C")
     (C            "C")
     (cc           "C++")
     (fortran      "fortran")
     (perl         "Perl")
     (cperl        "Perl")
     (Python       "Python")
     (python       "Python")
     (ruby         "Ruby")
     (html         "HTML")
     (xml          "XML")
     (tex          "TeX")
     (latex        "[LaTeX]TeX")
     (sh           "bash")
     (shell-script "bash")
     (gnuplot      "Gnuplot")
     (ocaml        "Caml")
     (caml         "Caml")
     (sql          "SQL")
     (sqlite       "sql")
     (makefile     "make")
     (make         "make")
     (R            "r")))
    ("lualatex -shell-escape -interaction nonstopmode %f"
     "lualatex -shell-escape -interaction nonstopmode %f"))
   org-latex-tables-booktabs t

   org-level-color-stars-only nil
   org-list-indent-offset 2
   org-log-done t

   org-outline-path-complete-in-steps nil

   org-refile-allow-creating-parent-nodes 'confirm
   org-refile-targets                     '((nil :maxlevel . 5) (org-agenda-files :maxlevel . 5))
   org-refile-use-cache                   nil
   org-refile-use-outline-path            t

   org-startup-indented  t
   org-startup-folded    'content
   org-startup-truncated nil

   org-src-lang-modes '(("C"         . c)
                        ("C++"       . c++)
                        ("asymptote" . asy)
                        ("bash"      . sh)
                        ("beamer"    . latex)
                        ("calc"      . fundamental)
                        ("makefile"  . fundamental)
                        ("make"      . fundamental)
                        ("cpp"       . c++)
                        ("ditaa"     . artist)
                        ("dot"       . fundamental)
                        ("elisp"     . emacs-lisp)
                        ("ocaml"     . tuareg)
                        ("screen"    . shell-script)
                        ("shell"     . sh)
                        ("sqlite"    . sql))

   org-support-shift-select t

   org-tags-column 80

   ;; to-do settings
   org-todo-keywords        (quote ((sequence "TODO(t)" "NEXT(n)" "|" "DONE(d!/!)")
                                    (sequence "PROJECT(p)" "|" "DONE(d!/!)" "CANCELLED([email protected]/!)")
                                    (sequence "WAITING([email protected]/!)" "DELEGATED(e!)" "HOLD(h)" "|" "CANCELLED([email protected]/!)")))
   org-todo-repeat-to-state "NEXT"
   org-todo-keyword-faces   (quote (("NEXT" :inherit warning)
                                    ("PROJECT" :inherit font-lock-string-face))))
  (gsetq org-display-custom-times t)
  (nasy/add-company-backend 'org-mode 'company-tabnine)
  ;; --------
   `((ditaa      . t)
     (dot        . t)
     (elvish     . t)
     (emacs-lisp . t)
     (gnuplot    . t)
     (haskell    . nil)
     (latex      . t)
     (ledger     . t)
     (ocaml      . nil)
     (octave     . t)
     (plantuml   . t)
     (python     . t)
     (R          . t)
     (ruby       . t)
     (screen     . nil)
     (,(if (locate-library "ob-sh") 'sh 'shell) . t)
     (sql . nil)
     (sqlite . t)))

  (gsetq org-babel-python-command "python3")

  ;; --------
  (gsetq luamagick
           :programs ("lualatex" "convert")
           :description "pdf > png"
           :message "you need to install lualatex and imagemagick."
           :use-xcolor t
           :image-input-type "pdf"
           :image-output-type "png"
           :image-size-adjust (1.0 . 1.0)
           :latex-compiler ("lualatex -interaction nonstopmode -output-directory %o %f")
           :image-converter ("convert -density %D -trim -antialias %f -quality 100 %O")))
  (add-to-list 'org-preview-latex-process-alist luamagick)

  (gsetq luasvg
           :programs ("lualatex" "dvisvgm")
           :description "dvi > svg"
           :message "you need to install lualatex and dvisvgm."
           :use-xcolor t
           :image-input-type "dvi"
           :image-output-type "svg"
           :image-size-adjust (1.7 . 1.5)
           :latex-compiler ("lualatex -interaction nonstopmode -output-format dvi -output-directory %o %f")
           :image-converter ("dvisvgm %f -n -b min -c %S -o %O")))
  (add-to-list 'org-preview-latex-process-alist luasvg)
  (gsetq org-preview-latex-default-process 'luasvg)

  (require 'org-tempo nil t)
  (after! ox
    (let ((oxs '(ox-rst
      (dolist (language oxs)
        (straight-use-package language)
        (require language nil t)))))

Org Agenda

(use-package org-agenda
  :init (gsetq-default org-agenda-clockreport-parameter-plist '(:link t :maxlevel 3))
  :hook ((org-agenda-mode . (lambda () (add-hook 'window-configuration-change-hook 'org-agenda-align-tags nil t)))
         (org-agenda-mode . hl-line-mode))
  :config (add-to-list 'org-agenda-after-show-hook 'org-show-entry)
  (let ((active-project-match "-INBOX/PROJECT"))

    (gsetq org-stuck-projects
           `(,active-project-match ("NEXT")))

     org-agenda-compact-blocks t
     org-agenda-sticky t
     org-agenda-start-on-weekday nil
     org-agenda-span 'day
     org-agenda-include-diary nil
     '((agenda habit-down time-up user-defined-up effort-up category-keep)
       (todo category-up effort-up)
       (tags category-up effort-up)
       (search category-up))
     org-agenda-window-setup 'current-window
     `(("N" "Notes" tags "NOTE"
        ((org-agenda-overriding-header "Notes")
         (org-tags-match-list-sublevels t)))
       ("g" "GTD"
        ((agenda "" nil)
         (tags "INBOX"
               ((org-agenda-overriding-header "Inbox")
                (org-tags-match-list-sublevels nil)))
         (stuck ""
                ((org-agenda-overriding-header "Stuck Projects")
                 (org-agenda-tags-todo-honor-ignore-options t)
                 (org-tags-match-list-sublevels t)
                 (org-agenda-todo-ignore-scheduled 'future)))
         (tags-todo "-INBOX"
                    ((org-agenda-overriding-header "Next Actions")
                     (org-agenda-tags-todo-honor-ignore-options t)
                     (org-agenda-todo-ignore-scheduled 'future)
                      '(lambda ()
                         (or (org-agenda-skip-subtree-if 'todo '("HOLD" "WAITING"))
                             (org-agenda-skip-entry-if 'nottodo '("NEXT")))))
                     (org-tags-match-list-sublevels t)
                      '(todo-state-down effort-up category-keep))))
         (tags-todo ,active-project-match
                    ((org-agenda-overriding-header "Projects")
                     (org-tags-match-list-sublevels t)
         (tags-todo "-INBOX/-NEXT"
                    ((org-agenda-overriding-header "Orphaned Tasks")
                     (org-agenda-tags-todo-honor-ignore-options t)
                     (org-agenda-todo-ignore-scheduled 'future)
                      '(lambda ()
                         (or (org-agenda-skip-subtree-if 'todo '("PROJECT" "HOLD" "WAITING" "DELEGATED"))
                             (org-agenda-skip-subtree-if 'nottododo '("TODO")))))
                     (org-tags-match-list-sublevels t)
         (tags-todo "/WAITING"
                    ((org-agenda-overriding-header "Waiting")
                     (org-agenda-tags-todo-honor-ignore-options t)
                     (org-agenda-todo-ignore-scheduled 'future)
         (tags-todo "/DELEGATED"
                    ((org-agenda-overriding-header "Delegated")
                     (org-agenda-tags-todo-honor-ignore-options t)
                     (org-agenda-todo-ignore-scheduled 'future)
         (tags-todo "-INBOX"
                    ((org-agenda-overriding-header "On Hold")
                      '(lambda ()
                         (or (org-agenda-skip-subtree-if 'todo '("WAITING"))
                             (org-agenda-skip-entry-if 'nottodo '("HOLD")))))
                     (org-tags-match-list-sublevels nil)

Org Bullets

(straight-use-package 'org-bullets)
(use-package org-bullets
  (defun nasy/org-bullets-mode ()
    (org-bullets-mode 1))
  :hook ((org-mode . nasy/org-bullets-mode))
  :init (gsetq org-bullets-bullet-list
               '(;;; Large
                 ;; ♥ ● ○ ◇ ✚ ✜ ☯ ◆ ♠ ♣ ♦ ☢ ❀ ◆ ◖ ▶
                 ;;; Small
                 ;; ► • ★ ▸

Org Capture

(use-package org-capture
  :defer t
  (unless (boundp 'org-capture-templates)
    (defvar org-capture-templates nil))

  (add-to-list 'org-capture-templates '("t" "Tasks"))

  (add-to-list 'org-capture-templates
               '("tr" "Book Reading Task" entry
                 (file+olp "~/notes/task.org" "Reading" "Book")
                 "* TODO %^{book name}\n%u\n%a\n" :clock-in t :clock-resume t))

  (add-to-list 'org-capture-templates
               '("tw" "Work Task" entry
                 (file+headline "~/notes/task.org" "Work")
                 "* TODO %^{task name}\n%u\n%a\n" :clock-in t :clock-resume t))

  (add-to-list 'org-capture-templates
               '("T" "Thoughts" entry
                 (file "~/notes/thoughts.org")
                 "* %t - %^{heading}\n\n%?"))

  (add-to-list 'org-capture-templates
               '("j" "Journal" entry
                 (file "~/notes/journal.org")
                 "* %U - %^{heading}\n  %?"))

  (add-to-list 'org-capture-templates
               '("i" "Inbox" entry
                 (file "~/notes/inbox.org")
                 "* %U - %^{heading} %^g\n %?\n"))

  (add-to-list 'org-capture-templates
               '("n" "Notes" entry
                 (file "~/notes/notes.org")
                 "* %^{heading} %t %^g\n  %?\n")))

Org Cliplink

(straight-use-package 'org-cliplink)

Org clock

(use-package org-clock
  (defun show-org-clock-in-header-line ()
    "Show the clocked-in task in header line"
    (setq-default header-line-format '((" " org-mode-line-string ""))))

  (defun hide-org-clock-from-header-line ()
    "Hide the clocked-in task from header line"
    (setq-default header-line-format nil))
  (gsetq org-clock-persist t
         org-clock-in-resume t
         ;; Save clock data and notes in the LOGBOOK drawer
         org-clock-into-drawer t
         ;; Save state changes in the LOGBOOK drawer
         org-log-into-drawer t
         ;; Removes clocked tasks with 0:00 duration
         org-clock-out-remove-zero-time-clocks t
         ;; Show clock sums as hours and minutes, not "n days" etc.
         '(:hours "%d" :require-hours t :minutes ":%02d" :require-minutes t))
  :hook ((org-clock-in . show-org-clock-in-header-line)
         ((org-clock-out . org-clock-cancel) . hide-org-clock-from-header))
  :bind (:map org-clock-mode-line-map
             ([header-line mouse-2] . org-clock-goto)
             ([header-line mouse-1] . org-clock-menu))
  (when (and *is-a-mac* (file-directory-p "/Applications/org-clock-statusbar.app"))
    (add-hook 'org-clock-in-hook
              (lambda () (call-process "/usr/bin/osascript" nil 0 nil "-e"
                                  (concat "tell application \"org-clock-statusbar\" to clock in \""
                                          org-clock-current-task "\""))))
    (add-hook 'org-clock-out-hook
              (lambda () (call-process "/usr/bin/osascript" nil 0 nil "-e"
                                  "tell application \"org-clock-statusbar\" to clock out")))))

Org Extra Jar – ob-ditaa & ob-plantuml

Include ob-ditaa and ob-plantuml

(use-package org
  :defer t
  (defun grab-ditaa (url jar-name)
    "Download URL and extract JAR-NAME as `org-ditaa-jar-path'."
    (message "Grabbing " jar-name " for org.")
    (let ((zip-temp (make-temp-name (no-littering-expand-var-file-name "emacs-ditaa"))))
            (when (executable-find "unzip")
              (url-copy-file url zip-temp)
              (shell-command (concat "unzip -p " (shell-quote-argument zip-temp)
                                     " " (shell-quote-argument jar-name) " > "
                                     (shell-quote-argument org-ditaa-jar-path)))))
        (when (file-exists-p zip-temp)
          (delete-file zip-temp)))))
  (unless (and (boundp 'org-ditaa-jar-path)
               (file-exists-p org-ditaa-jar-path))
    (let ((jar-name "ditaa0_9.jar")
          (url "http://jaist.dl.sourceforge.net/project/ditaa/ditaa/0.9/ditaa0_9.zip"))
      (setq org-ditaa-jar-path (no-littering-expand-var-file-name jar-name))
      (unless (file-exists-p org-ditaa-jar-path)
        (grab-ditaa url jar-name))))

  (let ((jar-name "plantuml.jar")
        (url "http://jaist.dl.sourceforge.net/project/plantuml/plantuml.jar"))
    (setq org-plantuml-jar-path (no-littering-expand-var-file-name jar-name))
    (unless (file-exists-p org-plantuml-jar-path)
      (url-copy-file url org-plantuml-jar-path))))

Org PDF view

(straight-use-package 'org-pdfview)

Org Pomodoro

(use-package org-pomodoro
  :defer t
  :init (gsetq org-pomodoro-keep-killed-pomodoro-time t)
  :bind (:map org-agenda-mode-map
              ("P" . org-pomodoro)))

Org Toc

(straight-use-package 'toc-org)

Org Wc

(straight-use-package 'org-wc)



Emojify and all-the-icons
(straight-use-package 'emojify)
(use-package emojify
  :commands emojify-mode
  :hook ((after-init . global-emojify-mode))
  :init (gsetq emojify-emoji-styles '(unicode github)
               emojify-display-style 'unicode))

(straight-use-package 'all-the-icons)
(use-package all-the-icons
  :init (gsetq inhibit-compacting-font-caches t))


I use cn-fonts, you can see my example cnfonts profile here

This example profile will automatically generate to etc/cnfonts/nasy-profile.el.

But disabled for it's tooo slow.

;; (use-package cnfonts
;;   :disabled t
;;   :straight t
;;   :init
;;   (gsetq cnfonts-directory (no-littering-expand-etc-file-name "cnfonts"))
;;   :hook ((after-init . cnfonts-enable))
;;   :config
;;   (defun nasy/set-symbol-fonts (fontsize-list)
;;     "Set symbol fonts with FONTSIZE-LIST."
;;     (let* ((fontname "Fira Code Symbol")
;;            (fontsize (nth 0 fontsize-list))
;;            (fontspec (font-spec :name fontname
;;                                 :size fontsize
;;                                 :weight 'normal
;;                                 :slant 'normal)))
;;       (if (cnfonts--fontspec-valid-p fontspec)
;;           (set-fontset-font t '(#Xe100 . #Xe16f) fontspec)
;;         (message "Font %S not exists!" fontname))))
;;   (defun nasy/set-symbol-extra-fonts (fontsize-list)
;;     "Set extra symbol fonts with FONTSIZE-LIST."
;;     (let* ((fontname "Arial")
;;            (fontsize (nth 0 fontsize-list))
;;            (fontspec (font-spec :name fontname
;;                                 :size fontsize
;;                                 :weight 'normal
;;                                 :slant 'normal)))
;;       (if (cnfonts--fontspec-valid-p fontspec)
;;           (set-fontset-font t '(#X1d400 . #X1d744) fontspec)
;;         (message "Font %S not exists!" fontname))))
;;   (add-hook #'cnfonts-set-font-finish-hook #'nasy/set-symbol-fonts)
;;   (add-hook #'cnfonts-set-font-finish-hook #'nasy/set-symbol-extra-fonts))
set fonts
(defun nasy/set-font ()
  "Nasy set font"
   'default nil
   :font (font-spec :name   *font*
                    :weight *font-weight*
                    :size   *font-size*))

  (when (display-graphic-p)
    (dolist (charset '(kana han symbol cjk-misc bopomofo))
       (frame-parameter nil 'font)
       (font-spec :name   *font-cjk*
                  :weight *font-weight-cjk*
                  :size   *font-size-cjk*)))))


Main Theme

I use doom-themes.

(straight-use-package 'doom-themes)
(use-package doom-themes
  :init (gsetq doom-dracula-brighter-comments t
               doom-dracula-colorful-headers  t
               doom-dracula-comment-bg        t)
  (after! treemacs
  (after! org
(when (eq *theme* 'darktooth-theme)
  (straight-use-package 'darktooth-theme)
  (use-package darktooth-theme
(when (eq *theme* 'soothe-theme)
  (straight-use-package 'soothe-theme))
Load Theme
(load-theme *theme* t)

Mode Line

(straight-use-package 'nyan-mode)
(use-package nyan-mode
  :init (gsetq nyan-animate-nyancat t
               nyan-bar-length 16
               nyan-wavy-trail t)
  :hook ((after-init . nyan-mode)))
(straight-use-package 'minions)
(use-package minions
  :hook ((after-init . minions-mode))
  :init (gsetq minions-mode-line-lighter "✬"))
(straight-use-package 'doom-modeline)
(use-package doom-modeline
  :hook ((after-init . doom-modeline-mode))
  :init (gsetq
         doom-modeline-height                      25
         doom-modeline-bar-width                   3
         doom-modeline-project-detection           'project  ;; changed
         doom-modeline-buffer-file-name-style      'relative-to-project  ;; changed
         doom-modeline-icon                        t  ;; changed
         doom-modeline-major-mode-icon             t
         doom-modeline-major-mode-color-icon       t
         doom-modeline-buffer-state-icon           t
         doom-modeline-buffer-modification-icon    t
         doom-modeline-unicode-fallback            t  ;; changed
         doom-modeline-minor-modes                 t
         doom-modeline-enable-word-count           t
         doom-modeline-continuous-word-count-modes '(markdown-mode gfm-mode org-mode text-mode)
         doom-modeline-buffer-encoding             nil
         doom-modeline-indent-info                 nil
         doom-modeline-checker-simple-format       nil
         doom-modeline-number-limit                99
         doom-modeline-vcs-max-length              12
         doom-modeline-persp-name                  t
         doom-modeline-display-default-persp-name  t
         doom-modeline-lsp                         t
         doom-modeline-github                      t
         doom-modeline-github-interval             (* 30 60)
         doom-modeline-modal-icon                  nil

         doom-modeline-env-version       t
         doom-modeline-env-enable-python t
         doom-modeline-env-enable-ruby   t
         doom-modeline-env-enable-perl   t
         doom-modeline-env-enable-go     t
         doom-modeline-env-enable-elixir t
         doom-modeline-env-enable-rust   t

         doom-modeline-env-python-executable "python"
         doom-modeline-env-ruby-executable   "ruby"
         doom-modeline-env-perl-executable   "perl"
         doom-modeline-env-go-executable     "go"
         doom-modeline-env-elixir-executable "iex"
         doom-modeline-env-rust-executable   "rustc"

         doom-modeline-env-load-string "..."

         doom-modeline-mu4e        t
         doom-modeline-irc         t
         doom-modeline-irc-stylize 'identity)
  (doom-modeline-def-segment nasy/time
    (when (doom-modeline--active)
       (format-time-string " %b %d, %Y - %H:%M ")
       'face (when (doom-modeline--active) `(:foreground "#1b335f" :background "#c0ffc2")))))

  ;; Remove
  ;; modals (evil, god, ryo and xah-fly-keys, etc.), parrot
  ;; buffer-encoding
  ;; Add
  ;; nasy/time
  (doom-modeline-def-modeline 'main
    '(bar workspace-name matches buffer-info buffer-position word-count selection-info " " misc-info process)
    '(grip github debug lsp minor-modes major-mode vcs checker nasy/time "        "))

  (doom-modeline-def-modeline 'minimal
    '(bar matches buffer-info-simple)
    '(media-info major-mode nasy/time "        "))

  (doom-modeline-def-modeline 'special
    '(bar window-number modals matches buffer-info buffer-position word-count parrot selection-info)
    '(misc-info battery irc-buffers debug minor-modes input-method indent-info buffer-encoding major-mode process nasy/time))

  (doom-modeline-def-modeline 'media
    '(bar window-number buffer-size buffer-info)
    '(misc-info media-info major-mode process vcs nasy/time))

  (doom-modeline-def-modeline 'pdf
    '(bar window-number buffer-size buffer-info pdf-pages)
    '(misc-info major-mode process vcs nasy/time))

  (doom-modeline-def-modeline 'project
    '(bar window-number buffer-default-directory)
    '(misc-info major-mode nasy/time "       "))

  ;; Change behaviors
  (defun nasy/doom-modeline-update-buffer-file-name (&rest _)
    "Update buffer file name in mode-line."
    (setq doom-modeline--buffer-file-name
          (if buffer-file-name
            (if (string-prefix-p "*Org Src" (format-mode-line "%b"))
              (propertize "%b"
                          'face (if (doom-modeline--active)
                          'help-echo "Buffer name
    mouse-1: Previous buffer\nmouse-3: Next buffer"
                          'local-map mode-line-buffer-identification-keymap)))))
  (advice-add #'doom-modeline-update-buffer-file-name :override #'nasy/doom-modeline-update-buffer-file-name)

  (set-face-attribute 'mode-line nil :font "OpenDyslexic" :background "#2d334a")
  (set-face-attribute 'mode-line-inactive nil :font "OpenDyslexic" ))


(straight-use-package 'dashboard)
(use-package dashboard
  ;; https://github.com/rakanalh/emacs-dashboard/issues/45
  :diminish (dashboard-mode page-break-lines-mode)
  :hook ((dashboard-mode . (lambda () (gsetq-local tab-width 1))))
   :keymaps 'dashboard-mode-map
   "<down-mouse-1>" nil
   "<mouse-1>"      'widget-button-click
   "<mouse-2>"      'widget-button-click
   "<up>"           'dashboard-previous-line
   "<down>"         'dashboard-next-line)
  (gsetq dashboard-startup-banner    (concat user-emacs-directory "ue.png")
         dashboard-center-content    t
         dashboard-show-shortcuts    t
         dashboard-set-heading-icons t
         dashboard-set-file-icons    t
         dashboard-set-init-info     t
         show-week-agenda-p          t
         dashboard-items '((recents   . 10)
                           (bookmarks . 5)
                           ;;(registers . 5 )
                           ;;(agenda    . 5)
                           (projects  . 5)))
  (straight-use-package 'noflet)
  (advice-add 'dashboard-next-line :after #'(lambda (&rest r) (forward-char 2)))
  (advice-add 'widget-forward :after #'(lambda (&rest r) (forward-char 2))))


(run-hooks 'nasy/config-before-hook)

(setq custom-file (no-littering-expand-etc-file-name "custom.el"))

(add-hook 'after-init-hook #'(lambda () (run-hooks 'nasy/config-after-hook)))

(when (file-exists-p custom-file)
  (load custom-file))

(when *server*
;;; init.el ends here


Hope you enjoy it.

Date: 2019-04-19 Fri 00:00

Author: Nasy

Created: 2020-02-16 Sun 14:18