5
votes

I am playing around with building a python script that play rhythms like a drum machine. I have used PyGame to handle the audio. However I experience significant/unacceptable delays between calling play and hearing the actual audio.

I pasted the following code into the interactive interpreter, and then execute the last line again and again:

import pygame
pygame.mixer.init(frequency=22050, size=-16, channels=2, buffer=4096)
s = pygame.mixer.Sound('snare.wav')
s.play(loops=0, maxtime=0, fade_ms=0)

The time between pressing enter and hearing the audio is by my best guess around 400ms, and indeed noticeable and unacceptable. The delay is approximately the same as if I click the play button in VLC and wait for the audio to play.

I have tried this on both Windows and Ubuntu with the same result. My computer is a bit old, an Intel Core i3, 2.53GHz, but I think this should not be a problem.

What can I do about this?

In a loop:

This code demonstrates the same lag.

for i in range(10):
  print i
  s.play(loops=0, maxtime=0, fade_ms=0)
  sleep(2)
2
1) Maybe a delay in the interpreter itself? Try raw_input();s.play(loops=0, maxtime=0, fade_ms=0), then press enter again. 2) Does the snare start at the very beginning of the sound file? If you open the file in Audacity, how much time is between the start and the actual sound? - Nick ODell
1) No difference. 2) The actual sound does begin instantly in the wave file. Also I've tried with other wave files. - Mads Skjern
could you post a link to the sound file, i wish to test this with my machine - Bartlomiej Lewandowski
This was for a school project last year, and we never even completed the project. I don't even remember which sound file, so I can't send it, but I believe it was like this for any sound file! And no, it's not because there was a "blank" part in the beginning of the file, we made sure about that. - Mads Skjern

2 Answers

9
votes

A possible solution is to decrease the buffer size (example 512):

import pygame
pygame.mixer.init(frequency=22050, size=-16, channels=2, buffer=512)
s = pygame.mixer.Sound('snare.wav')
s.play(loops=0, maxtime=0, fade_ms=0)
3
votes

I had the same problem a couple of minutes ago, and there's a solution that works for me in This other thread

It looks like an initialization problem, pygame doesn't get the buffers well if you init pygame first (or else XD). Initialize the mixer init() and pre_init() first, and experiment from there:

pygame.mixer.pre_init(44100, -16, 2, 512)
pygame.mixer.init()
pygame.init()

That should work :) Good luck!