Pygame plays a mp3 file faster than normal speed - python

I use Python to play a short mp3 audio file. But the playing speed is faster than other music players.
My Code:
import pygame
import time
pygame.mixer.init(frequency=22050, size=16, channels=2, buffer=4096)
file=r'test.mp3'
try:
pygame.mixer_music.load(file)
pygame.mixer_music.play()
while pygame.mixer_music.get_busy():
time.sleep(0.1)
except Exception as err:
print(err)
Please help me to solve this issue!

This will work:
import time, os
from pygame import mixer
from pydub import AudioSegment
# original file: "slow.mp3"
# new fast file: "fast.mp3"
# speed: 1.3 (1.0 is actual speed)
def speed_swifter(sound, speed=1.0):
sound_with_altered_frame_rate = sound._spawn(sound.raw_data, overrides={"frame_rate": int(sound.frame_rate * speed)})
return sound_with_altered_frame_rate
newSpeed = 1.3
sound = AudioSegment.from_file("slow.mp3")
speed_sound = speed_swifter(sound, newSpeed)
speed_sound.export(os.path.join("fast.mp3"), format="mp3")
mixer.init()
mixer.music.load("fast.mp3")
mixer.music.play()
while mixer.music.get_busy():
time.sleep(0.1)

import pygame, mutagen.mp3
song_file = "your_music.mp3"
mp3 = mutagen.mp3.MP3(song_file)
pygame.mixer.init(frequency=mp3.info.sample_rate)
pygame.mixer.music.load(song_file)
pygame.mixer.music.play()

Related

How to change the treble and bass of an mp3/ogg file?

I am aware you can do this via FFmpeg CLI, but I need to do this programmatically. I have tried setting high-pass and low-pass filters using pydub (the module I am using right now) but it kills the program.
My current code:
import os, asyncio, pydub
from pydub import AudioSegment
async def louder(filename:str, tag:bool, testing:bool=False, cb=None):
song = AudioSegment.from_mp3("audios/"+filename.replace(".mp3", "").replace("-", "_")+".mp3")
song = song + 15
song.export("audios/"+filename.replace(".mp3", "").replace("-", "_")+".ogg", format="ogg")
if not testing:
os.unlink(os.path.join(os.getcwd(), "audios/"+filename.replace(".mp3", "").replace("-", "_")+".mp3"))
if cb:
await cb()
if __name__ == "__main__":
async def callback_testing():
print("Done")
asyncio.run(mainAudioBypass(filename="test_mp3", tag=True, testing=True, cb=callback_testing))

Issues playing audio in pygame [duplicate]

