This patch hacks Emacs 20's browse-url.el to add and document BROWSER support. See the BROWSER page at http://www.tuxedo.org/~esr/BROWSER/ for discussion. --- browse-url.el 2001年01月24日 12:24:40 1.1 +++ browse-url.el 2001年01月24日 17:25:43 @@ -46,6 +46,19 @@ ;; browse-url-mmm MMM ? ;; browse-url-generic arbitrary +;; The user may set an explicit handler association list of URL-matching +;; regexps that dispatches to browser functions. If the environment +;; of Emacs includes a BROWSER variable, and the user has not set an +;; explicit list of URL handlers, the value of BROWSER is interpreted +;; a colon-separated series of browser command parts. These should be +;; tried in order until one succeeds. Each command part may +;; optionally contain the string "%s"; if it does, the URL to be +;; viewed is substituted there. If a command part does not contain +;; %s, the browser will be launched as if the URL had been supplied as +;; its first argument. If the user has neither set an explicit handler +;; list nor supplied BROWSER, Emacs falls back to a default browser +;; function (which the user may also configure). + ;; [A version of the Netscape browser is now free software ;; , albeit not GPLed, so it is ;; reasonable to have that as the default.] @@ -613,6 +626,53 @@ (browse-url-of-buffer)))) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; +;; Interpretation of the BROWSER variable. +;; See http://www.tuxedo.org/~esr/BROWSER/ for discussion. + +(defun browse-url-parse-colon-path (value) + "Explode a colon-separated search path into a list of parts." + (and value + (let (prefix part-list (start 0) colon) + (setq value (concat value ":")) + (while (setq colon (string-match ":" value start)) + (setq part-list + (nconc part-list + (list (if (= start colon) + nil + (substring value start colon))))) + (setq start (+ colon 1))) + part-list))) + +(defun browse-url-default-from-environment () + "Initialize browsers to be tried from the environment variable BROWSER. +The value of BROWSER may consist of a colon-separated series of +browser command parts. These should be tried in order until one succeeds. +Each command part may optionally contain the string \"%s\"; if it does, the +URL to be viewed is substituted there. If a command part does not +contain %s, the browser will be launched as if the URL had been +supplied as its first argument." + (mapcar + (lambda (part) + (cons "." + ;; First, look for the names of browsers we know about. + (cond ((string= part "netscape") 'browse-url-netscape) + ((string= part "mosaic") 'browse-url-mosaic) + ((string= part "grail") 'browse-url-grail) + ((string= part "iximosaic") 'browse-url-iximosaic) + ((string= part "w3") 'browse-url-w3) + ((string= part "lynx") 'browse-url-lynx-emacs) + ((string= part "mmm") 'browse-url-mmm) + ;; Not one we know about? OK, construct a lambda to call it. + (t + (let ((command + (cond ((string-match "%s" part) part) + (t (concat part " %s"))))) + `(lambda (url &optional new-window) + (start-process-shell-command + url nil (format ,command url)))))))) + (browse-url-parse-colon-path (getenv "BROWSER")))) + +;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;; Browser-independent commands ;; A generic command to call the current browse-url-browser-function @@ -623,19 +683,43 @@ Prompts for a URL, defaulting to the URL at or before point. Variable `browse-url-browser-function' says which browser to use." (interactive (browse-url-interactive-arg "URL: ")) - (if (functionp browse-url-browser-function) - (apply browse-url-browser-function url args) - ;; The `function' can be an alist; look down it for first match - ;; and apply the function (which might be a lambda). - (catch 'done - (mapcar - (lambda (bf) - (when (string-match (car bf) url) - (apply (cdr bf) url args) - (throw 'done t))) - browse-url-browser-function) - (error "No browser in browse-url-browser-function matching URL %s" - url)))) + ;; Weirdness here comes from trying to be backward compatible. The + ;; old behavior was to use `browse-url-browser-function' if it's a + ;; function, otherwise interpret it as a handler list. New + ;; behavior: if `browse-url-browser-function' is an explicit handler + ;; list, use it. Otherwise check to see if we can generate a handler + ;; list by parsing the BROWSER environment variable; if so, use that. + ;; Finally, if we neither have an explicit handler list nor can get one + ;; from BROWSER, just execute `browse-url-browser-function'. + (let ((handler-list + (cond ((and + browse-url-browser-function + (not (functionp browse-url-browser-function))) + browse-url-browser-function) + ((getenv "BROWSER") + (browse-url-default-from-environment)) + (t + nil)))) + (if (not handler-list) + (apply browse-url-browser-function url args) + ;; The `function' can be an alist; look down it for first match + ;; and apply the function (which might be a lambda). If the + ;; function throws an error, we take this as a signal that the attempt + ;; to launch the browser failed and continue down the list. Thus + ;; multiple handlers can match the same URL regexp; the first one + ;; to successfully launch terminates the search. + (catch 'done + (mapcar + (lambda (bf) + (when (string-match (car bf) url) + (condition-case nil + (progn + (apply (cdr bf) url args) + (throw 'done t)) + (error nil)))) + handler-list) + (error "No browser in browse-url-browser-function matching URL %s" + url))))) ;;;###autoload (defun browse-url-at-point ()

AltStyle によって変換されたページ (->オリジナル) /