Fixed critical sound timing bug. Finally, after a couple of days of banging my head against this problem and sound getting progressively worse, it's fixed. Turned out the fix was a very simple timing issue for when to play sounds.

This commit is contained in:
Storm Dragon
2025-09-19 12:51:45 -04:00
parent f2079261d1
commit a98783dbc4
2 changed files with 187 additions and 19 deletions

View File

@@ -120,24 +120,25 @@ class Sound:
pygame.event.clear()
pygame.mixer.stop()
# Play the sound
channel = self.sounds[soundName].play(-1 if loop else 0)
if not channel:
return None
# Apply appropriate volume settings
sfx_volume = self.volumeService.get_sfx_volume()
# Handle positional audio if positions are provided
# Handle positional audio if positions are provided - check range BEFORE starting sound
if playerPos is not None and objPos is not None:
# Calculate stereo panning
left_vol, right_vol = self._get_stereo_panning(playerPos, objPos, centerDistance)
# Don't play if out of range
if left_vol == 0 and right_vol == 0:
channel.stop()
return None
# Play the sound
channel = self.sounds[soundName].play(-1 if loop else 0)
if not channel:
return None
# Apply volume settings
if playerPos is not None and objPos is not None:
# Apply positional volume adjustments
channel.set_volume(volume * left_vol * sfx_volume, volume * right_vol * sfx_volume)
else:
@@ -351,6 +352,10 @@ def _find_matching_sound(soundPattern, sounds):
keys = [k for k in sounds.keys() if re.match("^" + soundPattern + ".*", k)]
return random.choice(keys) if keys else None
def get_available_channel():
"""Get an available channel for playing sounds."""
return pygame.mixer.find_channel()
# Global functions for backward compatibility
def play_bgm(musicFile):
"""Play background music with proper volume settings."""
@@ -425,20 +430,22 @@ def play_sound(sound_or_name, volume=1.0, loop=False, playerPos=None, objPos=Non
# Case 4: Sound name with dictionary
elif isinstance(sounds, dict) and isinstance(sound_or_name, str) and sound_or_name in sounds:
# Apply volume settings
sfx_vol = volumeService.get_sfx_volume()
# Handle positional audio - check range BEFORE starting sound
if playerPos is not None and objPos is not None:
left_vol, right_vol = _get_stereo_panning(playerPos, objPos, centerDistance)
if left_vol == 0 and right_vol == 0:
return None # Don't start sound if out of range
# Play the sound
channel = sounds[sound_or_name].play(-1 if loop else 0)
if not channel:
return None
# Apply volume settings
sfx_vol = volumeService.get_sfx_volume()
# Handle positional audio
if playerPos is not None and objPos is not None:
left_vol, right_vol = _get_stereo_panning(playerPos, objPos, centerDistance)
if left_vol == 0 and right_vol == 0:
channel.stop()
return None
channel.set_volume(volume * left_vol * sfx_vol, volume * right_vol * sfx_vol)
else:
channel.set_volume(volume * sfx_vol)