TGRO's Emacs Init
Split into multiple files!

Table of Contents

Site Map

Word Of Warning

These Emacs configuration and initialisation files are:

  • Largely un-commented.
  • Extremely messy.
  • Badly thrown together.
  • Borderline crazy.

.emacs.d/init.el

This file does basically nothing but load my other files.

It contains what I find convenient to have here, like installed packages in case I quickly need a list of them, and the customize stuff in case I have been messing around with that.

I also occasionally chuck stuff into it when I just need somewhere quick to put it.

(package-initialize)
(load "/home/fd/.emacs.d/finnit/finn_load.el")
(custom-set-variables
 ;; custom-set-variables was added by Custom.
 ;; If you edit it by hand, you could mess it up, so be careful.
 ;; Your init file should contain only one such instance.
 ;; If there is more than one, they won't work right.
 '(package-selected-packages
   (quote
    (org volume bongo clojure-mode writegood-mode w3m rust-mode prolog poker paradox ox-rst org-preview-html markdown-mode linum-relative inf-clojure htmlize haskell-mode gnuplot-mode gnuplot fish-mode fish-completion erlang bbcode-mode avy async artbollocks-mode aggressive-indent aggressive-fill-paragraph))))
(custom-set-faces
 ;; custom-set-faces was added by Custom.
 ;; If you edit it by hand, you could mess it up, so be careful.
 ;; Your init file should contain only one such instance.
 ;; If there is more than one, they won't work right.
 )

