[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

New class: window-menu-item-+ (comments appreciated)



I implemented this class as a more general replacement for 
window-menu-items.  Basically, it allows you to specify an applicability 
function in addition to the action function.  The applicability function 
determines whether or not the item should be enabled, and is called like 
the action function with the front window as its only argument.  I was 
originally inspired by the implmentation of window-save, and it seemed a 
shame not to generalize this idea.

Here is how you would do the window-save menu-item with this class 
(assuming I did things right): 

(make-instance 'window-menu-item-+
  :item-applicable-function #'window-needs-saving-p
  :menu-item-action #'window-save)
  
Here's the code for the class.  Comments are more than welcome, and feel 
free to use this code if it is useful to you.

(defclass window-menu-item-+ (menu-item)
  ((window-menu-item-+-applicable-function
   :accessor window-menu-item-+-applicable-function
   :initarg :item-applicable-function))
   (:default-initargs :item-applicable-function ()))
    
(defmethod menu-item-update ((self window-menu-item-+))
  (let ((front-win (front-window))
        (user-update-function
         (menu-item-update-function self)))
    (print "Working")
    (when front-win
      (if (compute-applicable-methods 
                    (menu-item-action-function self)
                    (list front-win))
        ;; Window can handle action
        (let ((applicable-fun (window-menu-item-+-applicable-function
self)))
          (if (compute-applicable-methods 
                      applicable-fun (list (front-window)))
            ;; Window has the applicability function
            (if (funcall applicable-fun front-win)
              (menu-item-enable self)
              (menu-item-disable self))
            ;; else no applicability fucntion
            ;; assume that window can handle it
            ;; could be a window counting on the old system
            (menu-item-enable self)))
        ;; else window can't handle action
        (menu-item-disable self)))
    (if user-update-function
      (funcall user-update-function self))))

(defmethod menu-item-action ((self window-menu-item-+))
  (let ((action (menu-item-action-function self)))
    (when action
      (funcall action (front-window)))))