カーナビでよくある、音楽流しながらナビしてると、ガイダンス中は音楽のボリュームを一時的に下げて、案内の音声を再生するってやつ。
に回答したので、その関連でやってみた。
//MainActivity.cs
[Activity(Label = "AudioFocusSample", MainLauncher = true, Icon = "@mipmap/icon")]
public class MainActivity : Activity, AudioManager.IOnAudioFocusChangeListener
{
protected override void OnCreate(Bundle savedInstanceState)
{
base.OnCreate(savedInstanceState);
SetContentView(Resource.Layout.Main);
var audioManager = (AudioManager)GetSystemService(Context.AudioService);
// 先に効果音を読み込んでおく
var soundPool = new SoundPool(1, Stream.Music, 0);
var soundId = soundPool.Load(ApplicationContext, Resource.Raw.cat, 0);
// SoundPool は再生完了のコールバックがないので、事前に長さを得ておく
var duration = GetSoundDuration(Resource.Raw.cat);
FindViewById<Button>(Resource.Id.buttonRequestFocus).Click += async (sender, e) =>
{
// ダッキングを許可する AudioFocus を要求
var result = audioManager.RequestAudioFocus(this, Stream.Music, AudioFocus.GainTransientMayDuck);
if (result == AudioFocusRequest.Granted)
{
// 効果音を再生する
soundPool.Play(soundId, 1.0f, 1.0f, 0, 0, 1.0f);
// 再生完了まで待つ
await Task.Delay((int)duration);
// AudioFocus を開放
audioManager.AbandonAudioFocus(this);
}
};
}
// 音声の再生長さを得る
private long GetSoundDuration(int rawId)
{
using (var player = MediaPlayer.Create(ApplicationContext, rawId))
{
return player.Duration;
}
}
// IOnAudioFocusChangeListener の実装(RequestAudioFocus のために必要)
public void OnAudioFocusChange([GeneratedEnum] AudioFocus focusChange)
{
// 今回は使用しない
}
}
効果音 Resource.Raw.cat
は、 On-Jin ~音人~ さんのを使わせてもらいました。
音量を小さくする=絞る=ダッキング、というのがなかなか連想しづらいので辿りつけない。
Android の音声再生は、他に MediaPlayer
とか AudioTrack
もあるし、リモコンなど外部からの操作のため?に BroadcastReceiver を使わないといけないし。
サンプルアプリはこちら。
次は Xamarin.iOS でやってみる。