[CM] Advice on using snd's (play) from another program?

Jenweil HerbertGrimsby at protonmail.com
Wed Jan 15 11:01:09 PST 2025


Hello,

I am driving snd from a comint buffer in emacs, and I was trying to (play "file.mp3"), which gives an error about "unknown sample type: unknown".

However, (open-sound "file.mp3") does work, and I've noticed snd does create a new file, "file.mp3.snd". It also gives a sound object in the repl printout like: #<sound 0>. Where I can (play 0) and hear sound. This seems to be expected behavior and maybe part of snd's design, that (play) wouldn't work off the bat, but (open-sound) would.

This presents a couple obstacles and I'd love advice on any of the following:
- I'm bad at scheme currently. One area I struggle with is tooling--I don't know how to autocomplete for symbols. Or step-through debug. I am used to elisp's debugger.

- In my usecase, I'm using user supplied filenames, and mainly using snd programatically. In order to support events where I might call (play), should I write a layer to map sound files to indices? (I'm assuming snd always starts from 0 and auto-increments as new sounds are loaded). This feels brittle because I'm not sure the speed at which I send commands is going to always allow the scheme repl to return a string to me, before the next time emacs sends a command. Is there a way to always state which sound id (like 0, 1, 2, 3) a sound should get, so I can avoid repl parsing?

- I've tried to get around this issue by using a documented hook: start-playing-hook
The idea is that 1) I intercept before the sound starts playing, 2) look at the file name, and 3) "redirect" the playing to "file.mp3.snd" if it is an mp3. This approach doesn't work for unopened sounds I try to play (it shows an error):

#+begin_src scheme
(define (my-hook hook)
(let* ((snd (hook 'snd)))
;; an error will occur, as calling file-name in this sound object
;; will fail for a sound called by (play) that has not loaded
;; even if it is a supported, playable .wav file
(display (file-name snd))
(display "\n")
;; (let ((ext (strrchr fd 46))) ; 46 is . in ascii
;; (when (string=? ext ".mp3")
;; (play (open-sound (append fd ".snd")))))
))
(hook-push
start-playing-hook
my-hook)
#+end_src

Apparently I cannot get the file-name this way. (sound-properties snd) will also fail. I was unsure how to view all the properties within this object.

If I print the sound object it shows #<sound 123456>

- I've also noticed snd likes to reread files from disk. I've observed this when I have a "file.wav" opened, but as a test, rename it to "file.wav.bak". snd will play it through it's sound id (play 1), but sometime later, it won't play because it says it cannot find it. Further, if I play an opened sound from (play "file.wav"), rename the file, it won't play because it cannot find it. It's not a huge deal, but ideally for performance I'd like to avoid re-reading from disk, and keep everything in memory

Thanks so much! All your wisdom is appreciated.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://cm-mail.stanford.edu/pipermail/cmdist/attachments/20250115/a40756b9/attachment.html>


More information about the Cmdist mailing list