我从wp8移植应用程序,需要播放可能重叠的各种声音。到目前为止我发现使用MediaElement的唯一方法,但这并不允许重叠声音。
问题 - 用于播放重叠音频的最简单,最好的音频引擎是什么?理想情况下,我需要一个如何做到这一点的小例子。
我已经查看了WASAPI(http://code.msdn.microsoft.com/windowsapps/Windows-Audio-Session-22dcab6b),但它看起来不支持简单播放吗?
也许我可以包装MediaFoundation并从winrt调用它? (MediaEngine audio playback on WinRT)
现在这是我的代码,但是当我播放新的声音时,它会切断之前播放的声音而不是混合它们。
ThreadUtility.runOnUiThread(
async delegate()
{
// TODO doesn't allow sounds to overlap!
Uri uri = new Uri(R.base_uri, R.raw.URI_PREFIX + resourceId);
StorageFile storageFile =
await Windows.Storage.StorageFile.GetFileFromApplicationUriAsync(
uri);
MediaElement element = new MediaElement();
var randomAccessStream = await storageFile.OpenReadAsync();
element.SetSource(randomAccessStream, storageFile.ContentType);
element.Volume = volume;
element.PlaybackRate = pitch;
//TODO element.Pan = pan;
element.Play();
}
);
解决方案(根据Filip的回答):
页面类中的:
var mediaElements = new LinkedList<MediaElement>();
{
for (int channel = 0; channel < TeacherSoundGroover.NUM_CHANNELS; channel++)
{
var mediaElement = new MediaElement();
mediaElements.add(mediaElement);
// Must be in the tree otherwise it won't overlap!
m_titlePanel.Children.Add(mediaElement);
}
}
m_soundPlayer = new MySoundPlayer(mediaElements);
}
MySoundPlayer类中的:
ThreadUtility.runOnUiThread(
async delegate()
{
Uri uri = new Uri(R.base_uri, R.raw.URI_PREFIX + resourceId);
StorageFile storageFile =
await Windows.Storage.StorageFile.GetFileFromApplicationUriAsync(
uri);
if(m_mediaElements != null)
{
int count = m_mediaElements.size();
if (count > 0)
{
int channel = m_nextMediaElementToUse % count;
m_nextMediaElementToUse++;
MediaElement element = m_mediaElements.get(channel);
var randomAccessStream = await storageFile.OpenReadAsync();
element.Stop();
element.DefaultPlaybackRate = rate;
element.SetSource(randomAccessStream, storageFile.ContentType);
element.Volume = volume;
element.Balance = pan;
element.Play();
}
}
}
);
答案 0 :(得分:2)
最简单的方法是使用多个MediaElement控件,但这可能无法提供所需的结果。最好的方法是直接或通过SharpDX使用XAudio2,如果你想避免创建C ++ / CX WinRT组件。