private struct SoundChannel
{
	ubyte[] data;
	void*   tag;
	int     position;
}



private SoundChannel[16] _soundChannels;



public void initialize()
{
	foreach(inout channel; _soundChannels)
	{
		channel.data     = null;
		channel.tag      = null;
		channel.position = 0;
	}

	SDL_AudioSpec fmt;

	/* 22khz の 16-bit ステレオ に設定 */
	fmt.freq     = 22050;
	fmt.format   = AUDIO_S16;
	fmt.channels = 2;
	fmt.samples  = 512;
	fmt.callback = &mixAudio;
	fmt.userdata = NULL;

	/* オーディオデバイスをオープンしてサウンドの再生を開始! */
	if( SDL_OpenAudio(&fmt, NULL) < 0 )
	{
		throw new Exception("SDL_OpenAudio fails!");
	}
	SDL_PauseAudio(0);
}



private void mixAudio(void* unused, ubyte* stream, int len)
{
	foreach(inout channel; _soundChannels)
	{
		if(channel.position < channel.data.length)
		{
			auto data = channel.data[channel.position .. length];
			if(data.length > len)
			{
				data = data[0 .. len];
			}

			SDL_MixAudio(stream, data.ptr, data.length, SDL_MIX_MAXVOLUME);

			channel.position += data.length;
		}
	}
}