(defvar org-electric-pairs '((?* . ?*) (?/ . ?/) (?_ . ?_) (?= . ?=) (?~ . ?~)) "Electric pairs for Org-mode.")
(defun org-add-electric-pairs ()
  (setq-local electric-pair-pairs (append electric-pair-pairs org-electric-pairs))
  (setq-local electric-pair-text-pairs electric-pair-pairs))
(add-hook 'org-mode-hook 'org-add-electric-pairs)

Split Files

I have multiple initialisation files, an idea stolen from Xah Lee. Where he split files up per-type (i.e. all keybindings in one file), I split per-mode, allowing Emacs to load different settings dynamically, depending on what type of file I am open; my large-ish init.el file meant Emacs was becoming slow to start (by which I mean a whole 1.5s!) and I am a big fan of instant gratification.

Currently I am using variables and eval-after-load statements to load these files, but I feel that there must be a better way. If you know then please let me know.

It also makes my configuration quite portable. I carry it on a USB stick on the off-chance that need to use Emacs on another computer for longer than minutes.

Load Files

This file simply loads the other files. This would usually be in the main init.el but is instead here in the interests of portability.

(defun full-path (@file-relative-path)
  "Get full path of file relative to caller file location."
  (concat (file-name-directory
           (or load-file-name buffer-file-name))
          @file-relative-path))

(load (full-path "finn_settings"))
(load (full-path "finn_other"))

(setq finn_bongo-path (full-path "finn_bongo"))
(eval-after-load
    'bongo '(progn (load finn_bongo-path)))

(setq finn_clojure-path (full-path "finn_clojure"))
(eval-after-load
    'clojure-mode '(progn (load finn_clojure-path)))

;; So far no problem with default Erlang config!
;; (eval-after-load
;;     'erlang '(progn (load "/home/fd/.emacs.d/finnit/finn_erlang")))

(setq finn_haskell-path (full-path "finn_haskell"))
(eval-after-load
    'haskell-mode '(progn (load finn_haskell-path)))

(setq finn_org-path (full-path "finn_org"))
(eval-after-load
    'org '(progn (load finn_org-path)))

(setq finn_w3m-path (full-path "finn_w3m"))
(eval-after-load
    'w3m '(progn (load finn_w3m-path)))

Generic

Assigns all the general settings that don't fit with a file-type.

;; Modes ==================================================
;; Disable ----------------------------------------
(gpm-mouse-mode -1)
(tooltip-mode -1)
;; Enable ----------------------------------------
(save-place-mode 1)
(electric-pair-mode 1)
(show-paren-mode 1)
;; (linum-relative-global-mode 1)
;; (global-visual-line-mode 1)

;; Convenience ==================================================
;; Line Truncation ----------------------------------------
(set-default 'truncate-lines nil)
(setq truncate-partial-width-windows 40)
;; Y/N Rather Than Yes/No
(defalias 'yes-or-no-p 'y-or-n-p)
;; Don't Ring Bell
(setq ring-bell-function nil)
;; Backup ----------------------------------------
(setq version-control t)
(setq backup-directory-alist '(("" . "/home/fd/.emacs.d/emacs-backup")))
;; Org-Agenda Dir
(setq org-agenda-files '(("/home/fd/todo")))
;; Set Browser
(setq browse-url-browser-function 'w3m-goto-url)
;; Inhibit startup screen
(setq inhibit-startup-screen t)
;; Example details
;; (setq user-full-name "FonnD")
;; (setq user-mail-address "FonnD@gmail.com")

;; Minibuffer ==================================================
(customize-set-variable
 'minibuffer-prompt-properties
 (quote (read-only t cursor-intangible t face minibuffer-prompt)))

;; UTF-8 Encoding ==================================================
(set-buffer-file-coding-system 'utf-8)
(set-terminal-coding-system 'utf-8)
(set-keyboard-coding-system 'utf-8)
(prefer-coding-system 'utf-8)

;; Mode-Line ==================================================
(setq display-time-mail-file 0)
(setq display-time-default-load-average nil)
(setq display-time-24hr-format t)
(column-number-mode 1)
(display-time-mode 1)
(setq-default mode-line-format
              (list "%e%@%F%Z%* "
                    mode-line-buffer-identification
                    " {%I}[%c,%l]"
                    mode-line-modes
                    mode-line-misc-info
                    " %-"))

;; Package Repos ==================================================
(setq package-archives '(("gnu" . "https://elpa.gnu.org/packages/")
                         ("marmalade" . "https://marmalade-repo.org/packages/")
                         ("melpa" . "https://melpa.org/packages/")
                         ("org" . "https://orgmode.org/elpa/")))
(setq paradox-github-token t)
(package-initialize)

;; Keybindings ==================================================
;; Remove ----------------------------------------
(global-unset-key (kbd "C-t"))
(global-unset-key (kbd "M-t"))
(global-unset-key (kbd "C-x C-t"))
(global-unset-key (kbd "M-o"))
(global-unset-key (kbd "<f1>"))
(global-unset-key (kbd "<f2>"))
(global-unset-key (kbd "<f3>"))
(global-unset-key (kbd "<f4>"))
(global-unset-key (kbd "<f11>"))
;; Add ----------------------------------------
(global-set-key (kbd "C-c a") 'org-agenda)
(global-set-key (kbd "C-z") 'avy-goto-char-2)
(global-set-key (kbd "C-c b") 'battery)
(global-set-key (kbd "M-q") 'visual-line-mode)
(global-set-key (kbd "M-Q") 'unfill-region)
(global-set-key (kbd "M-/") 'kmacro-bind-to-key)
(global-set-key (kbd "M-'") 'dabbrev-expand)
(global-set-key (kbd "C-c v") 'volume)
(global-set-key (kbd "C-c s") 'bongo-pause/resume)
(global-set-key (kbd "C-c m") 'bongo)
(global-set-key (kbd "C-c n") 'bongo-perform-next-action)

Other

Contains stuff I don't know where to put or have not made a dedicated section for.

;; Unfill function stolen from ergoemacs
(defun unfill-region (start end)
  "Unfills a region of text."
  (interactive "r")
  (let ((fill-column most-positive-fixnum))
    (fill-region start end)))
;; Python Settings
(setq python-indent-offset 4)
(setq python-indent-guess-indent-offset nil)

Org-Mode

Contains all the settings for Org-mode to run.

;; Backends
(setq org-export-backends '(html md rst latex org))

;; Requires:
(require 'ox-publish)
(require 'ox-html)
(require 'flyspell)
(require 'org-indent)
(require 'writegood-mode)

;; ==================================================
;; (setq org-publish-cache nil)

(setq org-html-preamble-format
      '(("en" 
          "<p class=\"author\">By: %a</p>
          <p class=\"email\">(%e)</p>
          <p class=\"creator\">In 
          <a href=\"https://www.gnu.org/software/emacs/\">Emacs</a>
           with 
          <a href=\"https://orgmode.org\">Org-mode</a></p>")))
(setq org-html-postamble-format
      '(("en" 
          "<p class=\"author\">By: %a</p>
          <p class=\"email\">(%e)</p>
          <p class=\"creator\">In 
          <a href=\"https://www.gnu.org/software/emacs/\">Emacs</a>
           with 
          <a href=\"https://orgmode.org\">Org-mode</a></p>")))


(setq org-startup-truncated nil)
(setq org-highlight-latex-and-related '(latex))
(setq org-image-actual-width nil)

(defun finn-org-keys ()
  "Finn's Keybindings for Org-mode."
  (interactive)
  (local-set-key (kbd "C-c p") 'org-preview-html/preview)
  (local-set-key (kbd "C-c e") 'flyspell-goto-next-error) )
(add-hook 'org-mode-hook 'finn-org-keys)

(defun finn-org-modes ()
  "Finn's Minor Modes for Org-mode."
  (interactive)
  (flyspell-mode t)
  (writegood-mode t)
  ;; (aggressive-indent-mode t)  
  (org-indent-mode t)
  ;; (visual-line-mode t)
  ;; (aggressive-fill-mode t)
  )
(add-hook 'org-mode-hook 'finn-org-modes)

;; Quick For Homework minus personal info
;; (add-to-list
;;  'org-structure-template-alist
;;  (list "HW" (concat "#+OPTIONS: html-postamble:nil email:t\n"
;;                  "#+OPTIONS: html-style:t html-scripts:nil\n"
;;                  "#+HTML_HEAD: \n"
;;                  "#+TITLE: ?\n"
;;                  "#+SUBTITLE: \n")))

;; Quick structure for tgro.neocitices.org
(add-to-list
 'org-structure-template-alist
 (list "tgro" (concat "#+OPTIONS: \n"
                      "#+HTML_HEAD: \n"
                      "#+SETUPFILE: ~/.emacs.d/org-templates/level-0.org\n"
                      "#+TITLE: ?\n"
                      "#+SUBTITLE: \n"
                      "* Site Map\n"
                      "  :PROPERTIES:\n"
                      "  :NOTOC: t\n"
                      "  :CUSTOM_ID: sitemap\n"
                      "  :HTML_CONTAINER_CLASS: sitemap\n"
                      "  :END:\n"
                      "  #+INCLUDE:\"sitemap.org\"\n")))

;; Quick Image Height
(add-to-list
 'org-structure-template-alist
 (list "ih" "#+ATTR_HTML: :height ?300px"))

;; Quick Image Width
(add-to-list
 'org-structure-template-alist
 (list "iw" "#+ATTR_HTML: :width ?300px"))

;; tgro.neocities.org Publishing Options
(setq org-publish-project-alist
      '(("tgro-org"
         :base-directory "~/org-tgro"
         :base-extension "org"
         :publishing-directory "~/tgro.neocities.org/"
         :publishing-function org-html-publish-to-html
         :recursive t

         ;; :makeindex t

         :auto-sitemap t
         :sitemap-filename "sitemap.org"
         :sitemap-title ""

         :author "FonnD"
         :language "en"
         :headline-levels 3

         :with-author t
         :with-date t
         :with-emphasize t
         :with-latex t
         :with-special-strings t
         :with-tables t
         :with-title t
         :with-timestamps t
         :with-toc t
         :with-email t

         :archived-trees nil
         :preserve-breaks nil
         :section-numbers nil
         :select-tags nil
         :with-broken-links nil
         :with-clocks nil
         :with-creator nil
         :with-drawers nil
         :with-fixed-width nil
         :with-footnotes nil
         :with-planning nil
         :with-priority nil
         :with-properties nil
         :with-sub-subscript nil
         :with-todo-keywords nil
         :with-tags nil
         :with-tasks nil
         :with-todo-keywords nil

         :html-checkbox-type "ascii"
         :html-container "div"
         :html-doctype "xhtml-strict"
         :html-extension "html"
         :html-head "css/tgro.css"
         :html-link-home ""
         :html-link-up ""
         :html-text-markup-alist ((bold . "<b>%s</b>")
                                  (code . "<code>%s</code>")
                                  (italic . "<i>%s</i>")
                                  (strike-through . "<del>%s</del>")
                                  (underline . "<span class=\"underline\">%s</span>")
                                  (verbatim . "<kbd>%s</kbd>"))
         :html-toplevel-hlevel 2
         :html-xml-declaration (("html" . "<!-- <?xml version=\"1.0\" encoding=\"%s\"?> -->")
                                ("php" . "<?php echo \"<?xml version=\\\"1.0\\\" encoding=\\\"%s\\\" ?>\"; ?>"))

         :html-inline-images t
         :html-link-org-files-as-html t
         :html-table-align-individual-fields t
         :html-table-caption-above t

         :html-allow-name-attribute-in-anchors  nil
         :html-head-include-default-style nil
         :html-head-include-scripts nil
         :html-html5-fancy nil
         :html-indent nil
         :html-link-use-abs-url nil
         :html-postamble nil
         :html-preamble nil
         :html-use-infojs nil
         :html-table-use-header-tags-for-first-column nil                                 
         )
        ("tgro-static"
         :base-directory "~/org-tgro/"
         :base-extension "css\\|png\\|jpg\\|gif\\|ico"
         :publishing-directory "~/tgro.neocities.org/"
         :recursive t
         :publishing-function org-publish-attachment)
        ("tgro" :components ("tgro-org" "tgro-static"))))


;; Need to make this in a seperate file that is loaded
(defun org-export-collect-headlines (info &optional n scope)
  "Collect headlines in order to build a table of contents.

INFO is a plist used as a communication channel.

When optional argument N is an integer, it specifies the depth of
the table of contents.  Otherwise, it is set to the value of the
last headline level.  See `org-export-headline-levels' for more
information.

Optional argument SCOPE, when non-nil, is an element.  If it is
a headline, only children of SCOPE are collected.  Otherwise,
collect children of the headline containing provided element.  If
there is no such headline, collect all headlines.  In any case,
argument N becomes relative to the level of that headline.

Return a list of all exportable headlines as parsed elements.
Footnote and NOTOC sections are ignored."
  (let* ((scope (cond ((not scope) (plist-get info :parse-tree))
                      ((eq (org-element-type scope) 'headline) scope)
                      ((org-export-get-parent-headline scope))
                      (t (plist-get info :parse-tree))))
         (limit (plist-get info :headline-levels))
         (n (if (not (wholenump n)) limit
              (min (if (eq (org-element-type scope) 'org-data) n
                     (+ (org-export-get-relative-level scope info) n))
                   limit))))
    (org-element-map (org-element-contents scope) 'headline
      (lambda (headline)
        (unless (or (org-element-property :footnote-section-p headline)
                    (org-element-property :NOTOC headline))
          (let ((level (org-export-get-relative-level headline info)))
            (and (<= level n) headline))))
      info)))

TGRO Setup

I place this into any file that I makes up this site to make the export do what I want using the line:

#+SETUPFILE: ~/.emacs.d/org-templates/level-0.org

Clojure

Clojure is a Lisp dialect that runs on the JVM that I am learning.

;; Requires:
(require 'inf-clojure)

;; ==================================================
(defun finn-clojure-modes ()
  "Finn's Minor Modes for Clojure-mode."
  (interactive)
  (setq inf-clojure-minor-mode 1) )
(add-hook 'clojure-mode-hook #'finn-clojure-modes)

(defun finn-clojure-keys ()
  "Finn's Keybindings for Clojure-mode."
  (interactive)
  (local-set-key (kbd "C-c C-k") #'inf-clojure-load-file) )
(add-hook 'clojure-mode-hook #'finn-clojure-keys)

Haskell

Haskell is a pure functional programming language.

(setq haskell-interactive-popup-errors nil)      
(setq haskell-process-show-debug-tips nil)

(defun finn-haskell-keys ()
  "Finn's Keybindings for Haskell-mode."
  (interactive)
  (local-set-key (kbd "C-c C-k") #'haskell-process-load-file) )
(add-hook 'haskell-mode-hook #'finn-haskell-keys)

W3M

W3M is a text based web browser (standing for World Wide Web wo Miru, Japanese for See the World Wide Web) that has an Emacs inteface. It has some improvements over the Emacs standard browser, EWW.

(setq w3m-home-page "https://duckduckgo.com/lite/")
(setq w3m-search-default-engine "duckduckgo")

Bongo

;; ==================== Bongo Music Player Config
;; Send me to right directory
(setq bongo-default-directory "~/sounds/")
(bongo-insert-directory-tree "~/sounds/")
;; Change mode-line settings
(setq bongo-mode-line-playing-string ">")
(setq bongo-mode-line-paused-string "=")
(defun bongo-default-mode-line-indicator-function ()
  (concat " +" (bongo-mode-line-pause/resume-button) "+"))
;; Play my playlist in a random order
(bongo-random-playback-mode t)
;; Fixes Ogg123/MPG123 occasionally not stopping on exit
(add-hook 'kill-emacs-hook 'bongo-stop)