summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--modules/video-audio-recording.el83
-rw-r--r--todo.org54
2 files changed, 134 insertions, 3 deletions
diff --git a/modules/video-audio-recording.el b/modules/video-audio-recording.el
index 73f782f6..f9311957 100644
--- a/modules/video-audio-recording.el
+++ b/modules/video-audio-recording.el
@@ -69,6 +69,74 @@ Returns device name or nil if not found."
(when (string-match "\\([^\t\n]+\\.monitor\\)" output)
(match-string 1 output))))
+(defun cj/recording-parse-sources ()
+ "Parse pactl sources output into structured list.
+Returns list of (device-name description state) tuples."
+ (let ((output (shell-command-to-string "pactl list sources short 2>/dev/null"))
+ (sources nil))
+ (dolist (line (split-string output "\n" t))
+ (when (string-match "^[0-9]+\t\\([^\t]+\\)\t\\([^\t]+\\)\t\\([^\t]+\\)\t\\([^\t]+\\)" line)
+ (let ((device (match-string 1 line))
+ (driver (match-string 2 line))
+ (state (match-string 4 line)))
+ (push (list device driver state) sources))))
+ (nreverse sources)))
+
+(defun cj/recording-list-devices ()
+ "Show all available audio sources in a readable format.
+Opens a buffer showing devices with their states."
+ (interactive)
+ (let ((sources (cj/recording-parse-sources)))
+ (with-current-buffer (get-buffer-create "*Recording Devices*")
+ (erase-buffer)
+ (insert "Available Audio Sources\n")
+ (insert "========================\n\n")
+ (insert "Current Configuration:\n")
+ (insert (format " Microphone: %s\n" (or cj/recording-mic-device "Not set")))
+ (insert (format " System Audio: %s\n\n" (or cj/recording-system-device "Not set")))
+ (insert "Available Devices:\n\n")
+ (if sources
+ (dolist (source sources)
+ (let ((device (nth 0 source))
+ (driver (nth 1 source))
+ (state (nth 2 source)))
+ (insert (format "%-10s [%s]\n" state driver))
+ (insert (format " %s\n\n" device))))
+ (insert " No audio sources found. Is PulseAudio/PipeWire running?\n"))
+ (goto-char (point-min))
+ (special-mode))
+ (switch-to-buffer-other-window "*Recording Devices*")))
+
+(defun cj/recording-select-device (prompt device-type)
+ "Interactively select an audio device.
+PROMPT is shown to user. DEVICE-TYPE is 'mic or 'monitor for filtering.
+Returns selected device name or nil."
+ (let* ((sources (cj/recording-parse-sources))
+ (filtered (if (eq device-type 'monitor)
+ (seq-filter (lambda (s) (string-match-p "\\.monitor$" (car s))) sources)
+ (seq-filter (lambda (s) (not (string-match-p "\\.monitor$" (car s)))) sources)))
+ (choices (mapcar (lambda (s)
+ (let ((device (nth 0 s))
+ (driver (nth 1 s))
+ (state (nth 2 s)))
+ (cons (format "%-10s %s" state device) device)))
+ filtered)))
+ (if choices
+ (cdr (assoc (completing-read prompt choices nil t) choices))
+ (user-error "No %s devices found" (if (eq device-type 'monitor) "monitor" "input")))))
+
+(defun cj/recording-select-devices ()
+ "Interactively select microphone and system audio devices.
+Sets cj/recording-mic-device and cj/recording-system-device."
+ (interactive)
+ (setq cj/recording-mic-device
+ (cj/recording-select-device "Select microphone device: " 'mic))
+ (setq cj/recording-system-device
+ (cj/recording-select-device "Select system audio monitor: " 'monitor))
+ (message "Devices set - Mic: %s, System: %s"
+ cj/recording-mic-device
+ cj/recording-system-device))
+
(defun cj/recording-get-devices ()
"Get or auto-detect audio devices.
Returns (mic-device . system-device) or nil on error."
@@ -78,9 +146,14 @@ Returns (mic-device . system-device) or nil on error."
(unless cj/recording-system-device
(setq cj/recording-system-device (cj/recording-detect-system-device)))
- ;; Validate devices
+ ;; If auto-detection failed, prompt user to select
+ (unless (and cj/recording-mic-device cj/recording-system-device)
+ (when (y-or-n-p "Could not auto-detect audio devices. Select manually? ")
+ (cj/recording-select-devices)))
+
+ ;; Final validation
(unless (and cj/recording-mic-device cj/recording-system-device)
- (user-error "Could not detect audio devices. Set cj/recording-mic-device and cj/recording-system-device manually"))
+ (user-error "Audio devices not configured. Run M-x cj/recording-select-devices"))
(cons cj/recording-mic-device cj/recording-system-device))
@@ -222,6 +295,8 @@ Otherwise use the default location in `audio-recordings-dir'."
(define-key map (kbd "A") #'cj/audio-recording-stop)
(define-key map (kbd "a") #'cj/audio-recording-start)
(define-key map (kbd "l") #'cj/recording-adjust-volumes)
+ (define-key map (kbd "d") #'cj/recording-list-devices)
+ (define-key map (kbd "s") #'cj/recording-select-devices)
map)
"Keymap for video/audio recording operations.")
@@ -234,7 +309,9 @@ Otherwise use the default location in `audio-recordings-dir'."
"C-; r V" "stop video"
"C-; r a" "start audio"
"C-; r A" "stop audio"
- "C-; r l" "adjust levels"))
+ "C-; r l" "adjust levels"
+ "C-; r d" "list devices"
+ "C-; r s" "select devices"))
(provide 'video-audio-recording)
;;; video-audio-recording.el ends here.
diff --git a/todo.org b/todo.org
index 572b7ccd..477abf9a 100644
--- a/todo.org
+++ b/todo.org
@@ -61,8 +61,62 @@ High priority - daily pain point.
** TODO [#B] Fix video/audio recording module (use constantly, just broke)
+Main issue: No way to select audio devices when multiple are available.
+Plugging in external audio interface broke recording - only captured input, not output.
+
Use constantly, needs to work reliably.
+*** TODO [#A] Add diagnostic command cj/recording-list-devices
+Show ALL available PulseAudio/PipeWire sources.
+Helps debug why auto-detection fails.
+User can copy device names if needed.
+
+*** TODO [#A] Add device selection UI
+Prompt user to select mic and system audio sources.
+Cache selected devices for future recordings.
+Allow switching devices without restarting Emacs.
+
+*** TODO [#B] Improve error messages
+Show which devices were found/not found.
+Include actual pactl output in error messages.
+Suggest manual device configuration.
+
+*** TODO [#B] Make device detection more flexible
+Try multiple regex patterns for different audio setups.
+Fallback to prompting user to select from list.
+Support both PulseAudio and PipeWire.
+
+*** TODO [#B] Validate recording startup
+Check process status after starting.
+Parse ffmpeg output for errors.
+Show actual ffmpeg command for debugging.
+
+*** TODO [#C] Add device testing command cj/recording-test-devices
+Records 3 seconds of audio.
+Plays it back.
+Confirms devices work before real recording.
+
+*** TODO [#C] Add recording status display (optional via flag, default off)
+Show "Recording: 00:05:23" in modeline or echo area.
+Timer showing duration.
+File size updating.
+
+*** TODO [#C] Add recording presets
+Screencast (video + audio, high quality).
+Podcast (audio only, voice optimized).
+Meeting (balanced, lower filesize).
+Quick note (audio, low quality, small file).
+
+*** TODO [#C] Build recording history buffer
+*Recordings* buffer showing history.
+Duration, file size, location.
+Quick actions: play, delete, rename, move.
+
+*** TODO [#C] Add post-processing hooks
+Auto-compress after recording.
+Move to cloud sync directory.
+Generate transcript (once transcription workflow exists).
+
** TODO [#B] Fix mail attachment workflow (currently awkward)
Daily workflow improvement.