Global functions and key bindings
Put it here to remove warning about prefix keys.
(global-unset-key (kbd "M-ESC ESC"))
(global-unset-key (kbd "C-z"))
(global-unset-key (kbd "M-c"))
(defun zarkone/reload-dir-locals-for-current-buffer ()
"reload dir locals for the current buffer"
(interactive)
(let ((enable-local-variables :all))
(hack-dir-local-variables-non-file-buffer)))
(defun nxml-where ()
"Display the hierarchy of XML elements the point is on as a path."
(interactive)
(let ((path nil))
(save-excursion
(save-restriction
(widen)
(while (and (< (point-min) (point)) ;; Doesn't error if point is at beginning of buffer
(condition-case nil
(progn
(nxml-backward-up-element) ; always returns nil
t)
(error nil)))
(setq path (cons (xmltok-start-tag-local-name) path)))
(if (called-interactively-p t)
(message "/%s" (mapconcat 'identity path "/"))
(format "/%s" (mapconcat 'identity path "/")))))))
(defun maybe-suspend-frame ()
"In a GUI environment, do nothing; otherwise `suspend-frame'."
(interactive)
(if (display-graphic-p)
(message "suspend-frame disabled for graphical displays.")
(suspend-frame)))
(defun font-names-list ()
"Get list of names of installed fonts,which can be used to set font."
(seq-filter (lambda (font)
(when-let ((info (font-info font)))
(string-match-p "spacing=100" (aref info 1))))
(font-family-list)))
(defun zarkone/prev-window ()
"Other-window, backward"
(interactive)
(other-window -1))
(defun zarkone/insert-current-date ()
"Insert current date here."
(interactive)
(insert
(shell-command-to-string "date")))
(defun vertical-three-windows-layout ()
"Vertical, three window layout"
(interactive)
(delete-other-windows)
(split-window-horizontally)
(split-window-horizontally)
(balance-windows))
(defun run-static-server (&optional on-random-port)
"Run static server in current dir, with default port (8000).
With prefix arg, run at random free port"
(interactive "P")
(let ((shell-command "python -m SimpleHTTPServer"))
(async-shell-command
(concat shell-command
(when on-random-port
" 0")))))
(defun emacs-reload ()
"reloads emacs config"
(interactive)
(org-babel-load-file (expand-file-name "literally.org" user-emacs-directory)))
(defun zarkone/comment-or-uncomment-region-or-line ()
"Comments or uncomments the region or the current line if there's no active region."
(interactive)
(let (beg end)
(if (region-active-p)
(setq beg (region-beginning) end (region-end))
(setq beg (line-beginning-position) end (line-end-position)))
(comment-or-uncomment-region beg end)
(next-line)))
(defun zarkone/switch-to-previous-buffer ()
(interactive)
(switch-to-buffer (other-buffer (current-buffer) 1)))
(defun zarkone/kill-region-or-backward-kill-word (&optional arg region)
"`kill-region' if the region is active, otherwise `backward-kill-word'"
(interactive
(list (prefix-numeric-value current-prefix-arg) (use-region-p)))
(if region
(kill-region (region-beginning) (region-end))
(backward-kill-word arg)))
(defun zarkone/filename-to-clipboard ()
"Put the current file name on the clipboard"
(interactive)
(let ((filename (if (equal major-mode 'dired-mode)
default-directory
(buffer-file-name))))
(when filename
(with-temp-buffer
(insert filename)
(clipboard-kill-region (point-min) (point-max)))
(message filename))))
(defun zarkone/duplicate-line ()
"Duplicate current line."
(interactive)
(move-beginning-of-line 1)
(kill-line)
(yank)
(open-line 1)
(next-line 1)
(yank))
(defun zarkone/delete-whitespace (&optional backward-only)
"Delete all spaces, tabs and newlinesaround point.
If BACKWARD-ONLY is non-nil, only delete them before point."
(interactive "*P")
(let ((orig-pos (point)))
(delete-region
(if backward-only
orig-pos
(progn
(skip-chars-forward " \t\n")
(constrain-to-field nil orig-pos t)))
(progn
(skip-chars-backward " \t\n")
(constrain-to-field nil orig-pos)))))
(defun bf-pretty-print-xml-region (begin end)
"Pretty format XML markup in region. You need to have nxml-mode
http://www.emacswiki.org/cgi-bin/wiki/NxmlMode installed to do
this. The function inserts linebreaks to separate tags that have
nothing but whitespace between them. It then indents the markup
by using nxml's indentation rules."
(interactive "r")
(save-excursion
(nxml-mode)
(goto-char begin)
(while (search-forward-regexp "\>[ \\t]*\<" nil t)
(backward-char) (insert "\n"))
(indent-region begin end)))
(defun zarkone/pretty-print-xml-buffer ()
(interactive)
(bf-pretty-print-xml-region (point-min) (point-max)))
(defun wl-paste-running ()
(and wl-copy-process
(process-live-p wl-copy-process)))
(defun is-wayland-session ()
(string= (getenv "XDG_SESSION_TYPE")
"wayland"))
(defun wl-clipboard-init ()
(when (is-wayland-session)
(setq wl-copy-process nil)
(setq interprogram-cut-function 'wl-copy)
(setq interprogram-paste-function 'wl-paste)))
(defun wl-copy (text)
(setq wl-copy-process (make-process :name "wl-copy"
:buffer nil
:command '("wl-copy" "-f" "-n")
:connection-type 'pipe))
(process-send-string wl-copy-process text)
(process-send-eof wl-copy-process))
(defun wl-paste ()
(when (not (wl-paste-running))
(let ((content-raw (shell-command-to-string "wl-paste -n")))
(replace-regexp-in-string "\s+$" "" content-raw))))
Removed all macroses to functions ATM; decided to leave defkbdmacro
here for
future reference.
(defmacro defkbdmacro (name keyseq-string &optional docstring)
`(fset (quote ,name)
(lambda (&optional arg)
,docstring
(interactive "p")
(kmacro-exec-ring-item (quote (,keyseq-string 0 "%d")) arg))))
(use-package use-package-chords
:demand t
:config (key-chord-mode 1))
(use-package corfu
;; Optional customizations
;; :custom
;; (corfu-cycle t) ;; Enable cycling for `corfu-next/previous'
;; (corfu-auto t) ;; Enable auto completion
;; (corfu-separator ?\s) ;; Orderless field separator
;; (corfu-quit-at-boundary nil) ;; Never quit at completion boundary
;; (corfu-quit-no-match nil) ;; Never quit, even if there is no match
;; (corfu-preview-current nil) ;; Disable current candidate preview
;; (corfu-preselect 'prompt) ;; Preselect the prompt
;; (corfu-on-exact-match nil) ;; Configure handling of exact matches
;; (corfu-scroll-margin 5) ;; Use scroll margin
;; Enable Corfu only for certain modes.
;; :hook ((prog-mode . corfu-mode)
;; (shell-mode . corfu-mode)
;; (eshell-mode . corfu-mode))
;; Recommended: Enable Corfu globally.
;; This is recommended since Dabbrev can be used globally (M-/).
;; See also `corfu-excluded-modes'.
:init
(global-corfu-mode))
;; A few more useful configurations...
;; Enable vertico
(use-package vertico
:init
(vertico-mode)
;; Different scroll margin
;; (setq vertico-scroll-margin 0)
;; Show more candidates
;; (setq vertico-count 20)
;; Grow and shrink the Vertico minibuffer
;; (setq vertico-resize t)
;; Optionally enable cycling for `vertico-next' and `vertico-previous'.
;; (setq vertico-cycle t)
)
;; Persist history over Emacs restarts. Vertico sorts by history position.
(use-package savehist
:init
(savehist-mode))
;; A few more useful configurations...
(use-package orderless
:init
;; Tune the global completion style settings to your liking!
;; This affects the minibuffer and non-lsp completion at point.
(setq completion-styles '(orderless partial-completion basic)
completion-category-defaults nil
completion-category-overrides '((eglot (styles orderless)))))
(use-package marginalia
;; Either bind `marginalia-cycle' globally or only in the minibuffer
:bind (("M-A" . marginalia-cycle)
:map minibuffer-local-map
("M-A" . marginalia-cycle))
;; The :init configuration is always executed (Not lazy!)
:init
;; Must be in the :init section of use-package such that the mode gets
;; enabled right away. Note that this forces loading the package.
(marginalia-mode))
;; Example configuration for Consult
(use-package consult
;; Replace bindings. Lazily loaded due by `use-package'.
:bind (;; C-c bindings (mode-specific-map)
("C-c h" . consult-history)
("C-c m" . consult-mode-command)
("C-c k" . consult-kmacro)
;; C-x bindings (ctl-x-map)
("C-x M-:" . consult-complex-command) ;; orig. repeat-complex-command
("C-z C-p" . consult-buffer) ;; orig. switch-to-buffer
("C-x 4 b" . consult-buffer-other-window) ;; orig. switch-to-buffer-other-window
("C-x 5 b" . consult-buffer-other-frame) ;; orig. switch-to-buffer-other-frame
("C-z C-b" . consult-bookmark) ;; orig. bookmark-jump
("C-z C-t" . consult-project-buffer) ;; orig. project-switch-to-buffer
;; Custom M-# bindings for fast register access
("M-#" . consult-register-load)
("M-'" . consult-register-store) ;; orig. abbrev-prefix-mark (unrelated)
("C-M-#" . consult-register)
;; Other custom bindings
("M-y" . consult-yank-pop) ;; orig. yank-pop
;; M-g bindings (goto-map)
("M-g e" . consult-compile-error)
("M-g f" . consult-flymake) ;; Alternative: consult-flycheck
("M-g g" . consult-goto-line) ;; orig. goto-line
("M-g M-g" . consult-goto-line) ;; orig. goto-line
("M-g o" . consult-outline) ;; Alternative: consult-org-heading
("M-g m" . consult-mark)
("M-g k" . consult-global-mark)
("M-g i" . consult-imenu)
("M-g I" . consult-imenu-multi)
;; M-s bindings (search-map)
("M-c M-d" . consult-find)
("M-c D" . consult-locate)
("M-c g" . consult-grep)
("M-c G" . consult-git-grep)
("M-c M-c" . consult-ripgrep)
("M-c l" . consult-line)
("M-c L" . consult-line-multi)
("M-c k" . consult-keep-lines)
("M-c u" . consult-focus-lines)
;; Isearch integration
("M-s e" . consult-isearch-history)
:map isearch-mode-map
("M-e" . consult-isearch-history) ;; orig. isearch-edit-string
("M-s e" . consult-isearch-history) ;; orig. isearch-edit-string
("M-s l" . consult-line) ;; needed by consult-line to detect isearch
("M-s L" . consult-line-multi) ;; needed by consult-line to detect isearch
;; Minibuffer history
:map minibuffer-local-map
("M-s" . consult-history) ;; orig. next-matching-history-element
("M-r" . consult-history)) ;; orig. previous-matching-history-element
;; Enable automatic preview at point in the *Completions* buffer. This is
;; relevant when you use the default completion UI.
:hook (completion-list-mode . consult-preview-at-point-mode)
;; The :init configuration is always executed (Not lazy)
:init
;; Optionally configure the register formatting. This improves the register
;; preview for `consult-register', `consult-register-load',
;; `consult-register-store' and the Emacs built-ins.
(setq register-preview-delay 0.5
register-preview-function #'consult-register-format)
;; Optionally tweak the register preview window.
;; This adds thin lines, sorting and hides the mode line of the window.
(advice-add #'register-preview :override #'consult-register-window)
;; Use Consult to select xref locations with preview
(setq xref-show-xrefs-function #'consult-xref
xref-show-definitions-function #'consult-xref)
;; Configure other variables and modes in the :config section,
;; after lazily loading the package.
:config
;; Optionally configure preview. The default value
;; is 'any, such that any key triggers the preview.
;; (setq consult-preview-key 'any)
;; (setq consult-preview-key (kbd "M-."))
;; (setq consult-preview-key (list (kbd "<S-down>") (kbd "<S-up>")))
;; For some commands and buffer sources it is useful to configure the
;; :preview-key on a per-command basis using the `consult-customize' macro.
(consult-customize
consult-theme :preview-key '(:debounce 0.2 any)
consult-ripgrep consult-git-grep consult-grep
consult-bookmark consult-recent-file consult-xref
consult--source-bookmark consult--source-file-register
consult--source-recent-file consult--source-project-recent-file
;; :preview-key (kbd "M-.")
:preview-key '(:debounce 0.4 any))
;; Optionally configure the narrowing key.
;; Both < and C-+ work reasonably well.
(setq consult-narrow-key "<") ;; (kbd "C-+")
;; Optionally make narrowing help available in the minibuffer.
;; You may want to use `embark-prefix-help-command' or which-key instead.
;; (define-key consult-narrow-map (vconcat consult-narrow-key "?") #'consult-narrow-help)
;; By default `consult-project-function' uses `project-root' from project.el.
;; Optionally configure a different project root function.
;; There are multiple reasonable alternatives to chose from.
;;;; 1. project.el (the default)
;; (setq consult-project-function #'consult--default-project--function)
;;;; 2. projectile.el (projectile-project-root)
;; (autoload 'projectile-project-root "projectile")
;; (setq consult-project-function (lambda (_) (projectile-project-root)))
;;;; 3. vc.el (vc-root-dir)
;; (setq consult-project-function (lambda (_) (vc-root-dir)))
;;;; 4. locate-dominating-file
;; (setq consult-project-function (lambda (_) (locate-dominating-file "." ".git")))
)
(use-package embark
:ensure t
:bind
(("C-`" . embark-act) ;; pick some comfortable binding
("C-;" . embark-dwim) ;; good alternative: M-.
("C-h B" . embark-bindings)) ;; alternative for `describe-bindings'
:init
;; Optionally replace the key help with a completing-read interface
(setq prefix-help-command #'embark-prefix-help-command)
;; Hide the mode line of the Embark live/completions buffers
(add-to-list 'display-buffer-alist
'("\\`\\*Embark Collect \\(Live\\|Completions\\)\\*"
nil
(window-parameters (mode-line-format . none)))))
;; Consult users will also want the embark-consult package.
(use-package embark-consult
:ensure t ; only need to install it, embark loads it after consult if found
:hook
(embark-collect-mode . consult-preview-at-point-mode))
(when window-system
(menu-bar-mode 0)
(scroll-bar-mode 0)
(tool-bar-mode 0)
(tooltip-mode 0))
(global-hl-line-mode 1)
(blink-cursor-mode 1)
(setq ring-bell-function 'ignore)
(setq-default indicate-buffer-boundaries 'left)
(use-package diminish)
(setq-default frame-title-format '("Emacs: %b"))
(load "~/.emacs.d/term-title.el")
(require 'term-title)
(term-title-mode)
(use-package diff-hl
:hook (after-init . global-diff-hl-mode))
(setq custom-safe-themes t)
(load-theme 'modus-vivendi t)
(set-face-attribute 'default nil :background "#112")
(use-package nix-mode)
(defun yank-remote-and-msg ()
(interactive)
(message (bar-to-clipboard)))
(use-package browse-at-remote
:bind (("C-x M-e" . browse-at-remote)
("C-x M-r" . yank-remote-and-msg)))
(use-package fish-mode
:hook ((before-save . fish_indent-before-save)))
(use-package expand-region
:bind (("C-x x" . er/expand-region)))
(use-package git-timemachine
:bind (("C-x G" . git-timemachine)))
(use-package magit
:bind (("C-z RET" . magit-status)
("C-z m" . magit-status)))
(use-package paredit
:diminish ""
:bind (("C-M-c" . paredit-comment-dwim))
:commands (enable-paredit-mode))
(use-package yasnippet
:diminish yas-minor-mode
:hook (after-init . yas-global-mode))
(use-package highlight-indentation)
(use-package smart-shift)
(use-package yaml-mode
:custom
(yaml-indent-offset 2)
:hook ((yaml-mode . highlight-indentation-mode)
(yaml-mode . smart-shift-mode)))
(use-package restclient)
(use-package markdown-mode
:ensure t
:commands (markdown-mode gfm-mode)
:mode (("README\\.md\\'" . gfm-mode)
("\\.md\\'" . markdown-mode)
("\\.markdown\\'" . markdown-mode))
:init (setq-default markdown-open-command "multimarkdown"))
(use-package direnv
:bind (("C-z M-d" . direnv-allow))
:custom
(direnv-always-show-summary t)
:config
(direnv-mode))
(use-package consult-eglot)
(use-package eglot
:bind (("C-c M-i" . eglot-code-action-organize-imports)
("C-c M-/" . eglot-find-implementation))
:init
(with-eval-after-load 'eglot
(setq completion-category-defaults nil)
(setq-default eglot-workspace-configuration
'((:gopls .
((staticcheck . t)
(matcher . "CaseSensitive")))))))
(defun my-gofmt-before-save ()
"Add this to .emacs to run gofmt on the current buffer when saving:
\(add-hook 'before-save-hook 'gofmt-before-save).
Note that this will cause ‘go-mode’ to get loaded the first time
you save any file, kind of defeating the point of autoloading."
(interactive)
(when (or (eq major-mode 'go-ts-mode)
(eq major-mode 'go-mode)) (gofmt)))
(use-package go-mode
:hook ((go-ts-mode . eglot-ensure)
(go-ts-mode . flycheck-mode)
(go-ts-mode . eldoc-mode)
(before-save . my-gofmt-before-save))
:custom
(tab-width 4)
(go-ts-mode-indent-offset 4)
;;(company-lsp-async t)
;;(go-coverage-display-buffer-func 'display-buffer-same-window)
(gofmt-command "goimports")
(compile-command "go build -v")
;;:config
(use-package go-snippets)
;; (setenv "GO111MODULE" "on")
;; (lsp-register-custom-settings
;; '(("gopls.completeUnimported" t t)
;; ("gopls.staticcheck" t t)))
)
(require 'ansi-color)
(defun rust--compile-color-hook ()
"Used to interpret cargo's colored output"
(ansi-color-apply-on-region compilation-filter-start (point)))
;; This cannot be done in a buffer-local variable since the hook must be set
;; in the compilation buffer.
(defadvice compilation-start (around add-ansi-color-hook activate)
(if (eq major-mode 'rust-mode)
(let ((compilation-start-hook (cons
(lambda (proc) (add-hook 'compilation-filter-hook
'rust--compile-color-hook
nil t))
compilation-start-hook)))
ad-do-it)
ad-do-it))
(use-package cargo)
(use-package flycheck-rust)
(use-package rust-mode
:hook ((flycheck-mode . flycheck-rust-setup)
(rust-mode . eglot-ensure)
(rust-mode . cargo-minor-mode)
(rust-mode . flycheck-mode))
:custom
(indent-tabs-mode nil)
(rust-format-on-save t)
:bind (:map rust-mode-map
("C-c C-m" . rust-run)
("C-c C-d" . eldoc-doc-buffer)
("C-c C-e" . flycheck-next-error)
("C-c C-t" . rust-test)))
(defun cider-save-and-compile-and-load-file ()
"Save file, then compile and load it"
(interactive)
(save-buffer)
(call-interactively 'cider-load-buffer))
;; (use-package rainbow-mode)
(defun zarkone/cider-refresh-all ()
(interactive)
(let* ((form "(user/restart-all)")
(override cider-interactive-eval-override)
(ns-form (if (cider-ns-form-p form) "" (format "(ns %s)" (cider-current-ns)))))
(with-current-buffer (get-buffer-create cider-read-eval-buffer)
(erase-buffer)
(clojure-mode)
(unless (string= "" ns-form)
(insert ns-form "\n\n"))
(insert form)
(let ((cider-interactive-eval-override override))
(cider-interactive-eval form
nil
nil
(cider--nrepl-pr-request-map))))))
(use-package cider
:commands (cider-mode)
:hook ((cider-mode . eldoc-mode))
:config
(setq cider-known-endpoints '(("pitch-app/desktop-app" "localhost" "7888")))
:bind (:map cider-mode-map
("C-c C-n" . zarkone/cider-refresh-all)
("C-c C-k" . cider-save-and-compile-and-load-file)
("C-c C-i" . cider-interrupt)
:map cider-repl-mode-map
("C-c C-l" . cider-repl-clear-buffer)))
(use-package flycheck-clj-kondo)
(use-package clj-refactor
:diminish ""
:commands (clj-refactor-mode)
:config
(cljr-add-keybindings-with-prefix "C-c C-j"))
(use-package clojure-mode
:hook (
;; requires clojure-lsp
;; (clojure-mode . lsp)
(clojure-mode . cider-mode)
;; (clojure-mode . rainbow-delimiters-mode)
(clojure-mode . enable-paredit-mode)
(clojure-mode . flycheck-mode)
(clojure-mode . clj-refactor-mode))
:config
(require 'flycheck-clj-kondo))
(use-package tide)
(use-package typescript-mode
:custom
(typescript-ts-mode)
(typescript-indent-level 4)
(typescript-ts-mode-indent-offset 4)
(js-indent-level 4)
(flycheck-check-syntax-automatically '(save mode-enabled))
:hook ((typescript-mode . typescript-ts-mode)
(typescript-ts-mode . tide-setup)
(typescript-ts-mode . tide-hl-identifier-mode)
(typescript-ts-mode . indent-tabs-mode)
(typescript-ts-mode . flycheck-mode)
;; (before-save . tide-format-before-save)
))
(use-package haskell-mode)
(use-package geiser-guile)
(use-package geiser
:hook (scheme-mode . enable-paredit-mode))
(use-package protobuf-mode
:hook (protobuf-mode . protobuf-ts-mode))
(use-package protobuf-ts-mode
:custom (protobuf-ts-mode-indent-offset 4))
This has to be in the end of file for emacs 29, it turns out. Otherwise getting a lot of nonsense like autoloads not created, file not found etc while installing packages.
I was thinking that I’ve fixed file not file problem with replacing :init to :config in certain cases (corfu, vertico, etc).
But now I’ve put it back and it went fine with deleted elpa, eln-cache. Which probably means that “use-package emacs which needs to be put in the end of file” solution wins.
(defun delete-whitespace-if-not-ts-ts ()
(interactive)
(when (not (eq major-mode 'typescript-ts-mode))
(delete-trailing-whitespace)))
(use-package emacs
:hook ((before-save . delete-whitespace-if-not-ts-ts)
(emacs-lisp-mode . enable-paredit-mode)
(org-mode . auto-fill-mode)
(org-mode . flyspell-mode)
(org-mode . org-indent-mode))
:custom
(auto-save-default nil)
(create-lockfiles nil)
(auth-sources '((:source "~/.emacs.d/secrets/.authinfo.gpg")))
(safe-local-variable-values '((url-max-redirections . 0)))
(dired-listing-switches "-alGh")
(indent-tabs-mode nil)
(truncate-lines t)
(word-wrap nil)
(select-enable-clipboard t)
(select-enable-primary nil)
(uniquify-buffer-name-style 'forward)
(save-interprogram-paste-before-kill t)
(compilation-always-kill t)
(apropos-do-all t)
(mouse-yank-at-point t)
(save-place-file (concat user-emacs-directory ".places"))
(backup-directory-alist `(("." . ,(concat user-emacs-directory ".backups"))))
(warning-suppress-types '((comp)))
(default-input-method 'russian-computer)
(browse-url-browser-function 'browse-url-firefox)
(safe-local-variable-values '((eval define-clojure-indent
(reg-cofx :defn)
(reg-event-db :defn)
(reg-event-fx :defn)
(reg-fx :defn)
(reg-sub :defn)
(reg-event-domain :defn)
(reg-block-event-fx :defn)
(reg-event-domain-fx :defn)
(this-as 0))
(url-max-redirections . 0)) nil nil "Customized with use-package emacs")
:config
;; TAB cycle if there are only few candidates
(setq completion-cycle-threshold 3)
;; Pinentry mode for gpg
(setq epa-pinentry-mode 'loopback)
;; Emacs 28: Hide commands in M-x which do not apply to the current mode.
;; Corfu commands are hidden, since they are not supposed to be used via M-x.
(setq read-extended-command-predicate
#'command-completion-default-include-p)
;; Enable indentation+completion using the TAB key.
;; `completion-at-point' is often bound to M-TAB.
(setq tab-always-indent 'complete)
(show-paren-mode 1)
(menu-bar-mode 0)
;; Add prompt indicator to `completing-read-multiple'.
;; We display [CRM<separator>], e.g., [CRM,] if the separator is a comma.
(defun crm-indicator (args)
(cons (format "[CRM%s] %s"
(replace-regexp-in-string
"\\`\\[.*?]\\*\\|\\[.*?]\\*\\'" ""
crm-separator)
(car args))
(cdr args)))
(advice-add #'completing-read-multiple :filter-args #'crm-indicator)
;; Do not allow the cursor in the minibuffer prompt
(setq minibuffer-prompt-properties
'(read-only t cursor-intangible t face minibuffer-prompt))
(add-hook 'minibuffer-setup-hook #'cursor-intangible-mode)
;; Emacs 28: Hide commands in M-x which do not work in the current mode.
;; Vertico commands are hidden in normal buffers.
;; (setq read-extended-command-predicate
;; #'command-completion-default-include-p)
;; Enable recursive minibuffers
(setq enable-recursive-minibuffers t)
;; workaround for gnupg 2.4.1 encryption
;; https://www.masteringemacs.org/article/keeping-secrets-in-emacs-gnupg-auth-sources
(fset 'epg-wait-for-status 'ignore)
;; use wl-clipboard for copy-paste
(wl-clipboard-init)
:config
(put 'narrow-to-region 'disabled nil)
(put 'narrow-to-page 'disabled nil)
(put 'downcase-region 'disabled nil)
:chords (("[]" . "[]\C-b")
("<>" . "<>\C-b")
("''" . "''\C-b")
("\"\"" . "\"\"\C-b")
("()" . "()\C-b")
("{}" . "{}\C-b"))
:bind (("C-x M-5" . delete-other-windows-vertically)
("C-z 3" . vertical-three-windows-layout)
("C-z C-d" . delete-other-windows)
("C-z C-x" . split-window-below)
("C-z C-r" . split-window-right)
("C-z C-z" . maybe-suspend-frame)
("C-z C-n" . zarkone/switch-to-previous-buffer)
("C-_" . undo) ;; for term comp-ty
("C-w" . zarkone/kill-region-or-backward-kill-word)
("C-x C-d" . dired-jump)
("C-c M-o" . occur)
("<C-return>" . save-buffer)
("M-o" . other-window)
("C-x RET RET" . project-compile)
("M-RET" . recompile)
("M-;" . replace-regexp)
("C-x H" . help)
("C-c M-." . zarkone/insert-current-date)
("C-x C-g" . goto-address-at-point)
("M-/" . hippie-expand)
("M--" . zarkone/delete-whitespace)
("C-x C-k DEL" . zarkone/kill-till-end)
("C-M-y" . zarkone/duplicate-line)
("C-x M-w" . zarkone/filename-to-clipboard)
("C-s" . isearch-forward-regexp)
("C-r" . isearch-backward-regexp)
("C-x M-v" . visual-line-mode)
("C-<backspace>" . undo)
:map prog-mode-map
("C-M-c" . zarkone/comment-or-uncomment-region-or-line)
))