diff options
Diffstat (limited to 'lisp/help.el')
| -rw-r--r-- | lisp/help.el | 308 |
1 files changed, 143 insertions, 165 deletions
diff --git a/lisp/help.el b/lisp/help.el index db76efb01a0..34b1a2fac61 100644 --- a/lisp/help.el +++ b/lisp/help.el | |||
| @@ -309,7 +309,7 @@ If that doesn't give a function, return nil." | |||
| 309 | The prefix described consists of all but the last event | 309 | The prefix described consists of all but the last event |
| 310 | of the key sequence that ran this command." | 310 | of the key sequence that ran this command." |
| 311 | (interactive) | 311 | (interactive) |
| 312 | (let* ((key (this-command-keys))) | 312 | (let ((key (this-command-keys))) |
| 313 | (describe-bindings | 313 | (describe-bindings |
| 314 | (if (stringp key) | 314 | (if (stringp key) |
| 315 | (substring key 0 (1- (length key))) | 315 | (substring key 0 (1- (length key))) |
| @@ -535,28 +535,6 @@ If INSERT (the prefix arg) is non-nil, insert the message in the buffer." | |||
| 535 | (princ string))))) | 535 | (princ string))))) |
| 536 | nil) | 536 | nil) |
| 537 | 537 | ||
| 538 | (defun string-key-binding (key) | ||
| 539 | "Value is the binding of KEY in a string. | ||
| 540 | If KEY is an event on a string, and that string has a `local-map' | ||
| 541 | or `keymap' property, return the binding of KEY in the string's keymap." | ||
| 542 | (let* ((defn nil) | ||
| 543 | (start (when (vectorp key) | ||
| 544 | (if (memq (aref key 0) | ||
| 545 | '(mode-line header-line left-margin right-margin)) | ||
| 546 | (event-start (aref key 1)) | ||
| 547 | (and (consp (aref key 0)) | ||
| 548 | (event-start (aref key 0)))))) | ||
| 549 | (string-info (and (consp start) (nth 4 start)))) | ||
| 550 | (when string-info | ||
| 551 | (let* ((string (car string-info)) | ||
| 552 | (pos (cdr string-info)) | ||
| 553 | (local-map (and (>= pos 0) | ||
| 554 | (< pos (length string)) | ||
| 555 | (or (get-text-property pos 'local-map string) | ||
| 556 | (get-text-property pos 'keymap string))))) | ||
| 557 | (setq defn (and local-map (lookup-key local-map key))))) | ||
| 558 | defn)) | ||
| 559 | |||
| 560 | (defun help-key-description (key untranslated) | 538 | (defun help-key-description (key untranslated) |
| 561 | (let ((string (key-description key))) | 539 | (let ((string (key-description key))) |
| 562 | (if (or (not untranslated) | 540 | (if (or (not untranslated) |
| @@ -589,11 +567,14 @@ temporarily enables it to allow getting help on disabled items and buttons." | |||
| 589 | (menu-bar-update-yank-menu "(any string)" nil)) | 567 | (menu-bar-update-yank-menu "(any string)" nil)) |
| 590 | (setq key (read-key-sequence "Describe key (or click or menu item): ")) | 568 | (setq key (read-key-sequence "Describe key (or click or menu item): ")) |
| 591 | ;; If KEY is a down-event, read and discard the | 569 | ;; If KEY is a down-event, read and discard the |
| 592 | ;; corresponding up-event. | 570 | ;; corresponding up-event. Note that there are also |
| 593 | (if (and (vectorp key) | 571 | ;; down-events on scroll bars and mode lines: the actual |
| 594 | (eventp (elt key 0)) | 572 | ;; event then is in the second element of the vector. |
| 595 | (memq 'down (event-modifiers (elt key 0)))) | 573 | (and (vectorp key) |
| 596 | (read-event)) | 574 | (let ((last-idx (1- (length key)))) |
| 575 | (and (eventp (aref key last-idx)) | ||
| 576 | (memq 'down (event-modifiers (aref key last-idx))))) | ||
| 577 | (read-event)) | ||
| 597 | (list | 578 | (list |
| 598 | key | 579 | key |
| 599 | (if current-prefix-arg (prefix-numeric-value current-prefix-arg)) | 580 | (if current-prefix-arg (prefix-numeric-value current-prefix-arg)) |
| @@ -604,46 +585,33 @@ temporarily enables it to allow getting help on disabled items and buttons." | |||
| 604 | (fset 'yank-menu (cons 'keymap yank-menu)))))) | 585 | (fset 'yank-menu (cons 'keymap yank-menu)))))) |
| 605 | (if (numberp untranslated) | 586 | (if (numberp untranslated) |
| 606 | (setq untranslated (this-single-command-raw-keys))) | 587 | (setq untranslated (this-single-command-raw-keys))) |
| 607 | (save-excursion | 588 | (let* ((event (if (and (symbolp (aref key 0)) |
| 608 | (let ((modifiers (event-modifiers (aref key 0))) | 589 | (> (length key) 1) |
| 609 | (standard-output (if insert (current-buffer) t)) | 590 | (consp (aref key 1))) |
| 610 | window position) | 591 | (aref key 1) |
| 611 | ;; For a mouse button event, go to the button it applies to | 592 | (aref key 0))) |
| 612 | ;; to get the right key bindings. And go to the right place | 593 | (modifiers (event-modifiers event)) |
| 613 | ;; in case the keymap depends on where you clicked. | 594 | (standard-output (if insert (current-buffer) t)) |
| 614 | (if (or (memq 'click modifiers) (memq 'down modifiers) | 595 | (mouse-msg (if (or (memq 'click modifiers) (memq 'down modifiers) |
| 615 | (memq 'drag modifiers)) | 596 | (memq 'drag modifiers)) " at that spot" "")) |
| 616 | (setq window (posn-window (event-start (aref key 0))) | 597 | (defn (key-binding key t)) |
| 617 | position (posn-point (event-start (aref key 0))))) | 598 | key-desc) |
| 618 | (if (windowp window) | 599 | ;; Handle the case where we faked an entry in "Select and Paste" menu. |
| 619 | (progn | 600 | (if (and (eq defn nil) |
| 620 | (set-buffer (window-buffer window)) | 601 | (stringp (aref key (1- (length key)))) |
| 621 | (goto-char position))) | 602 | (eq (key-binding (substring key 0 -1)) 'yank-menu)) |
| 622 | ;; Ok, now look up the key and name the command. | 603 | (setq defn 'menu-bar-select-yank)) |
| 623 | (let ((defn (or (string-key-binding key) | 604 | ;; Don't bother user with strings from (e.g.) the select-paste menu. |
| 624 | (key-binding key t))) | 605 | (if (stringp (aref key (1- (length key)))) |
| 625 | key-desc) | 606 | (aset key (1- (length key)) "(any string)")) |
| 626 | ;; Handle the case where we faked an entry in "Select and Paste" menu. | 607 | (if (and (> (length untranslated) 0) |
| 627 | (if (and (eq defn nil) | 608 | (stringp (aref untranslated (1- (length untranslated))))) |
| 628 | (stringp (aref key (1- (length key)))) | 609 | (aset untranslated (1- (length untranslated)) "(any string)")) |
| 629 | (eq (key-binding (substring key 0 -1)) 'yank-menu)) | 610 | ;; Now describe the key, perhaps as changed. |
| 630 | (setq defn 'menu-bar-select-yank)) | 611 | (setq key-desc (help-key-description key untranslated)) |
| 631 | ;; Don't bother user with strings from (e.g.) the select-paste menu. | 612 | (if (or (null defn) (integerp defn) (equal defn 'undefined)) |
| 632 | (if (stringp (aref key (1- (length key)))) | 613 | (princ (format "%s%s is undefined" key-desc mouse-msg)) |
| 633 | (aset key (1- (length key)) "(any string)")) | 614 | (princ (format "%s%s runs the command %S" key-desc mouse-msg defn))))) |
| 634 | (if (and (> (length untranslated) 0) | ||
| 635 | (stringp (aref untranslated (1- (length untranslated))))) | ||
| 636 | (aset untranslated (1- (length untranslated)) | ||
| 637 | "(any string)")) | ||
| 638 | ;; Now describe the key, perhaps as changed. | ||
| 639 | (setq key-desc (help-key-description key untranslated)) | ||
| 640 | (if (or (null defn) (integerp defn) (equal defn 'undefined)) | ||
| 641 | (princ (format "%s is undefined" key-desc)) | ||
| 642 | (princ (format (if (windowp window) | ||
| 643 | "%s at that spot runs the command %s" | ||
| 644 | "%s runs the command %s") | ||
| 645 | key-desc | ||
| 646 | (if (symbolp defn) defn (prin1-to-string defn))))))))) | ||
| 647 | 615 | ||
| 648 | (defun describe-key (&optional key untranslated up-event) | 616 | (defun describe-key (&optional key untranslated up-event) |
| 649 | "Display documentation of the function invoked by KEY. | 617 | "Display documentation of the function invoked by KEY. |
| @@ -673,109 +641,119 @@ temporarily enables it to allow getting help on disabled items and buttons." | |||
| 673 | (list | 641 | (list |
| 674 | key | 642 | key |
| 675 | (prefix-numeric-value current-prefix-arg) | 643 | (prefix-numeric-value current-prefix-arg) |
| 676 | ;; If KEY is a down-event, read the corresponding up-event | 644 | ;; If KEY is a down-event, read and discard the |
| 677 | ;; and use it as the third argument. | 645 | ;; corresponding up-event. Note that there are also |
| 678 | (if (and (vectorp key) | 646 | ;; down-events on scroll bars and mode lines: the actual |
| 679 | (eventp (elt key 0)) | 647 | ;; event then is in the second element of the vector. |
| 680 | (memq 'down (event-modifiers (elt key 0)))) | 648 | (and (vectorp key) |
| 681 | (read-event)))) | 649 | (let ((last-idx (1- (length key)))) |
| 650 | (and (eventp (aref key last-idx)) | ||
| 651 | (memq 'down (event-modifiers (aref key last-idx))))) | ||
| 652 | (or (and (eventp (aref key 0)) | ||
| 653 | (memq 'down (event-modifiers (aref key 0))) | ||
| 654 | ;; However, for the C-down-mouse-2 popup | ||
| 655 | ;; menu, there is no subsequent up-event. In | ||
| 656 | ;; this case, the up-event is the next | ||
| 657 | ;; element in the supplied vector. | ||
| 658 | (= (length key) 1)) | ||
| 659 | (and (> (length key) 1) | ||
| 660 | (eventp (aref key 1)) | ||
| 661 | (memq 'down (event-modifiers (aref key 1))))) | ||
| 662 | (read-event)))) | ||
| 682 | ;; Put yank-menu back as it was, if we changed it. | 663 | ;; Put yank-menu back as it was, if we changed it. |
| 683 | (when saved-yank-menu | 664 | (when saved-yank-menu |
| 684 | (setq yank-menu (copy-sequence saved-yank-menu)) | 665 | (setq yank-menu (copy-sequence saved-yank-menu)) |
| 685 | (fset 'yank-menu (cons 'keymap yank-menu)))))) | 666 | (fset 'yank-menu (cons 'keymap yank-menu)))))) |
| 686 | (if (numberp untranslated) | 667 | (if (numberp untranslated) |
| 687 | (setq untranslated (this-single-command-raw-keys))) | 668 | (setq untranslated (this-single-command-raw-keys))) |
| 688 | (save-excursion | 669 | (let* ((event (aref key (if (and (symbolp (aref key 0)) |
| 689 | (let ((modifiers (event-modifiers (aref key 0))) | 670 | (> (length key) 1) |
| 690 | window position) | 671 | (consp (aref key 1))) |
| 691 | ;; For a mouse button event, go to the button it applies to | 672 | 1 |
| 692 | ;; to get the right key bindings. And go to the right place | 673 | 0))) |
| 693 | ;; in case the keymap depends on where you clicked. | 674 | (modifiers (event-modifiers event)) |
| 694 | (if (or (memq 'click modifiers) (memq 'down modifiers) | 675 | (mouse-msg (if (or (memq 'click modifiers) (memq 'down modifiers) |
| 695 | (memq 'drag modifiers)) | 676 | (memq 'drag modifiers)) " at that spot" "")) |
| 696 | (setq window (posn-window (event-start (aref key 0))) | 677 | (defn (key-binding key t)) |
| 697 | position (posn-point (event-start (aref key 0))))) | 678 | defn-up defn-up-tricky ev-type |
| 698 | (when (windowp window) | 679 | mouse-1-remapped mouse-1-tricky) |
| 699 | (set-buffer (window-buffer window)) | 680 | |
| 700 | (goto-char position)) | 681 | ;; Handle the case where we faked an entry in "Select and Paste" menu. |
| 701 | (let ((defn (or (string-key-binding key) (key-binding key t)))) | 682 | (when (and (eq defn nil) |
| 702 | ;; Handle the case where we faked an entry in "Select and Paste" menu. | 683 | (stringp (aref key (1- (length key)))) |
| 703 | (if (and (eq defn nil) | 684 | (eq (key-binding (substring key 0 -1)) 'yank-menu)) |
| 704 | (stringp (aref key (1- (length key)))) | 685 | (setq defn 'menu-bar-select-yank)) |
| 705 | (eq (key-binding (substring key 0 -1)) 'yank-menu)) | 686 | (if (or (null defn) (integerp defn) (equal defn 'undefined)) |
| 706 | (setq defn 'menu-bar-select-yank)) | 687 | (message "%s%s is undefined" |
| 707 | (if (or (null defn) (integerp defn) (equal defn 'undefined)) | 688 | (help-key-description key untranslated) mouse-msg) |
| 708 | (message "%s is undefined" (help-key-description key untranslated)) | 689 | (help-setup-xref (list #'describe-function defn) (interactive-p)) |
| 709 | (help-setup-xref (list #'describe-function defn) (interactive-p)) | 690 | ;; Don't bother user with strings from (e.g.) the select-paste menu. |
| 710 | ;; Don't bother user with strings from (e.g.) the select-paste menu. | 691 | (when (stringp (aref key (1- (length key)))) |
| 711 | (if (stringp (aref key (1- (length key)))) | 692 | (aset key (1- (length key)) "(any string)")) |
| 712 | (aset key (1- (length key)) "(any string)")) | 693 | (when (and untranslated |
| 713 | (if (and untranslated | 694 | (stringp (aref untranslated (1- (length untranslated))))) |
| 714 | (stringp (aref untranslated (1- (length untranslated))))) | 695 | (aset untranslated (1- (length untranslated)) |
| 715 | (aset untranslated (1- (length untranslated)) | 696 | "(any string)")) |
| 716 | "(any string)")) | 697 | ;; Need to do this before erasing *Help* buffer in case event |
| 717 | (with-output-to-temp-buffer (help-buffer) | 698 | ;; is a mouse click in an existing *Help* buffer. |
| 718 | (princ (help-key-description key untranslated)) | 699 | (when up-event |
| 719 | (if (windowp window) | 700 | (setq ev-type (event-basic-type up-event)) |
| 720 | (princ " at that spot")) | 701 | (let ((sequence (vector up-event))) |
| 721 | (princ " runs the command ") | 702 | (when (and (eq ev-type 'mouse-1) |
| 722 | (prin1 defn) | 703 | mouse-1-click-follows-link |
| 723 | (princ "\n which is ") | 704 | (not (eq mouse-1-click-follows-link 'double)) |
| 724 | (describe-function-1 defn) | 705 | (setq mouse-1-remapped |
| 725 | (when up-event | 706 | (mouse-on-link-p (event-start up-event)))) |
| 726 | (let ((type (event-basic-type up-event)) | 707 | (setq mouse-1-tricky (and (integerp mouse-1-click-follows-link) |
| 727 | (hdr "\n\n-------------- up event ---------------\n\n") | 708 | (> mouse-1-click-follows-link 0))) |
| 728 | defn sequence | 709 | (cond ((stringp mouse-1-remapped) |
| 729 | mouse-1-tricky mouse-1-remapped) | 710 | (setq sequence mouse-1-remapped)) |
| 730 | (setq sequence (vector up-event)) | 711 | ((vectorp mouse-1-remapped) |
| 731 | (when (and (eq type 'mouse-1) | 712 | (setcar up-event (elt mouse-1-remapped 0))) |
| 732 | (windowp window) | 713 | (t (setcar up-event 'mouse-2)))) |
| 714 | (setq defn-up (key-binding sequence nil nil (event-start up-event))) | ||
| 715 | (when mouse-1-tricky | ||
| 716 | (setq sequence (vector up-event)) | ||
| 717 | (aset sequence 0 'mouse-1) | ||
| 718 | (setq defn-up-tricky (key-binding sequence nil nil (event-start up-event)))))) | ||
| 719 | (with-output-to-temp-buffer (help-buffer) | ||
| 720 | (princ (help-key-description key untranslated)) | ||
| 721 | (princ (format "\ | ||
| 722 | %s runs the command %S | ||
| 723 | which is " | ||
| 724 | mouse-msg defn)) | ||
| 725 | (describe-function-1 defn) | ||
| 726 | (when up-event | ||
| 727 | (unless (or (null defn-up) | ||
| 728 | (integerp defn-up) | ||
| 729 | (equal defn-up 'undefined)) | ||
| 730 | (princ (format " | ||
| 731 | |||
| 732 | ----------------- up-event %s---------------- | ||
| 733 | |||
| 734 | <%S>%s%s runs the command %S | ||
| 735 | which is " | ||
| 736 | (if mouse-1-tricky "(short click) " "") | ||
| 737 | ev-type mouse-msg | ||
| 738 | (if mouse-1-remapped | ||
| 739 | " is remapped to <mouse-2>\nwhich" "") | ||
| 740 | defn-up)) | ||
| 741 | (describe-function-1 defn-up)) | ||
| 742 | (unless (or (null defn-up-tricky) | ||
| 743 | (integerp defn-up-tricky) | ||
| 744 | (eq defn-up-tricky 'undefined)) | ||
| 745 | (princ (format " | ||
| 746 | |||
| 747 | ----------------- up-event (long click) ---------------- | ||
| 748 | |||
| 749 | Pressing <%S>%s for longer than %d milli-seconds | ||
| 750 | runs the command %S | ||
| 751 | which is " | ||
| 752 | ev-type mouse-msg | ||
| 733 | mouse-1-click-follows-link | 753 | mouse-1-click-follows-link |
| 734 | (not (eq mouse-1-click-follows-link 'double)) | 754 | defn-up-tricky)) |
| 735 | (setq mouse-1-remapped | 755 | (describe-function-1 defn-up-tricky))) |
| 736 | (with-current-buffer (window-buffer window) | 756 | (print-help-return-message))))) |
| 737 | (mouse-on-link-p (posn-point | ||
| 738 | (event-start up-event)))))) | ||
| 739 | (setq mouse-1-tricky (and (integerp mouse-1-click-follows-link) | ||
| 740 | (> mouse-1-click-follows-link 0))) | ||
| 741 | (cond ((stringp mouse-1-remapped) | ||
| 742 | (setq sequence mouse-1-remapped)) | ||
| 743 | ((vectorp mouse-1-remapped) | ||
| 744 | (setcar up-event (elt mouse-1-remapped 0))) | ||
| 745 | (t (setcar up-event 'mouse-2)))) | ||
| 746 | (setq defn (or (string-key-binding sequence) | ||
| 747 | (key-binding sequence))) | ||
| 748 | (unless (or (null defn) (integerp defn) (equal defn 'undefined)) | ||
| 749 | (princ (if mouse-1-tricky | ||
| 750 | "\n\n----------------- up-event (short click) ----------------\n\n" | ||
| 751 | hdr)) | ||
| 752 | (setq hdr nil) | ||
| 753 | (princ (symbol-name type)) | ||
| 754 | (if (windowp window) | ||
| 755 | (princ " at that spot")) | ||
| 756 | (if mouse-1-remapped | ||
| 757 | (princ " is remapped to <mouse-2>\n which" )) | ||
| 758 | (princ " runs the command ") | ||
| 759 | (prin1 defn) | ||
| 760 | (princ "\n which is ") | ||
| 761 | (describe-function-1 defn)) | ||
| 762 | (when mouse-1-tricky | ||
| 763 | (setcar up-event 'mouse-1) | ||
| 764 | (setq defn (or (string-key-binding (vector up-event)) | ||
| 765 | (key-binding (vector up-event)))) | ||
| 766 | (unless (or (null defn) (integerp defn) (eq defn 'undefined)) | ||
| 767 | (princ (or hdr | ||
| 768 | "\n\n----------------- up-event (long click) ----------------\n\n")) | ||
| 769 | (princ "Pressing mouse-1") | ||
| 770 | (if (windowp window) | ||
| 771 | (princ " at that spot")) | ||
| 772 | (princ (format " for longer than %d milli-seconds\n" | ||
| 773 | mouse-1-click-follows-link)) | ||
| 774 | (princ " runs the command ") | ||
| 775 | (prin1 defn) | ||
| 776 | (princ "\n which is ") | ||
| 777 | (describe-function-1 defn))))) | ||
| 778 | (print-help-return-message))))))) | ||
| 779 | 757 | ||
| 780 | (defun describe-mode (&optional buffer) | 758 | (defun describe-mode (&optional buffer) |
| 781 | "Display documentation of current major mode and minor modes. | 759 | "Display documentation of current major mode and minor modes. |
| @@ -786,7 +764,7 @@ descriptions of the minor modes, each on a separate page. | |||
| 786 | For this to work correctly for a minor mode, the mode's indicator | 764 | For this to work correctly for a minor mode, the mode's indicator |
| 787 | variable \(listed in `minor-mode-alist') must also be a function | 765 | variable \(listed in `minor-mode-alist') must also be a function |
| 788 | whose documentation describes the minor mode." | 766 | whose documentation describes the minor mode." |
| 789 | (interactive) | 767 | (interactive "@") |
| 790 | (unless buffer (setq buffer (current-buffer))) | 768 | (unless buffer (setq buffer (current-buffer))) |
| 791 | (help-setup-xref (list #'describe-mode buffer) | 769 | (help-setup-xref (list #'describe-mode buffer) |
| 792 | (interactive-p)) | 770 | (interactive-p)) |