X-Git-Url: https://git.hcoop.net/bpt/emacs.git/blobdiff_plain/1bad168e59601c1c843a38b2962e77b29f497f11..7185da524d81acaaa872f8f803870d8c57c8b4c9:/lisp/info-look.el diff --git a/lisp/info-look.el b/lisp/info-look.el index 6caf454546..13edc0269d 100644 --- a/lisp/info-look.el +++ b/lisp/info-look.el @@ -1,8 +1,7 @@ -;;; info-look.el --- major-mode-sensitive Info index lookup facility +;;; info-look.el --- major-mode-sensitive Info index lookup facility -*- lexical-binding: t -*- ;; An older version of this was known as libc.el. -;; Copyright (C) 1995, 1996, 1997, 1998, 1999, 2001, 2002, 2003, -;; 2004, 2005, 2006, 2007, 2008 Free Software Foundation, Inc. +;; Copyright (C) 1995-1999, 2001-2011 Free Software Foundation, Inc. ;; Author: Ralph Schleicher ;; (did not show signs of life (Nov 2001) -stef) @@ -10,10 +9,10 @@ ;; This file is part of GNU Emacs. -;; GNU Emacs is free software; you can redistribute it and/or modify +;; GNU Emacs 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 3, or (at your option) -;; any later version. +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. ;; GNU Emacs is distributed in the hope that it will be useful, ;; but WITHOUT ANY WARRANTY; without even the implied warranty of @@ -21,9 +20,7 @@ ;; 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. +;; along with GNU Emacs. If not, see . ;;; Commentary: @@ -130,9 +127,9 @@ OTHER-MODES is a list of cross references to other help modes.") (defun info-lookup-add-help (&rest arg) "Add or update a help specification. -Function arguments are one or more options of the form +Function arguments are specified as keyword/argument pairs: - KEYWORD ARGUMENT + \(KEYWORD . ARGUMENT) KEYWORD is either `:topic', `:mode', `:regexp', `:ignore-case', `:doc-spec', `:parse-rule', or `:other-modes'. @@ -337,29 +334,30 @@ If optional argument QUERY is non-nil, query for the help mode." (cons (list Info-current-file Info-current-node (point)) Info-history)))) found doc-spec node prefix suffix doc-found) - (if (not (eq major-mode 'Info-mode)) - (if (not info-lookup-other-window-flag) - (info) - (progn - (save-window-excursion (info)) - ;; Determine whether or not the Info buffer is visible in - ;; another frame on the same display. If it is, simply raise - ;; that frame. Otherwise, display it in another window. - (let* ((window (get-buffer-window "*info*" t)) - (info-frame (and window (window-frame window)))) - (if (and info-frame - (display-multi-frame-p) - (memq info-frame (frames-on-display-list)) - (not (eq info-frame (selected-frame)))) - (select-frame info-frame) - (switch-to-buffer-other-window "*info*")))))) + (unless (eq major-mode 'Info-mode) + (if (not info-lookup-other-window-flag) + (info) + (save-window-excursion (info)) + (let* ((info-window (get-buffer-window "*info*" t)) + (info-frame (and info-window (window-frame info-window)))) + (if (and info-frame + (not (eq info-frame (selected-frame))) + (display-multi-frame-p) + (memq info-frame (frames-on-display-list))) + ;; *info* is visible in another frame on same display. + ;; Raise that frame and select the window. + (progn + (select-window info-window) + (raise-frame info-frame)) + ;; In any other case, switch to *info* in another window. + (switch-to-buffer-other-window "*info*"))))) (while (and (not found) modes) (setq doc-spec (info-lookup->doc-spec topic (car modes))) (while (and (not found) doc-spec) (setq node (nth 0 (car doc-spec)) prefix (nth 2 (car doc-spec)) suffix (nth 3 (car doc-spec))) - (when (condition-case error-data + (when (condition-case nil (progn ;; Don't need Index menu fontifications here, and ;; they slow down the lookup. @@ -475,7 +473,7 @@ If optional argument QUERY is non-nil, query for the help mode." (t (nth 1 (car doc-spec))))) (with-current-buffer buffer (message "Processing Info node `%s'..." node) - (when (condition-case error-data + (when (condition-case nil (progn (Info-goto-node node) (setq doc-found t)) @@ -643,44 +641,42 @@ Return nil if there is nothing appropriate in the buffer near point." info-lookup-mode (info-lookup-change-mode 'file))))) +(defun info-lookup-completions-at-point (topic mode) + "Try to complete a help item." + (or mode (setq mode (info-lookup-select-mode))) + (when (info-lookup->mode-value topic mode) + (let ((modes (info-lookup-quick-all-modes topic mode)) + (start (point)) + try) + (while (and (not try) modes) + (setq mode (car modes) + modes (cdr modes) + try (info-lookup-guess-default* topic mode)) + (goto-char start)) + (when try + (let ((completions (info-lookup->completions topic mode))) + (when completions + (when (info-lookup->ignore-case topic mode) + (setq completions + (lambda (string pred action) + (let ((completion-ignore-case t)) + (complete-with-action + action completions string pred))))) + (save-excursion + ;; Find the original symbol and zap it. + (end-of-line) + (while (and (search-backward try nil t) + (< start (point)))) + (list (match-beginning 0) (match-end 0) completions + :exclusive 'no)))))))) + (defun info-complete (topic mode) "Try to complete a help item." (barf-if-buffer-read-only) - (or mode (setq mode (info-lookup-select-mode))) - (or (info-lookup->mode-value topic mode) - (error "No %s completion available for `%s'" topic mode)) - (let ((modes (info-lookup-quick-all-modes topic mode)) - (start (point)) - try) - (while (and (not try) modes) - (setq mode (car modes) - modes (cdr modes) - try (info-lookup-guess-default* topic mode)) - (goto-char start)) - (and (not try) - (error "Found no %S to complete" topic)) - (let ((completions (info-lookup->completions topic mode)) - (completion-ignore-case (info-lookup->ignore-case topic mode)) - completion) - (setq completion (try-completion try completions)) - (cond ((not completion) - (ding) - (message "No match")) - ((stringp completion) - (or (assoc completion completions) - (setq completion (completing-read - (format "Complete %S: " topic) - completions nil t completion - info-lookup-history))) - ;; Find the original symbol and zap it. - (end-of-line) - (while (and (search-backward try nil t) - (< start (point)))) - (replace-match "") - (insert completion)) - (t - (message "%s is complete" - (capitalize (prin1-to-string topic)))))))) + (let ((data (info-lookup-completions-at-point topic mode))) + (if (null data) + (error "No %s completion available for `%s' at point" topic mode) + (completion-in-region (nth 0 data) (nth 1 data) (nth 2 data))))) ;;; Initialize some common modes. @@ -722,11 +718,31 @@ Return nil if there is nothing appropriate in the buffer near point." :mode 'makefile-mode :regexp "\\$[^({]\\|\\.[_A-Z]*\\|[_a-zA-Z][_a-zA-Z0-9-]*" :doc-spec '(("(make)Name Index" nil - "^[ \t]*`" "'") - ("(automake)Macro and Variable Index" nil "^[ \t]*`" "'")) - :parse-rule "\\$[^({]\\|\\.[_A-Z]*\\|[_a-zA-Z0-9-]+" - :other-modes '(automake-mode)) + :parse-rule "\\$[^({]\\|\\.[_A-Z]*\\|[_a-zA-Z0-9-]+") + +(info-lookup-maybe-add-help + :topic 'symbol + :mode 'makefile-automake-mode + ;; similar regexp/parse-rule as makefile-mode, but also the following + ;; (which have index entries), + ;; "##" special automake comment + ;; "+=" append operator, separate from the GNU make one + :regexp "\\$[^({]\\|\\.[_A-Z]*\\|[_a-zA-Z][_a-zA-Z0-9-]*\\|##\\|\\+=" + :parse-rule "\\$[^({]\\|\\.[_A-Z]*\\|[_a-zA-Z0-9-]+\\|##\\|\\+=" + :doc-spec '( + ;; "(automake)Macro Index" is autoconf macros used in + ;; configure.in, not Makefile.am, so don't have that here. + ("(automake)Variable Index" nil "^[ \t]*`" "'") + ;; In automake 1.4 macros and variables were a combined node. + ("(automake)Macro and Variable Index" nil "^[ \t]*`" "'") + ;; Directives like "if" are in the "General Index". + ;; Prefix "`" since the text for say `+=' isn't always an + ;; @item etc and so not always at the start of a line. + ("(automake)General Index" nil "`" "'") + ;; In automake 1.3 there was just a single "Index" node. + ("(automake)Index" nil "`" "'")) + :other-modes '(makefile-mode)) (info-lookup-maybe-add-help :mode 'texinfo-mode @@ -757,12 +773,15 @@ Return nil if there is nothing appropriate in the buffer near point." ;; M4 Macro Index entries are without "AS_" prefixes, and ;; mostly without "m4_" prefixes. "dnl" is an exception, not ;; wanting any prefix. So AS_ is added back to upper-case - ;; names, m4_ to others which don't already an m4_. + ;; names (if needed), m4_ to others which don't already an m4_. ("(autoconf)M4 Macro Index" (lambda (item) (let ((case-fold-search nil)) (cond ((or (string-equal item "dnl") - (string-match "^m4_" item)) + (string-match "^m4_" item) + ;; Autoconf 2.62 index includes some macros + ;; (e.g., AS_HELP_STRING), so avoid prefixing. + (string-match "^AS_" item)) item) ((string-match "^[A-Z0-9_]+$" item) (concat "AS_" item)) @@ -859,6 +878,12 @@ Return nil if there is nothing appropriate in the buffer near point." ;; sort of fallback match scheme existed. ("(elisp)Index" nil "^ -+ .*: " "\\( \\|$\\)"))) +;; docstrings talk about elisp, so have apropos-mode follow emacs-lisp-mode +(info-lookup-maybe-add-help + :mode 'apropos-mode + :regexp "[^][()`',\" \t\n]+" ;; same as emacs-lisp-mode above + :other-modes '(emacs-lisp-mode)) + (info-lookup-maybe-add-help :mode 'lisp-interaction-mode :regexp "[^][()`',\" \t\n]+" @@ -881,10 +906,11 @@ Return nil if there is nothing appropriate in the buffer near point." (info-lookup-maybe-add-help :mode 'octave-mode - :regexp "[_a-zA-Z0-9]+" + :regexp "[_a-zA-Z0-9]+\\|\\s.+\\|[-!=^|*/.\\,><~&+]\\{1,3\\}\\|[][();,\"']" :doc-spec '(("(octave)Function Index" nil "^ -+ [^:]+:[ ]+\\(\\[[^=]*=[ ]+\\)?" nil) ("(octave)Variable Index" nil "^ -+ [^:]+:[ ]+" nil) + ("(octave)Operator Index" nil nil nil) ;; Catch lines of the form "xyz statement" ("(octave)Concept Index" (lambda (item) @@ -927,11 +953,18 @@ Return nil if there is nothing appropriate in the buffer near point." :doc-spec '(("(bash)Builtin Index" nil "^`" "[ .']") ("(bash)Reserved Word Index" nil "^`" "[ .']") ("(bash)Variable Index" nil "^`" "[ .']") + ;; coreutils (version 4.5.10) doesn't have a separate program ;; index, so exclude extraneous stuff (most of it) by demanding ;; "[a-z]+" in the trans-func. + ;; coreutils version 8.1 has node "Concept Index" and past + ;; versions have node "Index", look for both, whichever is + ;; absent is quietly ignored ("(coreutils)Index" (lambda (item) (if (string-match "\\`[a-z]+\\'" item) item))) + ("(coreutils)Concept Index" + (lambda (item) (if (string-match "\\`[a-z]+\\'" item) item))) + ;; diff (version 2.8.1) has only a few programs, index entries ;; are things like "foo invocation". ("(diff)Index" @@ -970,7 +1003,7 @@ Return nil if there is nothing appropriate in the buffer near point." "`" "("))) (info-lookup-maybe-add-help - :mode 'custom-mode + :mode 'Custom-mode :ignore-case t :regexp "[^][()`',:\" \t\n]+" :parse-rule 'info-lookup-guess-custom-symbol @@ -983,5 +1016,4 @@ Return nil if there is nothing appropriate in the buffer near point." (provide 'info-look) -;;; arch-tag: 0f1e3ea3-32a2-4461-bbab-3cff93539a74 ;;; info-look.el ends here