Skip to content

Instantly share code, notes, and snippets.

@MetroWind
Created November 21, 2011 16:29
Show Gist options
  • Save MetroWind/1383142 to your computer and use it in GitHub Desktop.
Save MetroWind/1383142 to your computer and use it in GitHub Desktop.
Proper quote in Emacs
;; -*- mode: emacs-lisp; -*-
;; Usage: Just type. In text-mode (and derived modes) when you type '
;; and ", they will be converted to ‘’ and “”. Two dashes "--" will
;; be converted to an en-dash, and with an extra dash followed, they
;; will be converted to an em-dash.
;;
;; This also works in AUCTeX automagically(TM). Just type and let
;; Emacs take care of the rest.
;;
;; The TeX part requires AUCTeX. It also changes a keybinding in
;; CDLaTeX. If you don't use CDLaTeX, just search for it and delete
;; that line.
;; Insert a proper pair of quotes
(defun insert-pair-and-retreat (str)
"Inserts `str' and go back one character."
(insert str)
(backward-char))
(defun insert-single-quotes ()
"Inserts a proper pair of single quotes."
(interactive)
;; If the last char is "\", inserts a literal char.
(if (search-backward "\\" (- (point) 1) t)
(progn (forward-char) (insert "'"))
;; We need to detect if the quote is for, for example, "I'm",
;; "It's", "Bob's", etc, or for quotation.
(if (re-search-backward "[A-Za-z]" (- (point) 1) t)
(progn (forward-char) (insert "’"))
(insert-pair-and-retreat "‘’"))))
(defun insert-double-quotes ()
"Inserts a proper pair of double quotes."
(interactive)
;; If the last char is "\", inserts a literal char.
(if (search-backward "\\" (- (point) 1) t)
(progn (forward-char) (insert "\""))
(insert-pair-and-retreat "“”")))
(defun auto-insert-and-convert-dash ()
"Converts two dashes into an en-dash, or converts a en-dash
followed by a dash to an em-dash."
(interactive)
;; If the last char is "\", inserts a literal char.
(if (search-backward "\\" (- (point) 1) t)
(progn (forward-char) (insert "-"))
(progn
(insert "-")
(if (search-backward "--" (- (point) 2) t)
(replace-match "–"))
(if (search-backward "–-" (- (point) 2) t)
(replace-match "—")))))
(define-key text-mode-map "-" 'auto-insert-and-convert-dash)
(define-key text-mode-map "'" 'insert-single-quotes)
(define-key text-mode-map "\"" 'insert-double-quotes)
(defun insert-context-single-quotes ()
"Inserts a proper pair of single quotes in ConTeXt."
(interactive)
;; If the last char is "\", inserts a literal char.
(if (search-backward "\\" (- (point) 1) t)
(progn (forward-char) (insert "'"))
;; We need to detect if the quote is for, for example, "I'm",
;; "It's", "Bob's", etc, or for quotation.
(if (re-search-backward "[A-Za-z]" (- (point) 1) t)
(progn (forward-char) (insert "’"))
(insert-pair-and-retreat "\\quote{}"))))
(defun insert-context-double-quotes ()
"Inserts a proper pair of double quotes in ConTeXt"
(interactive)
;; If the last char is "\", inserts a literal char.
(if (search-backward "\\" (- (point) 1) t)
(progn (forward-char) (insert "\""))
(insert-pair-and-retreat "\\quotation{}")))
(defun deal-with-latex-quote ()
"If in math mode, insert a literal ', \", or -. If in normal
mode, insert a proper pair of quotes, or dash."
(define-key cdlatex-mode-map "'" nil)
(define-key LaTeX-mode-map "'"
(lambda ()
(interactive)
(if (texmathp)
(insert "'")
(insert-single-quotes))))
(define-key LaTeX-mode-map "\""
(lambda ()
(interactive)
(if (texmathp)
(insert "\"")
(insert-double-quotes))))
(define-key LaTeX-mode-map "-"
(lambda ()
(interactive)
(if (texmathp)
(insert "-")
(auto-insert-and-convert-dash)))))
(defun deal-with-context-quote ()
"If in math mode, insert a literal ', \", or -. If in normal
mode, insert a proper pair of quotes, or dash."
(define-key cdlatex-mode-map "'" nil)
(define-key ConTeXt-mode-map "'"
(lambda ()
(interactive)
(if (texmathp)
(insert "'")
(insert-context-single-quotes))))
(define-key ConTeXt-mode-map "\""
(lambda ()
(interactive)
(if (texmathp)
(insert "\"")
(insert-context-double-quotes))))
(define-key ConTeXt-mode-map "-"
(lambda ()
(interactive)
(if (texmathp)
(insert "-")
(auto-insert-and-convert-dash)))))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment