はんぎょねこの憂鬱

耳から変な汁が出てきた

Pythonゲームプログラミング #5 サウンド

#0 環境構築
#1 メインループ
#2 画像表示
#3 アニメーション
#4 キー入力
#5 サウンド
#6 衝突判定
#7 ステートマシン
#8 マップチップ
#9 スクロール

サウンド

pygameを使ったゲームプログラミングについて説明していきます。

  • Windows10
  • Python3.6.1
  • pygame1.9.3

今回はサウンド処理です。

ゲームに必要な音について

ゲームに使うキー入力のパターンは大きく分けて2つあります。「効果音」と「BGM」です。

f:id:dungeonneko:20170515113724p:plain

pygameではどちらも簡単に実装できます。

サンプルコード

解説

初期化

5行目

pygame.mixer.pre_init(44100, -16, 1, 512)

第一引数:再生周波数
第二引数:ビット数(マイナスの場合はsigned, プラスの場合はunsigned)
第三引数:チャンネル数(1=モノラル、2=ステレオ)
第四引数:バッファサイズ(2の倍数)

pygame.initでmixerも初期化されるため、pre_init関数を使ってあらかじめ初期化の設定をしておきます。 バッファサイズは小さすぎるとサウンドが途切れがちになり、大きすぎると再生までのタイムラグが長くなります。 詳しくはドキュメントを読んでください。

効果音のロードと再生

11行目と26行目

se = pygame.mixer.Sound('se.wav')
se.play()

Soundクラスのドキュメントはこちら

BGMのロードと再生

14~16行目

pygame.mixer.music.load('bgm.wav')
pygame.mixer.music.set_volume(0.5)
pygame.mixer.music.play(-1)

playに渡してる引数はループ回数で-1は無限ループになります(Soundクラスでも同様にループ指定できます)。 musicのドキュメントはこちら

補足:メモリとストリーミング

ところで効果音とBGMのちがいは何でしょう?音の長さや使用する目的もちがいますが、プログラム上ではBGMを効果音として鳴らすこともできるわけです。 それなのに、なぜプログラムの書き方が違うかというと、現代のコンピュータには、メモリ容量という制限があるためです。

f:id:dungeonneko:20170515113758p:plain

コンピュータが色々な処理をするには、メモリ上に絵や音やプログラムを載せておかなければなりません。 ところがメモリの大きさは決まっていて、一度に載せることができる限度というものがあります。 ここで問題になるのがファイルサイズの大きい音楽や、映像などのデータです。

f:id:dungeonneko:20170515113816p:plain

大きなデータはそのままではメモリに載せることができなかったり、他のプログラムなどが載せられる場所が少なくなってしまうという問題があります。 そこで人類が考えたのがストリーミングという技術です。

f:id:dungeonneko:20170515113832p:plain

音楽全体はメモリに載せることができなくても「今聴いているところ」のデータだけをファイルから切り出してくれば、場所をとらずにメモリに載せることができるというわけです。