Ecosyste.ms: Awesome

An open API service indexing awesome lists of open source software.

Awesome Lists | Featured Topics | Projects

https://github.com/ttybitnik/emacs.d

My GNU Emacs configuration files along with an in-depth chronicle of my crafting process.
https://github.com/ttybitnik/emacs.d

emacs org-mode programming sysadmin translation writing

Last synced: 3 months ago
JSON representation

My GNU Emacs configuration files along with an in-depth chronicle of my crafting process.

Awesome Lists containing this project

README

        

#+TITLE: ttybitnik/emacs.d
#+AUTHOR: Vinícius Moraes
#+EMAIL: [email protected]
#+OPTIONS: num:nil

#+html:

This repository contains my *GNU Emacs* configuration files along with an in-depth chronicle of my crafting process. It includes links to valuable resources, in code, text and video, that have been important throughout my trajectory. In this sense, taking inspiration from [[https://github.com/munen][@Munen]]'s insightful presentation "[[https://www.youtube.com/watch?v=gfZDwYeBlO4][Play Emacs like an instrument]]", I have decided to expand his playful yet thoughtful metaphor into this unique creative process. Thus, this is the journey to *craft emacs.d like a luthier*.

*Table of contents*
- [[#wood-selection][Wood selection]]
- [[#design-and-planning][Design and planning]]
- [[#shaping-and-carving][Shaping and carving]]
- [[#stringing-it-up][Stringing it up]]
- [[#tunings-and-sound-adjustment][Tunings and sound adjustment]]
- [[#composition-and-performance][Composition and performance]]
- [[#collaborative-jamming][Collaborative jamming]]
- [[#ongoing-opus][Ongoing opus]]

#+begin_quote
ℹ️ The core of this project is built to my personal use case and workflow, which may or may not align with yours. The great news is that you are free, as in [[https://www.gnu.org/philosophy/free-sw.en.html][free software]], to inspire yourself and change it to do what you mean. Check the [[#license][license]] section for further details on that.
#+end_quote

** Wood selection

After having a solid grasp of Emacs basics, a good next move is learning from more experienced users. [[https://github.com/redguardtoo][@Redguardtoo]], in [[https://github.com/redguardtoo/mastering-emacs-in-one-year-guide/blob/master/guide-en.org][On the Shoulders of Giants]], also writes about the importance of this type of approach. Since it is a longstanding community tradition the sharing of *emacs.d*, using all this shared knowledge as /materia prima/ is an effective way to begin a vanilla Emacs journey.

Nowadays, in my case, I maintain locally a [[https://github.com/stars/ttybitnik/lists/book-emacs-d][curated list]] of *emacs.d* repositories of my interest. When I wish to implement a new feature or workflow, I use these repositories as practical references. Also, around once per semester, I review upstream changes to weigh whether any new idea or setting worth adapting into my configuration.

Therefore, this approach provides not only a source of hands-on configurations but also a window into evolving practices within the community.

If you are entirely new to Emacs, fear not. Further ahead, I provide some beginner-friendly guidance as well.

** Design and planning

Emacs.d configurations can take various forms, but they typically fall into two main styles:

- Literate Programming style
- Emacs Lisp style

Initially, my configuration followed the literate programming style, utilizing the ~use-package~ macro. It was managed through an Org file named after [[https://github.com/ttybitnik/emacs.d/blob/master/odysseus.org][Odysseus]], which I have kept in the repository for archival purposes. However, after using this style for 10 months, I developed a desire to deepen my understanding of Emacs Lisp. As a result, I decided to refactor my entire configuration ([[https://github.com/ttybitnik/emacs.d/commit/0e48f4df0405525780980cfc10f9c8ef10bca128][0e48f4d]]), shifting to an Emacs Lisp style without relying on ~use-package~. This refactoring allowed me not only to practice the [[https://www.gnu.org/software/emacs/manual/html_node/elisp/Packaging.html][Emacs Lisp way]], but also to introduce modularity into my configuration, enabling me to create more shareable, manageable, and independent components.

*** Outline of the directory structure:

- =.auth/= :: Private directory for restricted settings and secure [[https://www.gnu.org/software/emacs/manual/html_node/auth/Help-for-users.html][authentication]] within Emacs.
- =img/= :: Directory containing images for the Emacs dashboard and for this repository.
- =local/= :: Directory for offline utility files, including capture templates, presentation tools, and custom packages.
- =modules/= :: Directory containing Emacs Lisp modules and configuration files.
- =snippets/= :: Directory for programming snippets and templates.

*** Outline of the core Emacs Lisp files:

- =early-init.el= (optional) :: Pre-initialization settings. This file is loaded by Emacs.
- =init.el= :: Package archive settings, global functions and variables, and system-wide configuration. This file is loaded by Emacs after /early-init.el/.
- =modules.el= :: General configuration scopes that load pertinent /prefix-config.el/ files. These files are loaded by /init.el/.
- =prefix.config.el= :: Package configuration files with filenames inheriting module prefixes. These files are loaded by /modules.el/.
- =custom.el= (optional) :: Minor adjustments and temporary testing settings. This is the last file loaded by /init.el/.

The diagram below provides a visual synthesis of the core Emacs Lisp files alongside the directory structure, arranged in loading sequence order from left to right.

#+begin_src plantuml :exports none
@startuml
!include /home/ttybitnik/.emacs.d/local/theme-plantuml.puml
skinparam backgroundColor transparent
skinparam linetype ortho

agent "early-init.el" as Einit
agent "init.el" as Init
agent "modules.el" as Mod
agent "custom.el" as Cstm
agent "prefix-config.el" as Tun

agent ".auth/" as Auth
agent "img/" as Img
agent "local/" as Loc
agent "modules/" as Modd
agent "snippets/" as Snip

Einit .> Init
Init -d-> Modd
Modd -d-> Mod
Mod -d-> Tun
Init .r-> Cstm

Mod ~u->> Loc
Mod ~u->> Snip
Mod ~u->> Auth
Mod ~u->> Img

Auth -r[hidden]-> Loc
Img -l[hidden]-> Snip
Modd -l[hidden]-> Loc
Loc -r[hidden]-> Snip
@enduml
#+end_src

#+html:

** Shaping and carving

Moving from the conceptual phase to implementation, the following list describes each module:

- Communication Module :: Responsible for emailing and communication apparatus.
- Design Module :: Responsible for designing and modeling processes.
- Functionality Module :: Responsible for implementing new functionalities into Emacs.
- Miscellaneous Utilities Module :: Responsible for introducing or extending general utilities.
- Navigation Module :: Responsible for managing navigation throughout Emacs.
- Org-Mode Module :: Responsible for setting the org-mode milieu.
- Programming Module :: Responsible for supporting programming workflows.
- Project Management Module :: Responsible for integrating projects and version control.
- Publishing Module :: Responsible for exporting and publishing material.
- Text Module :: Responsible for complying writing processes.
- Visual Module :: Responsible for looking and feeling aspects.

In order to have a more sensible naming standard, each module filename is assigned with an abbreviation *prefix* prepended by "tty" to avoid conflicts, as with =org.el=. Thus, there are the following modules files:

#+begin_src text
init.el
└── modules/
├── tty-com.el communication module
├── tty-dsg.el design module
├── tty-func.el functionality module
├── tty-misc.el miscellaneous utilities module
├── tty-nav.el navigation module
├── tty-org.el org-mode module
├── tty-prog.el programming module
├── tty-proj.el project management module
├── tty-publ.el publishing module
├── tty-txt.el text module
└── tty-vis.el visual module
#+end_src

As mentioned earlier, in addition to managing general settings within its scope, each module is also responsible for loading relevant package configuration files. Each configuration file inherits its filename prefix from the module responsible for it. Thus, there are the following configuration files:

#+begin_src text
init.el
└── modules/
├── tty-com.el communication module
│ ├── tty-com-bbdb.el
│ ├── tty-com-erc.el
│ └── tty-com-gnus.el
├── tty-dsg.el design module
│ ├── tty-dsg-graphviz-dot.el
│ └── tty-dsg-plantuml.el
├── tty-func.el functionality module
│ ├── tty-func-embark.el
│ ├── tty-func-evil.el
│ ├── tty-func-expand-region.el
│ ├── tty-func-hungry-delete.el
│ ├── tty-func-move-dup.el
│ ├── tty-func-multiple-cursors.el
│ ├── tty-func-orderless.el
│ ├── !tty-func-popup-kill-ring.el
│ ├── tty-func-sudo-edit.el
│ ├── !tty-func-undo-tree.el
│ ├── tty-func-vundo.el
│ ├── tty-func-wgrep.el
│ └── tty-func-zzz-to-char.el
├── tty-misc.el miscellaneous utilities module
│ ├── tty-misc-bibtex.el
│ ├── tty-misc-centered-cursor.el
│ ├── tty-misc-company.el
│ ├── tty-misc-dired.el
│ ├── tty-misc-exec-path-from-shell.el
│ ├── tty-misc-nov.el
│ ├── tty-misc-olivetti.el
│ ├── tty-misc-paredit.el
│ ├── tty-misc-pdf-tools.el
│ └── tty-misc-vertico.el
├── tty-nav.el navigation module
│ ├── tty-nav-avy.el
│ ├── tty-nav-consult.el
│ ├── !tty-nav-helm.el
│ ├── tty-nav-switch-window.el
│ └── tty-nav-which-key.el
├── tty-org.el org-mode module
│ ├── tty-org-auto-tangle.el
│ ├── tty-org-bullets.el
│ ├── tty-org-noter.el
│ ├── tty-org-orgmdb.el
│ ├── tty-org-ref.el
│ ├── tty-org-roam.el
│ └── tty-org-toc-org.el
├── tty-prog.el programming module
│ ├── tty-prog-ansible.el
│ ├── tty-prog-c.el
│ ├── tty-prog-css.el
│ ├── tty-prog-eglot.el
│ ├── !tty-prog-flycheck.el
│ ├── tty-prog-flymake.el
│ ├── tty-prog-go.el
│ ├── tty-prog-html.el
│ ├── tty-prog-javascript.el
│ ├── tty-prog-json.el
│ ├── tty-prog-lisp.el
│ ├── !tty-prog-lsp.el
│ ├── tty-prog-lua.el
│ ├── tty-prog-markdown.el
│ ├── tty-prog-nix.el
│ ├── tty-prog-python.el
│ ├── tty-prog-rust.el
│ ├── tty-prog-scheme.el
│ ├── tty-prog-shell.el
│ ├── tty-prog-sql.el
│ ├── tty-prog-toml.el
│ ├── tty-prog-tree-sitter.el
│ ├── tty-prog-xml.el
│ ├── tty-prog-yaml.el
│ └── tty-prog-yasnippet.el
├── tty-proj.el project management module
│ ├── tty-proj-diff-hl.el
│ ├── tty-proj-magit.el
│ ├── tty-proj-project.el
│ └── !tty-proj-projectile.el
├── tty-publ.el publishing module
│ ├── tty-publ-easy-hugo.el
│ ├── tty-publ-htmlize.el
│ ├── tty-publ-ox-reveal.el
│ └── tty-publ-ox-twbs.el
├── tty-txt.el text module
│ ├── tty-txt-flyspell.el
│ ├── tty-txt-fountain.el
│ └── tty-txt-go-translate.el
└── tty-vis.el visual module
├── tty-vis-all-the-icons.el
├── tty-vis-beacon.el
├── tty-vis-dashboard.el
├── tty-vis-diminish.el
├── !tty-vis-gruvbox-theme.el
├── tty-vis-keycast.el
├── tty-vis-marginalia.el
├── tty-vis-modus-themes.el
├── !tty-vis-pulsar.el
├── tty-vis-rainbow.el
└── !tty-vis-spaceline.el
#+end_src

#+begin_quote
❕ Entries marked with an exclamation mark indicate that they were deactivated in favour of another package. Read the commentary section in the given file for more information.
#+end_quote

It is important to note that while the overview above suggests an one-to-one relationship between configuration files and packages, this is not always the case. Some configuration files are more inclined to handle a family of related packages. For instance, the =tty-org-roam.el= file consolidates configurations for /org-roam/, /org-roam-bibtex/, and /org-roam-ui/ packages.

At the Emacs Lisp file level, I have adapted the [[https://www.gnu.org/software/emacs/manual/html_node/elisp/Library-Headers.html][conventional library headers]] for this informal use case of a personal configuration. Each custom field added to the template is marked with the section comment separator =;;*=.

#+begin_src emacs-lisp
;;; foo.el --- Foo Title -*- lexical-binding: t -*-

;;; Commentary:

;; Crafting Emacs like a luthier.

;;; Code:

(require 'bar)

;;* Variables:

;;* Main:

;;* Bindings:

;;* Hooks:

;;* Appearance:

(provide 'foo)

;;; foo.el ends here
#+end_src

Although these custom fields are quite indicative, here are their purposes:

- =;;* Variables=: Section for defining variables.
- =;;* Functions=: Section for defining functions.
- =;;* Main=: Section for code execution.
- =;;* Bindings=: Section for setting bindings.
- =;;* Hooks=: Section for setting hooks.
- =;;* Appearance=: Section for cosmetic changes.

By following this approach, the code base remains stable and structured, enabling a more seamless navigation, regardless of the quantity or size of the files. Still, searching for the section comment separator, =;;\*=, is often a handy way for moving into specific segments as well. To further streamline the process, a snippet, =

** Tunings and sound adjustment

Once using it, you will soon find the need for personal tunings and adjustments. There are numerous ways to perform these operations, and over time, you will accumulate various techniques in your toolkit. Given the extensive nature of my configuration, below I am sharing some of my favorite methods and tools along with a visual demonstration for managing its multiple files.

1. ~dired-jump~ (C-x C-j) into =modules/=
2. ~grep~ (C-c M-s g) "foo" *
3. ~wgrep-change-to-wgrep-mode~ (C-c C-p)
- ~mc-mark-more~ (C->)
- ~query-replace~ (M-%)
- ~kmacro-start-macro-or-insert-counter~ ()

#+html:

#+begin_quote
⚠️️ This is a demonstration using the terminal as interface, *no-window-system* (nw), which means that certain visual elements may not display correctly due graphical/recording limitations.
#+end_quote

One essential thing to have in mind while doing modifications is that *very often the defaults are more powerful than you think*. It is just a matter of taking time to study and practice them. Besides that, maintaining a stable configuration is more conducive to in-depth skill development. So do be deliberate and thoughtful with every change you make.

Instead of altering the configuration whenever something triggers you, I recommend capturing descriptive tasks (C-c c t ~org-capture~) once you have a workflow modification or a new idea in mind. Periodically, such as once every semester, review this list of modification tasks. If they still make sense, proceed with their implementation. The =custom.el= file is also handy for testing these new changes, serving as a sort of trial period before fully incorporating them into the configuration.

** Composition and performance

Emacs offers powerful tools from coding to prose. Below are some links to key features and workflows that play a central role in my daily usage. They cover a wide range of areas, from note-taking and knowledge management system to programming, writing, and publishing.

- Org-mode: [[https://www.youtube.com/watch?v=oJTwQvgfgMM][A system for note-taking and project planning]].
- KMS: [[https://zettelkasten.de/posts/overview/][Zettelkasten]], [[https://www.youtube.com/watch?v=oyEMlIxIHXs][org-roam (unlinked references)]], [[https://www.youtube.com/watch?v=Wy9WvF5gWYg][org-roam-bibtex (quick presentation)]].
- Sprints: [[https://www.youtube.com/watch?v=dljNabciEGg][Literate DevOps with Emacs]].
- Blogging: [[https://gohugo.io/][Hugo]], [[https://github.com/masasam/emacs-easy-hugo][easy-hugo (blog with org-mode)]].
- Emailing: [[https://github.com/redguardtoo/mastering-emacs-in-one-year-guide/blob/master/gnus-guide-en.org][Practical guide to GNUS]].
- Presenting: [[https://revealjs.com/][Reveal.js]], [[https://www.youtube.com/watch?v=avtiR0AUVlo][org-reveal (classy slideshows from org-mode)]].
- Programming: [[https://github.com/joaotavora/eglot][Eglot]], [[https://company-mode.github.io/][company-mode]].

** Collaborative jamming

Embrace the [[https://www.youtube.com/watch?v=xSkCny-HtTw][collaborative jamming]] and contribute to the [[https://www.fsf.org/videos/escape-to-freedom/][freedom of software]]. If you encounter a bug or identify areas for improvement in the packages you use, consider collaborating by reporting issues or contributing to code and documentation.

Staying connected with the community is also helpful. Below are some of my preferred ways to do it through ~gnus~.

- [[https://savannah.gnu.org/mail/?group=emacs][Emacs Mailiing Lists]]
- Emacs Devel
- Emacs Tangents
- [[https://sachachua.com/blog/category/emacs-news/][Sasha Chua's Emacs News]]
- [[https://systemcrafters.net/newsletter/sc-news-001.html][System Crafters' Newsletter]]

** Ongoing opus

Among its peers, Emacs is a truly unique stradivarius—one that belongs to all of us and can be played by all of us. It embodies the elegance and wisdom of many experienced luthiers over the years. Thus, as I mentioned earlier, do not hesitate to appreciate and play with it as it is. Within Emacs lies an entire world of knowledge waiting to be discovered.

For all that, mastering such gracious instrument may take time. As one of my favorite blog titles on Emacs suggests, "[[https://tess.oconnor.cx/2009/07/learn-emacs-in-ten-years][Learn Emacs in 10 years]]", this journey can indeed be a lifelong commitment. However, with each day of practice, as you gather experience and uncover new areas and techniques, your proficiency evolves. It is an ongoing /opus/, a journey that every Emacs /virtuoso/ embarked on with the spirit of continuous learning, practicing, and, of course, sharing. Let the freedom of its music play through your fingers.

** License :noexport:

This project is licensed under the GNU General Public License v3.0 (GPL-3.0), *unless an exception is made explicit in context*. The GPL is a copyleft license that guarantees freedom to use, modify, and distribute software. It ensures that users have control over the software they use and promotes collaboration and sharing of knowledge. By requiring that derivative works also be licensed under the GPL, the freedoms it provides are extended to future generations of users and developers.

See the =COPYING= file for more information.

The source code for this project is available at .