Better faces, track selection without playing.
authorTim Vaughan <timv@ughan.xyz>
Sat, 7 Dec 2019 23:11:30 +0000 (00:11 +0100)
committerTim Vaughan <timv@ughan.xyz>
Sat, 7 Dec 2019 23:11:30 +0000 (00:11 +0100)
emus.el

diff --git a/emus.el b/emus.el
index c09f386..315ca6e 100644 (file)
--- a/emus.el
+++ b/emus.el
   :type '(string))
 
 (defface emus-artist
-  '((t :inherit font-lock-keyword-face))
+  '((t :inherit font-lock-keyword-face :background "#333"))
   "Face used for artist names in browser.")
 
 (defface emus-album
-  '((t :inherit font-lock-function-name-face))
+  '((t :inherit font-lock-function-name-face :background "#222"))
   "Face used for album names in browser.")
 
-(defface emus-title
+(defface emus-track
   '((t :inherit font-lock-string-face))
   "Face used for track titles in browser.")
 
+(defface emus-track-current
+  '((t :inherit font-lock-string-face :inverse-video t))
+  "Face used for track titles in browser.")
+
+(defface emus-cursor
+  '((t :inherit bold))
+  "Face used for current track cursor")
+
 ;;; Library
 ;;
 
@@ -83,7 +91,7 @@
 
 (defun emus-update-records ()
   (interactive)
-  (emus--suspend-cp)
+  (emus-suspend-cp)
   (setq emus-state 'stopped)
   (let ((proc (emus-get-process))
         (tagstr "")
                                    (setq emus-records (reverse emus-records))
                                    (emus-sort-records)
                                    (emus-render-records)
-                                   (emus--resume-cp)))))
+                                   (emus-resume-cp)))))
     (emus-send-cmd "lp" (car filenames))))
 
 (defun emus-sort-records ()
 (defvar emus-state 'stopped)
 (defvar emus-continuous-playback t)
 
-(defun emus--suspend-cp ()
+(defun emus-suspend-cp ()
   (setq emus-continuous-playback nil))
 
-(defun emus--resume-cp ()
+(defun emus-resume-cp ()
   (setq emus-continuous-playback t)
   (set-process-filter (emus-get-process)
                       (lambda (proc string)
                              (emus-play-next)))))
 
 (defun emus-play-record (record)
+  "Set RECORD as current and start playing."
   (let ((old-record emus-current-record))
     (emus-send-cmd "l" (emus-record-file record))
     (setq emus-state 'playing)
     (setq emus-current-record record)
     (emus-update-record old-record)
     (emus-update-record record)
-    (emus--resume-cp)))
+    (emus-resume-cp)))
+
+(defun emus-select-record (record)
+  "Set RECORD as current, but do not start playing."
+  (let ((old-record emus-current-record))
+    (setq emus-state 'stopped)
+    (setq emus-current-record record)
+    (emus-update-record old-record)
+    (emus-update-record record)
+    (emus-send-cmd "o")
+    (emus-resume-cp)))
 
 (defun emus-stop ()
+  "Stop playback of the current record."
   (interactive)
   (setq emus-state 'stopped)
   (emus-update-record emus-current-record)
   (interactive)
   (emus-volume-delta -10))
 
-(defun emus--play-nearby (offset)
+(defun emus-play-nearby (offset)
   (let ((idx (seq-position emus-records emus-current-record)))
     (if idx
         (let ((next-record (elt emus-records (+ idx offset))))
           (if next-record
-              (emus-play-record next-record)
+              (if (eq emus-state 'playing)
+                  (emus-play-record next-record)
+                (emus-select-record next-record))
             (error "Track does not exist")))
       (error "No track is currently selected."))))
 
 (defun emus-play-next ()
   (interactive)
-  (emus--play-nearby 1))
+  (emus-play-nearby 1))
 
 (defun emus-play-prev ()
   (interactive)
-  (emus--play-nearby -1))
+  (emus-play-nearby -1))
 
 (defun emus-display-status ()
   (interactive)
 ;;
 
 (defun emus-insert-record (record &optional prev-record first)
-  (let ((artist (emus-record-artist record))
-        (album (emus-record-album record))
-        (title (emus-record-title record)))
+  (let* ((artist (emus-record-artist record))
+         (album (emus-record-album record))
+         (title (emus-record-title record))
+         (help-str (format "mouse-1, RET: Play '%.30s' (%.20s)" title artist)))
     (when (or prev-record first)
       (unless (equal (emus-record-artist prev-record) artist)
         (insert-text-button
          (propertize artist 'face 'emus-artist)
          'action #'emus-click-record
          'follow-link t
+         'help-echo help-str
          'emus-record record)
-        (insert "\n"))
+        (insert (propertize "\n" 'face 'emus-artist)))
       (unless (equal (emus-record-album prev-record) album)
         (insert-text-button
          (propertize (concat "  " album) 'face 'emus-album)
          'action #'emus-click-record
          'follow-link t
+         'help-echo help-str
          'emus-record record)
-        (insert "\n")))
+        (insert (propertize "\n" 'face 'emus-album))))
     (emus-set-record-browser-pos record (point))
     (let ((is-current (equal record emus-current-record)))
       (insert-text-button
        (concat
         (if is-current
-            (pcase emus-state
-              ('playing (propertize ">" 'face 'bold))
-              ('paused (propertize ")" 'face 'bold))
-              ('stopped (propertize "]" 'face 'bold)))
-          (propertize " " 'face 'default))
-        (propertize (format "    %s" title)
-                    'face 'emus-title))
+            (propertize
+             (pcase emus-state
+               ('playing "->")
+               ('paused "-)")
+               ('stopped "-]"))
+             'face 'emus-cursor)
+          (propertize "  " 'face 'default))
+        (propertize (format "   %s" title)
+                    'face (if is-current
+                              'emus-track-current
+                            'emus-track)))
        'action #'emus-click-record
        'follow-link t
-       'emus-record record)))
-  (insert "\n"))
+       'help-echo help-str
+       'emus-record record)
+      (insert (propertize "\n"
+                          'face (if is-current
+                                    'emus-track-current
+                                  'emus-track))))))
 
 (defun emus-update-record (record)
   (let ((record-pos (emus-record-browser-pos record)))
             (goto-char old-point))))))
 
 (defun emus-render-records ()
-  (save-mark-and-excursion
-    (with-current-buffer "*emus*"
-      (let ((inhibit-read-only t))
-        (erase-buffer)
-        (goto-char (point-min))
-        (let ((prev-record nil))
-          (dolist (record emus-records)
-            (emus-insert-record record prev-record (not prev-record))
-            (setq prev-record record)))))))
+  (with-current-buffer "*emus*"
+    (let ((inhibit-read-only t)
+          (old-pos (point)))
+      (erase-buffer)
+      (goto-char (point-min))
+      (let ((prev-record nil))
+        (dolist (record emus-records)
+          (emus-insert-record record prev-record (not prev-record))
+          (setq prev-record record)))
+      (goto-char old-pos))))
 
 (defun emus-click-record (button)
   (emus-play-record (button-get button 'emus-record)))
 
+(defun emus-centre-current ()
+  (interactive)
+  (when (get-buffer "*emus*")
+    (switch-to-buffer "*emus*")
+    (when emus-current-record
+      (goto-char (emus-record-browser-pos emus-current-record))
+      (recenter))))
+
 (defun emus-browse ()
   "Switch to *emus* audio library browser."
   (interactive)
     (define-key map (kbd "R") 'emus-update-records)
     (define-key map (kbd "n") 'emus-play-next)
     (define-key map (kbd "p") 'emus-play-prev)
+    (define-key map (kbd "c") 'emus-centre-current)
     (when (fboundp 'evil-define-key*)
       (evil-define-key* 'motion map
         (kbd "SPC") 'emus-playpause
         (kbd "-") 'emus-volume-down
         (kbd "R") 'emus-update-records
         (kbd "n") 'emus-play-next
-        (kbd "p") 'emus-play-prev))
+        (kbd "p") 'emus-play-prev
+        (kbd "c") 'emus-centre-current))
     map)
   "Keymap for emus.")