I am recording audio using sounddevice and I want to play it through a virtual audio cable through pygame, I keep receiving this error Exception has occurred: error mpg123_seek: Invalid RVA mode. (code 12)
My code is below:
import sounddevice as sd
from scipy.io.wavfile import write
import random
import pygame
import time
pygame.init()
pygame.mixer.init(devicename='CABLE Input (VB-Audio Virtual Cable)')
fs = 44100 # Sample rate
seconds = 00.1 # Duration of recording
def main():
for x in range(10000):
number = random.randint(1,9999999)
myrecording = sd.rec(int(seconds * fs), samplerate=fs, channels=2)
sd.wait() # Wait until recording is finished
write(f'output/output{str(number)}.mp3', fs, myrecording) # Save as WAV file `
# PLAY MIC SOUND HERE
pygame.mixer.music.load(f'output/output{str(number)}.mp3') #Load the mp3
pygame.mixer.music.play() #Play it
time.sleep(00.1)
main()
Any help is appreciated.
There's a couple of issues.
The first is that scipi.io.wavefile.write() only writes an uncompressed WAV file (ref: https://docs.scipy.org/doc/scipy/reference/generated/scipy.io.wavfile.write.html ). You might name it .mp3, but it's not compressed that way.
The next issue is that pygame.mixer.music will not .load() uncompressed WAV files. So... what to do...
One work-around is to use the base pygame.mixer, which is happy to load uncompressed WAV. And while I don't have an 'CABLE Input (VB-Audio Virtual Cable)' device, I do get a nice file of silence, which I validated with the sound-editing program Audacity, and this seems to play OK.
import sounddevice as sd
from scipy.io.wavfile import write
import pygame
import time
import random
pygame.init()
pygame.mixer.init(devicename='CABLE Input (VB-Audio Virtual Cable)')
fs = 44100 # Sample rate
seconds = 00.1 # Duration of recording
def main():
for x in range(10000):
number = random.randint(1,9999999)
myrecording = sd.rec(int(seconds * fs), samplerate=fs, channels=2)
sd.wait() # Wait until recording is finished
filename = f'output/output{str(number)}.wav'
write(filename, fs, myrecording) # Save as uncompressed WAV file
# PLAY MIC SOUND HERE
print( "Playing [" + filename + "]" )
#pygame.mixer.music.load(filename) #Load the wav
#pygame.mixer.music.play() #Play it
#while ( pygame.mixer.music.get_busy() ): # wait for the sound to end
# time.sleep(00.1)
sound = pygame.mixer.Sound(filename) #Load the wav
sound.play() #Play it
while ( pygame.mixer.get_busy() ): # wait for the sound to end
time.sleep(00.1)
main()

How to stop audio with playsound module?

How do I stop the audio playing through playaudio module in Python code?
I have played music but I can't stop that music. How can I stop it?
playsound.playsound("name_of_file")
You can use the multiprocessing module to play the sound as a background process, then terminate it anytime you want:
import multiprocessing
from playsound import playsound
p = multiprocessing.Process(target=playsound, args=("file.mp3",))
p.start()
input("press ENTER to stop playback")
p.terminate()
Playsound is a single function module that plays sounds, and nothing else. It would seem that means it does not stop playing sounds either. From their own documentation:
The playsound module contains only one thing - the function (also named) playsound.
Personally, I like to use pyaudio. The following code is adapted from the example here. The code plays audio and has the space bar set as a pause/play button.
import pyaudio
import wave
import time
from pynput import keyboard
paused = False # global to track if the audio is paused
def on_press(key):
global paused
print (key)
if key == keyboard.Key.space:
if stream.is_stopped(): # time to play audio
print ('play pressed')
stream.start_stream()
paused = False
return False
elif stream.is_active(): # time to pause audio
print ('pause pressed')
stream.stop_stream()
paused = True
return False
return False
# you audio here
wf = wave.open('audio\\songs\\And_Your_Bird_Can_Sing_mp3_2_wav.wav', 'rb')
# instantiate PyAudio
p = pyaudio.PyAudio()
# define callback
def callback(in_data, frame_count, time_info, status):
data = wf.readframes(frame_count)
return (data, pyaudio.paContinue)
# open stream using callback
stream = p.open(format=p.get_format_from_width(wf.getsampwidth()),
channels=wf.getnchannels(),
rate=wf.getframerate(),
output=True,
stream_callback=callback)
# start the stream
stream.start_stream()
while stream.is_active() or paused==True:
with keyboard.Listener(on_press=on_press) as listener:
listener.join()
time.sleep(0.1)
# stop stream
stream.stop_stream()
stream.close()
wf.close()
# close PyAudio
p.terminate()
On windows try:
import winsound
winsound.PlaySound(r'C:\sound.wav', winsound.SND_ASYNC)
Stop Playback:
winsound.PlaySound(None, winsound.SND_PURGE)
#pip install pygame
from pygame import mixer
import time
mixer.init() #Initialzing pyamge mixer
mixer.music.load('lovingly-618.mp3') #Loading Music File
mixer.music.play() #Playing Music with Pygame
time.sleep(5)
mixer.music.stop()
Here is a much easier way:
wmp = win32com.client.dynamic.Dispatch("WMPlayer.OCX")
wmp.settings.autoStart = True
wmp.settings.volume = 100
wmp.URL = file
while globals()["allowSound"]:
PumpWaitingMessages()
You can change globals()["allowSound"] from another thread and set it to false when the audio has ended (you can get the length of the audio with wmp.durationString)
Here is some more info about this: Windows Media Player COM Automation works from VBS but not from Python
Although this does not use the playsound module it is a good alternative.
After successful execution of the program, audio file will start playing. Now Click on terminal, once you see the cursor, type Ctrl+C, it will bring you out of the terminal and audio will also stop playing.
Programming Instructions used:
from playsound import playsound
playsound('//path//to//a//sound//file//you//want//to//play.mp3')
EASY......
on your terminal tab, look for kill(delete) option on the right hand side.
click the delete option and it will stop playing

Error while re-opening sound file in python

I was in the process of making a program that simply repeats any text you enter, and seemed to be working when I first tested it. The problem is that the second time I attempt to type anything, it crashes and says that permission was denied to the sound file I was recording it to. I believe it is because the file was already opened, but none the less I do not know how to fix it. I am using the gTTS and Pygame modules.
from gtts import gTTS
from tempfile import TemporaryFile
from pygame import mixer
#Plays Sound
def play():
mixer.init()
mixer.music.load("Speech.mp3")
mixer.music.play()
#Voice
def voice(x):
text = gTTS(text= x, lang= 'en')
with open("Speech.mp3", 'wb') as f:
text.write_to_fp(f)
f.close()
play()
#Prompts user to enter text for speech
while True:
voice_input = input("What should Wellington Say: ")
voice(voice_input)
Figured it out. I added this function:
def delete():
sleep(2)
mixer.music.load("Holder.mp3")
os.remove("Speech.mp3")
And call it after .play(), so it now simply deletes the file when it is done and then re-creates it when you need to use it next.
To expand on my comment above (with help from this thread), I think play() may be locking the file. You can manually try the following:
def play():
mixer.init()
mixer.music.load("Speech.mp3")
mixer.music.play()
while pygame.mixer.music.get_busy():
pygame.time.Clock().tick(10)
or
def play():
mixer.init()
mixer.music.load("Speech.mp3")
mixer.music.play()
mixer.music.stop()
But this second fix might have the consequence of not hearing anything played back.
I fixed the problem by writing to a temporary file and using os.rename:
from gtts import gTTS
from pygame import mixer
import os
play_name = 'Speech.mp3'
save_name = "%s.%s" % (play_name, '.tmp')
def play():
mixer.music.load(play_name)
mixer.music.play()
def voice(x):
text = gTTS(text=x, lang='en')
with open(save_name, 'wb') as tmp_file:
text.write_to_fp(tmp_file)
os.rename(save_name, play_name)
try:
mixer.init()
while True:
voice_input = raw_input("What should Wellington Say: ")
voice(voice_input)
play()
except KeyboardInterrupt:
pass
I ran a test where I typed in a very long sentence and then another sentence while the first one was playing and everything still worked.

Play music and get user input simultaneously?

Can I get input and play music from pygame at the same time?
The code I have now:
from pygame import mixer
mixer.init()
mixer.music.load('song.mp3')
mixer.music.play()
var = raw_input("Input: ")
print "you said ", var
while pygame.mixer.music.get_busy():
pygame.time.Clock().tick(10)
It works fine until I enter something, and then the program stops:
Input: test
you said test
Traceback (most recent call last):
File "play.py", line 10, in <module>
while pygame.mixer.music.get_busy():
NameError: name 'pygame' is not defined
from pygame import mixer
puts mixer in your namespace, but not pygame
You can either:
while mixer.music.get_busy():
or
import pygame
from pygame import mixer
importing pygame as well as it's subpackages you need is usually a good approach

Categories

Resources