Pythonで音声ファイルの再生(失敗編termux)
Pythonで音声ファイルを再生するにはどうするのでしょ?
AndroidスマホのtermuxでPythonからやりたいのだが失敗しまくる記録。PCならすぐできそうですが…
画像や動画処理ならPillowやOpenCVのように「これ使っとけ」的な鉄板ライブラリがありますけど、音声ファイルは検索すると色々出てきます。
検索結果順にざっと並べると、pygame
、pyaudio
、vlc
、aplay
、mpg321
、winsound
、pydub
、etc.
vlc
、aplay
、mpg321
はPython用ライブラリではなくコマンドらしいので、termuxで使えればPythonからはsubprocessを通しての利用となる。
winsound
はWindows用のライブラリ。Androidスマホで動かしたいので今回は使えない。
実行環境
Androidスマホ
termux
Python3.7
JupyterNotebook
目次
- 実行環境
- 目次
- pyaudio失敗編
- pydub失敗編
- winsound番外編
- pygame失敗編
- vlc
- aplay、mpg321不明
- termux-media-playerコマンド成功編
- さいごに
pyaudio失敗編
Androidスマホにpyaudioライブラリのインストールが出来なかった。
https://shizenkarasuzon.hatenablog.com/entry/2018/12/31/145510 の写経させて頂きました。投稿時大学受験を控えた高校生のブログだそうです。
import numpy as np import wave import pyaudio import matplotlib.pyplot as plt def PlayWavFie(Filename = "sample.wav"): try: wf = wave.open(Filename, "r") except FileNotFoundError: #ファイルが存在しなかった場合 print("[Error 404] No such file or directory: " + Filename) return 0 # ストリームを開く p = pyaudio.PyAudio() stream = p.open(format=p.get_format_from_width(wf.getsampwidth()), channels=wf.getnchannels(), rate=wf.getframerate(), output=True) # 音声を再生 chunk = 1024 data = wf.readframes(chunk) while data != '': stream.write(data) data = wf.readframes(chunk) stream.close() p.terminate() if __name__ is "__main__": PlayWavFie("sample.wav")
termuxでpip install pyaudio
を試みるも失敗。
検索した限りC言語でビルドが云々かんぬんと。
下のURLにQ&Aでやり取りされている中の一番下にインストールの方法が書いてあるが、手間が掛かるし初心者向けではない。参考まで
https://github.com/termux/termux-packages/issues/2962
一旦放置で。
pydub失敗編
Androidスマホにpydubライブラリのインストールは難なく出来たが、実行時にエラーが出た。
https://algorithm.joho.info/programming/python/pydub-play/ の写経させて頂きました。
まずはpydub
をインストール。
(JupyterNotebookのマジックコマンドを使ってます。)
%pip install pydub
Collecting pydub
Downloading https://files.pythonhosted.org/packages/79/db/eaf620b73a1eec3c8c6f8f5b0b236a50f9da88ad57802154b7ba7664d0b8/pydub-0.23.1-py2.py3-none-any.whl
Installing collected packages: pydub
Successfully installed pydub-0.23.1
Note: you may need to restart the kernel to use updated packages.
pydubのインストールはできた。
続けて音声ファイルの再生を行う。
from pydub import AudioSegment from pydub.playback import play # 音声ファイルの読み込み sound = AudioSegment.from_file("input.mp3", "mp3") # 再生 play(sound)
/data/data/com.termux/files/home/python3.7/lib/python3.7/site-packages/pydub/utils.py:179: RuntimeWarning: Couldn't find ffplay or avplay - defaulting to ffplay, but may not work
warn("Couldn't find ffplay or avplay - defaulting to ffplay, but may not work", RuntimeWarning)
--------------------------------------------
FileNotFoundErrorTraceback (most recent call last)
<ipython-input-2-c26d40624fe1> in <module>
6
7 # 再生
----> 8 play(sound)
~/python3.7/lib/python3.7/site-packages/pydub/playback.py in play(audio_segment)
69 return
70
---> 71 _play_with_ffplay(audio_segment)
~/python3.7/lib/python3.7/site-packages/pydub/playback.py in _play_with_ffplay(seg)
17 with NamedTemporaryFile("w+b", suffix=".wav") as f:
18 seg.export(f.name, "wav")
---> 19 subprocess.call([PLAYER, "-nodisp", "-autoexit", "-hide_banner", f.name])
20
21
/data/data/com.termux/files/usr/lib/python3.7/subprocess.py in call(timeout, *popenargs, **kwargs)
321 retcode = call(["ls", "-l"])
322 """
--> 323 with Popen(*popenargs, **kwargs) as p:
324 try:
325 return p.wait(timeout=timeout)
/data/data/com.termux/files/usr/lib/python3.7/subprocess.py in __init__(self, args, bufsize, executable, stdin, stdout, stderr, preexec_fn, close_fds, shell, cwd, env, universal_newlines, startupinfo, creationflags, restore_signals, start_new_session, pass_fds, encoding, errors, text)
773 c2pread, c2pwrite,
774 errread, errwrite,
--> 775 restore_signals, start_new_session)
776 except:
777 # Cleanup if the child failed starting.
/data/data/com.termux/files/usr/lib/python3.7/subprocess.py in _execute_child(self, args, executable, preexec_fn, close_fds, pass_fds, cwd, env, startupinfo, creationflags, shell, p2cread, p2cwrite, c2pread, c2pwrite, errread, errwrite, restore_signals, start_new_session)
1518 if errno_num == errno.ENOENT:
1519 err_msg += ': ' + repr(err_filename)
-> 1520 raise child_exception_type(errno_num, err_msg, err_filename)
1521 raise child_exception_type(err_msg)
1522
FileNotFoundError: [Errno 2] No such file or directory: 'ffplay': 'ffplay'
またもや撃沈。
ffplayが見つからんぞ?
と。なんですの、そのffplayとは。
ffplay
を検索すると、ffmpeg
というものがやたら出てくる。
こちら
https://tmg0525.hatenadiary.jp/entry/2018/05/24/211022
によると、pydub
を使うにはffmpeg
をインストールしなければならないと書かれている。
また、ffplay
はffmpeg
をインストールすれば自動的にインストールされるとも。
我が輩のtermuxでapt list
コマンドを実行すると、ffmpeg
は[installed,automatic]
と表示されているのでインストール済みなのだろうが、なぜか動きませんねぇ。
ところでffmpeg
とは何なのか。マルチメディアの鉄板ライブラリっぽい。音声や動画の変換を何でもこなせる。「これ知らんやつはモグリ」だそうです。覚えとこ。
肝心のffplayがよく分からんので、pydubも一旦放置。
winsound番外編
Androidスマホで動かしたいので、このWindows用ライブラリは使えません。後日参考の為に記録しておく。
こちらを写経させて頂きました。 https://techacademy.jp/magazine/20870
import winsound with open('sample.wav', 'rb') as f: data = f.read() winsound.PlaySound(data, winsound.SND_MEMORY)
シンプル。
pygame失敗編
pygame
は2Dゲームを作るPython用定番ライブラリとのこと。音声ファイル専用ではないが試してみます。
こちらのサイトを写経させて頂きました。
https://algorithm.joho.info/programming/python/pygame/#toc7
%pip install pygame
Collecting pygame
Using cached https://files.pythonhosted.org/packages/0f/9c/78626be04e193c0624842090fe5555b3805c050dfaa81c8094d6441db2be/pygame-1.9.6.tar.gz
[31m ERROR: Command errored out with exit status 1:
command: /data/data/com.termux/files/home/python3.7/bin/python -c 'import sys, setuptools, tokenize; sys.argv[0] = '"'"'/data/data/com.termux/files/usr/tmp/pip-install-1ru1oywg/pygame/setup.py'"'"'; __file__='"'"'/data/data/com.termux/files/usr/tmp/pip-install-1ru1oywg/pygame/setup.py'"'"';f=getattr(tokenize, '"'"'open'"'"', open)(__file__);code=f.read().replace('"'"'\r\n'"'"', '"'"'\n'"'"');f.close();exec(compile(code, __file__, '"'"'exec'"'"'))' egg_info --egg-base /data/data/com.termux/files/usr/tmp/pip-install-1ru1oywg/pygame/pip-egg-info
cwd: /data/data/com.termux/files/usr/tmp/pip-install-1ru1oywg/pygame/
Complete output (12 lines):
WARNING, No "Setup" File Exists, Running "buildconfig/config.py"
Using UNIX configuration...
/data/data/com.termux/files/usr/bin/sh: 1: sdl-config: not found
/data/data/com.termux/files/usr/bin/sh: 1: sdl-config: not found
/data/data/com.termux/files/usr/bin/sh: 1: sdl-config: not found
Hunting dependencies...
WARNING: "sdl-config" failed!
Unable to run "sdl-config". Please make sure a development version of SDL is installed.
----------------------------------------[0m
[31mERROR: Command errored out with exit status 1: python setup.py egg_info Check the logs for full command output.[0m
Note: you may need to restart the kernel to use updated packages.
pygameのインストール失敗。
GUIを使いそうなPythonライブラリのインストールはtermuxでは大概失敗する。
音声ファイル再生用のコードを写経しておきます。
import pygame.mixer import time # メイン def main(): pygame.mixer.init(frequency = 44100) # 初期設定 pygame.mixer.music.load("test.mp3") # 音楽ファイルの読み込み(wavファイルも読み込み可能) pygame.mixer.music.play(1) # 音楽の再生回数(1回) ※-1を指定するとループ time.sleep(100) # 音楽の再生時間 pygame.mixer.music.stop() # 再生の終了 if __name__ == '__main__': main()
vlc
vlc
はあらゆるOSでほぼ全ての動画と音声ファイルに対応した高機能な無料のメディアプレイヤーだそうです。
参考 https://appli-world.jp/posts/5180
インストール方法と使い方 https://applica.info/vlc-media-player-how-to-use
termuxでapt list
コマンドを実行すると表示される一覧にvlc
が載っているのでインストールできそうではあるが、動かし方が分からないのでこれも一旦放置。
aplay、mpg321不明
Androidとtermuxに対応しているのか不明。放置。
termux-media-playerコマンド成功編
失敗続きです。そろそろ再生成功したい。
インチキしてtermuxのメディア再生コマンドを使う。
termux-media-player play 音声ファイル名
とコマンド打つとファイルが再生された。
停止するにはtermux-media-player stop
コマンド。
Pythonで動かすにはsubprocessを使えばいいだろう。方法は省略。参考まで。
さいごに
音声ファイルを再生すべくAndroidスマホでtermuxからPythonライブラリを幾つか試したが、ことごとく粉砕された。
これが動画ファイルとなると、GUIを動かす難易度が我が素人レベルでは太刀打ち出来ないのでほぼ不可能。コマンドをsubprocessで使うならどうにかできるかも。
参考にさせて貰ったサイトの方々に感謝申し上げます。ありがとうございました。
今回の玉砕日記は以上です。