diff --git a/docs/modules.org b/docs/modules.org index d0fa65e86..8f9e728c0 100644 --- a/docs/modules.org +++ b/docs/modules.org @@ -191,7 +191,7 @@ Aesthetic modules that affect the Emacs interface or user experience. + [[file:../modules/ui/neotree/README.org][neotree]] - TODO + [[file:../modules/ui/ophints/README.org][ophints]] - TODO + [[file:../modules/ui/popup/README.org][popup]] =+all +defaults= - Makes temporary/disposable windows less intrusive -+ pretty-code - TODO ++ [[file:../modules//ui/pretty-code/README.org][pretty-code]] =+fira +hasklig +iosevka +pragmata-pro= - TODO + [[file:../modules/ui/tabs/README.org][tabs]] - TODO + treemacs - TODO + [[file:../modules/ui/unicode/README.org][unicode]] - TODO diff --git a/init.example.el b/init.example.el index 25bf97f3f..2d61ce29f 100644 --- a/init.example.el +++ b/init.example.el @@ -38,7 +38,7 @@ ;;neotree ; a project drawer, like NERDTree for vim ophints ; highlight the region an operation acts on (popup +defaults) ; tame sudden yet inevitable temporary windows - ;;pretty-code ; replace bits of code with pretty symbols + ;;pretty-code ; ligatures or substitute text with pretty symbols ;;tabs ; an tab bar for Emacs ;;treemacs ; a project drawer, like neotree but cooler ;;unicode ; extended unicode support for various languages diff --git a/modules/ui/pretty-code/README.org b/modules/ui/pretty-code/README.org new file mode 100644 index 000000000..d22e506f7 --- /dev/null +++ b/modules/ui/pretty-code/README.org @@ -0,0 +1,56 @@ +#+TITLE: ui/pretty-code +#+DATE: June 16, 2018 +#+SINCE: v2.0.9 +#+STARTUP: inlineimages nofold + +* Table of Contents :TOC_3:noexport: +- [[#description][Description]] + - [[#maintainers][Maintainers]] + - [[#module-flags][Module Flags]] + - [[#plugins][Plugins]] +- [[#prerequisites][Prerequisites]] +- [[#features][Features]] +- [[#configuration][Configuration]] + - [[#set-pretty-symbols][~set-pretty-symbols!~]] +- [[#troubleshooting][Troubleshooting]] + +* Description +This module enables ligatures and/or arbitrary symbol substitutions with +~prettify-symbols-mode~. + +** Maintainers +This module has no dedicated maintainers. + +** Module Flags ++ =+fira= Enables =Fira Code= ligatures. This requires Fira Code Symbol and a + patched version of Fira Code (see below). ++ =+hasklig= Enable =Hasklig= ligatures. This requires a patched version of the + HaskLig font (see below). ++ =+iosevka= Enable =Iosevka= ligatures. This requires a patched version of the + Iosevka font (see below). ++ =+pragmata-pro= Enable =Pragmata Pro= ligatures. This requires the [[https://www.fsd.it/shop/fonts/pragmatapro/][Pragmata + Pro font]]. + +** Plugins +This module installs no packages. + +* Prerequisites +For ligatures to work, you must: + +1. Enable one of the four ligature font flags: =+fira=, =+hasklig=, =+iosevka= + or =+pragmata-pro=. +2. Install the patched version of the associated font with ~M-x + +pretty-code/install-patched-font~. Note: Pragmata Pro cannot be installed + this way because it isn't a non-free font and must be purchased and installed + manually. + +* TODO Features +# An in-depth list of features, how to use them, and their dependencies. + +* TODO Configuration +# How to configure this module, including common problems and how to address them. + +** TODO ~set-pretty-symbols!~ + +* TODO Troubleshooting +# Common issues and their solution, or places to look for help. diff --git a/modules/ui/pretty-code/autoload/fira.el b/modules/ui/pretty-code/autoload/fira.el deleted file mode 100644 index 2a559cbd9..000000000 --- a/modules/ui/pretty-code/autoload/fira.el +++ /dev/null @@ -1,19 +0,0 @@ -;;; ui/pretty-code/autoload/fira.el -*- lexical-binding: t; -*- - -(defvar +pretty-code--fira-font-names - '("FiraCode-Bold.ttf" - "FiraCode-Light.ttf" - "FiraCode-Medium.ttf" - "FiraCode-Regular.ttf" - "FiraCode-Retina.ttf")) - -;;;###autoload -(defun +pretty-code/install-fira-font (&optional prefix) - "Download and install Fira Code font based on OS. -When prefix is non-nil, ignore the prompt and just install." - (interactive "P") - (+pretty-code--install-font - prefix - "FiraCode" - "https://github.com/tonsky/FiraCode/raw/13234c0/distr/ttf/%s" - +pretty-code--fira-font-names)) diff --git a/modules/ui/pretty-code/autoload/hasklig.el b/modules/ui/pretty-code/autoload/hasklig.el deleted file mode 100644 index 90fc295a6..000000000 --- a/modules/ui/pretty-code/autoload/hasklig.el +++ /dev/null @@ -1,28 +0,0 @@ -;;; ui/pretty-code/autoload/hasklig.el -*- lexical-binding: t; -*- - -(defvar +pretty-code--hasklig-font-names - '("Hasklig-Black.otf" - "Hasklig-BlackIt.otf" - "Hasklig-Bold.otf" - "Hasklig-BoldIt.otf" - "Hasklig-ExtraLight.otf" - "Hasklig-ExtraLightIt.otf" - "Hasklig-It.otf" - "Hasklig-Light.otf" - "Hasklig-LightIt.otf" - "Hasklig-Medium.otf" - "Hasklig-MediumIt.otf" - "Hasklig-Regular.otf" - "Hasklig-Semibold.otf" - "Hasklig-SemiboldIt.otf")) - -;;;###autoload -(defun +pretty-code/install-hasklig-font (&optional prefix) - "Download and install Hasklig font based on OS. -When prefix is non-nil, ignore the prompt and just install." - (interactive "P") - (+pretty-code--install-font - prefix - "Hasklig" - "https://github.com/jsravn/hasklig-emacs/raw/33354a3/%s" - +pretty-code--hasklig-font-names)) diff --git a/modules/ui/pretty-code/autoload/install.el b/modules/ui/pretty-code/autoload/install.el new file mode 100644 index 000000000..1f6e50207 --- /dev/null +++ b/modules/ui/pretty-code/autoload/install.el @@ -0,0 +1,100 @@ +;;; ui/pretty-code/autoload/install.el -*- lexical-binding: t; -*- +;;;###if (or (featurep! +fira) (featurep! +hasklig) (featurep! +iosevka)) + +(defvar +pretty-code-font-alist + '(("Fira Code" + :url "https://github.com/tonsky/FiraCode/raw/13234c0/distr/ttf/%s" + :files ("FiraCode-Bold.ttf" + "FiraCode-Light.ttf" + "FiraCode-Medium.ttf" + "FiraCode-Regular.ttf" + "FiraCode-Retina.ttf")) + ("Hasklig" + :url "https://github.com/jsravn/hasklig-emacs/raw/33354a3/%s" + :files ("Hasklig-Black.otf" + "Hasklig-BlackIt.otf" + "Hasklig-Bold.otf" + "Hasklig-BoldIt.otf" + "Hasklig-ExtraLight.otf" + "Hasklig-ExtraLightIt.otf" + "Hasklig-It.otf" + "Hasklig-Light.otf" + "Hasklig-LightIt.otf" + "Hasklig-Medium.otf" + "Hasklig-MediumIt.otf" + "Hasklig-Regular.otf" + "Hasklig-Semibold.otf" + "Hasklig-SemiboldIt.otf")) + ("Iosevka" + :url "https://github.com/jsravn/iosevka-emacs/raw/20fc2c4/%s" + :files ("iosevka-custom-lightoblique.ttf" + "iosevka-custom-thinoblique.ttf" + "iosevka-custom-mediumitalic.ttf" + "iosevka-custom-light.ttf" + "iosevka-custom-heavy.ttf" + "iosevka-custom-bolditalic.ttf" + "iosevka-custom-bold.ttf" + "iosevka-custom-lightitalic.ttf" + "iosevka-custom-thin.ttf" + "iosevka-custom-extralight.ttf" + "iosevka-custom-oblique.ttf" + "iosevka-custom-italic.ttf" + "iosevka-custom-heavyoblique.ttf" + "iosevka-custom-heavyitalic.ttf" + "iosevka-custom-extralightitalic.ttf" + "iosevka-custom-thinitalic.ttf" + "iosevka-custom-medium.ttf" + "iosevka-custom-mediumoblique.ttf" + "iosevka-custom-extralightoblique.ttf" + "iosevka-custom-boldoblique.ttf" + "iosevka-custom-regular.ttf"))) + "An alist of font metadata for `+pretty-code/install-font'.") + +(defun +pretty-code--install-font (prefix name url-format fonts-alist &optional extra-fonts) + "Install fonts to the local system. + +If PREFIX is nil, will prompt whether or not to download. NAME is informational +only. URL-FORMAT is a format string that should be a url and have a single %s, +which is expanded for each font in FONTS-ALIST. FONTS-ALIST should be the +filename of each font. It is used as the source and destination filename." + (or prefix + (yes-or-no-p + (format "This will download and install the %s fonts, are you +sure you want to do this?" name)) + (user-error "Aborted")) + (let* ((font-dest + (pcase window-system + (`x + (expand-file-name + "/fonts/" (or (getenv "XDG_DATA_HOME") + (concat (getenv "HOME") "/.local/share")))) + ((or `mac `ns) + (expand-file-name "~/Library/Fonts/" )))) + (known-dest? (stringp font-dest)) + (font-dest (or font-dest (read-directory-name "Font installation directory: " "~/")))) + (unless (file-directory-p font-dest) + (mkdir font-dest t)) + (dolist (font fonts-alist) + (url-copy-file (format url-format font) + (expand-file-name font font-dest) + t)) + (when known-dest? + (message "Font downloaded, updating font cache... ") + (shell-command-to-string (format "fc-cache -f -v"))) + (message "Successfully %s `%s' fonts to `%s'!%s" + (if known-dest? "installed" "downloaded") + name + font-dest))) + +;;;###autoload +(defun +pretty-code/install-patched-font (font-name &optional prefix) + "Install FONT-NAME on your system. +When PREFIX is non-nil, ignore the prompt and just install it." + (interactive + (list (completing-read + "Install font: " + (mapcar #'car +pretty-code-font-alist)))) + (if-let (font-files (cdr (assoc font-name +pretty-code-font-alist))) + (cl-destructuring-bind (&keys url files) font-files + (+pretty-code--install-font prefix font-name url font-files)) + (user-error "%S is not a valid font"))) diff --git a/modules/ui/pretty-code/autoload/iosevka.el b/modules/ui/pretty-code/autoload/iosevka.el deleted file mode 100644 index 4fa4f83da..000000000 --- a/modules/ui/pretty-code/autoload/iosevka.el +++ /dev/null @@ -1,35 +0,0 @@ -;;; ui/pretty-code/autoload/iosevka.el -*- lexical-binding: t; -*- - -(defvar +pretty-code--iosevka-font-names - '("iosevka-custom-lightoblique.ttf" - "iosevka-custom-thinoblique.ttf" - "iosevka-custom-mediumitalic.ttf" - "iosevka-custom-light.ttf" - "iosevka-custom-heavy.ttf" - "iosevka-custom-bolditalic.ttf" - "iosevka-custom-bold.ttf" - "iosevka-custom-lightitalic.ttf" - "iosevka-custom-thin.ttf" - "iosevka-custom-extralight.ttf" - "iosevka-custom-oblique.ttf" - "iosevka-custom-italic.ttf" - "iosevka-custom-heavyoblique.ttf" - "iosevka-custom-heavyitalic.ttf" - "iosevka-custom-extralightitalic.ttf" - "iosevka-custom-thinitalic.ttf" - "iosevka-custom-medium.ttf" - "iosevka-custom-mediumoblique.ttf" - "iosevka-custom-extralightoblique.ttf" - "iosevka-custom-boldoblique.ttf" - "iosevka-custom-regular.ttf")) - -;;;###autoload -(defun +pretty-code/install-iosevka-font (&optional prefix) - "Download and install Iosevka font based on OS. -When prefix is non-nil, ignore the prompt and just install." - (interactive "P") - (+pretty-code--install-font - prefix - "Iosevka" - "https://github.com/jsravn/iosevka-emacs/raw/20fc2c4/%s" - +pretty-code--iosevka-font-names)) diff --git a/modules/ui/pretty-code/config.el b/modules/ui/pretty-code/config.el index bb378e39a..fd34c1f1a 100644 --- a/modules/ui/pretty-code/config.el +++ b/modules/ui/pretty-code/config.el @@ -38,6 +38,27 @@ This should not contain any symbols from the Unicode Private Area! There is no universal way of getting the correct symbol as that area varies from font to font.") +(defvar +pretty-code-enabled-modes t + "List of major modes in which `prettify-symbols-mode' should be enabled. +If t, enable it everywhere. If the first element is 'not, enable it in any mode +besides what is listed.") + +(defvar +pretty-code-symbols-alist '((t)) + "An alist containing a mapping of major modes to its value for +`prettify-symbols-alist'.") + + +;; +;;; Packages + +;;;###package prettify-symbols +;; When you get to the right edge, it goes back to how it normally prints +(setq prettify-symbols-unprettify-at-point 'right-edge) + + +;; +;;; Bootstrap + (defun +pretty-code--correct-symbol-bounds (ligature-alist) "Prepend non-breaking spaces to a ligature. @@ -50,14 +71,6 @@ correct width of the symbols instead of the width measured by `char-width'." len (1- len))) (cons (car ligature-alist) acc))) -(defvar +pretty-code-enabled-modes t - "List of major modes in which `prettify-symbols-mode' should be enabled. -If t, enable it everywhere. If the first element is 'not, enable it in any mode -besides what is listed.") - -;; When you get to the right edge, it goes back to how it normally prints -(setq prettify-symbols-unprettify-at-point 'right-edge) - (defun +pretty-code-init-pretty-symbols-h () "Enable `prettify-symbols-mode'. @@ -80,6 +93,7 @@ Otherwise it builds `prettify-code-symbols-alist' according to (prettify-symbols-mode -1)) (prettify-symbols-mode +1)))) + (add-hook 'after-change-major-mode-hook #'+pretty-code-init-pretty-symbols-h) ;; The emacs-mac build of Emacs appear to have built-in support for ligatures, @@ -95,38 +109,3 @@ Otherwise it builds `prettify-code-symbols-alist' according to (load! "+hasklig")) ((featurep! +pragmata-pro) (load! "+pragmata-pro"))) - -(defun +pretty-code--install-font (prefix name url-format fonts-alist) - "Install fonts to the local system. - -If PREFIX is nil, will prompt whether or not to download. NAME is informational only. -URL-FORMAT is a format string that should be a url and have a single %s, which is expanded -for each font in FONTS-ALIST. FONTS-ALIST should be the filename of each font. It is used -as the source and destination filename. -" - (when (or prefix (yes-or-no-p - (format "This will download and install the %s fonts, are you sure you want to do this?" name))) - (let* ((font-dest (cl-case window-system - ;; Linux - (x (concat (or (getenv "XDG_DATA_HOME") - (concat (getenv "HOME") "/.local/share")) - "/fonts/")) - ;; MacOS - (mac (concat (getenv "HOME") "/Library/Fonts/" )) - (ns (concat (getenv "HOME") "/Library/Fonts/" )))) - (known-dest? (stringp font-dest)) - (font-dest (or font-dest (read-directory-name "Font installation directory: " "~/")))) - - (unless (file-directory-p font-dest) (mkdir font-dest t)) - - (dolist (font fonts-alist) - (url-copy-file (format url-format font) (expand-file-name font font-dest) t)) - - (when known-dest? - (message "Font downloaded, updating font cache... ") - (shell-command-to-string (format "fc-cache -f -v"))) - (message "Successfully %s `%s' fonts to `%s'!" - (if known-dest? "installed" "downloaded") - name - font-dest))) - )