Mark Harmstone : dsound: Support 5.1 sound.

Alexandre Julliard julliard at wine.codeweavers.com
Fri Jan 9 11:49:15 CST 2015


Module: wine
Branch: master
Commit: 77b2ab21f45bc6773f539f2ae04edbf9cf09ac48
URL:    http://source.winehq.org/git/wine.git/?a=commit;h=77b2ab21f45bc6773f539f2ae04edbf9cf09ac48

Author: Mark Harmstone <hellas at burntcomma.com>
Date:   Tue Jan  6 19:27:21 2015 +0000

dsound: Support 5.1 sound.

---

 dlls/dsound/dsound.c         | 34 ++++++++++++++++++++++++++++++++++
 dlls/dsound/dsound_convert.c | 24 ++++++++++++++++++++++++
 dlls/dsound/dsound_private.h |  4 +++-
 dlls/dsound/mixer.c          |  7 +++++++
 dlls/dsound/primary.c        |  9 ++++++++-
 dlls/dsound/sound3d.c        | 11 +++++++++--
 6 files changed, 85 insertions(+), 4 deletions(-)

diff --git a/dlls/dsound/dsound.c b/dlls/dsound/dsound.c
index db4852f..8df778a 100644
--- a/dlls/dsound/dsound.c
+++ b/dlls/dsound/dsound.c
@@ -619,6 +619,40 @@ void DSOUND_ParseSpeakerConfig(DirectSoundDevice *device)
             device->lfe_channel = -1;
         break;
 
+        case DSSPEAKER_5POINT1_BACK:
+            device->speaker_angles[0] = M_PI/180.0f * -135.0f;
+            device->speaker_angles[1] = M_PI/180.0f *  -45.0f;
+            device->speaker_angles[2] = M_PI/180.0f *    0.0f;
+            device->speaker_angles[3] = M_PI/180.0f *   45.0f;
+            device->speaker_angles[4] = M_PI/180.0f *  135.0f;
+            device->speaker_angles[5] = 9999.0f;
+            device->speaker_num[0] = 4; /* Rear left */
+            device->speaker_num[1] = 0; /* Front left */
+            device->speaker_num[2] = 2; /* Front centre */
+            device->speaker_num[3] = 1; /* Front right */
+            device->speaker_num[4] = 5; /* Rear right */
+            device->speaker_num[5] = 3; /* LFE */
+            device->num_speakers = 6;
+            device->lfe_channel = 3;
+        break;
+
+        case DSSPEAKER_5POINT1_SURROUND:
+            device->speaker_angles[0] = M_PI/180.0f *  -90.0f;
+            device->speaker_angles[1] = M_PI/180.0f *  -30.0f;
+            device->speaker_angles[2] = M_PI/180.0f *    0.0f;
+            device->speaker_angles[3] = M_PI/180.0f *   30.0f;
+            device->speaker_angles[4] = M_PI/180.0f *   90.0f;
+            device->speaker_angles[5] = 9999.0f;
+            device->speaker_num[0] = 4; /* Rear left */
+            device->speaker_num[1] = 0; /* Front left */
+            device->speaker_num[2] = 2; /* Front centre */
+            device->speaker_num[3] = 1; /* Front right */
+            device->speaker_num[4] = 5; /* Rear right */
+            device->speaker_num[5] = 3; /* LFE */
+            device->num_speakers = 6;
+            device->lfe_channel = 3;
+        break;
+
         default:
             WARN("unknown speaker_config %u\n", device->speaker_config);
     }
diff --git a/dlls/dsound/dsound_convert.c b/dlls/dsound/dsound_convert.c
index a7f7ad4..5ac7a10 100644
--- a/dlls/dsound/dsound_convert.c
+++ b/dlls/dsound/dsound_convert.c
@@ -184,6 +184,30 @@ void put_stereo2quad(const IDirectSoundBufferImpl *dsb, DWORD pos, DWORD channel
     }
 }
 
