Merge branch 'develop'

* develop: (64 commits)
  Prepare for v2.0.5
  Temporarily disable doom-themes-visual-bell-config
  Fix neotree always changing root
  Update changelog
  Fix wrong-type-argument error from +org/insert-item
  Make +ivy-buffer-transformer autoloadable
  General refactor & cleanup
  Correct troubleshooting link in README
  org: set org-ellipsis to downward chevron
  Add elfeed-(show|search)-mode to evil-snipe-disabled-modes
  Autoload json library
  Rethink smartparens config #181
  README: expand troubleshooting
  Fix wiki links in README (again)
  Correct intro in README
  Fix wiki links in README
  Prevent private commands from affecting projectile cache
  Remove recentf-filename-handlers fix for projectile-recentf-files
  lang/sh: remove unused setup.sh
  Convert +ivy/switch-buffer to transformers + add mode icons #169
  ...
This commit is contained in:
Henrik Lissner 2017-09-03 23:32:23 +02:00
commit d2d71795e5
75 changed files with 1165 additions and 954 deletions

View file

@ -2,6 +2,7 @@
- [[#todo][Todo]] - [[#todo][Todo]]
- [[#unreleased-master][Unreleased (master)]] - [[#unreleased-master][Unreleased (master)]]
- [[#205-sep-03-2017][2.0.5 (Sep 03, 2017)]]
- [[#204-jul-14-2017][2.0.4 (Jul 14, 2017)]] - [[#204-jul-14-2017][2.0.4 (Jul 14, 2017)]]
- [[#203-jun-11-2017][2.0.3 (Jun 11, 2017)]] - [[#203-jun-11-2017][2.0.3 (Jun 11, 2017)]]
- [[#202-may-13-2017][2.0.2 (May 13, 2017)]] - [[#202-may-13-2017][2.0.2 (May 13, 2017)]]
@ -47,9 +48,7 @@
+ =lang/alda= -- Language support for [[https://github.com/alda-lang/alda][Alda]], the music programming language, using [[https://github.com/jgkamat/alda-mode][alda-mode]]. + =lang/alda= -- Language support for [[https://github.com/alda-lang/alda][Alda]], the music programming language, using [[https://github.com/jgkamat/alda-mode][alda-mode]].
+ =org/org-publish= -- publishing org files to HTML (thanks to [[https://github.com/matthewgraybosch][matthewgraybosch]]) + =org/org-publish= -- publishing org files to HTML (thanks to [[https://github.com/matthewgraybosch][matthewgraybosch]])
+ =org/org-attach= -- my own, simpler attachment system with drag-drop image attachment support and centralized storage. + =org/org-attach= -- my own, simpler attachment system with drag-drop image attachment support and centralized storage.
+ *Bug fixes:* + =core-ui= Replace or fix ~winner-mode~ unreliability (will close windows trying to revive killed buffers). Perhaps make ~doom/kill-this-buffer~ only disassociate buffer from persp-mode or bury buffer if persp-mode is inactive.
+ =core-ui= Replace or fix ~winner-mode~ unreliability (will close windows trying to revive killed buffers). Perhaps make ~doom/kill-this-buffer~ only disassociate buffer from persp-mode or bury buffer if persp-mode is inactive.
+ =ui/doom-modeline= Fix ~0/0~ leftover panel in modeline (caused by lingering anzu state).
+ =org= + =org=
+ Better shackle + org-agenda integration + Better shackle + org-agenda integration
+ Fix janky visual line motions (~evil-next-visual-line~, etc) + Fix janky visual line motions (~evil-next-visual-line~, etc)
@ -61,14 +60,59 @@
+ =tools/upload= Add ~+upload/open-remote-file~ command to open current file on the remote (with TRAMP). + =tools/upload= Add ~+upload/open-remote-file~ command to open current file on the remote (with TRAMP).
+ Add =bin/org-alert= script -- a cron script that scans TODOs in org files and dispatches system alerts. + Add =bin/org-alert= script -- a cron script that scans TODOs in org files and dispatches system alerts.
+ =feature/workspaces= Add a bookmarks feature, but for wconfs, that can revive file buffers. Also needs an interface. + =feature/workspaces= Add a bookmarks feature, but for wconfs, that can revive file buffers. Also needs an interface.
+ Add README.org's with working babel blocks to modules. + =ui/doom-modeline=
+ Document best practices for customizing DOOM emacs. + Fix hardcoded spacing in between segments.
+ =ui/doom-modeline= fix hardcoded spacing in between segments. + Fix ~0/0~ leftover panel in modeline (caused by lingering anzu state).
+ Rewrite main README.md to include more information about setting up, customizing, and troubleshooting DOOM Emacs.
+ Update =bin/org-capture= to read from stdin in the absence of arguments. + Update =bin/org-capture= to read from stdin in the absence of arguments.
+ =core-popups= Add support for moving popup windows to the ~+evil/window-move-*~ commands #171
* Unreleased (master) * Unreleased (master)
* 2.0.5 (Sep 03, 2017)
+ =doom=
+ Added new module: ~tools/rgb~, with tools for dealing with colors (thanks to [[https://github.com/bandresen][bandresen]])
+ Added new module: ~tools/prodigy~, with tools for managing external services (thanks to [[https://github.com/bandresen][bandresen]])
+ Added new module: ~feature/hydra~, offers an extra and customizable layer of modal keybinds (thanks to [[https://github.com/bandresen][bandresen]])
+ Added two new core-lib helpers for macros: ~doom-enlist~ and ~doom-unquote~.
+ Switch to ~doom-fallback-buffer~ after using ~doom/kill-all-buffers~ (or ~:killall!~).
+ ~make doctor~ now does font detection and will complain when fonts are missing.
+ When switching to a new project, a new workspace is spawned and a fuzzy find-file prompt is opened. However, a buffer from the previous workspace would linger on screen *and* the scratch buffer would CD to HOME, rather than the project root. This is fixed now.
+ Added module flags to the ~doom!~ macro in init.el, and modified the ~featurep!~ macro so that it can be used to detect these flags from within modules. It is up to modules how to interpret them. More information in [[https://github.com/hlissner/.emacs.d/commit/0b7b8800a2478588bde408c92fcdfa0e43a5baf0][0b7b880]].
+ Fix projectile-find-file not respecting ~default-directory~ (caused by changes upstream).
+ Rewrote, revised and expanded module documentation, and created a [[https://github.com/hlissner/.emacs.d/wiki][wiki]] with more information.
+ Removed the =:L= flag from =map!= and replaced it with a =:local= property.
+ Added new function: ~doom|disable-vi-tilde-fringe~ for turning off vi-tilde-fringe in select buffers.
+ Added support for relative line numbers (see ~doom-line-numbers-style~), using nlinum-relative on Emacs <26, and display-line-numbers on Emacs 26+.
+ =feature=
+ =File Templates= Added a file template for:
+ *.org files
+ Module README.org files.
+ =jump=
+ Added documentation for ~:jump~ setting, describing the three properties it supports (~:definition~, ~:references~ and ~:documentation~).
+ Rewrote ~+jump/online~ to:
+ Use the current selection, if active, or prompt for a query otherwise (with the thing at point as the initial input).
+ Prompts for the provider (search engine) on first use, and reuses the last provider on consecutive uses. If the universal argument is supplied, force ~+jump/online~ to prompt for the provider anyway.
+ =completion=
+ Added all-the-icons support to ~ivy-switch-buffer~ and ~+ivy/switch-workspace-buffer~. Enable this with ~(setq +ivy-buffer-icons t)~.
+ =ui=
+ rainbow-mode is no longer activated on ~prog-mode-hook~.
+ =doom-modeline=
+ Modeline now uses shrink-path.el to shrink the buffer name in the case of a small frame (thanks to [[https://github.com/bandresen][bandresen]]). [[https://github.com/hlissner/.emacs.d/pull/176][See #176]]
+ Fixed mode-line going blank in terminal Emacs (thanks to [[https://github.com/bandresen][bandresen]]).
+ =doom-dashboard= Fixed "Load last session" button on dashboard.
+ =tools=
+ =eshell= General improvements made to further integrate eshell with Doom (thanks to [[https://github.com/bandresen][bandresen]]). [[https://github.com/hlissner/.emacs.d/pull/160][See #160]]
+ =pass= ~+pass-get-field~ now no-ops if used in a non-interactive session (e.g. during testing or byte compilation).
+ =neotree= Add =r= and =d= bindings for renaming and deleting files, respectively.
+ =lang=
+ =cc= The advise function ~c-lineup-arglist~ was missing, and has now been reimplemented.
+ =haskell= With module flags implemented, Intero support is now available to lang/haskell and is now the default. Dante support is still available with the ~+dante~ flag.
+ =java= Now auto-installs meghanda-server on first use, and fixed code-completion in java buffers.
+ =org=
+ Fixed vanilla C-j/C-k bindings overshadowing custom window navigation bindings.
+ Added C-[hjkl] keybindings in insert mode for org table navigation.
+ Fixed ~+org/insert-item~ throwing =save-excursion: Wrong type argument: listp, 1= error when used from BOL on the first sub-item in a list.
* 2.0.4 (Jul 14, 2017) * 2.0.4 (Jul 14, 2017)
+ *Module changes:* + *Module changes:*
+ Added =tools/password-store= -- Emacs as a password manager, using [[https://www.passwordstore.org/][pass]] as a backend (contributed by [[https://github.com/bandresen][brandresen]]). + Added =tools/password-store= -- Emacs as a password manager, using [[https://www.passwordstore.org/][pass]] as a backend (contributed by [[https://github.com/bandresen][brandresen]]).

View file

@ -32,6 +32,9 @@ compile: init.el clean
compile\:core: init.el clean compile\:core: init.el clean
@$(EMACS) -f doom/compile -- init.el core @$(EMACS) -f doom/compile -- init.el core
compile\:elpa: init.el
@$(EMACS) -f doom/recompile-packages
$(patsubst %, compile\:%, $(MODULES)): init.el .local/autoloads.el $(patsubst %, compile\:%, $(MODULES)): init.el .local/autoloads.el
@rm -fv $(shell find $(patsubst compile:%, modules/%, $@) -type f -name '*.elc') @rm -fv $(shell find $(patsubst compile:%, modules/%, $@) -type f -name '*.elc')
@$(EMACS) -f doom/compile -- $(patsubst compile:%, modules/%, $@) @$(EMACS) -f doom/compile -- $(patsubst compile:%, modules/%, $@)

252
README.md
View file

@ -3,178 +3,138 @@
[![Develop Build Status](https://img.shields.io/travis/hlissner/.emacs.d/develop.svg?label=develop&style=flat-square)](https://travis-ci.org/hlissner/.emacs.d) [![Develop Build Status](https://img.shields.io/travis/hlissner/.emacs.d/develop.svg?label=develop&style=flat-square)](https://travis-ci.org/hlissner/.emacs.d)
[![MIT](https://img.shields.io/badge/license-MIT-green.svg?style=flat-square)](./LICENSE) [![MIT](https://img.shields.io/badge/license-MIT-green.svg?style=flat-square)](./LICENSE)
[![Main screenshot](/../screenshots/main.png?raw=true)][sc] [![Main screenshot](/../screenshots/main.png)](/../screenshots)
- - -
<p align="center">
<a href="/../../wiki">Documentation</a> |
<a href="/../screenshots">Screenshots</a> |
<a href="/../../wiki/FAQ#troubleshooting">Troubleshooting</a> |
<a href="/../../wiki/FAQ">FAQ</a> |
<a href="/CHANGELOG.org">Changelog</a>
</p>
- - -
<a href="http://ultravioletbat.deviantart.com/art/Yay-Evil-111710573"> <a href="http://ultravioletbat.deviantart.com/art/Yay-Evil-111710573">
<img src="https://raw.githubusercontent.com/hlissner/.emacs.d/screenshots/cacochan.png" align="right" /> <img src="/../screenshots/cacochan.png" align="right" />
</a> </a>
This is an Emacs configuration for a stubborn, shell-dwelling and melodramatic It is a story as old as time. A stubborn, shell-dwelling, and melodramatic
vimmer disappointed with the text-editor status quo. vimmer -- envious of the features of modern text editors -- spirals into despair
before he finally succumbs to the [dark side][evil-mode]. This is his config.
Doom tries to: look and act like modern editors (whatever that means to me on DOOM's philosophy is simple: be **fast**, be **readable**, and be **pretty**. It
any given day), espouse vim's modal philosophy as best it can and strive to is tailored for neckbeards with a blue-belt or better in command-line-fu who
surpass vim in any way possible. It fits my needs as a software developer, indie don't shy away from dabbling with Elisp.
game developer, scientist and doom enthusiast.
It was written for **Emacs 25.1+** on **MacOS 10.11+** and **Arch Linux 4.7+**. Rip and tear. Until it compiles.
I use [vim] everywhere else.
## Installation > **Important:** Doom only supports Emacs >= 25.1, and is tailored for Arch
> Linux 4.7+ and Mac OS 10.11+.
- - -
## Quick start
```bash ```bash
git clone https://github.com/hlissner/.emacs.d ~/.emacs.d git clone https://github.com/hlissner/.emacs.d ~/.emacs.d
cd ~/.emacs.d cd ~/.emacs.d
cp init.example.el init.el # maybe edit init.el cp init.example.el init.el # maybe edit init.el
make install make install
# Have problems? Run this to check for common issues with your setup
make doctor
``` ```
Once you've tweaked the config to your liking, you may optionally byte-compile Visit the wiki for [a more detailed guide on installing, customizing and
it. DOOM is designed to benefit from this. It will boost startup times and make grokking Doom][wiki].
Emacs feel a bit snappier in general.
```bash ## Feature highlights
make compile # may take a while
# or
make core # faster alternative; only compiles init.el & core files
# If you byte-compile, changes to the config won't take effect until you + A fast, organized and opinionated Emacs configuration with a command line
# recompile or delete the byte-compiled files with: interface.
make clean + A custom, declarative [package management system][doom-packages] that combines
``` package.el, [use-package] and [quelpa]. This lets you install packages from
sources other than ELPA, as well as manage packages from the command line.
## Package Management + A [popup management system][doom-popups] (powered by [shackle]) that minimizes
the presence and footprint of temporary and/or disposable buffers.
Plugins can be managed from the command line with `make`: + A vim-like experience with [evil-mode], including ports for several vim
plugins, <kbd>C-x</kbd> omnicompletion and a slew of [custom ex commands][doom-my-commands].
```bash + Integration with [editorconfig]. Let someone else argue about tabs and spaces
make install # install missing plugins (spaces, duh).
make update # update installed plugins + Code completion for a variety of languages, powered by [company-mode] (there
make autoremove # remove unused plugins may be other dependencies for certain languages).
# be sure to run install and autoremove after modifying init.el + Project-awareness powered by [projectile], with tools to navigate and manage
projects and project files.
# run this if you change autoload files + Fast project search (and replace) utilities, powered by [the_silver_searcher],
make autoloads [ripgrep] and [wgrep], with [ivy] (the default), [helm] and ido integration.
+ Isolated and persistent workspaces powered by [persp-mode]. This can
# this is the equivalent of running all four of the above commands substitute for vim tabs.
make + Inline/live code evaluation (using [quickrun]), including REPLs for a variety
of languages.
# you can run any make command with DEBUG=1 for extra logging, and YES=1 to
# auto-accept confirmation prompts:
DEBUG=1 make install
YES=1 make update
```
These commands are also available from within Emacs:
+ `doom/packages-install`
+ `doom/packages-update`
+ `doom/packages-autoremove`
+ `doom/reload-autoloads`
## Deciphering my emacs.d
So you want to grok this madness. Here are a few suggestions:
* **[init.example.el](init.example.el)**: a birds eye view of available modules
* **[modules/README.org](modules/README.org)**: a primer into module structure
* **[modules/private/hlissner/+bindings.el](modules/private/hlissner/+bindings.el)**:
my custom keybinds.
* **[modules/private/hlissner/+commands.el](modules/private/hlissner/+commands.el)**:
my custom ex-commands (for [evil-mode]).
* **[modules/ui](modules/ui)**: the modules that makes my Emacs look the way it
does, including [my theme][doom-theme], modeline, dashboard and more.
* Find screenshots in the [screenshots branch][sc].
### Highlights
* A [popup management system](core/core-popups.el) using **[shackle]** to
minimize mental context switching while dealing with temporary or disposable
buffers.
* Per-project code-style settings with **[editorconfig]**. Let someone else
argue about tabs versus spaces (spaces, of course).
* Workspaces & session persistence with **[persp-mode]**. Provides tab emulation
that vaguely resembles vim's tabs.
* Project & workspace-restricted buffer navigation and functions.
* A vim-centric environment with **[evil-mode]**
* 2-character motions (ala vim-seek/vim-sneak) with **[evil-snipe]**
* Sublime Text-esque [multiple cursors][sc-multiedit] with
**[evil-mc]** and **[evil-multiedit]**
* <kbd>C-x</kbd> omnicompletion in insert mode
* A better `:global` with buffer highlighting
* A slew of [custom ex commands](modules/private/hlissner/+commands.el)
* Fast search utilities:
* Project and buffer navigation with **[ivy]**
* File browser sidebar with **[neotree]**
* Project text search powered by [the silver searcher][ag] and [ripgrep][rg]
(see `:ag` and `:rg`)
* Project search & replace with **[wgrep]**
* Interactive buffer search with **[swiper]**
* Inline/live code evaluation (using **[quickrun]**) and REPLs for a variety of
languages, including Ruby, Python, PHP, JS, Elisp, Haskell, Lua and more.
* [Minimalistic diffs in the fringe][sc-diffs] with **[git-gutter-fringe]**.
* A do-what-I-mean jump-to-definition implementation that tries its darnest to
find the definition of what you're looking at. It tries major-mode commands,
xref (experimental Emacs library), **[dumb-jump]**, ctags (WIP), then
**[ripgrep][rg]** or **[the_silver_searcher][ag]**.
* Snippets and file-templates with **[yasnippet]** & **[auto-yasnippet]**.
* A smarter, perdier, Atom-inspired mode-line that adds:
* evil-search/iedit/evil-substitute mode-line integration
* Macro-recording indicator
* Python/ruby version in mode-line (for rbenv/pyenv)
* Emacs as an:
* Email client (using mu4e & offlineimap)
* Presentation app (using org-tree-slides, ox-reveal, +present/big-mode
& impatient-mode)
* RSS feed reader (using elfeed)
* Word Processor (using LaTeX, Org and Markdown)
## Troubleshooting ## Troubleshooting
My config wasn't intended for public use, but I'm happy to help you use or crib Found a problem? Here are some things to try:
from it.
+ If you have questions, drop me a line at henrik@lissner.net. + Make sure all plugins are installed with `make install`.
+ If you have issues running or setting up DOOM, use `make doctor` to diagnose + A `void-function` or `void-variable` might signal an out-of-date autoloads
any common problems. file. Update it with `make autoloads`.
+ If you still can't make sense of it, run `DEBUG=1 make doctor` and include + Diagnose common OS/environment issues that could interfere with Emacs with
it [with your bug report][new-issue]. `make doctor`.
+ If you byte-compiled Doom, run `make clean` or `M-x doom/clean-compiled-files`
and restart Emacs. Never debug byte-compiled code, it will interfere with your
efforts in subtle (and not-so-subtle) ways.
+ Check [the FAQ][wiki-troubleshooting] to see if your issue is mentioned.
+ If your issue is associated with a particular module, like code-completion,
check the module's README.org, if any.
**And please include steps to reproduce your issue, if possible.** If all else fails, [file a bug report][doom-new-issue].
## Contributing ## Contribute
I welcome contributions of any kind: documentation, bug fixes/reports, extra Doom (and my Emacs work in general) is a labor of love and incurable madness,
modules, even elisp tips. Really, done on my free time. It wasn't intended for public use, but I enjoy making Doom
[don't hesitate to tell me my Elisp-fu sucks][new-issue]! I'm eager to learn. a resource for others.
If you'd like to support my efforts, I welcome contributions of any kind:
+ I love pull requests and bug reports (read the [contribution
guidelines][wiki-contribute] first though!), and elisp pointers are especially
welcome. Seriously, don't hesitate to [tell me my Elisp-fu
sucks][doom-new-issue]!
+ I'm happy to discuss Emacs workflow, ideas or tooling. If you think I, Doom or
other Emacs users could benefit from them (or you just want to chat), drop me
a line at henrik@lissner.net. I'm eager to learn.
[ag]: https://github.com/ggreer/the_silver_searcher [wiki]: /../../wiki
[auto-yasnippet]: https://melpa.org/#/auto-yasnippet [wiki-contribute]: /../../wiki/Contribute
[company-mode]: https://melpa.org/#/company [wiki-conventions]: /../../wiki/Conventions
[wiki-modules]: /../../wiki/Modules
[wiki-customization]: /../../wiki/Customization
[wiki-troubleshooting]: /../../wiki/FAQ#troubleshooting
[doom-my-bindings]: modules/private/hlissner/+bindings.el
[doom-my-commands]: modules/private/hlissner/+commands.el
[doom-new-issue]: https://github.com/hlissner/.emacs.d/issues/new
[doom-packages]: core/autoload/packages.el
[doom-popups]: core/core-popups.el
[doom-theme]: https://github.com/hlissner/emacs-doom-theme [doom-theme]: https://github.com/hlissner/emacs-doom-theme
[dumb-jump]: https://melpa.org/#/dumb-jump
[company-mode]: https://github.com/company-mode/company-mode
[editorconfig]: http://editorconfig.org/ [editorconfig]: http://editorconfig.org/
[evil-mc]: https://github.com/gabesoft/evil-mc [evil-mode]: https://github.com/emacs-evil/evil
[evil-mode]: https://melpa.org/#/evil [git-gutter-fringe]: https://github.com/syohex/emacs-git-gutter-fringe
[evil-multiedit]: https://melpa.org/#/evil-multiedit [helm]: https://github.com/emacs-helm/helm
[evil-snipe]: https://melpa.org/#/evil-snipe [ivy]: https://github.com/abo-abo/swiper
[git-gutter-fringe]: https://melpa.org/#/git-gutter-fringe [persp-mode]: https://github.com/Bad-ptr/persp-mode.el
[ivy]: https://melpa.org/#/ivy [projectile]: https://github.com/bbatsov/projectile
[neotree]: https://melpa.org/#/neotree [quelpa]: https://github.com/quelpa/quelpa
[new-issue]: https://github.com/hlissner/.emacs.d/issues/new [quickrun]: https://github.com/syohex/emacs-quickrun
[persp-mode]: https://melpa.org/#/persp-mode [ripgrep]: https://github.com/BurntSushi/ripgrep
[quickrun]: https://melpa.org/#/quickrun [shackle]: https://github.com/wasamasa/shackle
[rg]: https://github.com/BurntSushi/ripgrep [the_silver_searcher]: https://github.com/ggreer/the_silver_searcher
[sc-diffs]: https://github.com/hlissner/.emacs.d/blob/screenshots/git-gutter.png?raw=true [use-package]: https://github.com/jwiegley/use-package
[sc-multiedit]: https://raw.githubusercontent.com/hlissner/evil-multiedit/screenshots/main.gif?raw=true
[sc]: https://github.com/hlissner/.emacs.d/tree/screenshots
[shackle]: https://melpa.org/#/shackle
[swiper]: https://melpa.org/#/swiper
[vim]: https://github.com/hlissner/.vim [vim]: https://github.com/hlissner/.vim
[wgrep]: https://melpa.org/#/wgrep [wgrep]: https://github.com/mhayashi1120/Emacs-wgrep
[yasnippet]: https://melpa.org/#/yasnippet
[yay-evil]: http://ultravioletbat.deviantart.com/art/Yay-Evil-111710573

View file

@ -75,6 +75,7 @@
(defmacro error! (&rest args) `(message (color 1 (color 31 ,@args)))) (defmacro error! (&rest args) `(message (color 1 (color 31 ,@args))))
(defmacro warn! (&rest args) `(message (color 1 (color 33 ,@args)))) (defmacro warn! (&rest args) `(message (color 1 (color 33 ,@args))))
(defmacro success! (&rest args) `(message (color 1 (color 32 ,@args)))) (defmacro success! (&rest args) `(message (color 1 (color 32 ,@args))))
(defmacro log! (&rest args) `(if doom-debug-mode (message (color 34 ,@args))))
(defmacro explain! (&rest args) `(message (indented 2 (autofill ,@args)))) (defmacro explain! (&rest args) `(message (indented 2 (autofill ,@args))))
;;; Polyfills ;;; Polyfills
@ -100,8 +101,9 @@
(let (doom-core-packages doom-debug-mode) (let (doom-core-packages doom-debug-mode)
(condition-case ex (condition-case ex
(progn (progn
(let ((inhibit-message t)) (let ((inhibit-message t)
(load "~/.emacs.d/core/core.el" nil t)) noninteractive)
(load "~/.emacs.d/init.el" nil t))
(doom-initialize-packages) (doom-initialize-packages)
(doom|finalize) (doom|finalize)
(success! "Attempt to load DOOM: success! Loaded v%s" doom-version) (success! "Attempt to load DOOM: success! Loaded v%s" doom-version)
@ -118,6 +120,7 @@
;; --- is emacs set up properly? ------------------------------ ;; --- is emacs set up properly? ------------------------------
(log! "test-emacs")
(check! (version< emacs-version "25.1") (check! (version< emacs-version "25.1")
(error! "Important: Emacs %s detected [%s]" emacs-version (executable-find "emacs")) (error! "Important: Emacs %s detected [%s]" emacs-version (executable-find "emacs"))
(explain! (explain!
@ -129,16 +132,48 @@
;; --- is the environment set up properly? -------------------- ;; --- is the environment set up properly? --------------------
(when (boundp 'doom-font) ;; windows? windows
(cond ((fboundp 'find-font) (log! "test-windows")
(unless (find-font doom-font) (check! (memq system-type '(windows-nt ms-dos cygwin))
(warn! "Warning: couldn't find %s font" (font-get doom-font :family)) (warn! "Warning: Windows detected")
(explain! "If you use a different font, you may ignore this warning."))) (explain! "DOOM was designed for MacOS and Linux. Expect a bumpy ride!"))
(t
(warn! "Couldn't detect font!") ;; are all default fonts present
(explain! "This could indicate the incorrect version of Emacs is being used!")))) (log! "test-fonts")
(if (not (fboundp 'find-font))
(progn
(warn! "Warning: unable to detect font")
(explain! "The `find-font' function is missing. This could indicate the incorrect "
"version of Emacs is being used!"))
(defun -find-font (family)
(when (fontp family)
(setq family (symbol-name (font-get doom-font :family))))
(let ((inhibit-message t))
(shell-command (format "fc-list | grep %s" (shell-quote-argument family)))))
(when (boundp 'doom-font)
(if (-find-font doom-font)
(success! "Found font %s" (font-get doom-font :family))
(warn! "Warning: couldn't find %s font (default) (%s)"
(font-get doom-font :family))))
;; all-the-icons fonts
(let ((font-dest (pcase system-type
('gnu/linux (concat (or (getenv "XDG_DATA_HOME")
(concat (getenv "HOME") "/.local/share"))
"/fonts/"))
('darwin (concat (getenv "HOME") "/Library/Fonts/")))))
(when (and font-dest (require 'all-the-icons nil t))
(dolist (font all-the-icons-font-names)
(if (file-exists-p (expand-file-name font font-dest))
(success! "Found font %s" font)
(warn! "Warning: couldn't find %s font in %s"
font font-dest)
(explain! "You can install it by running `M-x all-the-icons-install-fonts' within Emacs.\n\n"
"This could also mean you've installed them in non-standard locations, in which "
"case, ignore this warning."))))))
;; gnutls-cli & openssl ;; gnutls-cli & openssl
(log! "test-gnutls")
(cond ((executable-find "gnutls-cli")) (cond ((executable-find "gnutls-cli"))
((executable-find "openssl") ((executable-find "openssl")
(let* ((output (shell-command-to-string "openssl ciphers -v")) (let* ((output (shell-command-to-string "openssl ciphers -v"))
@ -174,12 +209,13 @@
"network, provider, government, neckbearded mother-in-laws, geeky roommates, " "network, provider, government, neckbearded mother-in-laws, geeky roommates, "
"or just about anyone who knows more about computers than you do!")))) "or just about anyone who knows more about computers than you do!"))))
(log! "test-tls")
(cond ((or (executable-find "gnutls-cli") (cond ((or (executable-find "gnutls-cli")
(executable-find "openssl")) (executable-find "openssl"))
(let ((tls-checktrust t) (let ((tls-checktrust t)
(gnutls-verify-error t)) (gnutls-verify-error t))
(dolist (url '("https://elpa.gnu.org/packages/archive-contents" (dolist (url '("https://elpa.gnu.org"
"https://melpa.org/packages/archive-contents")) "https://melpa.org"))
(condition-case-unless-debug ex (condition-case-unless-debug ex
(let (result) (let (result)
(let ((inhibit-message t)) (let ((inhibit-message t))
@ -214,12 +250,8 @@
(t (t
(error! "Nope!"))) (error! "Nope!")))
;; windows? windows
(check! (memq system-type '(windows-nt ms-dos cygwin))
(warn! "Warning: Windows detected")
(explain! "DOOM was designed for MacOS and Linux. Expect a bumpy ride!"))
;; bsd vs gnu tar ;; bsd vs gnu tar
(log! "test-tar")
(let ((tar-bin (or (executable-find "gtar") (let ((tar-bin (or (executable-find "gtar")
(executable-find "tar")))) (executable-find "tar"))))
(if tar-bin (if tar-bin

View file

@ -257,6 +257,8 @@ If PROJECT-P, kill all buffers that belong to the current project."
(let ((buffers (if project-p (doom-project-buffer-list) (doom-buffer-list)))) (let ((buffers (if project-p (doom-project-buffer-list) (doom-buffer-list))))
(mapc #'doom-kill-buffer-and-windows buffers) (mapc #'doom-kill-buffer-and-windows buffers)
(when (called-interactively-p 'interactive) (when (called-interactively-p 'interactive)
(unless (doom-real-buffer-p)
(switch-to-buffer (doom-fallback-buffer)))
(message "Killed %s buffers" (length buffers))))) (message "Killed %s buffers" (length buffers)))))
;;;###autoload ;;;###autoload

View file

@ -51,8 +51,8 @@ list, whose car is NAME, and cdr the current version list and latest version
list of the package." list of the package."
(cl-assert (symbolp name) t) (cl-assert (symbolp name) t)
(doom-initialize-packages) (doom-initialize-packages)
(when-let (pkg (assq name package-alist)) (when-let (desc (cadr (assq name package-alist)))
(let* ((old-version (package-desc-version (cadr pkg))) (let* ((old-version (package-desc-version desc))
(new-version (new-version
(pcase (doom-package-backend name) (pcase (doom-package-backend name)
('quelpa ('quelpa

View file

@ -27,8 +27,8 @@ If neither is available, run all tests in all enabled modules."
(let (targets) (let (targets)
;; ensure DOOM is initialized ;; ensure DOOM is initialized
(let (noninteractive) (let (noninteractive)
(load (expand-file-name "init.el" user-emacs-directory) nil t)) (load (expand-file-name "core/core.el" user-emacs-directory) nil t)
(remove-hook 'doom-init-hook #'doom--display-benchmark) (doom-initialize-modules nil))
;; collect targets ;; collect targets
(cond ((and command-line-args-left (cond ((and command-line-args-left
(equal (car command-line-args-left) "--")) (equal (car command-line-args-left) "--"))
@ -77,7 +77,8 @@ If neither is available, run all tests in all enabled modules."
finally do (quiet! (mapc #'load-file items))) finally do (quiet! (mapc #'load-file items)))
;; run all loaded tests ;; run all loaded tests
(when noninteractive (when noninteractive
(ert-run-tests-batch-and-exit))) (let (noninteractive)
(ert-run-tests-batch-and-exit))))
('error ('error
(lwarn 'doom-test :error (lwarn 'doom-test :error
"%s -> %s" "%s -> %s"

View file

@ -213,27 +213,11 @@ with functions that require it (like modeline segments)."
(add-hook 'doom-init-hook #'smartparens-global-mode) (add-hook 'doom-init-hook #'smartparens-global-mode)
(require 'smartparens-config) (require 'smartparens-config)
;; Smartparens interferes with Replace mode
;; disable smartparens in evil-mode's replace state (they conflict)
(add-hook 'evil-replace-state-entry-hook #'turn-off-smartparens-mode) (add-hook 'evil-replace-state-entry-hook #'turn-off-smartparens-mode)
(add-hook 'evil-replace-state-exit-hook #'turn-on-smartparens-mode) (add-hook 'evil-replace-state-exit-hook #'turn-on-smartparens-mode)
;; Auto-close more conservatively
(let ((unless-list '(sp-point-before-word-p
sp-point-after-word-p
sp-point-before-same-p)))
(sp-pair "'" nil :unless unless-list)
(sp-pair "\"" nil :unless unless-list))
(sp-pair "{" nil :post-handlers '(("||\n[i]" "RET") ("| " " "))
:unless '(sp-point-before-word-p sp-point-before-same-p))
(sp-pair "(" nil :post-handlers '(("||\n[i]" "RET") ("| " " "))
:unless '(sp-point-before-word-p sp-point-before-same-p))
(sp-pair "[" nil :post-handlers '(("| " " "))
:unless '(sp-point-before-word-p sp-point-before-same-p))
(sp-local-pair 'css-mode "/*" "*/"
:post-handlers '(("[d-3]||\n[i]" "RET") ("| " "SPC")))
(sp-local-pair '(sh-mode markdown-mode) "`" nil
:unless '(sp-point-before-word-p sp-point-before-same-p))
(sp-local-pair '(xml-mode nxml-mode php-mode) "<!--" "-->" (sp-local-pair '(xml-mode nxml-mode php-mode) "<!--" "-->"
:post-handlers '(("| " "SPC")))) :post-handlers '(("| " "SPC"))))

View file

@ -21,6 +21,9 @@
(dolist (sym '(when-let if-let string-trim string-join string-blank-p string-lessp)) (dolist (sym '(when-let if-let string-trim string-join string-blank-p string-lessp))
(autoload sym "subr-x" nil nil 'macro)) (autoload sym "subr-x" nil nil 'macro))
(dolist (sym '(json-read json-read-file json-read-from-string json-encode))
(autoload sym "json"))
;; ;;
;; Helpers ;; Helpers

View file

@ -90,6 +90,7 @@ missing) and shouldn't be deleted.")
"A backup of `load-path' before it was altered by `doom-initialize'. Used as a "A backup of `load-path' before it was altered by `doom-initialize'. Used as a
base by `doom!' and for calculating how many packages exist.") base by `doom!' and for calculating how many packages exist.")
(defvar doom--module nil)
(defvar doom--refresh-p nil) (defvar doom--refresh-p nil)
(setq load-prefer-newer (or noninteractive doom-debug-mode) (setq load-prefer-newer (or noninteractive doom-debug-mode)
@ -207,19 +208,20 @@ This aggressively reloads core autoload files."
(when (or force-p (not doom-modules)) (when (or force-p (not doom-modules))
(setq doom-modules nil) (setq doom-modules nil)
(funcall load-fn (expand-file-name "init.el" doom-emacs-dir)) (funcall load-fn (expand-file-name "init.el" doom-emacs-dir))
(funcall load-fn (doom-module-path :private user-login-name "init.el") t)
(when load-p (when load-p
(cl-loop for file (let (noninteractive)
in (append (nreverse (file-expand-wildcards (expand-file-name "core*.el" doom-core-dir))) (funcall load-fn (doom-module-path :private user-login-name "init.el") t)
(file-expand-wildcards (expand-file-name "autoload/*.el" doom-core-dir)) (funcall load-fn (expand-file-name "core.el" doom-core-dir)))
(doom--module-paths "config.el")) (mapc load-fn (file-expand-wildcards (expand-file-name "autoload/*.el" doom-core-dir))))
do (funcall load-fn file t)))
(doom|finalize)) (doom|finalize))
(when (or force-p (not doom-packages)) (when (or force-p (not doom-packages))
(setq doom-packages nil) (setq doom-packages nil)
(funcall load-fn (expand-file-name "packages.el" doom-core-dir)) (funcall load-fn (expand-file-name "packages.el" doom-core-dir))
(dolist (file (doom--module-paths "packages.el")) (cl-loop for (module . submodule) in (doom--module-pairs)
(funcall load-fn file t))))) for path = (doom-module-path module submodule "packages.el")
do
(let ((doom--module (cons module submodule)))
(funcall load-fn path t))))))
(defun doom-initialize-modules (modules) (defun doom-initialize-modules (modules)
"Adds MODULES to `doom-modules'. MODULES must be in mplist format. "Adds MODULES to `doom-modules'. MODULES must be in mplist format.
@ -233,15 +235,10 @@ This aggressively reloads core autoload files."
(setq mode m)) (setq mode m))
((not mode) ((not mode)
(error "No namespace specified on `doom!' for %s" m)) (error "No namespace specified on `doom!' for %s" m))
((eq m '*) ((listp m)
(doom-initialize-modules (doom-module-enable mode (car m) (cdr m)))
(cl-loop with modpath = (expand-file-name (substring (symbol-name mode) 1) doom-modules-dir)
for path in (directory-files modpath t "^\\w")
if (file-directory-p path)
collect (intern (file-name-nondirectory path)) into paths
finally return (cons mode paths))))
(t (t
(doom--enable-module mode m)))))) (doom-module-enable mode m))))))
(defun doom-module-path (module submodule &optional file) (defun doom-module-path (module submodule &optional file)
"Get the full path to a module: e.g. :lang emacs-lisp maps to "Get the full path to a module: e.g. :lang emacs-lisp maps to
@ -253,37 +250,43 @@ This aggressively reloads core autoload files."
(expand-file-name (concat module "/" submodule "/" file) (expand-file-name (concat module "/" submodule "/" file)
doom-modules-dir)) doom-modules-dir))
(defun doom-module-flags (module submodule)
"Returns a list of flags provided for MODULE SUBMODULE."
(and (hash-table-p doom-modules)
(gethash (cons module submodule) doom-modules)))
(defun doom-module-loaded-p (module submodule) (defun doom-module-loaded-p (module submodule)
"Returns t if MODULE->SUBMODULE is present in `doom-modules'." "Returns t if MODULE->SUBMODULE is present in `doom-modules'."
(and doom-modules (and (doom-module-flags module submodule) t))
(gethash (cons module submodule) doom-modules)))
(defun doom-module-enable (module submodule &optional flags)
"Adds MODULE and SUBMODULE to `doom-modules', overwriting it if it exists.
MODULE is a keyword, SUBMODULE is a symbol. e.g. :lang 'emacs-lisp.
Used by `require!' and `depends-on!'."
(puthash (cons module submodule)
(doom-enlist (or flags t))
doom-modules))
(defun doom--module-pairs () (defun doom--module-pairs ()
"Returns `doom-modules' as a list of (MODULE . SUBMODULE) cons cells. The list "Returns `doom-modules' as a list of (MODULE . SUBMODULE) cons cells. The list
is sorted by order of insertion unless ALL-P is non-nil. If ALL-P is non-nil, is sorted by order of insertion unless ALL-P is non-nil. If ALL-P is non-nil,
include all modules, enabled or otherwise." include all modules, enabled or otherwise."
(if (hash-table-p doom-modules) (unless (hash-table-p doom-modules)
(error "doom-modules is uninitialized"))
(cl-loop for key being the hash-keys of doom-modules (cl-loop for key being the hash-keys of doom-modules
collect (cons (car key) (cdr key))) collect key))
(error "doom-modules is uninitialized")))
(defun doom--module-paths (&optional append-file) (defun doom--module-paths (&optional append-file)
"Returns a list of absolute file paths to activated modules, with APPEND-FILE "Returns a list of absolute file paths to activated modules, with APPEND-FILE
added, if the file exists." added, if the file exists."
(let (paths) (cl-loop for (module . submodule) in (doom--module-pairs)
(dolist (pair (doom--module-pairs) (nreverse paths)) for path = (doom-module-path module submodule append-file)
(let ((path (doom-module-path (car pair) (cdr pair) append-file))) if (file-exists-p path)
(when (file-exists-p path) collect path))
(push path paths))))))
(defun doom--enable-module (module submodule &optional force-p)
"Adds MODULE and SUBMODULE to `doom-modules', if it isn't already there (or if
FORCE-P is non-nil). MODULE is a keyword, SUBMODULE is a symbol. e.g. :lang
'emacs-lisp.
Used by `require!' and `depends-on!'."
(unless (or force-p (doom-module-loaded-p module submodule))
(puthash (cons module submodule) t doom-modules)))
(defun doom--display-benchmark () (defun doom--display-benchmark ()
(message "Loaded %s packages in %.03fs" (message "Loaded %s packages in %.03fs"
@ -307,20 +310,14 @@ MODULES is an malformed plist of modules to load."
(doom-initialize-modules modules) (doom-initialize-modules modules)
(when (and user-login-name (when (and user-login-name
(not (doom-module-loaded-p :private (intern user-login-name)))) (not (doom-module-loaded-p :private (intern user-login-name))))
(doom--enable-module :private user-login-name)) (doom-module-enable :private user-login-name))
`(let (file-name-handler-alist) `(let (file-name-handler-alist)
(setq doom-modules ',doom-modules) (setq doom-modules ',doom-modules)
(unless noninteractive (unless noninteractive
(require 'core-ui) ; draw me like one of your French editors
(require 'core-popups) ; taming sudden yet inevitable windows
(require 'core-editor) ; baseline configuration for text editing
(require 'core-projects) ; making Emacs project-aware
(require 'core-keybinds) ; centralized keybind system + which-key
(load ,(doom-module-path :private user-login-name "init") t t) (load ,(doom-module-path :private user-login-name "init") t t)
,@(cl-loop for (module . submodule) in (doom--module-pairs) ,@(cl-loop for (module . submodule) in (doom--module-pairs)
collect `(require! ,module ,submodule t)) collect `(require! ,module ,submodule nil t))
(when (display-graphic-p) (when (display-graphic-p)
(require 'server) (require 'server)
@ -383,7 +380,8 @@ If NOERROR is non-nil, don't throw an error if the file doesn't exist."
(and load-file-name (file-name-directory load-file-name)) (and load-file-name (file-name-directory load-file-name))
(and (bound-and-true-p byte-compile-current-file) (and (bound-and-true-p byte-compile-current-file)
(file-name-directory byte-compile-current-file)) (file-name-directory byte-compile-current-file))
(and buffer-file-name (file-name-directory buffer-file-name)))) (and buffer-file-name
(file-name-directory buffer-file-name))))
(filename (cond ((stringp filesym) filesym) (filename (cond ((stringp filesym) filesym)
((symbolp filesym) (symbol-name filesym)) ((symbolp filesym) (symbol-name filesym))
(t (error "load! expected a string or symbol, got %s (a %s)" (t (error "load! expected a string or symbol, got %s (a %s)"
@ -392,28 +390,40 @@ If NOERROR is non-nil, don't throw an error if the file doesn't exist."
(error "Could not find %s" filename)) (error "Could not find %s" filename))
(let ((file (expand-file-name (concat filename ".el") path))) (let ((file (expand-file-name (concat filename ".el") path)))
(if (file-exists-p file) (if (file-exists-p file)
`(load ,(file-name-sans-extension file) ,noerror ,(not doom-debug-mode)) `(load ,(file-name-sans-extension file) ,noerror
,(not doom-debug-mode))
(unless noerror (unless noerror
(error "Could not load! file %s" file)))))) (error "Could not load! file %s" file))))))
(defmacro require! (module submodule &optional reload-p) (defmacro require! (module submodule &optional flags reload-p)
"Loads the module specified by MODULE (a property) and SUBMODULE (a symbol). "Loads the module specified by MODULE (a property) and SUBMODULE (a symbol).
The module is only loaded once. If RELOAD-P is non-nil, load it again." The module is only loaded once. If RELOAD-P is non-nil, load it again."
(let ((loaded-p (doom-module-loaded-p module submodule))) (let ((loaded-p (doom-module-loaded-p module submodule)))
(when (or reload-p (not loaded-p)) (when (or reload-p (not loaded-p))
(unless loaded-p (unless loaded-p
(doom--enable-module module submodule t)) (doom-module-enable module submodule flags))
`(condition-case-unless-debug ex `(condition-case-unless-debug ex
(load! config ,(doom-module-path module submodule) t) (let ((doom--module ',(cons module submodule)))
(load! config ,(doom-module-path module submodule) t))
('error ('error
(lwarn 'doom-modules :error (lwarn 'doom-modules :error
"%s in '%s %s' -> %s" "%s in '%s %s' -> %s"
(car ex) ,module ',submodule (error-message-string ex))))))) (car ex) ,module ',submodule
(error-message-string ex)))))))
(defmacro featurep! (module submodule) (defmacro featurep! (module &optional submodule flag)
"Convenience macro wrapper for `doom-module-loaded-p'." "A convenience macro wrapper for `doom-module-loaded-p'. It is evaluated at
(doom-module-loaded-p module submodule)) compile-time/macro-expansion time."
(unless submodule
(unless doom--module
(error "featurep! was used incorrectly (doom--module wasn't unset)"))
(setq flag module
module (car doom--module)
submodule (cdr doom--module)))
(if flag
(and (memq flag (doom-module-flags module submodule)) t)
(doom-module-loaded-p module submodule)))
;; ;;
@ -467,7 +477,7 @@ Only use this macro in a module's packages.el file.
MODULE is a keyword, and SUBMODULE is a symbol. Under the hood, this simply MODULE is a keyword, and SUBMODULE is a symbol. Under the hood, this simply
loads MODULE SUBMODULE's packages.el file." loads MODULE SUBMODULE's packages.el file."
(doom--enable-module module submodule) (doom-module-enable module submodule)
`(load! packages ,(doom-module-path module submodule) t)) `(load! packages ,(doom-module-path module submodule) t))
@ -632,6 +642,12 @@ If ONLY-RECOMPILE-P is non-nil, only recompile out-of-date files."
;; Forcibly recompile core.el in case `load-path' has changed ;; Forcibly recompile core.el in case `load-path' has changed
(byte-recompile-file (expand-file-name "core.el" doom-core-dir) t)) (byte-recompile-file (expand-file-name "core.el" doom-core-dir) t))
(defun doom/recompile-packages ()
"Recompile all installed elpa packages. If you're getting odd errors after
upgrading Emacs, this may fix it."
(interactive)
(byte-recompile-directory package-user-dir 0 t))
(defun doom/reset () (defun doom/reset ()
"Clear the local cache completely (in `doom-cache-dir'). "Clear the local cache completely (in `doom-cache-dir').

View file

@ -33,18 +33,6 @@ state are passed in.")
(append (list doom-local-dir ".sync") (append (list doom-local-dir ".sync")
projectile-globally-ignored-directories)) projectile-globally-ignored-directories))
;; Add `recentf-filename-handlers' support to `projectile-recentf-files'.
(defun doom*projectile-abbreviate-project-root (orig-fn &rest args)
"Abbreviate `projectile-project-root'."
(cl-letf (((symbol-function 'projectile-project-root)
`(lambda ()
(cl-loop with dir = (,(symbol-function 'projectile-project-root))
for fn in recentf-filename-handlers
do (setq dir (funcall fn dir))
finally return dir))))
(apply orig-fn args)))
(advice-add #'projectile-recentf-files :around #'doom*projectile-abbreviate-project-root)
;; Projectile root-searching functions can cause an infinite loop on TRAMP ;; Projectile root-searching functions can cause an infinite loop on TRAMP
;; connections, so disable them. ;; connections, so disable them.
(defun doom*projectile-locate-dominating-file (orig-fn &rest args) (defun doom*projectile-locate-dominating-file (orig-fn &rest args)

View file

@ -148,7 +148,7 @@ local value, whether or not it's permanent-local. Therefore, we cycle
;; undo/redo changes to Emacs' window layout ;; undo/redo changes to Emacs' window layout
(defvar winner-dont-bind-my-keys t) ; I'll bind keys myself (defvar winner-dont-bind-my-keys t) ; I'll bind keys myself
(autoload 'winner-mode "winner" nil t) (autoload 'winner-mode "winner" nil t)
(add-hook 'doom-init-hook #'winner-mode) (add-hook 'doom-init-ui-hook #'winner-mode)
;; highlight matching delimiters ;; highlight matching delimiters
(setq show-paren-delay 0.1 (setq show-paren-delay 0.1
@ -185,7 +185,7 @@ local value, whether or not it's permanent-local. Therefore, we cycle
;; Getting themes to remain consistent across GUI Emacs, terminal Emacs and ;; Getting themes to remain consistent across GUI Emacs, terminal Emacs and
;; daemon Emacs is hairy. ;; daemon Emacs is hairy.
;; ;;
;; + Running `+doom|init-ui' directly sorts out the initial GUI frame. ;; + Running `doom|init-ui' directly sorts out the initial GUI frame.
;; + Attaching it to `after-make-frame-functions' sorts out daemon Emacs. ;; + Attaching it to `after-make-frame-functions' sorts out daemon Emacs.
;; + Waiting for 0.1s in `doom|reload-ui-in-daemon' fixes daemon Emacs started ;; + Waiting for 0.1s in `doom|reload-ui-in-daemon' fixes daemon Emacs started
;; with `server-start' in an interactive session of Emacs AND in tty Emacs. ;; with `server-start' in an interactive session of Emacs AND in tty Emacs.
@ -193,16 +193,21 @@ local value, whether or not it's permanent-local. Therefore, we cycle
"Set the theme and load the font, in that order." "Set the theme and load the font, in that order."
(when doom-theme (when doom-theme
(load-theme doom-theme t)) (load-theme doom-theme t))
(condition-case-unless-debug ex
(when (display-graphic-p) (when (display-graphic-p)
(with-demoted-errors "FONT ERROR: %s"
(when (fontp doom-font) (when (fontp doom-font)
(set-frame-font doom-font nil (if frame (list frame) t))) (set-frame-font doom-font nil (if frame (list frame) t))
(set-face-attribute 'fixed-pitch frame :font doom-font))
;; Fallback to `doom-unicode-font' for Unicode characters ;; Fallback to `doom-unicode-font' for Unicode characters
(when (fontp doom-unicode-font) (when (fontp doom-unicode-font)
(set-fontset-font t 'unicode doom-unicode-font frame)) (set-fontset-font t 'unicode doom-unicode-font frame))
;; ...and for variable-pitch-mode: ;; ...and for variable-pitch-mode:
(when (fontp doom-variable-pitch-font) (when (fontp doom-variable-pitch-font)
(set-face-attribute 'variable-pitch frame :font doom-variable-pitch-font)))) (set-face-attribute 'variable-pitch frame :font doom-variable-pitch-font)))
('error
(lwarn 'doom-ui :error
"Failed to set fonts because %s"
(error-message-string ex))))
(run-hooks 'doom-init-ui-hook)) (run-hooks 'doom-init-ui-hook))
(defun doom|reload-ui-in-daemon (frame) (defun doom|reload-ui-in-daemon (frame)

View file

@ -15,7 +15,7 @@
;; Autoloaded functions are in core/autoload/*.el and modules/*/*/autoload.el or ;; Autoloaded functions are in core/autoload/*.el and modules/*/*/autoload.el or
;; modules/*/*/autoload/*.el. ;; modules/*/*/autoload/*.el.
(defvar doom-version "2.0.4" (defvar doom-version "2.0.5"
"Current version of DOOM emacs.") "Current version of DOOM emacs.")
(defvar doom-debug-mode (or (getenv "DEBUG") init-file-debug) (defvar doom-debug-mode (or (getenv "DEBUG") init-file-debug)
@ -149,7 +149,7 @@ ability to invoke the debugger in debug mode."
nil) nil)
(defun doom|finalize () (defun doom|finalize ()
(unless doom-init-p (unless (or doom-init-p noninteractive)
(dolist (hook '(doom-init-hook doom-post-init-hook)) (dolist (hook '(doom-init-hook doom-post-init-hook))
(run-hook-wrapped hook #'doom-try-run-hook hook)) (run-hook-wrapped hook #'doom-try-run-hook hook))
(setq doom-init-p t)) (setq doom-init-p t))
@ -185,7 +185,14 @@ ability to invoke the debugger in debug mode."
('error ('error
(lwarn 'doom-autoloads :warning (lwarn 'doom-autoloads :warning
"%s in autoloads.el -> %s" "%s in autoloads.el -> %s"
(car ex) (error-message-string ex))))) (car ex) (error-message-string ex))))
(unless noninteractive
(load! core-ui) ; draw me like one of your French editors
(load! core-popups) ; taming sudden yet inevitable windows
(load! core-editor) ; baseline configuration for text editing
(load! core-projects) ; making Emacs project-aware
(load! core-keybinds))) ; centralized keybind system + which-key
(add-hook! '(emacs-startup-hook doom-reload-hook) (add-hook! '(emacs-startup-hook doom-reload-hook)
#'doom|finalize) #'doom|finalize)

View file

@ -8,7 +8,9 @@
(push `(,bsym (get-buffer-create ,(symbol-name bsym))) (push `(,bsym (get-buffer-create ,(symbol-name bsym)))
buffers)) buffers))
`(save-window-excursion `(save-window-excursion
(cl-flet ((buffer-list (lambda () (list ,@(reverse (mapcar #'car buffers)))))) (cl-flet ((buffer-list
(lambda ()
(cl-remove-if-not #'buffer-live-p (list ,@(reverse (mapcar #'car buffers)))))))
(let* (persp-mode (let* (persp-mode
,@buffers) ,@buffers)
,@body ,@body
@ -64,7 +66,7 @@
(switch-to-buffer a) (switch-to-buffer a)
(should (eq (current-buffer) a)) (should (eq (current-buffer) a))
(should (eq (selected-window) (get-buffer-window a))) (should (eq (selected-window) (get-buffer-window a)))
(split-window) (split-window nil 1)
(switch-to-buffer b) (switch-to-buffer b)
(should (eq (current-buffer) b)) (should (eq (current-buffer) b))
(should (eq (selected-window) (get-buffer-window b))) (should (eq (selected-window) (get-buffer-window b)))

View file

@ -1,168 +0,0 @@
#+TITLE: DOOM modules
* Table of Contents :TOC:noexport:
- [[#overview][Overview]]
- [[#module-overview][Module overview]]
- [[#the-structure-of-a-module][The structure of a module]]
- [[#configel][config.el]]
- [[#packagesel][packages.el]]
- [[#autoloadel-or-autoloadel][autoload.el OR autoload/*.el]]
- [[#additional-files][Additional files]]
- [[#appendix][Appendix]]
* Overview
DOOM is comprised of its core files and then its modules. A small list of macros are used to manage and configure plugins, other modules and DOOM Emacs itself.
These macros are:
+ Package management
+ ~(featurep! MODULE SUBMODULE)~: returns =t= if =:module submodule= is activated.
+ ~(load! NAME)~: loads NAME.el, relative to the current file.
+ ~(require! MODULE SUBMODULE &optional RELOAD-P)~: activates a module & loads its config.el, if it isn't already loaded.
+ ~(package! NAME &key recipe pin)~: declares a package to be installed and where to get it.
+ ~(depends-on! MODULE SUBMODULE)~: loads a module's packages.el.
+ Configuration
+ ~(set! SETTING &rest ARGS)~: safely cross-configure other modules. Use ~M-x doom/describe-setting~ to see what's available.
+ ~(def-package! NAME &rest PLIST)~: configure a package (wrapper around ~use-package~).
+ ~(def-setting! SETTING &rest ARGS)~: defines a setting other modules can ~set!~.
The TL;DR of this document is:
+ Modules are comprised of: =config.el=, =packages.el=, either =autoload.el= or =autoload/*.el=, and =+*.el= files; these are all optional.
+ =config.el= is the only file loaded when a module is activated, and is where you configure the module and its plugins.
+ =packages.el= files inform DOOM what plugins to install and where from, using the ~package!~ macro. This macro accepts a MELPA-style recipe plist to specify a location other than the ELPA for fetching plugins.
+ Use ~set!~ to safely cross-configure modules; ~doom/describe-setting~ can help you discover what settings are available.
+ Packages are deferred by default; add ~:demand t~ to their ~def-package!~ declaration to load them immediately.
+ The =private/{user-login-name}= module is automatically loaded. It is harmless to keep =:private {user-login-name}= in your init.el however.
+ =private/{user-login-name}/init.el= is a special file that is automatically loaded after DOOM core files, but before modules are loaded. Use it to configure DOOM.
** Module overview
These modules are in their ideal load order.
+ :feature :: Broad modules that bring essential functionality to Emacs as an editor.
+ :completion :: Swappable completion modules for narrowing down candidate lists quickly.
+ :ui :: Aesthetic modules that affect the Emacs interface or user experience.
+ :tools :: Small modules that add specific, non-essential functionality to Emacs.
+ :lang :: Modules that bring support for a language or group of languages to Emacs.
+ :org :: Modules that affect and extend org-mode.
+ :app :: Large, opinionated modules that transform Emacs' UI to serve a specific purpose.
+ :private :: Private configuration modules that are untracked by version control (except for my personal one; use it as a reference).
Change the ~doom!~ block in your ~init.el~ file to enable/disable modules on startup. You'll need to restart Emacs.
Don't forget to run ~make~ afterwards to ensure that the needed packages are installed (and unneeded ones are uninstalled).
#+begin_quote
*Remember*: if you've byte-compiled your config, your changes won't take effect
until you recompile or delete the \*.elc files.
#+end_quote
* The structure of a module
Modules are made up of five *optional* parts:
+ config.el :: The heart of a module; loaded when the module is activated.
+ packages.el :: Tells DOOM what packages to install and where from. Isn't loaded until package management commands are used.
+ autoload.el (or autoload/*.el) :: Lazily-loaded functions for that module.
+ +*.el :: Additional config files; not automatically loaded.
+ test/*.el :: unit tests for that module, if any.
** config.el
*config.el* is loaded immediately. It is the only file proactively loaded by the DOOM module system. Additional files must be explicitly loaded using ~load!~.
It should expect dependencies (in =packages.el=) to be installed and available, but shouldn't make assumptions about what modules are activated (use ~featurep!~ for this).
Packages should be configured using ~after!~ or ~def-package!~ (an alias for ~use-package~).
#+BEGIN_SRC emacs-lisp
;; from modules/completion/company/config.el
(def-package! company
:commands (company-mode global-company-mode company-complete
company-complete-common company-manual-begin company-grab-line)
:config
(setq company-idle-delay nil
company-tooltip-limit 10
company-dabbrev-downcase nil
company-dabbrev-ignore-case nil)
[...])
#+END_SRC
+ Packages are *deferred* by default: add ~:demand t~ to ~def-package!~ blocks to load them immediately.
+ Use ~featurep!~ to test DOOM module availability for conditional packages.
+ Use ~set!~ to cross-configure modules safely, e.g. company backends:
#+BEGIN_SRC emacs-lisp
;; from modules/lang/python/config.el
(set! :company-backend 'python-mode '(company-anaconda))
#+END_SRC
** packages.el
This file isn't loaded until you use DOOM's package management commands.
Evaluating them should be deterministic, idempotent, and without side-effects (besides updating ~doom-modules~ and ~doom-packages~).
Packages are declared with the ~package!~ macro, e.g.
#+BEGIN_SRC emacs-lisp
;; from modules/lang/org/packages.el
(package! org-bullets)
;; from modules/tools/rotate-text/packages.el
(package! rotate-text :recipe (:fetcher github :repo "debug-ito/rotate-text.el"))
#+END_SRC
The packages.el of another module can loaded with ~depends-on!~:
#+BEGIN_SRC emacs-lisp
;; from modules/feature/file-templates/packages.el
(depends-on! :feature snippets)
#+END_SRC
** autoload.el OR autoload/*.el
Functions in these files are lazily loaded. ~doom/reload-autoloads~ will scan these and produce an =autoloads.el= file, which tells Emacs where to find these functions.
For example:
#+BEGIN_SRC emacs-lisp
;; from modules/lang/org/autoload/org.el
;;;###autoload
(defun +org/toggle-checkbox ()
(interactive)
[...])
;; from modules/lang/org/autoload/evil.el
;;;###autoload (autoload '+org:attach "lang/org/autoload/evil" nil t)
(evil-define-command +org:attach (&optional uri)
(interactive "<a>")
[...])
#+END_SRC
Autoload files named ~evil*.el~ will be ignored if =:feature evil= isn't loaded.
** Additional files
The only convention is to prefix additional elisp files with a =+=, e.g.
=modules/feature/version-control/+git.el=.
These are /not/ loaded automatically. Use ~load!~ to do so.
#+BEGIN_SRC emacs-lisp
;; from modules/feature/version-control/config.el
(load +git)
#+END_SRC
* Appendix
+ Macros
+ ~(featurep! CATEGORY MODULE)~
+ ~(load! NAME)~
+ ~(package! NAME &key recipe pin)~
+ ~(require! CATEGORY MODULE &optional RELOAD-P)~
+ ~(def-package! NAME &rest PLIST)~
+ ~(set! SETTING &rest ARGS)~
+ ~(def-setting! NAME ARGLIST &rest BODY)~
+ Commands
+ ~doom/reload~
+ ~doom/reload-autoloads~
+ ~doom/compile~
+ ~doom/recompile~
+ ~doom/reset~
+ ~doom/clean-compiled~

View file

@ -1,4 +1,4 @@
* :app email #+TITLE: :app email
This module makes Emacs an email client, using ~mu4e~. This module makes Emacs an email client, using ~mu4e~.
@ -10,41 +10,45 @@ It uses ~mu4e~ to read my email, but depends on ~offlineimap~ (to sync my email
WARNING: my config is gmail/gsuite oriented, and since Google has its own opinions on the IMAP standard, it is unlikely to translate to other hosts. WARNING: my config is gmail/gsuite oriented, and since Google has its own opinions on the IMAP standard, it is unlikely to translate to other hosts.
#+end_quote #+end_quote
** Install * Table of Contents :TOC:
- [[#install][Install]]
- [[#macos][MacOS]]
- [[#arch-linux][Arch Linux]]
- [[#dependencies][Dependencies]]
* Install
This module requires: This module requires:
+ ~offlineimap~ (to sync mail with) + ~offlineimap~ (to sync mail with)
+ ~mu~ (to index your downloaded messages) + ~mu~ (to index your downloaded messages)
*** MacOS ** MacOS
#+BEGIN_SRC sh :tangle (if (doom-system-os 'macos) "yes") #+BEGIN_SRC sh :tangle (if (doom-system-os 'macos) "yes")
brew install mu --with-emacs brew install mu --with-emacs
brew install offlineimap brew install offlineimap
#+END_SRC #+END_SRC
*** Arch Linux ** Arch Linux
#+BEGIN_SRC sh :dir /sudo:: :tangle (if (doom-system-os 'arch) "yes") #+BEGIN_SRC sh :dir /sudo:: :tangle (if (doom-system-os 'arch) "yes")
sudo pacman --noconfirm --needed -S offlineimap mu sudo pacman --noconfirm --needed -S offlineimap mu
#+END_SRC #+END_SRC
** Dependencies * Dependencies
You need to do the following: You need to do the following:
1. Write a ~\~/.offlineimaprc~. Mine can be found [[https://github.com/hlissner/dotfiles/tree/master/shell/+mu][in my dotfiles repository]]. It is configured to download mail to ~\~/.mail~. I use unix pass to securely store my login credentials. 1. Write a ~\~/.offlineimaprc~. Mine can be found [[https://github.com/hlissner/dotfiles/tree/master/shell/+mu][in my dotfiles repository]]. It is configured to download mail to ~\~/.mail~. I use [[https://www.passwordstore.org/][unix pass]] to securely store my login credentials.
2. Download your email: ~offlineimap -o~ (may take a while) 2. Download your email: ~offlineimap -o~ (may take a while)
3. Index it with mu: ~mu index --maildir ~/.mail~ 3. Index it with mu: ~mu index --maildir ~/.mail~
Then configure Emacs to use your email address: Then configure Emacs to use your email address:
#+BEGIN_SRC emacs-lisp :tangle no #+BEGIN_SRC emacs-lisp :tangle no
;; + %s is replaced with the label, e.g. /%s/Drafts => /lissner.net/Drafts ;; Each path is relative to `+email-mu4e-mail-path', which is ~/.mail by default
;; + Each path is relative to `+email-mu4e-mail-path', which is ~/.mail by (set! :email "Lissner.net"
;; default '((mu4e-sent-folder . "/Lissner.net/Sent Mail")
(set! :email "lissner.net" (mu4e-drafts-folder . "/Lissner.net/Drafts")
'((mu4e-sent-folder . "/%s/Sent Mail") (mu4e-trash-folder . "/Lissner.net/Trash")
(mu4e-drafts-folder . "/%s/Drafts") (mu4e-refile-folder . "/Lissner.net/All Mail")
(mu4e-trash-folder . "/%s/Trash")
(mu4e-refile-folder . "/%s/All Mail")
(smtpmail-smtp-user . "henrik@lissner.net") (smtpmail-smtp-user . "henrik@lissner.net")
(user-mail-address . "henrik@lissner.net") (user-mail-address . "henrik@lissner.net")
(mu4e-compose-signature . "---\nHenrik Lissner")) (mu4e-compose-signature . "---\nHenrik Lissner"))

View file

@ -1,11 +1,17 @@
* :app irc #+TITLE: :app irc
This module turns adds an IRC client to Emacs ([[https://github.com/jorgenschaefer/circe][~circe~)]] with native notifications ([[https://github.com/eqyiel/circe-notifications][circe-notifications]]). This module turns adds an IRC client to Emacs ([[https://github.com/jorgenschaefer/circe][~circe~)]] with native notifications ([[https://github.com/eqyiel/circe-notifications][circe-notifications]]).
** Dependencies * Table of Contents :TOC:
- [[#dependencies][Dependencies]]
- [[#configure][Configure]]
- [[#pass-the-unix-password-manager][Pass: the unix password manager]]
- [[#emacs-auth-source-api][Emacs' auth-source API]]
* Dependencies
This module has no dependencies, besides =gnutls-cli= or =openssl= for secure connections. This module has no dependencies, besides =gnutls-cli= or =openssl= for secure connections.
** Configure * Configure
Use the ~:irc~ setting to configure IRC servers. Its second argument (a plist) takes the same arguments as ~circe-network-options~. Use the ~:irc~ setting to configure IRC servers. Its second argument (a plist) takes the same arguments as ~circe-network-options~.
#+BEGIN_SRC emacs-lisp :tangle no #+BEGIN_SRC emacs-lisp :tangle no
@ -19,7 +25,7 @@ Use the ~:irc~ setting to configure IRC servers. Its second argument (a plist) t
*It is a obviously a bad idea to store auth-details in plaintext,* so here are some ways to avoid that: *It is a obviously a bad idea to store auth-details in plaintext,* so here are some ways to avoid that:
*** Pass: the unix password manager ** Pass: the unix password manager
[[https://www.passwordstore.org/][Pass]] is my tool of choice. I use it to manage my passwords. If you activate the [[/modules/tools/password-store/README.org][:tools password-store]] module you get an elisp API through which to access your password store. [[https://www.passwordstore.org/][Pass]] is my tool of choice. I use it to manage my passwords. If you activate the [[/modules/tools/password-store/README.org][:tools password-store]] module you get an elisp API through which to access your password store.
~:irc~'s plist can use functions instead of strings. ~+pass-get-user~ and ~+pass-get-secret~ can help here: ~:irc~'s plist can use functions instead of strings. ~+pass-get-user~ and ~+pass-get-secret~ can help here:
@ -46,7 +52,7 @@ But wait, there's more! This stores your password in a public variable which cou
And you're good to go! And you're good to go!
*** Emacs' auth-source API ** Emacs' auth-source API
~auth-source~ is built into Emacs. As suggested [[https://github.com/jorgenschaefer/circe/wiki/Configuration#safer-password-management][in the circe wiki]], you can store (and retrieve) encrypted passwords with it. ~auth-source~ is built into Emacs. As suggested [[https://github.com/jorgenschaefer/circe/wiki/Configuration#safer-password-management][in the circe wiki]], you can store (and retrieve) encrypted passwords with it.
#+BEGIN_SRC emacs-lisp :tangle no #+BEGIN_SRC emacs-lisp :tangle no

View file

@ -1,29 +1,33 @@
* :completion company #+TITLE: :completion company
This module adds completion support powered by [[https://github.com/company-mode/company-mode][company]]. This module adds code-completion support, powered by [[https://github.com/company-mode/company-mode][company]].
+ Uses ~company-quickhelp~ for documentation tooltips + Uses ~company-quickhelp~ for documentation tooltips
+ Uses ~company-statistics~ to order results by usage frequency + Uses ~company-statistics~ to order results by usage frequency
[[/../screenshots/company.png]] [[/../screenshots/company.png]]
** Install * Table of Contents :TOC:
Specific languages may require additional setup. Some languages may have no completion support at all. - [[#install][Install]]
- [[#configure][Configure]]
- [[#auto-completion][Auto-completion]]
- [[#troubleshooting][Troubleshooting]]
* Install
Certain languages may require additional setup, and some languages may have no completion support at all.
Check the README.org in that language's module for details. Check the README.org in that language's module for details.
** Customization * Configure
This module is configured to suit my preferences. Here are some things you may want to change: ** Auto-completion
By default, I've disabled auto-completion. This is my preference. I prefer to invoke company when I need it by calling ~company-complete~ manually (typically, bound to =C-SPC= in insert mode). However, some may not share my preference.
*** as-you-type completion To enable auto-completion you must:
By default, I've disabled auto-completion. This is my preference. I prefer to invoke company when I need it by pressing ~C-SPC~ from insert mode. Some don't like this.
To make it automatic, you need to do two things:
1. Load ~company~, 1. Load ~company~,
2. and change ~company-idle-delay~ to a non-nil float (the default is 0.5) 2. and change ~company-idle-delay~ to a non-nil float (the default is 0.5)
To do this, add the following to your ~modules/private/<username>~ module (remember, ~:private <username>~ needs to be added to init.el): For example, add the following to your ~modules/private/<username>/config.el~ module:
#+BEGIN_SRC emacs-lisp #+BEGIN_SRC emacs-lisp
(require 'company) (require 'company)
@ -31,9 +35,9 @@ To do this, add the following to your ~modules/private/<username>~ module (remem
company-minimum-prefix-length 3) company-minimum-prefix-length 3)
#+END_SRC #+END_SRC
** Troubleshooting * Troubleshooting
If completion isn't working for you, please consider the following before posting a bug report: If completion isn't working for you, please consider the following before posting a bug report:
+ Different languages will have different dependencies in order for auto-completion to work. Please look for the README.org in that language's respective module for details. + If what you are expecting is popup-as-you-type completion (which is disabled by default), see the "Customize" section above; it includes instructions on how to enable this.
+ Certain languages may have extra dependencies in order for auto-completion to work. Please look for that module's README.org for details.
+ Some languages don't have any auto-completion support. + Some languages don't have any auto-completion support.
+ Check [[*Customization][Customization]], perhaps what you are expecting is popup-as-you-type completion, which is disabled by default.

View file

@ -1,84 +1,88 @@
* :completion ivy #+TITLE: :completion ivy
This module adds the Ivy completion backend. This module adds Ivy, a completion backend.
I prefer ivy over ido and helm, for its speed and simplicity. With ivy's help and some hackery, I get the following features: #+begin_quote
I prefer ivy over ido for its flexibility. I prefer ivy over helm because it's lighter.
#+end_quote
+ Project-wide search & replace powered by ~rg~ and ~ag~ + Project-wide search & replace powered by ~rg~ or ~ag~
+ Project jump-to navigation ala Command-T, Sublime Text's Jump-to-anywhere or Vim's CtrlP plugin. + Project jump-to navigation ala Command-T, Sublime Text's Jump-to-anywhere or Vim's CtrlP plugin.
+ Ivy integration for ~M-x~, ~imenu~, ~recentf~ and others. + Ivy integration for ~M-x~, ~imenu~, ~recentf~ and others.
+ A powerful, interactive in-buffer search using ~swiper~. + A powerful, interactive in-buffer search using ~swiper~.
+ Ivy-powered TODO/FIXME navigation + Ivy-powered TODO/FIXME navigation
** Install * Table of Contents :TOC:
- [[#install][Install]]
- [[#macos][MacOS]]
- [[#arch-linux][Arch Linux]]
- [[#usage][Usage]]
- [[#project-search--replace][Project search & replace]]
- [[#jump-to-file-project-navigation][Jump-to-file project navigation]]
- [[#in-buffer-searching][In-buffer searching]]
- [[#task-lookup][Task lookup]]
- [[#appendix][Appendix]]
- [[#commands][Commands]]
- [[#hacks][Hacks]]
* Install
This module optionally depends on [[https://github.com/BurntSushi/ripgrep][ripgrep]] and [[https://github.com/ggreer/the_silver_searcher][the_silver_searcher]]. This module optionally depends on [[https://github.com/BurntSushi/ripgrep][ripgrep]] and [[https://github.com/ggreer/the_silver_searcher][the_silver_searcher]].
~rg~ is faster, but its results aren't deterministic and it doesn't support multiline search or full PCRE, that's where ~ag~ is useful. ~rg~ is faster, but its results aren't deterministic, neither does it support multiline search or full PCRE, that's where ~ag~ is useful.
*** MacOS ** MacOS
#+BEGIN_SRC sh :tangle (if (doom-system-os 'macos) "yes") #+BEGIN_SRC sh :tangle (if (doom-system-os 'macos) "yes")
brew install ripgrep the_silver_searcher brew install ripgrep the_silver_searcher
#+END_SRC #+END_SRC
*** Arch Linux ** Arch Linux
#+BEGIN_SRC sh :dir /sudo:: :tangle (if (doom-system-os 'arch) "yes") #+BEGIN_SRC sh :dir /sudo:: :tangle (if (doom-system-os 'arch) "yes")
sudo pacman --needed --noconfirm -S ripgrep the_silver_searcher sudo pacman --needed --noconfirm -S ripgrep the_silver_searcher
#+END_SRC #+END_SRC
** Usage * Usage
*** Search & Replace Here is some insight into how I use this module. Keep in mind that the referenced commands and keybindings are defined [[/modules/private/hlissner][in my private module]].
A project-wide search can be performed with Ag (the silver searcher) or Rg
(ripgrep) via their ex commands: ~:ag[!]~ and ~:rg[!]~ (or their ** Project search & replace
current-directory counterparts ~:agcwd[!]~ and ~:rgcwd[!]~) Ex interfaces to Ag (the silver searcher) and Rg (ripgrep) are available: ~:ag[!]~ and ~:rg[!]~, or their current-directory counterparts ~:agcwd[!]~ and ~:rgcwd[!]~.
[[/../screenshots/modules/completion/ivy/ivy-search.gif]] [[/../screenshots/modules/completion/ivy/ivy-search.gif]]
From this session, you can press =Shift + Tab= to create an writeable occur From this session, you can press =S+Tab= to create a writeable occur-buffer in wgrep mode.
buffer in wgrep mode.
[[/../screenshots/modules/completion/ivy/ivy-search-replace.gif]] [[/../screenshots/modules/completion/ivy/ivy-search-replace.gif]]
Make your modifications and press =C-c C-c= to commit them, or =C-c C-k= to Make your modifications and press =C-c C-c= to commit them, or =C-c C-k= to abort.
abort.
*** Jump-to-file project navigation ** Jump-to-file project navigation
Inspired by Sublime Text's jump-to-anywhere, Vim's CtrlP or Unite plugins, and Inspired by Sublime Text's jump-to-anywhere, Vim's CtrlP or Unite plugins, and Textmate's Command-T, a marriage of ~projectile~ and ~ivy~ makes this available to you in Emacs. Invoke it with =SPC f /=, =SPC SPC= or ~counsel-projectile-find-file~.
Textmate's Command-T, a marriage of ~projectile~ and ~ivy~ makes this available
to you in Emacs. Invoke it with =<leader> /= or ~counsel-projectile-find-file~.
[[/../screenshots/modules/completion/ivy/ivy-projectile.gif]] [[/../screenshots/modules/completion/ivy/ivy-projectile.gif]]
*** In-buffer searching ** In-buffer searching
I prefer to use ~evil-search~ (invoked by pressing =/= in normal mode) when I use ~evil-search~ (invoked by pressing =/= in normal mode) when jumping small/moderate (or predictable) distances. However, there are occasions where I need more feedback, so I turn to ~swiper~ (available directly with =M-x swiper RET=, or via ~:sw[iper]~).
jumping small/moderate (or predictable) distances. On occasion I need more
feedback, so I turn to ~swiper~ (available directly with =M-x swiper RET=, or
via ~:sw[iper]~).
[[/../screenshots/modules/completion/ivy/ivy-swiper.gif]] [[/../screenshots/modules/completion/ivy/ivy-swiper.gif]]
*** TODO-Task lookup ** Task lookup
I sprinkle my projects with TODO's & FIXME's. Using ivy and ripgrep, I wrote I sprinkle my projects with TODO's & FIXME's. You can navigate to and peruse them via ~M-x +ivy/tasks~ or ~:todo[!]~ (ex command).
~+ivy/tasks~ to help me navigate to them. It can be invoked via ~:todo[!]~ as
well.
[[/../screenshots/modules/completion/ivy/ivy-todo.gif]] [[/../screenshots/modules/completion/ivy/ivy-todo.gif]]
** Appendix * Appendix
*** Commands & Keybindings ** Commands
Here is a list of my commonly used commands, their default keybinds (defined in Here is a list of my commonly used commands, their default keybinds (defined in [[../../private/hlissner/+bindings.el][private/hlissner/+bindings.el]]), and their corresponding ex command (defined in [[../../private/hlissner/+commands.el][private/hlissner/+commands.el]]).
[[../../private/hlissner/+bindings.el][private/hlissner/+bindings.el]]), and their corresponding ex command (defined in
[[../../private/hlissner/+commands.el][private/hlissner/+commands.el]]).
| command | key / ex command | description | | command | key / ex command | description |
|-------------------------------------+---------------------+------------------------------------------------------------------| |-------------------------------------+------------------------+------------------------------------------------------------------|
| ~counsel-M-x~ | =M-x= | Smarter, smex-powered M-x | | ~counsel-M-x~ | =M-x= | Smarter, smex-powered M-x |
| ~counsel-bookmark~ | =<leader> b= | Find bookmark | | ~counsel-bookmark~ | =SPC RET= | Find bookmark |
| ~counsel-find-file~ | =<leader> .= | Browse from current directory | | ~counsel-find-file~ | =SPC f .= or =SPC .= | Browse from current directory |
| ~counsel-projectile-find-file~ | =<leader> /= | Find file in project | | ~counsel-projectile-find-file~ | =SPC f /= or =SPC SPC= | Find file in project |
| ~counsel-projectile-switch-project~ | =<leader> p= | Open another project | | ~counsel-projectile-switch-project~ | =SPC p p= | Open another project |
| ~counsel-recentf~ | =<leader> r= | Find recently opened file | | ~counsel-recentf~ | =SPC f r= | Find recently opened file |
| ~+ivy/switch-buffer~ | =<leader> ,= | Jump to buffer in current workspace | | ~ivy-switch-buffer~ | =SPC b b= | Jump to buffer in current workspace |
| ~+ivy/switch-workspace-buffer~ | =<leader> <= | Jump to buffer across workspaces | | ~+ivy/switch-workspace-buffer~ | =SPC b B= | Jump to buffer across workspaces |
| ~+ivy:ag~ | ~:ag[!] [QUERY]~ | Search project (BANG = ignore gitignore) | | ~+ivy:ag~ | ~:ag[!] [QUERY]~ | Search project (BANG = ignore gitignore) |
| ~+ivy:ag-cwd~ | ~:agcwd[!] [QUERY]~ | Search this directory (BANG = don't recurse into subdirectories) | | ~+ivy:ag-cwd~ | ~:agcwd[!] [QUERY]~ | Search this directory (BANG = don't recurse into subdirectories) |
| ~+ivy:rg~ | ~:rg[!] [QUERY]~ | Search project (if BANG, ignore gitignore) | | ~+ivy:rg~ | ~:rg[!] [QUERY]~ | Search project (if BANG, ignore gitignore) |
@ -86,8 +90,7 @@ Here is a list of my commonly used commands, their default keybinds (defined in
| ~+ivy:swiper~ | ~:sw[iper] [QUERY]~ | Search current buffer | | ~+ivy:swiper~ | ~:sw[iper] [QUERY]~ | Search current buffer |
| ~+ivy:todo~ | ~:todo[!]~ | List all TODO/FIXMEs in project (or current file if BANG) | | ~+ivy:todo~ | ~:todo[!]~ | List all TODO/FIXMEs in project (or current file if BANG) |
While in a search (e.g. invoked from ~+ivy:ag~ or ~+ivy:rg~), these new While in a search (e.g. invoked from ~+ivy:ag~ or ~+ivy:rg~), these new keybindings are available to you:
keybindings are available to you:
| key | description | | key | description |
|-------------+--------------------------------------------------------------------------------| |-------------+--------------------------------------------------------------------------------|
@ -95,10 +98,8 @@ keybindings are available to you:
| =C-SPC= | Preview the current candidate | | =C-SPC= | Preview the current candidate |
| =M-RET= | Open the selected candidate in other-window | | =M-RET= | Open the selected candidate in other-window |
*** Hacks ** Hacks
+ Where possible, functions with ivy/counsel equivalents have been remapped + Functions with ivy/counsel equivalents have been globally remapped (like ~find-file~ => ~counsel-find-file~). So a keybinding to ~find-file~ will invoke ~counsel-find-file~ instead.
(like ~find-file~ => ~counsel-find-file~). So a keybinding to ~find-file~ will
invoke ~counsel-find-file~ instead.
+ ~counsel-[arp]g~'s 3-character limit was reduced to 1 (mainly for the ex command) + ~counsel-[arp]g~'s 3-character limit was reduced to 1 (mainly for the ex command)
+ ~counsel-[arp]g~'s parentheses quoting behavior was reversed. Now, if you + ~counsel-[arp]g~'s parentheses quoting behavior was reversed. Now, if you
want literal parentheses, you must escape them: e.g. ~\(match\)~ is literal, want literal parentheses, you must escape them: e.g. ~\(match\)~ is literal,

View file

@ -1,72 +1,48 @@
;;; completion/ivy/autoload/ivy.el -*- lexical-binding: t; -*- ;;; completion/ivy/autoload/ivy.el -*- lexical-binding: t; -*-
;; Show more information in ivy-switch-buffer; and only display (defsubst +ivy--icon-for-mode (mode)
;; workgroup-relevant buffers. "Apply `all-the-icons-for-mode' on MODE but either return an icon or nil."
(defun +ivy--get-buffers (&optional buffer-list) (let ((icon (all-the-icons-icon-for-mode mode)))
(when-let (buffer-list (delq (current-buffer) (or buffer-list (doom-buffer-list)))) (unless (symbolp icon) icon)))
(let* ((min-name
(+ 5 (cl-loop for buf in buffer-list ;;;###autoload
maximize (length (buffer-name buf))))) (defun +ivy-buffer-transformer (str)
(min-mode (let* ((buf (get-buffer str))
(+ 5 (cl-loop for buf in buffer-list (path (buffer-file-name buf))
maximize (length (symbol-name (buffer-local-value 'major-mode buf))))))) (mode (buffer-local-value 'major-mode buf))
(cl-loop (faces
with project-root = (doom-project-root)
for buf in buffer-list
collect
(cl-destructuring-bind (type mode path)
(with-current-buffer buf (with-current-buffer buf
(list (concat (cond ((string-match-p "^ ?\\*" (buffer-name buf))
(let ((buffer-name (buffer-name buf)))
(propertize
buffer-name
'face (cond ((string-match-p "^ ?\\*" buffer-name)
'font-lock-comment-face) 'font-lock-comment-face)
((not (string= project-root (doom-project-root))) ((buffer-modified-p buf)
'warning) 'doom-modeline-buffer-modified)
(buffer-read-only (buffer-read-only
'error)))) 'error)))))
(when (and buffer-file-name (buffer-modified-p)) (propertize
(propertize "[+]" 'face 'doom-modeline-buffer-modified))) (format "%-40s %s%-20s %s"
(propertize (symbol-name major-mode) 'face 'font-lock-constant-face) str
(when buffer-file-name (if +ivy-buffer-icons
(abbreviate-file-name (concat (propertize " " 'display
(file-name-directory buffer-file-name))))) (or (+ivy--icon-for-mode mode)
(format (format "%%-%ds %%-%ds %%s" min-name min-mode) (+ivy--icon-for-mode (get mode 'derived-mode-parent))))
type mode (or path ""))))))) "\t")
"")
(defun +ivy--select-buffer-action (buffer) mode
(ivy--switch-buffer-action (or (and path (abbreviate-file-name (file-name-directory (file-truename path))))
(string-remove-suffix ""))
"[+]" 'face faces)))
(substring buffer 0 (string-match-p (regexp-quote " ") buffer)))))
(defun +ivy--select-buffer-other-window-action (buffer)
(ivy--switch-buffer-other-window-action
(string-remove-suffix
"[+]"
(substring buffer 0 (string-match-p (regexp-quote " ") buffer)))))
;;;###autoload ;;;###autoload
(defun +ivy/switch-workspace-buffer (&optional other-window-p) (defun +ivy/switch-workspace-buffer (&optional arg)
"Switch to an open buffer in the current workspace. "Switch to another buffer within the current workspace.
If OTHER-WINDOW-P (universal arg), then open target in other window." If ARG (universal argument), open selection in other-window."
(interactive "P") (interactive "P")
(+ivy/switch-buffer other-window-p t)) (ivy-read "Switch to workspace buffer: "
(mapcar #'buffer-name (delq (current-buffer) (doom-buffer-list)))
;;;###autoload :action (if arg
(defun +ivy/switch-buffer (&optional other-window-p workspace-only-p) #'ivy--switch-buffer-other-window-action
"Switch to an open buffer in the global buffer list. #'ivy--switch-buffer-action)
If OTHER-WINDOW-P (universal arg), then open target in other window.
If WORKSPACE-ONLY-P (universal arg), limit to buffers in the current workspace."
(interactive "P")
(ivy-read (format "%s buffers: " (if workspace-only-p "Workspace" "Global"))
(+ivy--get-buffers (unless workspace-only-p (buffer-list)))
:action (if other-window-p
#'+ivy--select-buffer-other-window-action
#'+ivy--select-buffer-action)
:matcher #'ivy--switch-buffer-matcher :matcher #'ivy--switch-buffer-matcher
:keymap ivy-switch-buffer-map :keymap ivy-switch-buffer-map
:caller #'+ivy/switch-workspace-buffer)) :caller #'+ivy/switch-workspace-buffer))

View file

@ -1,5 +1,8 @@
;;; completion/ivy/config.el -*- lexical-binding: t; -*- ;;; completion/ivy/config.el -*- lexical-binding: t; -*-
(defvar +ivy-buffer-icons nil
"If non-nil, show buffer mode icons in `ivy-switch-buffer' and the like.")
(defvar +ivy-task-tags (defvar +ivy-task-tags
'(("TODO" . warning) '(("TODO" . warning)
("FIXME" . error)) ("FIXME" . error))
@ -22,7 +25,8 @@ session)."
;; ;;
(def-package! ivy (def-package! ivy
:demand t :commands ivy-mode
:init (add-hook 'doom-init-hook #'ivy-mode)
:config :config
(setq ivy-height 12 (setq ivy-height 12
ivy-do-completion-in-region nil ivy-do-completion-in-region nil
@ -40,13 +44,11 @@ session)."
(after! magit (setq magit-completing-read-function #'ivy-completing-read)) (after! magit (setq magit-completing-read-function #'ivy-completing-read))
(after! yasnippet (push #'+ivy-yas-prompt yas-prompt-functions)) (after! yasnippet (push #'+ivy-yas-prompt yas-prompt-functions))
(add-hook 'doom-init-hook #'ivy-mode)
(map! :map ivy-mode-map (map! :map ivy-mode-map
[remap apropos] #'counsel-apropos [remap apropos] #'counsel-apropos
[remap describe-face] #'counsel-describe-face [remap describe-face] #'counsel-describe-face
[remap find-file] #'counsel-find-file [remap find-file] #'counsel-find-file
[remap switch-to-buffer] #'+ivy/switch-buffer [remap switch-to-buffer] #'ivy-switch-buffer
[remap persp-switch-to-buffer] #'+ivy/switch-workspace-buffer [remap persp-switch-to-buffer] #'+ivy/switch-workspace-buffer
[remap recentf] #'counsel-recentf [remap recentf] #'counsel-recentf
[remap imenu] #'counsel-imenu [remap imenu] #'counsel-imenu
@ -59,6 +61,12 @@ session)."
[remap describe-variable] #'counsel-describe-variable [remap describe-variable] #'counsel-describe-variable
[remap describe-face] #'counsel-describe-face) [remap describe-face] #'counsel-describe-face)
;; Show more buffer information in switch-buffer commands
(ivy-set-display-transformer 'ivy-switch-buffer #'+ivy-buffer-transformer)
(ivy-set-display-transformer 'ivy-switch-buffer-other-window #'+ivy-buffer-transformer)
(ivy-set-display-transformer '+ivy/switch-workspace-buffer #'+ivy-buffer-transformer)
(ivy-set-display-transformer 'counsel-recentf #'abbreviate-file-name)
(when (featurep! :feature workspaces) (when (featurep! :feature workspaces)
(nconc ivy-sort-functions-alist (nconc ivy-sort-functions-alist
'((persp-kill-buffer . nil) '((persp-kill-buffer . nil)

View file

@ -1,17 +1,21 @@
* :feature eval #+TITLE: :feature eval
This module adds support for: This modules adds support for REPLs, build tasks and code evaluation.
+ [[#repls][Defining, invoking & interacting with REPLs]], * Table of Contents :TOC:
+ [[#build-tasks][Defining & invoking build tasks for projects and files]], - [[#install][Install]]
+ and [[#code-evaluation][evaluating code or entire buffers, printing their output to a popup window]]. - [[#usage][Usage]]
- [[#configuration][Configuration]]
- [[#repls][REPLs]]
- [[#build-tasks][Build Tasks]]
- [[#code-evaluation][Code Evaluation]]
** Install * Install
This module has no external dependencies. However, specific languages may require additional setup. This module has no external dependencies. However, specific languages may require additional setup.
Check the README.org in that language's module for details. Check the README.org in that language's module for details.
** Usage * Usage
+ *REPLs* + *REPLs*
Invoked via: Invoked via:
+ ~:repl~ (evil ex-command) + ~:repl~ (evil ex-command)
@ -33,13 +37,15 @@ Check the README.org in that language's module for details.
+ ~M-x +eval/region-and-replace~ + ~M-x +eval/region-and-replace~
+ Evil users can use the ~gr~ operator to select and run a region. + Evil users can use the ~gr~ operator to select and run a region.
** Configuration * Configuration
*** REPLs ** REPLs
REPLs have been defined for most of the languages DOOM supports (check its README.org to see if it does). REPLs are defined for most of the languages Doom supports (check its README.org to see if it does).
Otherwise, you can define your own: Otherwise, you can define your own for a specified major-mode with the =:repl= setting.
A REPL definition consists of two parts: an interactive command that opens (and returns) a REPL buffer and a ~:repl~ definition that maps a major-mode to said command: ~(set! :repl MAJOR-MODE FUNCTION)~
FUNCTION must return the repl buffer. Any window changes are ignored, then handed off to shackle (assuming shackle-mode is on) to display in a popup window.
#+BEGIN_SRC emacs-lisp #+BEGIN_SRC emacs-lisp
(defun +emacs-lisp/repl () (defun +emacs-lisp/repl ()
@ -54,8 +60,8 @@ A REPL definition consists of two parts: an interactive command that opens (and
(set! :repl 'emacs-lisp-mode #'+emacs-lisp/repl) (set! :repl 'emacs-lisp-mode #'+emacs-lisp/repl)
#+END_SRC #+END_SRC
*** Build Tasks ** Build Tasks
A build task is little more than major-mode-local commands, comprised of an interactive command, an association with a major mode and an optional predicate function. A build task is little more than a major-mode-local interactive command that performs a task, such as compiling the current project or running unit tests. A predicate function can be supplied to ensure a command is only available when it is appropriate.
#+BEGIN_SRC emacs-lisp #+BEGIN_SRC emacs-lisp
(defun +lua/run-love () (defun +lua/run-love ()
@ -83,7 +89,7 @@ A build task is little more than major-mode-local commands, comprised of an inte
(set! :build 'generate-docs 'lua-mode #'+lua/generate-docs) (set! :build 'generate-docs 'lua-mode #'+lua/generate-docs)
#+END_SRC #+END_SRC
*** Code Evaluation ** Code Evaluation
Run regions or entire buffers with [[https://github.com/syohex/emacs-quickrun][Quickrun]]. Output will be sent to a popup window. Run regions or entire buffers with [[https://github.com/syohex/emacs-quickrun][Quickrun]]. Output will be sent to a popup window.
Quickrun includes support for many languages, but occasionally, you'll find a language without support, such as [[https://crystal-lang.org/][Crystal]]. A "runner" can be defined like so: Quickrun includes support for many languages, but occasionally, you'll find a language without support, such as [[https://crystal-lang.org/][Crystal]]. A "runner" can be defined like so:

View file

@ -1,20 +1,27 @@
* :feature evil #+TITLE: :feature evil
This holy module brings vim to Emacs. This holy module brings the vim experience to Emacs.
** Removing evil-mode * Table of Contents :TOC:
Some users want vanilla Emacs back. To do so remove =:feature evil= from init.el. Evil-specific configuration and keybindings (defined with ~map!~) will be ignored without evil present (and removed when byte-compiling). - [[#removing-evil-mode][Removing evil-mode]]
- [[#features][Features]]
- [[#multiple-cursors][Multiple-cursors]]
- [[#a-hybrid-code-folding-system][A hybrid code-folding system]]
- [[#hacks][Hacks]]
- [[#differences-from-vim][Differences from vim]]
** Differences from vanilla evil * Removing evil-mode
*** Overview To get back a more vanilla Emacs experience, remove =:feature evil= from init.el. Evil-specific configuration and keybindings (defined with ~map!~) will be ignored without evil present (and removed when byte-compiling).
+ A better ~:g[lobal]~ command with match highlighting
+ ~:al[ign]~: an ex interface to ~align-regexp~ with match highlighting * Features
+ A better ~:g[lobal]~ command with incremental highlighting.
+ Adds the ~:al[ign]~ ex command: offers an ex interface to ~align-regexp~ with incremental highlighting.
+ Support for more of vim's filename modifiers in ex commands (like ~:p~, ~:p:h~ or ~:t~) than vanilla evil-mode offers. + Support for more of vim's filename modifiers in ex commands (like ~:p~, ~:p:h~ or ~:t~) than vanilla evil-mode offers.
+ A list of new text objects: + A list of new text objects:
+ Blocks: ~B~ (from ~evil-textobj-anyblock~) + Blocks: ~B~ (from ~evil-textobj-anyblock~)
+ Args: ~a~ (from ~evil-args~) + Args: ~a~ (from ~evil-args~)
+ Indentation: ~i~ / ~I~ / ~J~ (from ~evil-indent-plus~) + Indentation: ~i~ / ~I~ / ~J~ (from ~evil-indent-plus~)
+ Ported vim plugins: + Incorporates vim functionality ported to evil:
+ ~vim-commentary~ => ~evil-commentary~ + ~vim-commentary~ => ~evil-commentary~
+ ~vim-easymotion~ => ~evil-easymotion~ + ~vim-easymotion~ => ~evil-easymotion~
+ ~vim-multiedit~ => ~evil-multiedit~ + ~vim-multiedit~ => ~evil-multiedit~
@ -23,19 +30,21 @@ Some users want vanilla Emacs back. To do so remove =:feature evil= from init.el
+ ~vim-surround~ => ~evil-embrace~ & ~evil-surround~ + ~vim-surround~ => ~evil-embrace~ & ~evil-surround~
+ =NERDTree= equivalent is available in =:tools neotree= + =NERDTree= equivalent is available in =:tools neotree=
*** Multiple-cursors ** Multiple-cursors
Two multiple-cursor implementations exist in this module: ~evil-mc~ and ~evil-multiedit~. Together, these provide the functionality of ~vim-multiple-cursors~. Two multiple-cursor implementations exist in this module: ~evil-mc~ and ~evil-multiedit~. Together, these provide the functionality of ~vim-multiple-cursors~.
The former lets you place "clone" cursors. The latter lets you interactively edit many regions from one place (like an interactive version of ~:%s~). The former lets you place "clone" cursors. The latter lets you interactively edit many regions from one place (like an interactive version of ~:%s~).
*** A saner code-folding system ** A hybrid code-folding system
This module combines ~evil-vimish-fold~ (allows arbitrary folds) and ~hideshow~ (folds based on markers and indent) to create a more consistent code-folding system. All the vim folding keys should work (=zr=, =zm=, =za=, =zo=, etc). This module combines ~evil-vimish-fold~ and ~hideshow~. The former allows arbitrary folds and the latter allows folds on markers and indentation. Together, they create a more consistent (and feature-complete) code-folding system.
*** Hacks Most vim folding keys should work, e.g. =zr=, =zm=, =za=, =zo=, etc.
** Hacks
+ Automatically moves to new window when splitting + Automatically moves to new window when splitting
+ If in visual mode, =*= and =#= will search for the current selection instead of the word-at-point. + If in visual mode, =*= and =#= will search for the current selection instead of the word-at-point.
** Differences from vim ** Differences from vim
+ Column-wise ranges in ex commands are enabled by default. i.e. the range in =:'<,'>s/a/b= will only affects the visual selection, not full lines (see ~evil-ex-visual-char-range~). + Column-wise ranges in ex commands are enabled by default. i.e. the range in =:'<,'>s/a/b= will only affects the visual selection, not full lines (see ~evil-ex-visual-char-range~).
+ =:g= will highlight buffer matches incrementally. + =:g= will incrementally highlight buffer matches.

View file

@ -323,6 +323,7 @@ the new algorithm is confusing, like in python or ruby."
evil-snipe-scope 'line evil-snipe-scope 'line
evil-snipe-repeat-scope 'visible evil-snipe-repeat-scope 'visible
evil-snipe-char-fold t evil-snipe-char-fold t
evil-snipe-disabled-modes '(magit-mode elfeed-show-mode elfeed-search-mode)
evil-snipe-aliases '((?\[ "[[{(]") evil-snipe-aliases '((?\[ "[[{(]")
(?\] "[]})]") (?\] "[]})]")
(?\; "[;:]"))) (?\; "[;:]")))

View file

@ -55,6 +55,7 @@
("-test\\.el$" "__" emacs-ert-mode) ("-test\\.el$" "__" emacs-ert-mode)
("/.emacs.d/.+\\.el$" "__doom-module" emacs-lisp-mode) ("/.emacs.d/.+\\.el$" "__doom-module" emacs-lisp-mode)
("/.emacs.d/.+/packages\\.el$" "__doom-packages" emacs-lisp-mode) ("/.emacs.d/.+/packages\\.el$" "__doom-packages" emacs-lisp-mode)
("/.emacs.d/.+/README\\.org$" "__doom-readme" org-mode)
(snippet-mode "__" snippet-mode) (snippet-mode "__" snippet-mode)
;; Go ;; Go
("\\.go$" "__.go" go-mode) ("\\.go$" "__.go" go-mode)
@ -78,6 +79,8 @@
("/conf\\.lua$" "__conf.lua" love-mode) ("/conf\\.lua$" "__conf.lua" love-mode)
;; Markdown ;; Markdown
("\\.md$" "__" markdown-mode) ("\\.md$" "__" markdown-mode)
;; Org
("\\.org$" "__" org-mode)
;; PHP ;; PHP
("\\.php$" "__" php-mode) ("\\.php$" "__" php-mode)
("\\.class\\.php$" "__.class.php" php-mode) ("\\.class\\.php$" "__.class.php" php-mode)

View file

@ -1,6 +1,6 @@
# -*- mode: snippet -*- # -*- mode: snippet -*-
# name: Org template # name: Org template
# -- # --
#+TITLE:${1:`(file-name-base buffer-file-name)`} #+TITLE: ${1:`(file-name-base buffer-file-name)`}
$0 $0

View file

@ -0,0 +1,48 @@
# -*- mode: snippet -*-
# name: Doom module readme
# --
#+TITLE: ${1:`(progn (string-match "modules/\\([^/]+\\)/\\([^/]+\\)/.+" buffer-file-name)
(format ":%s %s"
(match-string 1 buffer-file-name)
(match-string 2 buffer-file-name)))`}
${2:A short summary about what this module does.}
${3:If necessary, include a longer description below it that goes into more detail. This may be as long as you like.
+ If possible, include a list of features
+ Include links to major plugins that the module uses, if applicable
+ Use links whenever you can
+ Mention dependencies on other modules here}
* Table of Contents :TOC:
* Install
** Main dependencies
*** MacOS
#+BEGIN_SRC sh :tangle (if (doom-system-os 'macos) "yes")
brew install x
#+END_SRC
*** Arch Linux
#+BEGIN_SRC sh :dir /sudo:: :tangle (if (doom-system-os 'arch) "yes")
sudo pacman --needed --noconfirm -S X
#+END_SRC
** Extra Dependencies
+ A
+ B
+ C
#+BEGIN_SRC sh
Y install A B C
#+END_SRC
* Configuration
* Usage
* Appendix
** Commands
** Hacks
$0

View file

@ -0,0 +1,27 @@
#+TITLE: :feature snippets
This module adds snippets to Emacs, powered by yasnippet.
* Table of Contents :TOC:
- [[#install][Install]]
* Install
There are no extra dependencies for this module.
By default, this module uses the snippet library included with yasnippet.
For the best experience, I'd suggest installing mine from https://github.com/hlissner/emacs-snippets -- they have been tailored specifically for Doom.
1. Clone the repo to your private module:
#+BEGIN_SRC bash
git clone https://github.com/hlissner/emacs-snippets ~/.emacs.d/modules/private/$(whoami)/snippets
#+END_SRC
2. Tell yasnippet where to look for them:
#+BEGIN_SRC emacs-lisp
;; modules/private/{USERNAME}/config.el
(after! yasnippet
(setq yas-snippet-dirs
(append (list (expand-file-name "snippets/" (file-name-directory load-file-name)))
(delq 'yas-installed-snippets-dir yas-snippet-dirs))))
#+END_SRC

View file

@ -1,12 +1,17 @@
;;; feature/version-control/config.el -*- lexical-binding: t; -*- ;;; feature/version-control/config.el -*- lexical-binding: t; -*-
(unless (featurep! -git)
(load! +git))
;; TODO hg support
;; (unless (featurep! -hg)
;; (load! +hg))
;;
(setq vc-make-backup-files nil) (setq vc-make-backup-files nil)
(defvar +vcs-auto-hydra-smerge t (defvar +vcs-auto-hydra-smerge t
"When entering `smerge-mode' automatically open associated hydra.") "When entering `smerge-mode' automatically open associated hydra.")
(load! +git)
;; (load! +hg)
(after! vc-annotate (after! vc-annotate
(set! :popup (set! :popup

View file

@ -5,11 +5,12 @@
;; n/a ;; n/a
;;; +git ;;; +git
(package! git-gutter-fringe) (unless (featurep! -git)
(package! git-link) (package! git-gutter-fringe)
(package! git-timemachine) (package! git-link)
(package! gitconfig-mode) (package! git-timemachine)
(package! gitignore-mode) (package! gitconfig-mode)
(package! magit) (package! gitignore-mode)
(package! magit))
;;; TODO +hg ;;; TODO +hg

View file

@ -0,0 +1,75 @@
#+TITLE: :feature workspaces
This module adds support for workspaces, powered by persp_mode, as well as a unified API for manipulating them.
#+begin_quote
There are many ways to use workspaces. Some use them to group buffers/windows by project or categories (views, models, logic, etc). I use them differently: on a per-task basis, which may traverse multiple projects or aspects, but are tied to an objective. For example: implement a specific feature or fix a certain bug; sometimes unrelated to the project at hand.
#+end_quote
* Table of Contents :TOC:
- [[#install][Install]]
- [[#features][Features]]
- [[#isolated-buffer-list][Isolated buffer-list]]
- [[#automatic-workspaces][Automatic workspaces]]
- [[#session-persistence][Session persistence]]
- [[#workspace-persistence][Workspace persistence]]
- [[#appendix][Appendix]]
- [[#commands--keybindings][Commands & Keybindings]]
- [[#api][API]]
* Install
This module has no additional dependencies.
* Features
** Isolated buffer-list
When persp-mode is active, ~doom-buffer-list~ becomes workspace-restricted. You can overcome this by using ~buffer-list~.
** Automatic workspaces
A workspace is automatically created (and switched to) when you:
+ Create a new frame (with =make-frame=; bound to =M-N= by default)
+ Switch to a project using ~projectile-switch-project~ (or its ivy/helm equivalents)
** Session persistence
By default, your session is autosaved when you quit Emacs (or disable ~persp-mode~). You can load a previous session with ~M-x +workspace/load-session~ or ~:sl[oad]~ (ex command).
You can supply either a name to load a specific session to replace your current one.
** Workspace persistence
If you'd like to save a specific workspace, use ~M-x +workspace/save~, which can be loaded into the current session (as another workspace) with ~M-x +workspace/load~.
* Appendix
** Commands & Keybindings
Here is a list of available commands, their default keybindings (defined in private/hlissner/+bindings.el), and corresponding ex commands (if any -- defined in private/hlissner/+commands.el).
| command | key / ex command | description |
|---------------------------+----------------------------+------------------------------------------------------------|
| ~+workspace/new~ | =SPC TAB n= | Create a new, blank workspace |
| ~+workspace/display~ | =SPC TAB TAB= | Display open workspaces in the mode-line |
| ~+workspace/load~ | =SPC TAB l= | Load a saved workspace into the current session |
| ~+workspace/load-session~ | =SPC TAB L= / =:sl[oad]= | Replace current session with a saved one |
| ~+workspace/save~ | =SPC TAB s= | Save the current workspace to a file |
| ~+workspace/save-session~ | =SPC TAB S= / =:ss[ave]= | Save current session |
| ~+workspace/switch-to~ | =SPC TAB .= | Switch to an open workspace |
| ~+workspace/switch-left~ | =SPC TAB [= / =[ w= / =gT= | Switch to previous workspace |
| ~+workspace/switch-right~ | =SPC TAB [= / =] w= / =gt= | Switch to next workspace |
| ~+workspace/kill-session~ | =SPC TAB X= / =:sclear= | Clears the current session (kills all windows and buffers) |
** API
+ ~+workspace-list~ -> list<Struct>
+ ~+workspace-list-names~ -> list<string>
+ ~+workspace-buffer-list &optional PERSP~ -> bool
+ ~+workspace-p OBJ~ -> bool
+ ~+workspace-exists-p NAME~ -> bool
+ ~+workspace-get NAME &optional NOERROR~ -> Struct
+ ~+workspace-current &optional FRAME WINDOW~ -> Struct
+ ~+workspace-current-name~ -> string
+ ~+workspace-load NAME~
+ ~+workspace-load-session NAME~
+ ~+workspace-save NAME~
+ ~+workspace-save-session NAME~
+ ~+workspace-new NAME~
+ ~+workspace-rename NAME NEW-NAME~
+ ~+workspace-delete NAME &optional INHIBIT-KILL-P~
+ ~+workspace-switch NAME &optional AUTO-CREATE-P~
+ ~+workspace-protected-p NAME~ -> bool

View file

@ -459,12 +459,6 @@ the workspace and move to the next."
(+workspace/new) (+workspace/new)
(set-frame-parameter frame 'assoc-persp (+workspace-current-name))) (set-frame-parameter frame 'assoc-persp (+workspace-current-name)))
;;;###autoload
(defun +workspaces|create-project-workspace ()
"Create a new workspace when switching project with `projectile'."
(when persp-mode
(+workspace-switch (projectile-project-name) t)))
;;;###autoload ;;;###autoload
(defun +workspaces|delete-associated-workspace-maybe (frame) (defun +workspaces|delete-associated-workspace-maybe (frame)
"Delete workspace associated with current frame IF it has no real buffers." "Delete workspace associated with current frame IF it has no real buffers."
@ -480,3 +474,15 @@ the workspace and move to the next."
(when (doom-real-buffer-list) (when (doom-real-buffer-list)
(apply orig-fn args)) (apply orig-fn args))
t) t)
;;;###autoload
(defun +workspaces*switch-project-by-name (orig-fn &rest args)
"Switch to a project and prompt for a file to open.
Ensures the scratch (or dashboard) buffers are CDed into the project's root."
(when persp-mode
(+workspace-switch (car args) t)
(with-current-buffer (switch-to-buffer (doom-fallback-buffer))
(setq default-directory (car args))))
(apply orig-fn args))

View file

@ -10,7 +10,7 @@
;; load the last autosaved session. You can give sessions a custom name so they ;; load the last autosaved session. You can give sessions a custom name so they
;; can be loaded later. ;; can be loaded later.
;; ;;
;; FYI persp-mode requires `workgroups' for file persistence in Emacs 24.4. ;; NOTE persp-mode requires `workgroups' for file persistence in Emacs 24.4.
(defvar +workspaces-main "main" (defvar +workspaces-main "main"
"The name of the primary and initial workspace, which cannot be deleted or "The name of the primary and initial workspace, which cannot be deleted or
@ -41,16 +41,17 @@ renamed.")
persp-auto-save-opt (if noninteractive 0 1)) persp-auto-save-opt (if noninteractive 0 1))
;; Bootstrap ;; Bootstrap
(add-hook 'doom-init-hook #'+workspaces|init) (add-hook 'doom-post-init-hook #'+workspaces|init)
(add-hook 'after-make-frame-functions #'+workspaces|init) (add-hook 'after-make-frame-functions #'+workspaces|init)
(define-key persp-mode-map [remap delete-window] #'+workspace/close-window-or-workspace) (define-key persp-mode-map [remap delete-window] #'+workspace/close-window-or-workspace)
;; per-frame workspaces ;; per-frame and per-project workspaces
(setq persp-init-new-frame-behaviour-override nil (setq persp-init-new-frame-behaviour-override nil
persp-interactive-init-frame-behaviour-override #'+workspace-on-new-frame) persp-interactive-init-frame-behaviour-override #'+workspace-on-new-frame
(add-hook 'projectile-before-switch-project-hook #'+workspaces|create-project-workspace) projectile-switch-project-action #'projectile-find-file)
(add-hook 'delete-frame-functions #'+workspaces|delete-associated-workspace-maybe) (add-hook 'delete-frame-functions #'+workspaces|delete-associated-workspace-maybe)
(advice-add #'projectile-switch-project-by-name :around #'+workspaces*switch-project-by-name)
;; only auto-save when real buffers are present ;; only auto-save when real buffers are present
(advice-add #'persp-asave-on-exit :around #'+workspaces*autosave-real-buffers) (advice-add #'persp-asave-on-exit :around #'+workspaces*autosave-real-buffers)

View file

@ -1,4 +1,4 @@
* :lang cc #+TITLE: :lang cc
This module adds support for the C-family of languages: C, C++, and Objective-C. This module adds support for the C-family of languages: C, C++, and Objective-C.
@ -8,17 +8,23 @@ This module adds support for the C-family of languages: C, C++, and Objective-C.
+ Code navigation (~irony~) + Code navigation (~irony~)
+ File Templates ([[../../feature/file-templates/templates/c-mode][c-mode]], [[../../feature/file-templates/templates/c++-mode][c++-mode]]) + File Templates ([[../../feature/file-templates/templates/c-mode][c-mode]], [[../../feature/file-templates/templates/c++-mode][c++-mode]])
+ Snippets ([[https://github.com/hlissner/emacs-snippets/tree/master/cc-mode][cc-mode]], [[https://github.com/hlissner/emacs-snippets/tree/master/c-mode][c-mode]], [[https://github.com/hlissner/emacs-snippets/tree/master/c++-mode][c++-mode]]) + Snippets ([[https://github.com/hlissner/emacs-snippets/tree/master/cc-mode][cc-mode]], [[https://github.com/hlissner/emacs-snippets/tree/master/c-mode][c-mode]], [[https://github.com/hlissner/emacs-snippets/tree/master/c++-mode][c++-mode]])
+ Several improvements to C++11 indentation and syntax highlighting.
#+begin_quote #+begin_quote
C contends with Haskell and Ruby for my favorite language. It's hard to beat this combination of simplicity and power. I've used C for my work since 2009, and it (along with C++) is a personal favorite for game development (with SDL, SFML or, more recently, cocos2d). C contends with Haskell and Ruby for my favorite language. That said, it's more accurate to say I write C, but with two or three C++ features.
The module provides nominal support for Objective-C, which I really only use to inspect generated glue code for iOS mobile apps. Otherwise, I prefer Swift. The module provides nominal support for Objective-C, which I really only use to inspect generated glue code for iOS mobile apps. Otherwise, I prefer Swift.
#+end_quote #+end_quote
** Install * Table of Contents :TOC:
- [[#install][Install]]
- [[#macos][MacOS]]
- [[#arch-linux][Arch Linux]]
* Install
This module requires ~irony-server~ for most of its features, which depends on ~cmake~ and ~libclang~. This module requires ~irony-server~ for most of its features, which depends on ~cmake~ and ~libclang~.
*** MacOS ** MacOS
Due to linking issues, MacOS users must compile irony-server manually: Due to linking issues, MacOS users must compile irony-server manually:
#+BEGIN_SRC sh :tangle (if (doom-system-os 'macos) "yes") #+BEGIN_SRC sh :tangle (if (doom-system-os 'macos) "yes")
@ -43,9 +49,10 @@ popd
rm -rf irony-mode rm -rf irony-mode
#+END_SRC #+END_SRC
*** Arch Linux ** Arch Linux
#+BEGIN_SRC sh :tangle (if (doom-system-os 'arch) "yes") #+BEGIN_SRC sh :tangle (if (doom-system-os 'arch) "yes")
sudo pacman --needed --noconfirm -S clang cmake sudo pacman --needed --noconfirm -S clang cmake
#+END_SRC #+END_SRC
Then run ~M-x irony-install-server~ in Emacs. Then run ~M-x irony-install-server~ in Emacs.

View file

@ -1,5 +1,18 @@
;;; lang/cc/autoload.el -*- lexical-binding: t; -*- ;;; lang/cc/autoload.el -*- lexical-binding: t; -*-
;;;###autoload
(defun +cc*lineup-arglist (orig-fun &rest args)
"Improve indentation of continued C++11 lambda function opened as argument."
(if (and (eq major-mode 'c++-mode)
(ignore-errors
(save-excursion
(goto-char (c-langelem-pos langelem))
;; Detect "[...](" or "[...]{". preceded by "," or "(",
;; and with unclosed brace.
(looking-at-p ".*[(,][ \t]*\\[[^]]*\\][ \t]*[({][^}]*$"))))
0 ; no additional indent
(apply orig-fun args)))
;;;###autoload ;;;###autoload
(defun +cc/autoclose->-maybe () (defun +cc/autoclose->-maybe ()
"For some reason smartparens won't autoskip >'s, this hack does." "For some reason smartparens won't autoskip >'s, this hack does."

View file

@ -49,7 +49,7 @@
(sp-local-pair "/*!" "*/" :post-handlers '(("||\n[i]" "RET") ("[d-1]< | " "SPC")))) (sp-local-pair "/*!" "*/" :post-handlers '(("||\n[i]" "RET") ("[d-1]< | " "SPC"))))
;; Improve indentation of inline lambdas in C++11 ;; Improve indentation of inline lambdas in C++11
(advice-add #'c-lineup-arglist :around #'+c-lineup-arglist) (advice-add #'c-lineup-arglist :around #'+cc*lineup-arglist)
;; C/C++ style settings ;; C/C++ style settings
(c-toggle-electric-state -1) (c-toggle-electric-state -1)
@ -76,7 +76,7 @@
(c-set-offset 'inclass #'+cc--c-lineup-inclass) (c-set-offset 'inclass #'+cc--c-lineup-inclass)
;; Certain mappings interfere with smartparens and custom bindings, ;; Certain electric mappings interfere with smartparens and custom bindings,
;; so unbind them ;; so unbind them
(map! :map c-mode-map (map! :map c-mode-map
"DEL" nil "DEL" nil

View file

@ -1,4 +1,4 @@
* :lang go #+TITLE: :lang go
This module adds [[https://golang.org][Go]] support. This module adds [[https://golang.org][Go]] support.
@ -13,12 +13,18 @@ This module adds [[https://golang.org][Go]] support.
+ [[https://github.com/hlissner/emacs-snippets/tree/master/go-mode][Snippets]] + [[https://github.com/hlissner/emacs-snippets/tree/master/go-mode][Snippets]]
#+begin_quote #+begin_quote
I have mixed feelings about Go. It's a decent compromise between C and higher-level languages. It's a pleasantly straight-forward language with elegant syntax, but it lacks /native/ support for certain luxuries I miss from other languages, like generics, optional arguments, and function overloading. You've got to learn to love ~interface{}~. I have mixed feelings about Go. It's a decent compromise between C and higher-level languages, is pleasantly straight-forward and elegant, but lacks /native/ support for luxuries I miss from other languages, like generics, optional arguments, and function overloading. You've got to learn to love ~interface{}~.
Still, Go has been a remarkably useful (and fast!) companion for a variety of small-to-medium backend web and CLI projects. Still, Go has been a remarkably useful (and fast!) companion for a variety of small-to-medium backend web and CLI projects.
#+end_quote #+end_quote
** Install * Table of Contents :TOC:
- [[#install][Install]]
- [[#go][Go]]
- [[#dependencies][Dependencies]]
* Install
** Go
To get started with Go, you need the ~go~ tool: To get started with Go, you need the ~go~ tool:
*** MacOS *** MacOS

View file

@ -0,0 +1,13 @@
;;; lang/haskell/+dante.el -*- lexical-binding: t; -*-
(def-package! dante
:after haskell-mode
:init
(add-hook! 'haskell-mode-hook #'(dante-mode interactive-haskell-mode))
:config
(unless (executable-find "cabal")
(warn "haskell-mode: couldn't find cabal")
(remove-hook 'haskell-mode-hook #'dante-mode))
(add-hook 'dante-mode-hook #'flycheck-mode))

View file

@ -0,0 +1,21 @@
;;; lang/haskell/+intero.el -*- lexical-binding: t; -*-
(def-package! intero
:commands intero-mode
:init
(add-hook 'haskell-mode-hook #'intero-mode)
:config
(unless (executable-find "stack")
(warn "haskell-mode: couldn't find stack, disabling intero")
(remove-hook 'haskell-mode-hook #'intero-mode))
(add-hook! 'intero-mode-hook #'(flycheck-mode eldoc-mode))
(set! :popup "^intero:backend:" :regex t :size 12)
(set! :jump :definition #'intero-goto-definition))
(def-package! hindent
:commands hindent-mode
:init
(add-hook 'haskell-mode-hook #'hindent-mode))

View file

@ -1,4 +1,4 @@
* :lang haskell #+TITLE: :lang haskell
This module adds [[https://www.haskell.org/][Haskell]] support. This module adds [[https://www.haskell.org/][Haskell]] support.
@ -11,52 +11,55 @@ This module adds [[https://www.haskell.org/][Haskell]] support.
+ [[https://github.com/hlissner/emacs-snippets/tree/master/haskell-mode][Snippets]] + [[https://github.com/hlissner/emacs-snippets/tree/master/haskell-mode][Snippets]]
#+begin_quote #+begin_quote
Haskell contends with C and Ruby as my favorite language. I don't think my Haskell code will ever save the world, but I'll reach for it when working on smaller projects and programming exercises (like projecteuler.com or exercism.io). Haskell contends with C and Ruby as my favorite language. I don't think my Haskell code will ever save the world, but I'll reach for it for small projects and programming exercises (like projecteuler.com or exercism.io).
I'd love to incorporate more of it into my machine learning work, but Python and Julia hold that crown. For now. I'd love to incorporate more of it into my machine learning work, but Python and Julia hold that crown. For now.
#+end_quote #+end_quote
** Install * Table of Contents :TOC:
To get started with Haskell, you need: - [[#install][Install]]
- [[#haskell][Haskell]]
- [[#dependencies][Dependencies]]
- [[#troubleshooting][Troubleshooting]]
- [[#resources][Resources]]
+ cabal (the haskell package builder) * Install
+ ghc/ghci (the compiler, syntax checker & repl) ** Haskell
To get started with Haskell, you need *stack* installed.
*** MacOS *** MacOS
#+BEGIN_SRC sh :tangle (if (doom-system-os 'macos) "yes") #+BEGIN_SRC sh :tangle (if (doom-system-os 'macos) "yes")
brew install cabal-install ghc brew install haskell-stack
stack setup
#+END_SRC #+END_SRC
*** Arch Linux *** Arch Linux
#+BEGIN_SRC sh :dir /sudo:: :tangle (if (doom-system-os 'arch) "yes") #+BEGIN_SRC sh :dir /sudo:: :tangle (if (doom-system-os 'arch) "yes")
sudo pacman --needed --noconfirm -S cabal-install ghc sudo pacman --needed --noconfirm -S stack
# Replace pacaur with your AUR package manager of choice
pacaur --needed --noconfirm -S ncurses5-compat-lib
stack setup
#+END_SRC #+END_SRC
** Dependencies ** Dependencies
This module requires the following ~cabal~ packages: This module requires ~ghc-mod~ (as well as ~intero~, but those will be automatically installed).
+ ~happy~ (required by ~haskell-src-exts~)
+ ~haskell-src-exts~ (required by ~ghc-mod~ & ~hoogle~)
+ ~ghc-mod~ (for auto-completion)
+ ~hoogle~ (for documentation lookup)
#+BEGIN_SRC sh #+BEGIN_SRC sh
cabal update stack install ghc-mod
cabal install happy haskell-src-exts ghc-mod hoogle
#+END_SRC #+END_SRC
Ensure that ~\~/.cabal/bin~ is in ~PATH~: Also ensure that ~\~/.local/bin~ is in ~PATH~:
#+BEGIN_SRC sh #+BEGIN_SRC sh
# place this in your profile file, like ~/.bash_profile or ~/.zshenv # place this in your profile file, like ~/.bash_profile or ~/.zshenv
export PATH="~/.cabal/bin:$PATH" export PATH="~/.local/bin:$PATH"
#+END_SRC #+END_SRC
** Troubleshooting * Troubleshooting
+ Stack users: if a ~dist/setup-config~ file exists in your project, [[ https://github.com/DanielG/ghc-mod/wiki#known-issues-related-to-stack][ghc-mod may + Stack users: if a ~dist/setup-config~ file exists in your project, [[ https://github.com/DanielG/ghc-mod/wiki#known-issues-related-to-stack][ghc-mod may
refuse to work]]. refuse to work]].
** Resources * Resources
Here are a few resources I've found indespensible in my Haskell adventures: Here are a few resources I've found indespensible in my Haskell adventures:
+ [[http://learnyouahaskell.com/][Learn you a haskell for great good]] + [[http://learnyouahaskell.com/][Learn you a haskell for great good]]

View file

@ -17,21 +17,21 @@
(map! :map inf-haskell-mode-map "ESC ESC" #'doom/popup-close))) (map! :map inf-haskell-mode-map "ESC ESC" #'doom/popup-close)))
(def-package! dante
:after haskell-mode
:config
(if (executable-find "cabal")
(add-hook! 'haskell-mode-hook
#'(flycheck-mode dante-mode interactive-haskell-mode))
(warn "haskell-mode: couldn't find cabal")))
(def-package! company-ghc (def-package! company-ghc
:when (featurep! :completion company) :when (featurep! :completion company)
:after haskell-mode :after haskell-mode
:config :init
(set! :company-backend 'haskell-mode #'company-ghc)
(setq company-ghc-show-info 'oneline)
(if (executable-find "ghc-mod")
(add-hook 'haskell-mode-hook #'ghc-comp-init) (add-hook 'haskell-mode-hook #'ghc-comp-init)
(warn "haskell-mode: couldn't find ghc-mode"))) :config
(if (executable-find "ghc-mod")
(set! :company-backend 'haskell-mode #'company-ghc)
(warn "haskell-mode: couldn't find ghc-mode")
(remove-hook 'haskell-mode-hook #'ghc-comp-init))
(setq company-ghc-show-info 'oneline))
;;
(if (featurep! +dante)
(load! +dante)
(load! +intero))

View file

@ -2,7 +2,13 @@
;;; lang/haskell/packages.el ;;; lang/haskell/packages.el
(package! haskell-mode) (package! haskell-mode)
(package! dante)
(when (featurep! :completion company) (when (featurep! :completion company)
(package! company-ghc)) (package! company-ghc))
;;
(cond ((featurep! +dante)
(package! dante))
(t
(package! intero)
(package! hindent)))

View file

@ -1,16 +0,0 @@
# javascript
Javascript support, including auto-completion (tern), REPL support
(nodejs-repl), refactoring commands (js2-refactor), and syntax checking
(flycheck).
Includes coffescript and jsx support, as well as project minor modes for nodejs
projects (with a package.json) or launchbar 6 actions.
## External Dependencies
Run `make bootstrap js` to install these.
+ NodeJS & NPM (`brew install node`, `pacman -S nodejs npm`)
+ tern: `npm -g install tern` (for completion)

View file

@ -0,0 +1,46 @@
#+TITLE: :lang javascript
This module adds Javascript support.
+ Code completion (tern)
+ REPL support (nodejs-repl)
+ Refactoring commands (js2-refactor)
+ Syntax checking (flycheck)
+ Browser code injection with skewer-mode
+ Coffeescript & JSX support
+ Jump-to-definitions and references support (xref)
* Table of Contents :TOC:
- [[#install][Install]]
- [[#node--npm][Node & NPM]]
- [[#dependencies][Dependencies]]
- [[#appendix][Appendix]]
- [[#commands][Commands]]
* Install
** Node & NPM
To get started with Javascript, you'll need node and its package manager, NPM, installed.
*** MacOS
#+BEGIN_SRC sh :tangle (if (doom-system-os 'macos) "yes")
brew install node
#+END_SRC
*** Arch Linux
#+BEGIN_SRC sh :dir /sudo:: :tangle (if (doom-system-os 'arch) "yes")
sudo pacman --needed --noconfirm -S nodejs npm
#+END_SRC
** Dependencies
This module optionally requires ~tern~ for code completion.
#+BEGIN_SRC sh
npm -g install tern
#+END_SRC
* Appendix
** Commands
| command | key / ex command | description |
|----------------------------------+------------------+------------------------------------------------------------|
| ~+javascript/repl~ | =:repl= | Open the NodeJS REPL (or send the current selection to it) |
| ~+javascript/skewer-this-buffer~ | =SPC m S= | Attaches a browser to the current buffer |

View file

@ -119,8 +119,9 @@
(set! :electric 'rjsx-mode :chars '(?\} ?\) ?. ?>)) (set! :electric 'rjsx-mode :chars '(?\} ?\) ?. ?>))
;; disable electric keys (I use snippets and `emmet-mode' instead) ;; disable electric keys (I use snippets and `emmet-mode' instead)
(define-key rjsx-mode-map "<" nil) (map! :map rjsx-mode-map
(define-key rjsx-mode-map (kbd "C-d") nil) "<" nil
"C-d" nil)
(add-hook! rjsx-mode (add-hook! rjsx-mode
;; jshint doesn't really know how to deal with jsx ;; jshint doesn't really know how to deal with jsx
(push 'javascript-jshint flycheck-disabled-checkers))) (push 'javascript-jshint flycheck-disabled-checkers)))

View file

@ -1,9 +1,9 @@
;;; lang/markdown/config.el -*- lexical-binding: t; -*- ;;; lang/markdown/config.el -*- lexical-binding: t; -*-
(def-package! markdown-mode (def-package! markdown-mode
:mode ("/README\\.md$" . gfm-mode)
:mode "\\.m\\(d\\|arkdown\\)$"
:mode "/README$" :mode "/README$"
:mode "\\.m\\(d\\|arkdown\\)$"
:mode ("/README\\.md$" . gfm-mode)
:init :init
(setq markdown-enable-wiki-links t (setq markdown-enable-wiki-links t
markdown-enable-math t markdown-enable-math t
@ -20,14 +20,7 @@
(setq line-spacing 2 (setq line-spacing 2
fill-column 80)) fill-column 80))
(sp-local-pair (map! (:map markdown-mode-map
'(markdown-mode gfm-mode)
"\`\`\`" "\`\`\`" :post-handlers '(("||\n" "RET")))
(map! (:map gfm-mode-map
"`" #'self-insert-command)
(:map markdown-mode-map
[remap find-file-at-point] #'markdown-follow-thing-at-point [remap find-file-at-point] #'markdown-follow-thing-at-point
"M-*" #'markdown-insert-list-item "M-*" #'markdown-insert-list-item
"M-b" #'markdown-insert-bold "M-b" #'markdown-insert-bold

View file

@ -0,0 +1,13 @@
#+TITLE: :lang perl
This module adds support for Perl 6, and flycheck support for all versions of Perl.
* Table of Contents :TOC:
- [[#install][Install]]
* Install
This module depends on perl itself. Perl <5 typically comes bundled with most OSes and Linux distros.
You'll have to install
There are no other dependencies.

View file

@ -1,4 +1,4 @@
* :lang php #+TITLE: :lang php
This module adds support for PHP 5.3+ (including PHP7). This module adds support for PHP 5.3+ (including PHP7).
@ -12,14 +12,18 @@ This module adds support for PHP 5.3+ (including PHP7).
+ [[https://github.com/hlissner/emacs-snippets/tree/master/php-mode][Snippets]] + [[https://github.com/hlissner/emacs-snippets/tree/master/php-mode][Snippets]]
#+begin_quote #+begin_quote
PHP was the first programming language I got paid to code in, back in the Cretaceous period (2003). I'm so, so sorry. All those programmers who inherited my earliest PHP work. I know you're out there, writhing in your straitjackets. PHP was the first programming language I got paid to code in, back in the Cretaceous period (2003). My sincerest apologies go out to all the programmers who inherited my earliest PHP work. I know you're out there, writhing in your straitjackets.
I suppose it's hip for programmers to projectile vomit to any mention of PHP, but they have good reason to. Not because it's /necessarily/ a bad language, and not /just/ because of a couple inconsistently ordered parameters, but because it's too easy to make junk with. You've heard the war stories.
Save a programmer today. Stop a friend from choosing PHP as their first language. Save a programmer today. Stop a friend from choosing PHP as their first language.
#+end_quote #+end_quote
** Install * Table of Contents :TOC:
- [[#install][Install]]
- [[#php][PHP]]
- [[#dependencies][Dependencies]]
* Install
** PHP
To get started with PHP, you'll need ~php~ (5.3+) and ~composer~: To get started with PHP, you'll need ~php~ (5.3+) and ~composer~:
*** MacOS *** MacOS
@ -37,7 +41,7 @@ sudo pacman --needed --noconfirm -S php composer # or php53, php54, php55
#+END_SRC #+END_SRC
** Dependencies ** Dependencies
The features in this module optionally depends on the following php packages: The features in this module optionally depend on the following php packages:
+ ~boris~ (REPL) + ~boris~ (REPL)
+ ~phpctags~ (better code completion) + ~phpctags~ (better code completion)

View file

@ -12,7 +12,6 @@
(set! :repl 'python-mode #'+python/repl) (set! :repl 'python-mode #'+python/repl)
(set! :electric 'python-mode :chars '(?:)) (set! :electric 'python-mode :chars '(?:))
(define-key python-mode-map (kbd "DEL") nil) ; interferes with smartparens
(when (executable-find "ipython") (when (executable-find "ipython")
(setq python-shell-interpreter "ipython" (setq python-shell-interpreter "ipython"
@ -25,6 +24,7 @@
python-shell-completion-string-code python-shell-completion-string-code
"';'.join(get_ipython().Completer.all_completions('''%s'''))\n")) "';'.join(get_ipython().Completer.all_completions('''%s'''))\n"))
(define-key python-mode-map (kbd "DEL") nil) ; interferes with smartparens
(sp-with-modes 'python-mode (sp-with-modes 'python-mode
(sp-local-pair "'" nil :unless '(sp-point-before-word-p sp-point-after-word-p sp-point-before-same-p)))) (sp-local-pair "'" nil :unless '(sp-point-before-word-p sp-point-after-word-p sp-point-before-same-p))))
@ -50,9 +50,11 @@
:after anaconda-mode :after anaconda-mode
:config :config
(set! :company-backend 'python-mode '(company-anaconda)) (set! :company-backend 'python-mode '(company-anaconda))
(set! :jump 'python-mode
:definition #'anaconda-mode-find-definitions
:references #'anaconda-mode-find-referenences
:documentation #'anaconda-mode-show-doc)
(map! :map python-mode-map (map! :map python-mode-map
:m "gd" #'anaconda-mode-find-definitions
:m "gD" #'anaconda-mode-find-references
:localleader :localleader
:prefix "f" :prefix "f"
:nv "d" #'anaconda-mode-find-definitions :nv "d" #'anaconda-mode-find-definitions

View file

@ -1,4 +1,4 @@
* :lang rest #+TITLE: :lang rest
This module adds [[https://en.wikipedia.org/wiki/Representational_state_transfer][REST]] support. This module adds [[https://en.wikipedia.org/wiki/Representational_state_transfer][REST]] support.
@ -10,10 +10,14 @@ This module adds [[https://en.wikipedia.org/wiki/Representational_state_transfer
~restclient-mode~ is tremendously useful for testing REST APIs. My workflow is to open an ~org-mode~ buffer, create a restclient source block and hack away. ~restclient-mode~ and ~company-restclient~ power this arcane wizardry. ~restclient-mode~ is tremendously useful for testing REST APIs. My workflow is to open an ~org-mode~ buffer, create a restclient source block and hack away. ~restclient-mode~ and ~company-restclient~ power this arcane wizardry.
#+end_quote #+end_quote
** Install * Table of Contents :TOC:
- [[#install][Install]]
- [[#example][Example]]
* Install
No additional setup required. No additional setup required.
** Example * Example
#+BEGIN_SRC restclient #+BEGIN_SRC restclient
GET https://jsonplaceholder.typicode.com/posts/1 GET https://jsonplaceholder.typicode.com/posts/1
#+END_SRC #+END_SRC

View file

@ -0,0 +1,22 @@
#+TITLE: :lang sh
This module adds support for shell scripting languages.
+ Code completion (company-shell)
+ Syntax Checking (flycheck)
+ Added command substitution and variable interpolation fontification
+ REPL support
* Table of Contents :TOC:
- [[#install][Install]]
- [[#appendix][Appendix]]
- [[#commands][Commands]]
* Install
This module has no dependencies.
* Appendix
** Commands
| command | key / ex command | description |
|------------+------------------+-------------------------------------------------------|
| ~+sh/repl~ | =:repl= | Open a terminal (or send the current selection to it) |

View file

@ -35,6 +35,9 @@
(,(regexp-opt +sh-builtin-keywords 'words) (,(regexp-opt +sh-builtin-keywords 'words)
(0 'font-lock-builtin-face append)))) (0 'font-lock-builtin-face append))))
;; autoclose backticks
(sp-local-pair 'sh-mode "`" nil :unless '(sp-point-before-word-p sp-point-before-same-p))
;; sh-mode has file extensions checks for other shells, but not zsh, so... ;; sh-mode has file extensions checks for other shells, but not zsh, so...
(defun +sh|detect-zsh () (defun +sh|detect-zsh ()
(when (or (and buffer-file-name (when (or (and buffer-file-name

View file

@ -1,12 +0,0 @@
#!/usr/bin/env bash
source VARS
#
echo "Setting up zsh/bash (zshdb, bashdb)"
if is-mac; then
brew install zshdb bashdb
elif is-arch; then
sudo pacman --noconfirm -S zshdb bashdb
fi

View file

@ -146,7 +146,7 @@ wrong places)."
'(table table-row headline inlinetask item plain-list) '(table table-row headline inlinetask item plain-list)
t)) t))
(type (org-element-type context))) (type (org-element-type context)))
(cond ((eq type 'item) (cond ((memq type '(item plain-list))
(let ((marker (org-element-property :bullet context)) (let ((marker (org-element-property :bullet context))
(pad (save-excursion (pad (save-excursion
(back-to-indentation) (back-to-indentation)
@ -157,7 +157,7 @@ wrong places)."
(insert (concat "\n" (make-string pad ? ) marker))) (insert (concat "\n" (make-string pad ? ) marker)))
('above ('above
(goto-char (line-beginning-position)) (goto-char (line-beginning-position))
(insert (make-string pad ? ) marker) (insert (make-string pad 32) (or marker ""))
(save-excursion (insert "\n"))))) (save-excursion (insert "\n")))))
(when (org-element-property :checkbox context) (when (org-element-property :checkbox context)
(insert "[ ] "))) (insert "[ ] ")))
@ -167,15 +167,13 @@ wrong places)."
('below (org-table-insert-row t)) ('below (org-table-insert-row t))
('above (+org/table-prepend-row-or-shift-up)))) ('above (+org/table-prepend-row-or-shift-up))))
((memq type '(headline inlinetask plain-list)) ((memq type '(headline inlinetask))
(let* ((subcontext (org-element-context)) (let* ((subcontext (org-element-context))
(level (save-excursion (level (save-excursion
(org-back-to-heading) (org-back-to-heading)
(org-element-property
:level
(if (eq (org-element-type subcontext) 'headline) (if (eq (org-element-type subcontext) 'headline)
subcontext (org-element-property :level subcontext)
1))))) 1))))
(pcase direction (pcase direction
('below ('below
(let ((at-eol (= (point) (1- (line-end-position))))) (let ((at-eol (= (point) (1- (line-end-position)))))

View file

@ -98,6 +98,7 @@
org-cycle-separator-lines 1 org-cycle-separator-lines 1
;; org-ellipsis "  " ;; org-ellipsis "  "
org-entities-user '(("flat" "\\flat" nil "" "" "266D" "") ("sharp" "\\sharp" nil "" "" "266F" "")) org-entities-user '(("flat" "\\flat" nil "" "" "266D" "") ("sharp" "\\sharp" nil "" "" "266F" ""))
org-ellipsis ""
org-fontify-done-headline t org-fontify-done-headline t
org-fontify-quote-and-verse-blocks t org-fontify-quote-and-verse-blocks t
org-fontify-whole-heading-line t org-fontify-whole-heading-line t
@ -132,65 +133,22 @@
(when (or (featurep! :completion ivy) (when (or (featurep! :completion ivy)
(featurep! :completion helm)) (featurep! :completion helm))
(setq-default org-completion-use-ido nil (setq-default org-completion-use-ido nil
org-outline-path-complete-in-steps nil)) org-outline-path-complete-in-steps nil)))
;; Custom fontification
(defsubst +org--tag-face (n)
(let ((kwd (match-string n)))
(or (and (equal kwd "#") 'org-tag)
(and (equal kwd "@") 'org-special-keyword))))
(defun +org|init-custom-fontification ()
"Correct (and improve) org-mode's font-lock keywords.
1. Re-set `org-todo' & `org-headline-done' faces, to make them respect
underlying faces.
2. Fontify item bullets
3. Fontify item checkboxes (and when they're marked done)
4. Fontify dividers/separators (5+ dashes)
5. Fontify #hashtags and @at-tags, for personal convenience"
(let ((org-todo (format org-heading-keyword-regexp-format
org-todo-regexp))
(org-done (format org-heading-keyword-regexp-format
(concat "\\(?:" (mapconcat #'regexp-quote org-done-keywords "\\|") "\\)"))))
(setq
org-font-lock-extra-keywords
(append (org-delete-all
`(("\\[\\([0-9]*%\\)\\]\\|\\[\\([0-9]*\\)/\\([0-9]*\\)\\]"
(0 (org-get-checkbox-statistics-face) t))
(,org-todo (2 (org-get-todo-face 2) t))
(,org-done (2 'org-headline-done t)))
org-font-lock-extra-keywords)
`((,org-todo (2 (org-get-todo-face 2) prepend))
(,org-done (2 'org-headline-done prepend))
;; Make checkbox statistic cookies respect underlying faces
("\\[\\([0-9]*%\\)\\]\\|\\[\\([0-9]*\\)/\\([0-9]*\\)\\]"
(0 (org-get-checkbox-statistics-face) prepend))
;; I like how org-mode fontifies checked TODOs and want this to extend to
;; checked checkbox items:
("^[ \t]*\\(?:[-+*]\\|[0-9]+[).]\\)[ \t]+\\(\\(?:\\[@\\(?:start:\\)?[0-9]+\\][ \t]*\\)?\\[\\(?:X\\|\\([0-9]+\\)/\\2\\)\\][^\n]*\n\\)"
1 'org-headline-done prepend)
;; make plain list bullets stand out
("^ *\\([-+]\\|[0-9]+[).]\\) " 1 'org-list-dt append)
;; and separators/dividers
("^ *\\(-----+\\)$" 1 'org-meta-line)
;; custom #hashtags & @at-tags for another level of organization
("\\s-\\(\\([#@]\\)[^ \n.,]+\\)" 1 (+org--tag-face 2)))))))
(add-hook 'org-font-lock-set-keywords-hook #'+org|init-custom-fontification))
(defun +org-init-keybinds () (defun +org-init-keybinds ()
"Sets up org-mode and evil keybindings. Tries to fix the idiosyncrasies "Sets up org-mode and evil keybindings. Tries to fix the idiosyncrasies
between the two." between the two."
(map! (:map org-mode-map "RET" #'org-return-indent) (map! (:map org-mode-map
"RET" #'org-return-indent)
(:map +org-evil-mode-map (:map +org-evil-mode-map
:n "RET" #'+org/dwim-at-point :n "RET" #'+org/dwim-at-point
;; Navigate table cells (from insert-mode) ;; Navigate table cells (from insert-mode)
:i "C-L" #'+org/table-next-field :i "C-l" #'+org/table-next-field
:i "C-H" #'+org/table-previous-field :i "C-h" #'+org/table-previous-field
:i "C-K" #'+org/table-previous-row :i "C-k" #'+org/table-previous-row
:i "C-J" #'+org/table-next-row :i "C-j" #'+org/table-next-row
;; Expand tables (or shiftmeta move) ;; Expand tables (or shiftmeta move)
:ni "C-S-l" #'+org/table-append-field-or-shift-right :ni "C-S-l" #'+org/table-append-field-or-shift-right
:ni "C-S-h" #'+org/table-prepend-field-or-shift-left :ni "C-S-h" #'+org/table-prepend-field-or-shift-left

View file

@ -1,61 +1,8 @@
* :private #+TITLE: :private modules
Modules here represent all your personal customizations. I suggest you keep them contained here to minimize friction when updating from upstream (if that matters to you).
I include my private module as a reference. I recommend you don't delete/rename it as that could cause merge conflicts. Use this directory to store your private configuration modules.
** Loading your private module Mine is included as a reference. I recommend you neither delete nor rename it, to avoid merge conflicts upstream.
~:private {user-login-name}~ is loaded automatically after all other modules.
Keeping it in your init.el is unnecessary, but harmless. -----
You'll find [[/wiki/Customization][more information about customizing Doom]] on the [[/wiki][wiki]].
~private/{user-login-name}/init.el~ is a special file, unique to the private module named after your username in ~user-login-name~. It is loaded immediately after DOOM core is, but before any module is. This gives you an opportunity to overwrite variables and settings earlier. I will refer to this as your "private init.el".
** Reconfiguring packages
If your configuration needs are simple, ~add-hook!~ and ~after!~ will be sufficient to reconfigure packages:
#+BEGIN_SRC emacs-lisp
;; private/hlissner/config.el
(after! evil
(setq evil-magic nil))
;; Takes a major-mode or a quoted hook function
(add-hook! python-mode
(setq python-shell-interpreter "bpython"))
#+END_SRC
Look into ~def-package-hook!~ if you need more customizability. It lets you disable, add to or overwrite DOOM's ~def-package!~ blocks. These are powered by ~use-package~'s inject-hooks under the hood.
*They must be used from your private init.el to work.*
#+BEGIN_SRC emacs-lisp
;; private/hlissner/init.el
;; To disable a package
(def-package-hook! evil-goggles :disable)
;; If a :pre-init / :pre-config hook returns nil, it overwrites that
;; package's original :init / :config block. Exploit this to overwrite
;; DOOM's config. Otherwise, make sure they always return non-nil!
(def-package-hook! doom-themes
:post-config
(setq doom-neotree-file-icons t)
nil)
;; Otherwise, you append to a packages config
(def-package-hook! evil
:post-init
(setq evil-magic nil)
t)
#+END_SRC
** Installing your own packages
Your private module is otherwise like any other module. It may possess a packages.el file, which -- with the advantage of being loaded last -- may be used not only to install your own packages, but overwrite past ~package!~ declarations.
#+BEGIN_SRC emacs-lisp
;; prevent a certain package from being installed; pair this with something
;; like (def-package-hook! evil-goggles :disable) in your private init.el
(package! evil-goggles :ignore t)
;; Tell doom to get evil from somewhere else
(package! evil :recipe (:fetcher github :repo "hlissner/my-evil-fork"))
#+END_SRC

View file

@ -47,11 +47,6 @@
"M-8" (λ! (+workspace/switch-to 7)) "M-8" (λ! (+workspace/switch-to 7))
"M-9" (λ! (+workspace/switch-to 8)) "M-9" (λ! (+workspace/switch-to 8))
"M-0" #'+workspace/switch-to-last "M-0" #'+workspace/switch-to-last
;; Basic escape keys for emacs mode
"C-h" #'evil-window-left
"C-j" #'evil-window-down
"C-k" #'evil-window-up
"C-l" #'evil-window-right
;; Other sensible, textmate-esque global bindings ;; Other sensible, textmate-esque global bindings
"M-r" #'+eval/buffer "M-r" #'+eval/buffer
"M-R" #'+eval/region-and-replace "M-R" #'+eval/region-and-replace
@ -65,6 +60,12 @@
"C-M-f" #'doom/toggle-fullscreen "C-M-f" #'doom/toggle-fullscreen
:m "A-j" #'+hlissner:multi-next-line :m "A-j" #'+hlissner:multi-next-line
:m "A-k" #'+hlissner:multi-previous-line :m "A-k" #'+hlissner:multi-previous-line
:nv "C-SPC" #'+evil:fold-toggle
;; Easier window navigation
:en "C-h" #'evil-window-left
:en "C-j" #'evil-window-down
:en "C-k" #'evil-window-up
:en "C-l" #'evil-window-right
(:prefix "C-x" (:prefix "C-x"
"p" #'doom/other-popup) "p" #'doom/other-popup)
@ -552,6 +553,8 @@
:n "RET" #'neotree-enter :n "RET" #'neotree-enter
:n [backspace] #'evil-window-prev :n [backspace] #'evil-window-prev
:n "c" #'neotree-create-node :n "c" #'neotree-create-node
:n "r" #'neotree-rename-node
:n "d" #'neotree-delete-node
:n "j" #'neotree-next-line :n "j" #'neotree-next-line
:n "k" #'neotree-previous-line :n "k" #'neotree-previous-line
:n "n" #'neotree-next-line :n "n" #'neotree-next-line

View file

@ -23,7 +23,8 @@ private/hlissner/snippets."
(interactive) (interactive)
(let ((default-directory ,dir) (let ((default-directory ,dir)
projectile-require-project-root projectile-require-project-root
projectile-cached-buffer-file-name) projectile-cached-buffer-file-name
projectile-cached-project-root)
(call-interactively (command-remapping #'projectile-find-file)))) (call-interactively (command-remapping #'projectile-find-file))))
(defun ,(intern (format "+hlissner/browse-%s" name)) () (defun ,(intern (format "+hlissner/browse-%s" name)) ()
(interactive) (interactive)

View file

@ -4,11 +4,8 @@
(load! +bindings) ; my key bindings (load! +bindings) ; my key bindings
(load! +commands)) ; my custom ex commands (load! +commands)) ; my custom ex commands
(defvar +hlissner-dir (defvar +hlissner-dir (file-name-directory load-file-name))
(file-name-directory load-file-name)) (defvar +hlissner-snippets-dir (expand-file-name "snippets/" +hlissner-dir))
(defvar +hlissner-snippets-dir
(expand-file-name "snippets/" +hlissner-dir))
(setq epa-file-encrypt-to user-mail-address (setq epa-file-encrypt-to user-mail-address
auth-sources (list (expand-file-name ".authinfo.gpg" +hlissner-dir))) auth-sources (list (expand-file-name ".authinfo.gpg" +hlissner-dir)))
@ -19,6 +16,21 @@
(apply orig-fn args))) (apply orig-fn args)))
(advice-add #'tramp-read-passwd :around #'+hlissner*no-authinfo-for-tramp) (advice-add #'tramp-read-passwd :around #'+hlissner*no-authinfo-for-tramp)
;;
(after! smartparens
;; Auto-close more conservatively
(let ((unless-list '(sp-point-before-word-p
sp-point-after-word-p
sp-point-before-same-p)))
(sp-pair "'" nil :unless unless-list)
(sp-pair "\"" nil :unless unless-list))
(sp-pair "{" nil :post-handlers '(("||\n[i]" "RET") ("| " " "))
:unless '(sp-point-before-word-p sp-point-before-same-p))
(sp-pair "(" nil :post-handlers '(("||\n[i]" "RET") ("| " " "))
:unless '(sp-point-before-word-p sp-point-before-same-p))
(sp-pair "[" nil :post-handlers '(("| " " "))
:unless '(sp-point-before-word-p sp-point-before-same-p)))
;; ;;
(after! doom-themes (after! doom-themes
@ -45,24 +57,26 @@
;; app/irc ;; app/irc
(setq +irc-notifications-watch-strings '("v0" "vnought" "hlissner")) (after! circe
(setq +irc-notifications-watch-strings '("v0" "vnought" "hlissner"))
(set! :irc "irc.snoonet.org" (set! :irc "irc.snoonet.org"
`(:tls t `(:tls t
:nick "v0" :nick "v0"
:port 6697 :port 6697
:sasl-username ,(+pass-get-user "irc/snoonet.org") :sasl-username ,(+pass-get-user "irc/snoonet.org")
:sasl-password ,(+pass-get-secret "irc/snoonet.org") :sasl-password ,(+pass-get-secret "irc/snoonet.org")
:channels (:after-auth "#ynought"))) :channels (:after-auth "#ynought"))))
;; app/email ;; app/email
(setq smtpmail-stream-type 'starttls (after! mu4e
(setq smtpmail-stream-type 'starttls
smtpmail-default-smtp-server "smtp.gmail.com" smtpmail-default-smtp-server "smtp.gmail.com"
smtpmail-smtp-server "smtp.gmail.com" smtpmail-smtp-server "smtp.gmail.com"
smtpmail-smtp-service 587) smtpmail-smtp-service 587)
(set! :email "gmail.com" (set! :email "gmail.com"
'((mu4e-sent-folder . "/gmail.com/Sent Mail") '((mu4e-sent-folder . "/gmail.com/Sent Mail")
(mu4e-drafts-folder . "/gmail.com/Drafts") (mu4e-drafts-folder . "/gmail.com/Drafts")
(mu4e-trash-folder . "/gmail.com/Trash") (mu4e-trash-folder . "/gmail.com/Trash")
@ -71,7 +85,7 @@
(user-mail-address . "hlissner@gmail.com") (user-mail-address . "hlissner@gmail.com")
(mu4e-compose-signature . "---\nHenrik"))) (mu4e-compose-signature . "---\nHenrik")))
(set! :email "lissner.net" (set! :email "lissner.net"
'((mu4e-sent-folder . "/lissner.net/Sent Mail") '((mu4e-sent-folder . "/lissner.net/Sent Mail")
(mu4e-drafts-folder . "/lissner.net/Drafts") (mu4e-drafts-folder . "/lissner.net/Drafts")
(mu4e-trash-folder . "/lissner.net/Trash") (mu4e-trash-folder . "/lissner.net/Trash")
@ -79,4 +93,4 @@
(smtpmail-smtp-user . "henrik@lissner.net") (smtpmail-smtp-user . "henrik@lissner.net")
(user-mail-address . "henrik@lissner.net") (user-mail-address . "henrik@lissner.net")
(mu4e-compose-signature . "---\nHenrik Lissner")) (mu4e-compose-signature . "---\nHenrik Lissner"))
t) t))

View file

@ -7,16 +7,19 @@
user-mail-address "henrik@lissner.net" user-mail-address "henrik@lissner.net"
user-full-name "Henrik Lissner") user-full-name "Henrik Lissner")
;; An extra measure to prevent the flash of unstyled mode-line while Emacs is
;; booting up (when Doom is byte-compiled).
(setq-default mode-line-format nil)
;; host-specific settings ;; host-specific settings
(pcase (system-name) (pcase (system-name)
("proteus" ;; ("triton")
(setq +doom-modeline-height 25 ((or "proteus" "halimede")
doom-font (font-spec :family "Fira Mono" :size 10) ;; smaller screen, smaller fonts
doom-variable-pitch-font (font-spec :family "Fira Sans" :size 10) (set! :font "Fira Mono" :size 10)
doom-unicode-font (font-spec :family "DejaVu Sans Mono" :size 10) (set! :variable-font "Fira Sans" :size 10)
doom-line-number-lpad 3)) (set! :unicode-font "DejaVu Sans Mono" :size 10)
("halimede" (setq +doom-modeline-height 25))
(setq +doom-modeline-height 27))
;; ("nereid") ;; ("nereid")
;; ("io") ;; ("io")
;; ("sao") ;; ("sao")

View file

@ -1,4 +1,4 @@
* :evil neotree #+TITLE: :evil neotree
This module brings a side panel for browsing project files, inspired by vim's NERDTree. This module brings a side panel for browsing project files, inspired by vim's NERDTree.

View file

@ -9,7 +9,6 @@
(require 'neotree) (require 'neotree)
(cond ((and (neo-global--window-exists-p) (cond ((and (neo-global--window-exists-p)
(get-buffer-window neo-buffer-name t)) (get-buffer-window neo-buffer-name t))
(neotree-hide)
(neotree-find path project-root)) (neotree-find path project-root))
((not (and (neo-global--window-exists-p) ((not (and (neo-global--window-exists-p)
(equal (file-truename (neo-global--with-buffer neo-buffer--start-node)) (equal (file-truename (neo-global--with-buffer neo-buffer--start-node))

View file

@ -12,11 +12,12 @@
;;;###autoload ;;;###autoload
(defun +pass-get-field (entry fields) (defun +pass-get-field (entry fields)
(unless noninteractive
(if-let (data (if (listp entry) entry (auth-pass-parse-entry entry))) (if-let (data (if (listp entry) entry (auth-pass-parse-entry entry)))
(cl-loop for key in (doom-enlist fields) (cl-loop for key in (doom-enlist fields)
when (assoc key data) when (assoc key data)
return (cdr it)) return (cdr it))
(error "Couldn't find entry: %s" entry))) (error "Couldn't find entry: %s" entry))))
;;;###autoload ;;;###autoload
(defun +pass-get-user (entry) (defun +pass-get-user (entry)

View file

@ -29,11 +29,14 @@
"C-k" #'pass-next-directory)) "C-k" #'pass-next-directory))
(def-package! auth-password-store
:demand t
:config (auth-pass-enable))
(def-package! helm-pass (def-package! helm-pass
:when (featurep! :completion helm) :when (featurep! :completion helm)
:commands helm-pass) :commands helm-pass)
;; Is built into Emacs 26+
(if (require 'auth-store-pass nil t)
(auth-source-pass-enable)
(def-package! auth-password-store
:demand t
:config (auth-pass-enable)))

View file

@ -4,15 +4,13 @@
;; Plugins ;; Plugins
;; ;;
(def-package! rainbow-mode (def-package! rainbow-mode)
:init
(add-hook 'prog-mode-hook #'rainbow-mode))
(def-package! kurecolor (def-package! kurecolor
:after rainbow-mode :after rainbow-mode
:config :config
(when (featurep! :feature hydra) (when (featurep! :feature hydra)
(require 'hydra)
(defhydra hydra-kurecolor (:color pink (defhydra hydra-kurecolor (:color pink
:hint nil) :hint nil)
" "

View file

@ -0,0 +1,17 @@
#+TITLE: :ui doom-dashboard
This module gives Doom Emacs a dashboard buffer.
It is loosely inspired by Atom's dashboard.
* Table of Contents :TOC:
- [[#install][Install]]
- [[#keybindings][Keybindings]]
- [[#customization][Customization]]
* Install
This module only requires that ~all-the-icons~'s icon fonts are installed. Use ~M-x all-the-icons-install-fonts~ to do so.
* Keybindings
* Customization

View file

@ -1,4 +1,4 @@
* :ui doom-modeline #+TITLE: :ui doom-modeline
This module customizes the Emacs mode-line. This module customizes the Emacs mode-line.
@ -17,12 +17,18 @@ The DOOM modeline was designed for minimalism, and offers:
[[/../screenshots/ml-version.png]] [[/../screenshots/ml-version.png]]
[[/../screenshots/ml-errors.png]] [[/../screenshots/ml-errors.png]]
** Install * Table of Contents :TOC:
- [[#install][Install]]
- [[#extracting-my-modeline][Extracting my modeline]]
- [[#troubleshooting][Troubleshooting]]
- [[#where-are-my-minor-modes][Where are my minor modes?]]
* Install
This module requires the fonts included with ~all-the-icons~ to be installed. This module requires the fonts included with ~all-the-icons~ to be installed.
Run ~M-x all-the-icons-install-fonts~ to do so. Run ~M-x all-the-icons-install-fonts~ to do so.
** Extracting my modeline * Extracting my modeline
Some might want my modeline without the DOOM config altogether. I've tried to make this easier for you, but there are a few things you'll need to do: Some might want my modeline without the DOOM config altogether. I've tried to make this easier for you, but there are a few things you'll need to do:
+ Ensure [[https://github.com/bbatsov/projectile][projectile]] and [[https://github.com/domtronn/all-the-icons.el][all-the-icons]] are installed. + Ensure [[https://github.com/bbatsov/projectile][projectile]] and [[https://github.com/domtronn/all-the-icons.el][all-the-icons]] are installed.
@ -30,7 +36,6 @@ Some might want my modeline without the DOOM config altogether. I've tried to ma
+ Ensure the fonts included with ~all-the-icons~ are installed (~M-x all-the-icons-install-fonts~). + Ensure the fonts included with ~all-the-icons~ are installed (~M-x all-the-icons-install-fonts~).
+ Replace ~def-package!~ calls with ~use-package~. + Replace ~def-package!~ calls with ~use-package~.
+ Replace ~doom-project-root~ calls with ~projectile-project-root~. + Replace ~doom-project-root~ calls with ~projectile-project-root~.
+ Change the one ~def-memoized!~ function to ~defun~.
+ The ~+doom-modeline--make-xpm~ function is memoized with the ~def-memoized!~ macro. Change ~def-memoized!~ to ~defun~. + The ~+doom-modeline--make-xpm~ function is memoized with the ~def-memoized!~ macro. Change ~def-memoized!~ to ~defun~.
+ Copy the ~add-hook!~ macro definition from [[/master/core/core-lib.el][core/core-lib.el]]. + Copy the ~add-hook!~ macro definition from [[/master/core/core-lib.el][core/core-lib.el]].
+ Copy the following macros and functions from [[/master/core/core-ui.el][core/core-ui.el]]: + Copy the following macros and functions from [[/master/core/core-ui.el][core/core-ui.el]]:
@ -40,8 +45,8 @@ Some might want my modeline without the DOOM config altogether. I've tried to ma
+ ~doom-modeline~ + ~doom-modeline~
+ ~doom-set-modeline~ + ~doom-set-modeline~
That /should/ be everything. As I have never used this out of my config I can't guarantee immediate success, but I'd be happy to help you out. File an issue. That /should/ be everything. As I have never used this out of my config I can't guarantee immediate success, but I'd be happy to help you out if you file an issue.
** Troubleshooting * Troubleshooting
*** Where are my minor-modes? ** Where are my minor modes?
I didn't need it, so I removed it. I wrote ~doom/what-minor-mode~ in the rare case I needed to investigate the currently active minor modes however. I didn't need it, so I removed it. Run ~M-x doom/what-minor-mode~ to investigate what minor modes are currently active.

View file

@ -0,0 +1,7 @@
#+TITLE: :ui doom-quit
Remember these?
[[http://cf.geekdo-images.com/images/pic969210_md.jpg]]
Yeah.

View file

@ -1,32 +1,60 @@
* :ui doom #+TITLE: :ui doom
This module modifies Emacs' user interface. This module modifies Emacs' user interface.
DOOM's look is loosely inspired by Atom's One Dark theme, and is largely contained in the [[https://github.com/hlissner/emacs-doom-theme/][doom-themes]] plugin. Doom's look is loosely inspired by Atom's One Dark theme, and is largely contained in the] plugin.
By default, this module uses: + A colorscheme inspired by Atom's One Dark theme (now available in a separate plugin: [[https://github.com/hlissner/emacs-doom-theme/][doom-themes]])
+ Uses the [[https://github.com/mozilla/Fira][Fira Mono and Fira Sans]] fonts, and [[https://dejavu-fonts.github.io/][DejaVu Sans Mono]] for unicode symbols.
+ A custom folded-region indicator for ~hideshow~
+ "Thin bar" fringe bitmaps for ~git-gutter-fringe~
+ File-visiting buffers are slightly brighter (powered by solaire-mode)
+ [[https://github.com/mozilla/Fira][Fira Mono and Fira Sans]] (fonts) * Table of Contents :TOC:
+ [[https://dejavu-fonts.github.io/][DejaVu Sans Mono]] (font, for displaying unicode characters) - [[#install][Install]]
+ ~hideshow~, modified to use a nicer folded-region indicator. - [[#macos][MacOS]]
+ Custom fringe bitmaps for ~git-gutter-fringe~ (thin bars) - [[#arch-linux][Arch Linux]]
- [[#configuration][Configuration]]
- [[#changing-fonts][Changing fonts]]
- [[#troubleshooting][Troubleshooting]]
- [[#strange-font-symbols][Strange font symbols]]
** Install * Install
[[https://github.com/mozilla/Fira][Fira Mono]] is this module's only dependency (if you want to use it). This module optionally depends on:
*** MacOS + The [[https://github.com/mozilla/Fira][Fira Mono]] family of fonts
+ [[https://dejavu-fonts.github.io/][DejaVu Sans Mono]]
You don't have to install these if you use a different font.
** MacOS
#+BEGIN_SRC sh :tangle (if (doom-system-os 'macos) "yes") #+BEGIN_SRC sh :tangle (if (doom-system-os 'macos) "yes")
brew tap caskroom/fonts brew tap caskroom/fonts
brew cask install font-fira-{sans,mono} font-dejavu-sans brew cask install font-fira-{sans,mono} font-dejavu-sans
#+END_SRC #+END_SRC
*** Arch Linux ** Arch Linux
#+BEGIN_SRC sh :dir /sudo:: :tangle (if (doom-system-os 'arch) "yes") #+BEGIN_SRC sh :dir /sudo:: :tangle (if (doom-system-os 'arch) "yes")
sudo pacman --noconfirm --needed -S ttf-fira-{sans,mono} ttf-dejavu sudo pacman --noconfirm --needed -S ttf-fira-{sans,mono} ttf-dejavu
#+END_SRC #+END_SRC
** Troubleshooting * Configuration
*** Strange font symbols ** Changing fonts
If you're getting strange unicode symbols, that is likely ~all-the-icons~ doing (caused by other UI modules, specifically [[../doom-modeline][doom-modeline]] and [[../doom-dashboard][doom-dashboard]]). There are four font settings you can change:
You must install the fonts included with ~all-the-icons~ with: ~M-x all-the-icons-install-fonts~. + ~:font~ :: the default font.
+ ~:big-font~ :: the font to use when ~doom-big-font-mode~ is enabled.
+ ~:variable-font~ :: the font to use when ~variable-pitch-mode~ is active (or where the ~variable-pitch~ face is used).
+ ~:unicode-font~ :: the font used to display unicode symbols. This is ignored if the =:ui unicode= module is enabled.
#+BEGIN_SRC emacs-lisp
;; These are the defaults of this module
(set! :font "Fira Mono" :size 12)
(set! :big-font "Fira Mono" :size 18)
(set! :variable-font "Fira Sans" :size 12)
(set! :unicode-font "DejaVu Sans Mono" :size 12)
#+END_SRC
* Troubleshooting
** Strange font symbols
If you're seeing strange unicode symbols, this is likely because you don't have ~all-the-icons~'s font icon installed. You can install them with ~M-x all-the-icons-install-fonts~.

View file

@ -16,8 +16,11 @@
(load "doom-themes-common.el" nil t)) (load "doom-themes-common.el" nil t))
(add-hook 'doom-pre-reload-theme-hook #'+doom|reload-theme) (add-hook 'doom-pre-reload-theme-hook #'+doom|reload-theme)
;; improve integration with org-mode
(add-hook 'doom-init-ui-hook #'doom-themes-org-config)
;; blink mode-line on errors ;; blink mode-line on errors
(add-hook 'doom-init-ui-hook #'doom-themes-visual-bell-config) ;; (add-hook 'doom-init-ui-hook #'doom-themes-visual-bell-config)
;; Add file icons to doom-neotree ;; Add file icons to doom-neotree
(add-hook 'doom-init-ui-hook #'doom-themes-neotree-config) (add-hook 'doom-init-ui-hook #'doom-themes-neotree-config)
@ -40,6 +43,7 @@
(add-hook 'doom-popup-mode-hook #'turn-off-solaire-mode) (add-hook 'doom-popup-mode-hook #'turn-off-solaire-mode)
:config :config
(setq solaire-mode-real-buffer-fn #'doom-real-buffer-p) (setq solaire-mode-real-buffer-fn #'doom-real-buffer-p)
(add-hook 'doom-init-ui-hook #'solaire-mode-swap-bg t)
;; Prevent color glitches when reloading either DOOM or the theme ;; Prevent color glitches when reloading either DOOM or the theme
(defun +doom|reset-solaire-mode (&rest _) (solaire-mode-reset)) (defun +doom|reset-solaire-mode (&rest _) (solaire-mode-reset))

View file

@ -1,12 +1,16 @@
* :ui evil-goggles #+TITLE: :ui evil-goggles
This module uses ~evil goggles~ to displays visual hints when editing with evil. This module uses ~evil goggles~ to displays visual hints when editing with evil.
** Install * Table of Contents :TOC:
- [[#install][Install]]
- [[#configure][Configure]]
* Install
This module requires: This module requires:
+ ~evil~ (inherently tied to evil mode) + ~evil~ (inherently tied to evil mode)
** Configure * Configure
By default, ~evil-goggles~ will be enabled by default and requires no additional configuration. By default, ~evil-goggles~ will be enabled by default and requires no additional configuration.

View file

@ -0,0 +1,13 @@
#+TITLE: :ui hl-todo
This module adds syntax highlighting for TODO/FIXME/NOTE tags in programming major-modes.
What keywords are highlighted (and their color) can be customized through ~hl-todo-keyword-faces~.
#+BEGIN_SRC emacs-lisp
;; the default
(setq hl-todo-keyword-faces
`(("TODO" . ,(face-foreground 'warning))
("FIXME" . ,(face-foreground 'error))
("NOTE" . ,(face-foreground 'success))))
#+END_SRC

View file

@ -1,4 +1,4 @@
* :ui nav-flash #+TITLE: :ui nav-flash
This module uses ~nav-flash~ to flash the line around the cursor after any motion command that might reasonably send the cursor somewhere the eyes can't follow. This module uses ~nav-flash~ to flash the line around the cursor after any motion command that might reasonably send the cursor somewhere the eyes can't follow.
@ -6,10 +6,14 @@ This module uses ~nav-flash~ to flash the line around the cursor after any motio
Tremendously helpful on a 30" 2560x1600 display. Tremendously helpful on a 30" 2560x1600 display.
#+end_quote #+end_quote
** Install * Table of Contents :TOC:
- [[#install][Install]]
- [[#configure][Configure]]
* Install
This module has no other dependencies. This module has no other dependencies.
** Configure * Configure
By default, ~nav-flash~ will be triggered whenever ~recenter~ is called. =:feature jump= attaches ~recenter~ to various hooks: By default, ~nav-flash~ will be triggered whenever ~recenter~ is called. =:feature jump= attaches ~recenter~ to various hooks:
#+BEGIN_SRC emacs-lisp #+BEGIN_SRC emacs-lisp

View file

@ -0,0 +1,5 @@
#+TITLE: :ui tabbar
This module adds a tabbar to the Emacs UI.
I don't recommend you use this module. It is here for reference, is unstable and doesn't integrate with Doom's UI well. I find ivy, helm or even ~buffer-menu~ to be better suited for buffer management.

View file

@ -0,0 +1,10 @@
#+TITLE: :ui unicode
This unicode extends Doom's ability to display non-English unicode.
This is for non-English Emacs users, for whom Doom's built-in unicode support in insufficient.
When this module is enabled...
+ The first time you run Emacs a unicode cache will be generated -- this will take a while!
+ Doom will ignore the ~doom-unicode-font~ variable and the ~:unicode-font~ setting.