diff options
author | Sean Whitton <spwhitton@spwhitton.name> | 2017-01-28 20:34:56 -0700 |
---|---|---|
committer | Sean Whitton <spwhitton@spwhitton.name> | 2017-01-28 20:34:56 -0700 |
commit | 22194540508d25e545df5c35a971f27eb7ed56ea (patch) | |
tree | ba50920880a4c7e38b5d388c5febd1bbc5a6e8e3 /openwith.el |
import upstream version 0.8g
Diffstat (limited to 'openwith.el')
-rw-r--r-- | openwith.el | 120 |
1 files changed, 120 insertions, 0 deletions
diff --git a/openwith.el b/openwith.el new file mode 100644 index 0000000..e3cf3d0 --- /dev/null +++ b/openwith.el @@ -0,0 +1,120 @@ +;;; openwith.el --- Open files with external programs + +;; Copyright (C) 2007, 2013 Markus Triska + +;; Author: Markus Triska <markus.triska@gmx.at> +;; Keywords: files, processes + +;; This file is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation; either version 2, or (at your option) +;; any later version. + +;; This file is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with GNU Emacs; see the file COPYING. If not, write to +;; the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, +;; Boston, MA 02110-1301, USA. + +;;; Commentary: + +;; This lets you associate external applications with files so that +;; you can open them via C-x C-f, with RET in dired, etc. + +;; Copy openwith.el to your load-path and add to your .emacs: + +;; (require 'openwith) +;; (openwith-mode t) + +;; To customize associations etc., use: +;; +;; M-x customize-group RET openwith RET +;; +;; To prevent openwith-mode from interfering with attachments when +;; writing a message in Gnus, add the following to your .emacs: +;; +;; (require 'mm-util) +;; (add-to-list 'mm-inhibit-file-name-handlers 'openwith-file-handler) + +;;; Code: + +(defconst openwith-version "0.8g") + +(defgroup openwith nil + "Associate external applications with file name patterns." + :group 'files + :group 'processes) + +(defcustom openwith-associations + '(("\\.pdf\\'" "acroread" (file)) + ("\\.mp3\\'" "xmms" (file)) + ("\\.\\(?:mpe?g\\|avi\\|wmv\\)\\'" "mplayer" ("-idx" file)) + ("\\.\\(?:jp?g\\|png\\)\\'" "display" (file))) + "Associations of file patterns to external programs. +File pattern is a regular expression describing the files to +associate with a program. The program arguments are a list of +strings and symbols and are passed to the program on invocation, +where the symbol 'file' is replaced by the file to be opened." + :group 'openwith + :type '(repeat (list (regexp :tag "Files") + (string :tag "Program") + (sexp :tag "Parameters")))) + +(defcustom openwith-confirm-invocation nil + "Ask for confirmation before invoking external programs." + :group 'openwith + :type 'boolean) + +(defun openwith-file-handler (operation &rest args) + "Open file with external program, if an association is configured." + (when (and openwith-mode (not (buffer-modified-p)) (zerop (buffer-size))) + (let ((assocs openwith-associations) + (file (car args)) + oa) + ;; do not use `dolist' here, since some packages (like cl) + ;; temporarily unbind it + (while assocs + (setq oa (car assocs) + assocs (cdr assocs)) + (when (save-match-data (string-match (car oa) file)) + (let ((params (mapcar (lambda (x) (if (eq x 'file) file x)) + (nth 2 oa)))) + (when (or (not openwith-confirm-invocation) + (y-or-n-p (format "%s %s? " (cadr oa) + (mapconcat #'identity params " ")))) + (apply #'start-process "openwith-process" nil (cadr oa) params) + (kill-buffer nil) + ;; inhibit actions that would follow the regular + ;; insertion of file contents + (let (debug-on-error) + (error "Opened %s in external program" + (file-name-nondirectory file))))))))) + ;; when no association was found, relay the operation to other handlers + (let ((inhibit-file-name-handlers + (cons 'openwith-file-handler + (and (eq inhibit-file-name-operation operation) + inhibit-file-name-handlers))) + (inhibit-file-name-operation operation)) + (apply operation args))) + +;;;###autoload +(define-minor-mode openwith-mode + "Automatically open files with external programs." + :lighter "" + :global t + (if openwith-mode + (progn + ;; register `openwith-file-handler' for all files + (put 'openwith-file-handler 'safe-magic t) + (put 'openwith-file-handler 'operations '(insert-file-contents)) + (add-to-list 'file-name-handler-alist '("" . openwith-file-handler))) + (setq file-name-handler-alist + (delete '("" . openwith-file-handler) file-name-handler-alist)))) + +(provide 'openwith) + +;;; openwith.el ends here |