+void put_mono2surround51(const IDirectSoundBufferImpl *dsb, DWORD pos, DWORD channel, float value)
+{
+    dsb->put_aux(dsb, pos, 0, value);
+    dsb->put_aux(dsb, pos, 1, value);
+    dsb->put_aux(dsb, pos, 2, value);
+    dsb->put_aux(dsb, pos, 3, value);
+    dsb->put_aux(dsb, pos, 4, value);
+    dsb->put_aux(dsb, pos, 5, value);
+}
+
+void put_stereo2surround51(const IDirectSoundBufferImpl *dsb, DWORD pos, DWORD channel, float value)
+{
+    if (channel == 0) { /* Left */
+        dsb->put_aux(dsb, pos, 0, value); /* Front left */
+        dsb->put_aux(dsb, pos, 4, value); /* Back left */
+
+        dsb->put_aux(dsb, pos, 2, 0.0f); /* Mute front centre */
+        dsb->put_aux(dsb, pos, 3, 0.0f); /* Mute LFE */
+    } else if (channel == 1) { /* Right */
+        dsb->put_aux(dsb, pos, 1, value); /* Front right */
+        dsb->put_aux(dsb, pos, 5, value); /* Back right */
+    }
+}
+
 void mixieee32(float *src, float *dst, unsigned samples)
 {
     TRACE("%p - %p %d\n", src, dst, samples);
diff --git a/dlls/dsound/dsound_private.h b/dlls/dsound/dsound_private.h
index 0ade63e..af2034a 100644
--- a/dlls/dsound/dsound_private.h
+++ b/dlls/dsound/dsound_private.h
@@ -30,7 +30,7 @@
 
 #include "wine/list.h"
 
-#define DS_MAX_CHANNELS 4
+#define DS_MAX_CHANNELS 6
 
 extern int ds_hel_buflen DECLSPEC_HIDDEN;
 extern int ds_snd_queue_max DECLSPEC_HIDDEN;
@@ -181,6 +181,8 @@ float get_mono(const IDirectSoundBufferImpl *dsb, DWORD pos, DWORD channel) DECL
 void put_mono2stereo(const IDirectSoundBufferImpl *dsb, DWORD pos, DWORD channel, float value) DECLSPEC_HIDDEN;
 void put_mono2quad(const IDirectSoundBufferImpl *dsb, DWORD pos, DWORD channel, float value) DECLSPEC_HIDDEN;
 void put_stereo2quad(const IDirectSoundBufferImpl *dsb, DWORD pos, DWORD channel, float value) DECLSPEC_HIDDEN;
+void put_mono2surround51(const IDirectSoundBufferImpl *dsb, DWORD pos, DWORD channel, float value) DECLSPEC_HIDDEN;
+void put_stereo2surround51(const IDirectSoundBufferImpl *dsb, DWORD pos, DWORD channel, float value) DECLSPEC_HIDDEN;
 
 HRESULT IDirectSoundBufferImpl_Create(
     DirectSoundDevice *device,
diff --git a/dlls/dsound/mixer.c b/dlls/dsound/mixer.c
index 363ca47..b367086 100644
--- a/dlls/dsound/mixer.c
+++ b/dlls/dsound/mixer.c
@@ -156,6 +156,8 @@ void DSOUND_RecalcFormat(IDirectSoundBufferImpl *dsb)
 			dsb->put = put_mono2stereo;
 		else if (ochannels == 4)
 			dsb->put = put_mono2quad;
+		else if (ochannels == 6)
+			dsb->put = put_mono2surround51;
 	}
 	else if (ochannels == 1)
 	{
@@ -167,6 +169,11 @@ void DSOUND_RecalcFormat(IDirectSoundBufferImpl *dsb)
 		dsb->mix_channels = 2;
 		dsb->put = put_stereo2quad;
 	}
+	else if (ichannels == 2 && ochannels == 6)
+	{
+		dsb->mix_channels = 2;
+		dsb->put = put_stereo2surround51;
+	}
 	else
 	{
 		if (ichannels > 2)
diff --git a/dlls/dsound/primary.c b/dlls/dsound/primary.c
index bed588d..d3c2689 100644
--- a/dlls/dsound/primary.c
+++ b/dlls/dsound/primary.c
@@ -70,6 +70,9 @@ static DWORD speaker_config_to_channel_mask(DWORD speaker_config)
 
         case DSSPEAKER_QUAD:
             return SPEAKER_FRONT_LEFT | SPEAKER_FRONT_RIGHT | SPEAKER_BACK_LEFT | SPEAKER_BACK_RIGHT;
+
+        case DSSPEAKER_5POINT1_BACK:
+            return SPEAKER_FRONT_LEFT | SPEAKER_FRONT_RIGHT | SPEAKER_FRONT_CENTER | SPEAKER_LOW_FREQUENCY | SPEAKER_BACK_LEFT | SPEAKER_BACK_RIGHT;
     }
 
     WARN("unknown speaker_config %u\n", speaker_config);
@@ -195,7 +198,11 @@ static DWORD DSOUND_FindSpeakerConfig(IMMDevice *mmdevice)
     PropVariantClear(&pv);
     IPropertyStore_Release(store);
 
-    if ((phys_speakers & KSAUDIO_SPEAKER_QUAD) == KSAUDIO_SPEAKER_QUAD)
+    if ((phys_speakers & KSAUDIO_SPEAKER_5POINT1) == KSAUDIO_SPEAKER_5POINT1)
+        return DSSPEAKER_5POINT1_BACK;
+    else if ((phys_speakers & KSAUDIO_SPEAKER_5POINT1_SURROUND) == KSAUDIO_SPEAKER_5POINT1_SURROUND)
+        return DSSPEAKER_5POINT1_SURROUND;
+    else if ((phys_speakers & KSAUDIO_SPEAKER_QUAD) == KSAUDIO_SPEAKER_QUAD)
         return DSSPEAKER_QUAD;
     else if ((phys_speakers & KSAUDIO_SPEAKER_STEREO) == KSAUDIO_SPEAKER_STEREO)
         return DSSPEAKER_COMBINED(DSSPEAKER_STEREO, DSSPEAKER_GEOMETRY_WIDE);
diff --git a/dlls/dsound/sound3d.c b/dlls/dsound/sound3d.c
index 329de94..f720478 100644
--- a/dlls/dsound/sound3d.c
+++ b/dlls/dsound/sound3d.c
@@ -162,7 +162,7 @@ void DSOUND_Calc3DBuffer(IDirectSoundBufferImpl *dsb)
 	/* panning related stuff */
 	D3DVALUE flAngle, flAngle2;
 	D3DVECTOR vLeft;
-	int i;
+	int i, num_main_speakers;
 	float a, ingain;
 	/* doppler shift related stuff */
 
@@ -311,8 +311,15 @@ if(0)
 	for (i = 0; i < dsb->device->pwfx->nChannels; i++)
 		dsb->volpan.dwTotalAmpFactor[i] = 0;
 
+	num_main_speakers = dsb->device->pwfx->nChannels;
+
+	if (dsb->device->lfe_channel != -1) {
+		dsb->volpan.dwTotalAmpFactor[dsb->device->lfe_channel] = ingain;
+		num_main_speakers--;
+	}
+
 	/* adapted from OpenAL's Alc/panning.c */
-	for (i = 0; i < dsb->device->pwfx->nChannels - 1; i++)
+	for (i = 0; i < num_main_speakers - 1; i++)
 	{
 		if(flAngle >= dsb->device->speaker_angles[i] && flAngle < dsb->device->speaker_angles[i+1])
 		{




More information about the wine-cvs mailing list