]> code.delx.au - gnu-emacs/blobdiff - lisp/menu-bar.el
Initial revision
[gnu-emacs] / lisp / menu-bar.el
index 7494867bfa8911ae58ec406406ef51e4da910e1b..c4a2ea013b8db68d44b48efa57a0bd223e5f237b 100644 (file)
 ;;; Code:
 
 (define-key global-map [menu-bar] (make-sparse-keymap "menu-bar"))
-(setq menu-bar-help-menu (make-sparse-keymap "Help"))
+(defvar menu-bar-help-menu (make-sparse-keymap "Help"))
 (define-key global-map [menu-bar help] (cons "Help" menu-bar-help-menu))
-(setq menu-bar-edit-menu (make-sparse-keymap "Edit"))
+(defvar menu-bar-edit-menu (make-sparse-keymap "Edit"))
 (define-key global-map [menu-bar edit] (cons "Edit" menu-bar-edit-menu))
-(setq menu-bar-file-menu (make-sparse-keymap "File"))
+(defvar menu-bar-file-menu (make-sparse-keymap "File"))
 (define-key global-map [menu-bar file] (cons "File" menu-bar-file-menu))
 
 (define-key menu-bar-file-menu [exit-emacs]
@@ -47,6 +47,8 @@
 
 (define-key menu-bar-edit-menu [fill] '("Fill" . fill-region))
 (define-key menu-bar-edit-menu [clear] '("Clear" . delete-region))
+(define-key menu-bar-edit-menu [choose-next-paste]
+  '("Choose Next Paste" . mouse-menu-choose-yank))
 (define-key menu-bar-edit-menu [paste] '("Paste" . yank))
 (define-key menu-bar-edit-menu [copy] '("Copy" . kill-ring-save))
 (define-key menu-bar-edit-menu [cut] '("Cut" . kill-region))
               (and (boundp 'pending-undo-list)
                    pending-undo-list)
             buffer-undo-list)))
+
+(defvar yank-menu-length 100
+  "*Maximum length of an item in the menu for \
+\\[mouse-menu-choose-yank].")
+
+(defun mouse-menu-choose-yank (event)
+  "Pop up a menu of the kill-ring for selection with the mouse.
+The kill-ring-yank-pointer is moved to the selected element.
+A subsequent \\[yank] yanks the choice just selected."
+  (interactive "e")
+  (let* ((count 0)
+        (menu (mapcar (lambda (string)
+                        (if (> (length string) yank-menu-length)
+                            (setq string (substring string
+                                                    0 yank-menu-length)))
+                        (prog1 (cons string count)
+                          (setq count (1+ count))))
+                      kill-ring))
+        (arg (x-popup-menu event 
+                           (list "Yank Menu"
+                                 (cons "Choose Next Yank" menu)))))
+    ;; A mouse click outside the menu returns nil.
+    ;; Avoid a confusing error from passing nil to rotate-yank-pointer.
+    ;; XXX should this perhaps do something other than simply return? -rm
+    (if arg
+       (progn
+         (rotate-yank-pointer arg)
+         (if (interactive-p)
+             (message "The next yank will insert the selected text.")
+           (current-kill 0))))))
+(put 'mouse-menu-choose-yank 'menu-enable 'kill-ring)
 \f
-(define-key global-map [menu-bar buffer] '("Buffers" . mouse-buffer-menu))
+(define-key global-map [menu-bar buffer] '("Buffers" . mouse-menu-bar-buffers))
 
 (defvar complex-buffers-menu-p nil
   "*Non-nil says, offer a choice of actions after you pick a buffer.
@@ -117,7 +150,7 @@ If this is 10, then only the ten most-recently-selected buffers are shown.
 If this is nil, then all buffers are shown.
 A large number or nil slows down menu responsiveness.")
 
-(defun mouse-buffer-menu (event)
+(defun mouse-menu-bar-buffers (event)
   "Pop up a menu of buffers for selection with the mouse.
 This switches buffers in the window that you clicked on,
 and selects that window."
@@ -133,8 +166,16 @@ and selects that window."
          (list "Buffer Menu"
                (cons "Select Buffer"
                      (let ((tail buffers)
+                           (maxbuf 0)
                            (maxlen 0)
                            head)
+                       (while tail
+                         (or (eq ?\ (aref (buffer-name (car tail)) 0))
+                             (setq maxbuf
+                                   (max maxbuf
+                                        (length (buffer-name (car tail))))))
+                         (setq tail (cdr tail)))
+                       (setq tail buffers)
                        (while tail
                          (let ((elt (car tail)))
                            (if (not (string-match "^ "
@@ -142,8 +183,13 @@ and selects that window."
                                (setq head (cons
                                            (cons
                                             (format
-                                             "%14s   %s"
+                                             (format "%%%ds  %%s%%s  %%s"
+                                                     maxbuf)
                                              (buffer-name elt)
+                                             (if (buffer-modified-p elt) "*" " ")
+                                             (save-excursion
+                                               (set-buffer elt)
+                                               (if buffer-read-only "%" " "))
                                              (or (buffer-file-name elt) ""))
                                             elt)
                                            head)))
@@ -151,7 +197,7 @@ and selects that window."
                                 (setq maxlen (length (car (car head))))))
                          (setq tail (cdr tail)))
                        (nconc (reverse head)
-                              (list (cons (concat (make-string (- (/ maxlen 2) 8) ?\ )
+                              (list (cons (concat (make-string (max 0 (- (/ maxlen 2) 8)) ?\ )
                                                   "List All Buffers")
                                           'list-buffers)))))))
 
@@ -227,7 +273,8 @@ turn off menu bars; otherwise, turn on menu bars."
       (setq frames (cdr frames)))))
 
 ;; Make frames created from now on have a menu bar.
-(menu-bar-mode t)
+(if window-system
+    (menu-bar-mode t))
 
 (provide 'menu-bar)