/*  			DirectSound
 *
 * Copyright 1998 Marcus Meissner
 * Copyright 1998 Rob Riggs
 * Copyright 2000-2001 TransGaming Technologies, Inc.
 * Copyright 2002-2003 Rok Mandeljc <rok.mandeljc@gimb.org>
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
 */
/*
 * Most thread locking is complete. There may be a few race
 * conditions still lurking.
 *
 * Tested with a Soundblaster clone, a Gravis UltraSound Classic,
 * and a Turtle Beach Tropez+.
 *
 * TODO:
 *	Implement SetCooperativeLevel properly (need to address focus issues)
 *	Implement DirectSound3DBuffers (stubs in place)
 *	Use hardware 3D support if available
 *      Add critical section locking inside Release and AddRef methods
 *      Handle static buffers - put those in hardware, non-static not in hardware
 *      Hardware DuplicateSoundBuffer
 *      Proper volume calculation, and setting volume in HEL primary buffer
 *      Optimize WINMM and negotiate fragment size, decrease DS_HEL_MARGIN
 */

#include <stdarg.h>
#include <math.h>	/* Insomnia - pow() function */

#include "windef.h"
#include "winbase.h"
#include "winuser.h"
#include "mmsystem.h"
#include "winternl.h"
#include "mmddk.h"
#include "wine/debug.h"
#include "dsound.h"
#include "dsound_private.h"

/* default velocity of sound in the air */
#define DEFAULT_VELOCITY 340

WINE_DEFAULT_DEBUG_CHANNEL(dsound3d);

/*******************************************************************************
 *              Auxiliary functions
 */

/* scalar product (I believe it's called dot product in English) */
static inline D3DVALUE ScalarProduct (const D3DVECTOR *a, const D3DVECTOR *b)
{
	D3DVALUE c;
	c = (a->x*b->x) + (a->y*b->y) + (a->z*b->z);
	TRACE("(%f,%f,%f) * (%f,%f,%f) = %f)\n", a->x, a->y, a->z, b->x, b->y,
	      b->z, c);
	return c;
}

/* vector product (I believe it's called cross product in English */
static inline D3DVECTOR VectorProduct (const D3DVECTOR *a, const D3DVECTOR *b)
{
	D3DVECTOR c;
	c.x = (a->y*b->z) - (a->z*b->y);
	c.y = (a->z*b->x) - (a->x*b->z);
	c.z = (a->x*b->y) - (a->y*b->x);
	TRACE("(%f,%f,%f) x (%f,%f,%f) = (%f,%f,%f)\n", a->x, a->y, a->z, b->x, b->y,
	      b->z, c.x, c.y, c.z);
	return c;
}

/* magnitude (length) of vector */
static inline D3DVALUE VectorMagnitude (const D3DVECTOR *a)
{
	D3DVALUE l;
	l = sqrt (ScalarProduct (a, a));
	TRACE("|(%f,%f,%f)| = %f\n", a->x, a->y, a->z, l);
	return l;
}

/* conversion between radians and degrees */
static inline D3DVALUE RadToDeg (D3DVALUE angle)
{
	D3DVALUE newangle;
	newangle = angle * (360/(2*M_PI));
	TRACE("%f rad = %f deg\n", angle, newangle);
	return newangle;
}

/* angle between vectors - rad version */
static inline D3DVALUE AngleBetweenVectorsRad (const D3DVECTOR *a, const D3DVECTOR *b)
{
	D3DVALUE la, lb, product, angle, cos;
	/* definition of scalar product: a*b = |a|*|b|*cos... therefore: */
	product = ScalarProduct (a,b);
	la = VectorMagnitude (a);
	lb = VectorMagnitude (b);
	if (!la || !lb)
		return 0;

	cos = product/(la*lb);
	angle = acos(cos);
	if (cos < 0.0f) { angle -= M_PI; }
	TRACE("angle between (%f,%f,%f) and (%f,%f,%f) = %f radians (%f degrees)\n",  a->x, a->y, a->z, b->x,
	      b->y, b->z, angle, RadToDeg(angle));
	return angle;	
}

static inline D3DVALUE AngleBetweenVectorsDeg (const D3DVECTOR *a, const D3DVECTOR *b)
{
	return RadToDeg(AngleBetweenVectorsRad(a, b));
}

/* calculates vector between two points */
static inline D3DVECTOR VectorBetweenTwoPoints (const D3DVECTOR *a, const D3DVECTOR *b)
{
	D3DVECTOR c;
	c.x = b->x - a->x;
	c.y = b->y - a->y;
	c.z = b->z - a->z;
	TRACE("A (%f,%f,%f), B (%f,%f,%f), AB = (%f,%f,%f)\n", a->x, a->y, a->z, b->x, b->y,
	      b->z, c.x, c.y, c.z);
	return c;
}

/* calculates the length of vector's projection on another vector */
static inline D3DVALUE ProjectVector (const D3DVECTOR *a, const D3DVECTOR *p)
{
	D3DVALUE prod, result;
	prod = ScalarProduct(a, p);
	result = prod/VectorMagnitude(p);
	TRACE("length projection of (%f,%f,%f) on (%f,%f,%f) = %f\n", a->x, a->y, a->z, p->x,
              p->y, p->z, result);
	return result;
}

/*******************************************************************************
 *              3D Buffer and Listener mixing
 */

void DSOUND_Calc3DBuffer(IDirectSoundBufferImpl *dsb)
{
	/* volume, at which the sound will be played after all calcs. */
	D3DVALUE lVolume = 0;
	/* stuff for distance related stuff calc. */
	D3DVECTOR vDistance;
	D3DVALUE flDistance = 0;
	/* panning related stuff */
	D3DVALUE flAngle, flAngle2;
	D3DVECTOR vLeft;
	int i, num_main_speakers;
	float a, ingain;
	/* doppler shift related stuff */

	TRACE("(%p)\n",dsb);

	/* initial buffer volume */
	lVolume = dsb->ds3db_lVolume;
	
	switch (dsb->ds3db_ds3db.dwMode)
	{
		case DS3DMODE_DISABLE:
			TRACE("3D processing disabled\n");
			/* this one is here only to eliminate annoying warning message */
			DSOUND_RecalcVolPan (&dsb->volpan);
			return;
		case DS3DMODE_NORMAL:
			TRACE("Normal 3D processing mode\n");
			/* we need to calculate distance between buffer and listener*/
			vDistance = VectorBetweenTwoPoints(&dsb->device->ds3dl.vPosition, &dsb->ds3db_ds3db.vPosition);
			flDistance = VectorMagnitude (&vDistance);
			break;
		case DS3DMODE_HEADRELATIVE:
			TRACE("Head-relative 3D processing mode\n");
			/* distance between buffer and listener is same as buffer's position */
			vDistance = dsb->ds3db_ds3db.vPosition;
			flDistance = VectorMagnitude (&vDistance);
			break;
	}
	
	if (flDistance > dsb->ds3db_ds3db.flMaxDistance)
	{
		/* some apps don't want you to hear too distant sounds... */
		if (dsb->dsbd.dwFlags & DSBCAPS_MUTE3DATMAXDISTANCE)
		{
			dsb->volpan.lVolume = DSBVOLUME_MIN;
			DSOUND_RecalcVolPan (&dsb->volpan);		
			/* i guess mixing here would be a waste of power */
			return;
		}
		else
			flDistance = dsb->ds3db_ds3db.flMaxDistance;
	}		

	if (flDistance < dsb->ds3db_ds3db.flMinDistance)
		flDistance = dsb->ds3db_ds3db.flMinDistance;
	
	/* attenuation proportional to the distance squared, converted to millibels as in lVolume*/
	lVolume -= log10(flDistance/dsb->ds3db_ds3db.flMinDistance * flDistance/dsb->ds3db_ds3db.flMinDistance)*1000;
	TRACE("dist. att: Distance = %f, MinDistance = %f => adjusting volume %d to %f\n", flDistance, dsb->ds3db_ds3db.flMinDistance, dsb->ds3db_lVolume, lVolume);

	/* conning */
	/* sometimes it happens that vConeOrientation vector = (0,0,0); in this case angle is "nan" and it's useless*/
	if (dsb->ds3db_ds3db.vConeOrientation.x == 0 && dsb->ds3db_ds3db.vConeOrientation.y == 0 && dsb->ds3db_ds3db.vConeOrientation.z == 0)
	{
		TRACE("conning: cones not set\n");
	}
	else
	{
		D3DVECTOR vDistanceInv;

		vDistanceInv.x = -vDistance.x;
		vDistanceInv.y = -vDistance.y;
		vDistanceInv.z = -vDistance.z;

		/* calculate angle */
		flAngle = AngleBetweenVectorsDeg(&dsb->ds3db_ds3db.vConeOrientation, &vDistanceInv);
		/* if by any chance it happens that OutsideConeAngle = InsideConeAngle (that means that conning has no effect) */
		if (dsb->ds3db_ds3db.dwInsideConeAngle != dsb->ds3db_ds3db.dwOutsideConeAngle)
		{
			/* my test show that for my way of calc., we need only half of angles */
			DWORD dwInsideConeAngle = dsb->ds3db_ds3db.dwInsideConeAngle/2;
			DWORD dwOutsideConeAngle = dsb->ds3db_ds3db.dwOutsideConeAngle/2;
			if (dwOutsideConeAngle == dwInsideConeAngle)
				++dwOutsideConeAngle;

			/* full volume */
			if (flAngle < dwInsideConeAngle)
				flAngle = dwInsideConeAngle;
			/* min (app defined) volume */
			if (flAngle > dwOutsideConeAngle)
				flAngle = dwOutsideConeAngle;
			/* this probably isn't the right thing, but it's ok for the time being */
			lVolume += ((dsb->ds3db_ds3db.lConeOutsideVolume)/((dwOutsideConeAngle) - (dwInsideConeAngle))) * flAngle;
		}
		TRACE("conning: Angle = %f deg; InsideConeAngle(/2) = %d deg; OutsideConeAngle(/2) = %d deg; ConeOutsideVolume = %d => adjusting volume to %f\n",
		       flAngle, dsb->ds3db_ds3db.dwInsideConeAngle/2, dsb->ds3db_ds3db.dwOutsideConeAngle/2, dsb->ds3db_ds3db.lConeOutsideVolume, lVolume);
	}
	dsb->volpan.lVolume = lVolume;

	ingain = pow(2.0, dsb->volpan.lVolume / 600.0) * 0xffff;

	if (dsb->device->pwfx->nChannels == 1)
	{
		dsb->volpan.dwTotalAmpFactor[0] = ingain;
		return;
	}
	
	/* panning */
	if (vDistance.x == 0.0f && vDistance.y == 0.0f && vDistance.z == 0.0f)
		flAngle = 0.0;
	else
	{
		vLeft = VectorProduct(&dsb->device->ds3dl.vOrientFront, &dsb->device->ds3dl.vOrientTop);
		flAngle = AngleBetweenVectorsRad(&dsb->device->ds3dl.vOrientFront, &vDistance);
		flAngle2 = AngleBetweenVectorsRad(&vLeft, &vDistance);

		/* AngleBetweenVectorsRad performs a dot product, which gives us the cosine of the angle
		 * between two vectors. Unfortunately, because cos(theta) = cos(-theta), we've no idea from
		 * this whether the sound is to our left or to our right. We have to perform another dot
		 * product, with a vector at right angles to the initial one, to get the correct angle.
		 * The angle should be between -180 degrees and 180 degrees. */
		if (flAngle < 0.0f) { flAngle += M_PI; }
		if (flAngle2 > 0.0f) { flAngle = -flAngle; }
	}
	TRACE("panning: Angle = %f rad, lPan = %d\n", flAngle, dsb->volpan.lPan);

	/* FIXME: Doppler Effect disabled since i have no idea which frequency to change and how to do it */
if(0)
{
	D3DVALUE flFreq, flBufferVel, flListenerVel;
	/* doppler shift*/
	if (!VectorMagnitude(&dsb->ds3db_ds3db.vVelocity) && !VectorMagnitude(&dsb->device->ds3dl.vVelocity))
	{
		TRACE("doppler: Buffer and Listener don't have velocities\n");
	}
	else if (!(dsb->ds3db_ds3db.vVelocity.x == dsb->device->ds3dl.vVelocity.x &&
	           dsb->ds3db_ds3db.vVelocity.y == dsb->device->ds3dl.vVelocity.y &&
	           dsb->ds3db_ds3db.vVelocity.z == dsb->device->ds3dl.vVelocity.z))
	{
		/* calculate length of ds3db_ds3db.vVelocity component which causes Doppler Effect
		   NOTE: if buffer moves TOWARDS the listener, it's velocity component is NEGATIVE
		         if buffer moves AWAY from listener, it's velocity component is POSITIVE */
		flBufferVel = ProjectVector(&dsb->ds3db_ds3db.vVelocity, &vDistance);
		/* calculate length of ds3dl.vVelocity component which causes Doppler Effect
		   NOTE: if listener moves TOWARDS the buffer, it's velocity component is POSITIVE
		         if listener moves AWAY from buffer, it's velocity component is NEGATIVE */
		flListenerVel = ProjectVector(&dsb->device->ds3dl.vVelocity, &vDistance);
		/* formula taken from Gianicoli D.: Physics, 4th edition: */
		/* FIXME: replace dsb->freq with appropriate frequency ! */
		flFreq = dsb->freq * ((DEFAULT_VELOCITY + flListenerVel)/(DEFAULT_VELOCITY + flBufferVel));
		TRACE("doppler: Buffer velocity (component) = %f, Listener velocity (component) = %f => Doppler shift: %d Hz -> %f Hz\n",
		      flBufferVel, flListenerVel, dsb->freq, flFreq);
		/* FIXME: replace following line with correct frequency setting ! */
		dsb->freq = flFreq;
		DSOUND_RecalcFormat(dsb);
	}
}

	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 < num_main_speakers - 1; i++)
	{
		if(flAngle >= dsb->device->speaker_angles[i] && flAngle < dsb->device->speaker_angles[i+1])
		{
			/* Sound is between speakers i and i+1 */
			a = (flAngle-dsb->device->speaker_angles[i]) / (dsb->device->speaker_angles[i+1]-dsb->device->speaker_angles[i]);
			dsb->volpan.dwTotalAmpFactor[dsb->device->speaker_num[i]] = sqrtf(1.0f-a) * ingain;
			dsb->volpan.dwTotalAmpFactor[dsb->device->speaker_num[i+1]] = sqrtf(a) * ingain;
			return;
		}
	}

	/* Sound is between last and first speakers */
	if (flAngle < dsb->device->speaker_angles[0]) { flAngle += M_PI*2.0f; }
	a = (flAngle-dsb->device->speaker_angles[i]) / (M_PI*2.0f + dsb->device->speaker_angles[0]-dsb->device->speaker_angles[i]);
	dsb->volpan.dwTotalAmpFactor[dsb->device->speaker_num[i]] = sqrtf(1.0f-a) * ingain;
	dsb->volpan.dwTotalAmpFactor[dsb->device->speaker_num[0]] = sqrtf(a) * ingain;
}

static void DSOUND_Mix3DBuffer(IDirectSoundBufferImpl *dsb)
{
	TRACE("(%p)\n",dsb);

	DSOUND_Calc3DBuffer(dsb);
}

static void DSOUND_ChangeListener(IDirectSoundBufferImpl *ds3dl)
{
	int i;
	TRACE("(%p)\n",ds3dl);
	for (i = 0; i < ds3dl->device->nrofbuffers; i++)
	{
		/* check if this buffer is waiting for recalculation */
		if (ds3dl->device->buffers[i]->ds3db_need_recalc)
		{
			DSOUND_Mix3DBuffer(ds3dl->device->buffers[i]);
		}
	}
}

/*******************************************************************************
 *              IDirectSound3DBuffer
 */
static inline IDirectSoundBufferImpl *impl_from_IDirectSound3DBuffer(IDirectSound3DBuffer *iface)
{
    return CONTAINING_RECORD(iface, IDirectSoundBufferImpl, IDirectSound3DBuffer_iface);
}

/* IUnknown methods */
static HRESULT WINAPI IDirectSound3DBufferImpl_QueryInterface(IDirectSound3DBuffer *iface,
        REFIID riid, void **ppobj)
{
    IDirectSoundBufferImpl *This = impl_from_IDirectSound3DBuffer(iface);

    TRACE("(%p, %s, %p)\n", This, debugstr_guid(riid), ppobj);

    return IDirectSoundBuffer8_QueryInterface(&This->IDirectSoundBuffer8_iface, riid, ppobj);
}

static ULONG WINAPI IDirectSound3DBufferImpl_AddRef(IDirectSound3DBuffer *iface)
{
    IDirectSoundBufferImpl *This = impl_from_IDirectSound3DBuffer(iface);
    ULONG ref = InterlockedIncrement(&This->ref3D);

    TRACE("(%p) ref was %d\n", This, ref - 1);

    if(ref == 1)
        InterlockedIncrement(&This->numIfaces);

    return ref;
}

static ULONG WINAPI IDirectSound3DBufferImpl_Release(IDirectSound3DBuffer *iface)
{
    IDirectSoundBufferImpl *This = impl_from_IDirectSound3DBuffer(iface);
    ULONG ref = InterlockedDecrement(&This->ref3D);

    TRACE("(%p) ref was %d\n", This, ref + 1);

    if (!ref && !InterlockedDecrement(&This->numIfaces))
        secondarybuffer_destroy(This);

    return ref;
}

/* IDirectSound3DBuffer methods */
static HRESULT WINAPI IDirectSound3DBufferImpl_GetAllParameters(IDirectSound3DBuffer *iface,
	DS3DBUFFER *lpDs3dBuffer)
{
	IDirectSoundBufferImpl *This = impl_from_IDirectSound3DBuffer(iface);

	TRACE("(%p,%p)\n",This,lpDs3dBuffer);

	if (lpDs3dBuffer == NULL) {
		WARN("invalid parameter: lpDs3dBuffer == NULL\n");
		return DSERR_INVALIDPARAM;
	}

	if (lpDs3dBuffer->dwSize < sizeof(*lpDs3dBuffer)) {
		WARN("invalid parameter: lpDs3dBuffer->dwSize = %d\n",lpDs3dBuffer->dwSize);
		return DSERR_INVALIDPARAM;
	}
	
	TRACE("returning: all parameters\n");
	*lpDs3dBuffer = This->ds3db_ds3db;
	return DS_OK;
}

static HRESULT WINAPI IDirectSound3DBufferImpl_GetConeAngles(IDirectSound3DBuffer *iface,
        DWORD *lpdwInsideConeAngle, DWORD *lpdwOutsideConeAngle)
{
    IDirectSoundBufferImpl *This = impl_from_IDirectSound3DBuffer(iface);

    TRACE("returning: Inside Cone Angle = %d degrees; Outside Cone Angle = %d degrees\n",
            This->ds3db_ds3db.dwInsideConeAngle, This->ds3db_ds3db.dwOutsideConeAngle);
    *lpdwInsideConeAngle = This->ds3db_ds3db.dwInsideConeAngle;
    *lpdwOutsideConeAngle = This->ds3db_ds3db.dwOutsideConeAngle;
    return DS_OK;
}

static HRESULT WINAPI IDirectSound3DBufferImpl_GetConeOrientation(IDirectSound3DBuffer *iface,
        D3DVECTOR *lpvConeOrientation)
{
    IDirectSoundBufferImpl *This = impl_from_IDirectSound3DBuffer(iface);

    TRACE("returning: Cone Orientation vector = (%f,%f,%f)\n",
            This->ds3db_ds3db.vConeOrientation.x,
            This->ds3db_ds3db.vConeOrientation.y,
            This->ds3db_ds3db.vConeOrientation.z);
    *lpvConeOrientation = This->ds3db_ds3db.vConeOrientation;
    return DS_OK;
}

static HRESULT WINAPI IDirectSound3DBufferImpl_GetConeOutsideVolume(IDirectSound3DBuffer *iface,
        LONG *lplConeOutsideVolume)
{
    IDirectSoundBufferImpl *This = impl_from_IDirectSound3DBuffer(iface);

    TRACE("returning: Cone Outside Volume = %d\n", This->ds3db_ds3db.lConeOutsideVolume);
    *lplConeOutsideVolume = This->ds3db_ds3db.lConeOutsideVolume;
    return DS_OK;
}

static HRESULT WINAPI IDirectSound3DBufferImpl_GetMaxDistance(IDirectSound3DBuffer *iface,
        D3DVALUE *lpfMaxDistance)
{
    IDirectSoundBufferImpl *This = impl_from_IDirectSound3DBuffer(iface);

    TRACE("returning: Max Distance = %f\n", This->ds3db_ds3db.flMaxDistance);
    *lpfMaxDistance = This->ds3db_ds3db.flMaxDistance;
    return DS_OK;
}

static HRESULT WINAPI IDirectSound3DBufferImpl_GetMinDistance(IDirectSound3DBuffer *iface,
        D3DVALUE *lpfMinDistance)
{
    IDirectSoundBufferImpl *This = impl_from_IDirectSound3DBuffer(iface);

    TRACE("returning: Min Distance = %f\n", This->ds3db_ds3db.flMinDistance);
    *lpfMinDistance = This->ds3db_ds3db.flMinDistance;
    return DS_OK;
}

static HRESULT WINAPI IDirectSound3DBufferImpl_GetMode(IDirectSound3DBuffer *iface,
        DWORD *lpdwMode)
{
    IDirectSoundBufferImpl *This = impl_from_IDirectSound3DBuffer(iface);

    TRACE("returning: Mode = %d\n", This->ds3db_ds3db.dwMode);
    *lpdwMode = This->ds3db_ds3db.dwMode;
    return DS_OK;
}

static HRESULT WINAPI IDirectSound3DBufferImpl_GetPosition(IDirectSound3DBuffer *iface,
        D3DVECTOR *lpvPosition)
{
    IDirectSoundBufferImpl *This = impl_from_IDirectSound3DBuffer(iface);

    TRACE("returning: Position vector = (%f,%f,%f)\n", This->ds3db_ds3db.vPosition.x,
            This->ds3db_ds3db.vPosition.y, This->ds3db_ds3db.vPosition.z);
    *lpvPosition = This->ds3db_ds3db.vPosition;
    return DS_OK;
}

static HRESULT WINAPI IDirectSound3DBufferImpl_GetVelocity(IDirectSound3DBuffer *iface,
        D3DVECTOR *lpvVelocity)
{
    IDirectSoundBufferImpl *This = impl_from_IDirectSound3DBuffer(iface);

    TRACE("returning: Velocity vector = (%f,%f,%f)\n", This->ds3db_ds3db.vVelocity.x,
            This->ds3db_ds3db.vVelocity.y, This->ds3db_ds3db.vVelocity.z);
    *lpvVelocity = This->ds3db_ds3db.vVelocity;
    return DS_OK;
}

static HRESULT WINAPI IDirectSound3DBufferImpl_SetAllParameters(IDirectSound3DBuffer *iface,
	const DS3DBUFFER *lpcDs3dBuffer, DWORD dwApply)
{
	IDirectSoundBufferImpl *This = impl_from_IDirectSound3DBuffer(iface);
	DWORD status = DSERR_INVALIDPARAM;

	TRACE("(%p,%p,%x)\n",iface,lpcDs3dBuffer,dwApply);

	if (lpcDs3dBuffer == NULL) {
		WARN("invalid parameter: lpcDs3dBuffer == NULL\n");
		return status;
	}

	if (lpcDs3dBuffer->dwSize != sizeof(DS3DBUFFER)) {
		WARN("invalid parameter: lpcDs3dBuffer->dwSize = %d\n", lpcDs3dBuffer->dwSize);
		return status;
	}

	TRACE("setting: all parameters; dwApply = %d\n", dwApply);
	This->ds3db_ds3db = *lpcDs3dBuffer;

	if (dwApply == DS3D_IMMEDIATE)
	{
		DSOUND_Mix3DBuffer(This);
	}
	This->ds3db_need_recalc = TRUE;
	status = DS_OK;

	return status;
}

static HRESULT WINAPI IDirectSound3DBufferImpl_SetConeAngles(IDirectSound3DBuffer *iface,
        DWORD dwInsideConeAngle, DWORD dwOutsideConeAngle, DWORD dwApply)
{
    IDirectSoundBufferImpl *This = impl_from_IDirectSound3DBuffer(iface);

    TRACE("setting: Inside Cone Angle = %d; Outside Cone Angle = %d; dwApply = %d\n",
            dwInsideConeAngle, dwOutsideConeAngle, dwApply);
    This->ds3db_ds3db.dwInsideConeAngle = dwInsideConeAngle;
    This->ds3db_ds3db.dwOutsideConeAngle = dwOutsideConeAngle;
    if (dwApply == DS3D_IMMEDIATE)
        DSOUND_Mix3DBuffer(This);
    This->ds3db_need_recalc = TRUE;
    return DS_OK;
}

static HRESULT WINAPI IDirectSound3DBufferImpl_SetConeOrientation(IDirectSound3DBuffer *iface,
        D3DVALUE x, D3DVALUE y, D3DVALUE z, DWORD dwApply)
{
    IDirectSoundBufferImpl *This = impl_from_IDirectSound3DBuffer(iface);

    TRACE("setting: Cone Orientation vector = (%f,%f,%f); dwApply = %d\n", x, y, z, dwApply);
    This->ds3db_ds3db.vConeOrientation.x = x;
    This->ds3db_ds3db.vConeOrientation.y = y;
    This->ds3db_ds3db.vConeOrientation.z = z;
    if (dwApply == DS3D_IMMEDIATE)
    {
        This->ds3db_need_recalc = FALSE;
        DSOUND_Mix3DBuffer(This);
    }
    This->ds3db_need_recalc = TRUE;
    return DS_OK;
}

static HRESULT WINAPI IDirectSound3DBufferImpl_SetConeOutsideVolume(IDirectSound3DBuffer *iface,
        LONG lConeOutsideVolume, DWORD dwApply)
{
    IDirectSoundBufferImpl *This = impl_from_IDirectSound3DBuffer(iface);

    TRACE("setting: ConeOutsideVolume = %d; dwApply = %d\n", lConeOutsideVolume, dwApply);
    This->ds3db_ds3db.lConeOutsideVolume = lConeOutsideVolume;
    if (dwApply == DS3D_IMMEDIATE)
    {
        This->ds3db_need_recalc = FALSE;
        DSOUND_Mix3DBuffer(This);
    }
    This->ds3db_need_recalc = TRUE;
    return DS_OK;
}

static HRESULT WINAPI IDirectSound3DBufferImpl_SetMaxDistance(IDirectSound3DBuffer *iface,
        D3DVALUE fMaxDistance, DWORD dwApply)
{
    IDirectSoundBufferImpl *This = impl_from_IDirectSound3DBuffer(iface);

    TRACE("setting: MaxDistance = %f; dwApply = %d\n", fMaxDistance, dwApply);
    This->ds3db_ds3db.flMaxDistance = fMaxDistance;
    if (dwApply == DS3D_IMMEDIATE)
    {
        This->ds3db_need_recalc = FALSE;
        DSOUND_Mix3DBuffer(This);
    }
    This->ds3db_need_recalc = TRUE;
    return DS_OK;
}

static HRESULT WINAPI IDirectSound3DBufferImpl_SetMinDistance(IDirectSound3DBuffer *iface,
        D3DVALUE fMinDistance, DWORD dwApply)
{
    IDirectSoundBufferImpl *This = impl_from_IDirectSound3DBuffer(iface);

    TRACE("setting: MinDistance = %f; dwApply = %d\n", fMinDistance, dwApply);
    This->ds3db_ds3db.flMinDistance = fMinDistance;
    if (dwApply == DS3D_IMMEDIATE)
    {
        This->ds3db_need_recalc = FALSE;
        DSOUND_Mix3DBuffer(This);
    }
    This->ds3db_need_recalc = TRUE;
    return DS_OK;
}

static HRESULT WINAPI IDirectSound3DBufferImpl_SetMode(IDirectSound3DBuffer *iface, DWORD dwMode,
        DWORD dwApply)
{
    IDirectSoundBufferImpl *This = impl_from_IDirectSound3DBuffer(iface);

    TRACE("setting: Mode = %d; dwApply = %d\n", dwMode, dwApply);
    This->ds3db_ds3db.dwMode = dwMode;
    if (dwApply == DS3D_IMMEDIATE)
    {
        This->ds3db_need_recalc = FALSE;
        DSOUND_Mix3DBuffer(This);
    }
    This->ds3db_need_recalc = TRUE;
    return DS_OK;
}

static HRESULT WINAPI IDirectSound3DBufferImpl_SetPosition(IDirectSound3DBuffer *iface, D3DVALUE x,
        D3DVALUE y, D3DVALUE z, DWORD dwApply)
{
    IDirectSoundBufferImpl *This = impl_from_IDirectSound3DBuffer(iface);

    TRACE("setting: Position vector = (%f,%f,%f); dwApply = %d\n", x, y, z, dwApply);
    This->ds3db_ds3db.vPosition.x = x;
    This->ds3db_ds3db.vPosition.y = y;
    This->ds3db_ds3db.vPosition.z = z;
    if (dwApply == DS3D_IMMEDIATE)
    {
        This->ds3db_need_recalc = FALSE;
        DSOUND_Mix3DBuffer(This);
    }
    This->ds3db_need_recalc = TRUE;
    return DS_OK;
}

static HRESULT WINAPI IDirectSound3DBufferImpl_SetVelocity(IDirectSound3DBuffer *iface,
        D3DVALUE x, D3DVALUE y, D3DVALUE z, DWORD dwApply)
{
    IDirectSoundBufferImpl *This = impl_from_IDirectSound3DBuffer(iface);

    TRACE("setting: Velocity vector = (%f,%f,%f); dwApply = %d\n", x, y, z, dwApply);
    This->ds3db_ds3db.vVelocity.x = x;
    This->ds3db_ds3db.vVelocity.y = y;
    This->ds3db_ds3db.vVelocity.z = z;
    if (dwApply == DS3D_IMMEDIATE)
    {
        This->ds3db_need_recalc = FALSE;
        DSOUND_Mix3DBuffer(This);
    }
    This->ds3db_need_recalc = TRUE;
    return DS_OK;
}

const IDirectSound3DBufferVtbl ds3dbvt =
{
	/* IUnknown methods */
	IDirectSound3DBufferImpl_QueryInterface,
	IDirectSound3DBufferImpl_AddRef,
	IDirectSound3DBufferImpl_Release,
	/* IDirectSound3DBuffer methods */
	IDirectSound3DBufferImpl_GetAllParameters,
	IDirectSound3DBufferImpl_GetConeAngles,
	IDirectSound3DBufferImpl_GetConeOrientation,
	IDirectSound3DBufferImpl_GetConeOutsideVolume,
	IDirectSound3DBufferImpl_GetMaxDistance,
	IDirectSound3DBufferImpl_GetMinDistance,
	IDirectSound3DBufferImpl_GetMode,
	IDirectSound3DBufferImpl_GetPosition,
	IDirectSound3DBufferImpl_GetVelocity,
	IDirectSound3DBufferImpl_SetAllParameters,
	IDirectSound3DBufferImpl_SetConeAngles,
	IDirectSound3DBufferImpl_SetConeOrientation,
	IDirectSound3DBufferImpl_SetConeOutsideVolume,
	IDirectSound3DBufferImpl_SetMaxDistance,
	IDirectSound3DBufferImpl_SetMinDistance,
	IDirectSound3DBufferImpl_SetMode,
	IDirectSound3DBufferImpl_SetPosition,
	IDirectSound3DBufferImpl_SetVelocity,
};


/*******************************************************************************
 *	      IDirectSound3DListener
 */
static inline IDirectSoundBufferImpl *impl_from_IDirectSound3DListener(IDirectSound3DListener *iface)
{
    return CONTAINING_RECORD(iface, IDirectSoundBufferImpl, IDirectSound3DListener_iface);
}


/* IUnknown methods */
static HRESULT WINAPI IDirectSound3DListenerImpl_QueryInterface(IDirectSound3DListener *iface,
        REFIID riid, void **ppobj)
{
        IDirectSoundBufferImpl *This = impl_from_IDirectSound3DListener(iface);

        TRACE("(%p,%s,%p)\n", iface, debugstr_guid(riid), ppobj);

        return IDirectSoundBuffer_QueryInterface(&This->IDirectSoundBuffer8_iface, riid, ppobj);
}

static ULONG WINAPI IDirectSound3DListenerImpl_AddRef(IDirectSound3DListener *iface)
{
    IDirectSoundBufferImpl *This = impl_from_IDirectSound3DListener(iface);
    ULONG ref = InterlockedIncrement(&This->ref3D);

    TRACE("(%p) ref was %d\n", This, ref - 1);

    if(ref == 1)
        InterlockedIncrement(&This->numIfaces);

    return ref;
}

static ULONG WINAPI IDirectSound3DListenerImpl_Release(IDirectSound3DListener *iface)
{
    IDirectSoundBufferImpl *This = impl_from_IDirectSound3DListener(iface);
    ULONG ref;

    ref = capped_refcount_dec(&This->ref3D);
    if(!ref)
        capped_refcount_dec(&This->numIfaces);

    TRACE("(%p) ref is now %d\n", This, ref);

    return ref;
}

/* IDirectSound3DListener methods */
static HRESULT WINAPI IDirectSound3DListenerImpl_GetAllParameter(IDirectSound3DListener *iface,
        DS3DLISTENER *lpDS3DL)
{
        IDirectSoundBufferImpl *This = impl_from_IDirectSound3DListener(iface);

	TRACE("(%p,%p)\n",This,lpDS3DL);

	if (lpDS3DL == NULL) {
		WARN("invalid parameter: lpDS3DL == NULL\n");
		return DSERR_INVALIDPARAM;
	}

	if (lpDS3DL->dwSize < sizeof(*lpDS3DL)) {
		WARN("invalid parameter: lpDS3DL->dwSize = %d\n",lpDS3DL->dwSize);
		return DSERR_INVALIDPARAM;
	}
	
	TRACE("returning: all parameters\n");
	*lpDS3DL = This->device->ds3dl;
	return DS_OK;
}

static HRESULT WINAPI IDirectSound3DListenerImpl_GetDistanceFactor(IDirectSound3DListener *iface,
        D3DVALUE *lpfDistanceFactor)
{
        IDirectSoundBufferImpl *This = impl_from_IDirectSound3DListener(iface);

	TRACE("returning: Distance Factor = %f\n", This->device->ds3dl.flDistanceFactor);
	*lpfDistanceFactor = This->device->ds3dl.flDistanceFactor;
	return DS_OK;
}

static HRESULT WINAPI IDirectSound3DListenerImpl_GetDopplerFactor(IDirectSound3DListener *iface,
        D3DVALUE *lpfDopplerFactor)
{
        IDirectSoundBufferImpl *This = impl_from_IDirectSound3DListener(iface);

	TRACE("returning: Doppler Factor = %f\n", This->device->ds3dl.flDopplerFactor);
	*lpfDopplerFactor = This->device->ds3dl.flDopplerFactor;
	return DS_OK;
}

static HRESULT WINAPI IDirectSound3DListenerImpl_GetOrientation(IDirectSound3DListener *iface,
        D3DVECTOR *lpvOrientFront, D3DVECTOR *lpvOrientTop)
{
        IDirectSoundBufferImpl *This = impl_from_IDirectSound3DListener(iface);

	TRACE("returning: OrientFront vector = (%f,%f,%f); OrientTop vector = (%f,%f,%f)\n", This->device->ds3dl.vOrientFront.x,
	This->device->ds3dl.vOrientFront.y, This->device->ds3dl.vOrientFront.z, This->device->ds3dl.vOrientTop.x, This->device->ds3dl.vOrientTop.y,
	This->device->ds3dl.vOrientTop.z);
	*lpvOrientFront = This->device->ds3dl.vOrientFront;
	*lpvOrientTop = This->device->ds3dl.vOrientTop;
	return DS_OK;
}

static HRESULT WINAPI IDirectSound3DListenerImpl_GetPosition(IDirectSound3DListener *iface,
        D3DVECTOR *lpvPosition)
{
        IDirectSoundBufferImpl *This = impl_from_IDirectSound3DListener(iface);

	TRACE("returning: Position vector = (%f,%f,%f)\n", This->device->ds3dl.vPosition.x, This->device->ds3dl.vPosition.y, This->device->ds3dl.vPosition.z);
	*lpvPosition = This->device->ds3dl.vPosition;
	return DS_OK;
}

static HRESULT WINAPI IDirectSound3DListenerImpl_GetRolloffFactor(IDirectSound3DListener *iface,
        D3DVALUE *lpfRolloffFactor)
{
        IDirectSoundBufferImpl *This = impl_from_IDirectSound3DListener(iface);

	TRACE("returning: RolloffFactor = %f\n", This->device->ds3dl.flRolloffFactor);
	*lpfRolloffFactor = This->device->ds3dl.flRolloffFactor;
	return DS_OK;
}

static HRESULT WINAPI IDirectSound3DListenerImpl_GetVelocity(IDirectSound3DListener *iface,
        D3DVECTOR *lpvVelocity)
{
        IDirectSoundBufferImpl *This = impl_from_IDirectSound3DListener(iface);

	TRACE("returning: Velocity vector = (%f,%f,%f)\n", This->device->ds3dl.vVelocity.x, This->device->ds3dl.vVelocity.y, This->device->ds3dl.vVelocity.z);
	*lpvVelocity = This->device->ds3dl.vVelocity;
	return DS_OK;
}

static HRESULT WINAPI IDirectSound3DListenerImpl_SetAllParameters(IDirectSound3DListener *iface,
        const DS3DLISTENER *lpcDS3DL, DWORD dwApply)
{
        IDirectSoundBufferImpl *This = impl_from_IDirectSound3DListener(iface);

	TRACE("setting: all parameters; dwApply = %d\n", dwApply);
	This->device->ds3dl = *lpcDS3DL;
	if (dwApply == DS3D_IMMEDIATE)
	{
		This->device->ds3dl_need_recalc = FALSE;
		DSOUND_ChangeListener(This);
	}
	This->device->ds3dl_need_recalc = TRUE;
	return DS_OK;
}

static HRESULT WINAPI IDirectSound3DListenerImpl_SetDistanceFactor(IDirectSound3DListener *iface,
        D3DVALUE fDistanceFactor, DWORD dwApply)
{
        IDirectSoundBufferImpl *This = impl_from_IDirectSound3DListener(iface);

	TRACE("setting: Distance Factor = %f; dwApply = %d\n", fDistanceFactor, dwApply);
	This->device->ds3dl.flDistanceFactor = fDistanceFactor;
	if (dwApply == DS3D_IMMEDIATE)
	{
		This->device->ds3dl_need_recalc = FALSE;
		DSOUND_ChangeListener(This);
	}
	This->device->ds3dl_need_recalc = TRUE;
	return DS_OK;
}

static HRESULT WINAPI IDirectSound3DListenerImpl_SetDopplerFactor(IDirectSound3DListener *iface,
        D3DVALUE fDopplerFactor, DWORD dwApply)
{
        IDirectSoundBufferImpl *This = impl_from_IDirectSound3DListener(iface);

	TRACE("setting: Doppler Factor = %f; dwApply = %d\n", fDopplerFactor, dwApply);
	This->device->ds3dl.flDopplerFactor = fDopplerFactor;
	if (dwApply == DS3D_IMMEDIATE)
	{
		This->device->ds3dl_need_recalc = FALSE;
		DSOUND_ChangeListener(This);
	}
	This->device->ds3dl_need_recalc = TRUE;
	return DS_OK;
}

static HRESULT WINAPI IDirectSound3DListenerImpl_SetOrientation(IDirectSound3DListener *iface,
        D3DVALUE xFront, D3DVALUE yFront, D3DVALUE zFront, D3DVALUE xTop, D3DVALUE yTop,
        D3DVALUE zTop, DWORD dwApply)
{
        IDirectSoundBufferImpl *This = impl_from_IDirectSound3DListener(iface);

	TRACE("setting: Front vector = (%f,%f,%f); Top vector = (%f,%f,%f); dwApply = %d\n",
	xFront, yFront, zFront, xTop, yTop, zTop, dwApply);
	This->device->ds3dl.vOrientFront.x = xFront;
	This->device->ds3dl.vOrientFront.y = yFront;
	This->device->ds3dl.vOrientFront.z = zFront;
	This->device->ds3dl.vOrientTop.x = xTop;
	This->device->ds3dl.vOrientTop.y = yTop;
	This->device->ds3dl.vOrientTop.z = zTop;
	if (dwApply == DS3D_IMMEDIATE)
	{
		This->device->ds3dl_need_recalc = FALSE;
		DSOUND_ChangeListener(This);
	}
	This->device->ds3dl_need_recalc = TRUE;
	return DS_OK;
}

static HRESULT WINAPI IDirectSound3DListenerImpl_SetPosition(IDirectSound3DListener *iface,
        D3DVALUE x, D3DVALUE y, D3DVALUE z, DWORD dwApply)
{
        IDirectSoundBufferImpl *This = impl_from_IDirectSound3DListener(iface);

	TRACE("setting: Position vector = (%f,%f,%f); dwApply = %d\n", x, y, z, dwApply);
	This->device->ds3dl.vPosition.x = x;
	This->device->ds3dl.vPosition.y = y;
	This->device->ds3dl.vPosition.z = z;
	if (dwApply == DS3D_IMMEDIATE)
	{
		This->device->ds3dl_need_recalc = FALSE;
		DSOUND_ChangeListener(This);
	}
	This->device->ds3dl_need_recalc = TRUE;
	return DS_OK;
}

static HRESULT WINAPI IDirectSound3DListenerImpl_SetRolloffFactor(IDirectSound3DListener *iface,
        D3DVALUE fRolloffFactor, DWORD dwApply)
{
        IDirectSoundBufferImpl *This = impl_from_IDirectSound3DListener(iface);

	TRACE("setting: Rolloff Factor = %f; dwApply = %d\n", fRolloffFactor, dwApply);
	This->device->ds3dl.flRolloffFactor = fRolloffFactor;
	if (dwApply == DS3D_IMMEDIATE)
	{
		This->device->ds3dl_need_recalc = FALSE;
		DSOUND_ChangeListener(This);
	}
	This->device->ds3dl_need_recalc = TRUE;
	return DS_OK;
}

static HRESULT WINAPI IDirectSound3DListenerImpl_SetVelocity(IDirectSound3DListener *iface,
        D3DVALUE x, D3DVALUE y, D3DVALUE z, DWORD dwApply)
{
        IDirectSoundBufferImpl *This = impl_from_IDirectSound3DListener(iface);

	TRACE("setting: Velocity vector = (%f,%f,%f); dwApply = %d\n", x, y, z, dwApply);
	This->device->ds3dl.vVelocity.x = x;
	This->device->ds3dl.vVelocity.y = y;
	This->device->ds3dl.vVelocity.z = z;
	if (dwApply == DS3D_IMMEDIATE)
	{
		This->device->ds3dl_need_recalc = FALSE;
		DSOUND_ChangeListener(This);
	}
	This->device->ds3dl_need_recalc = TRUE;
	return DS_OK;
}

static HRESULT WINAPI IDirectSound3DListenerImpl_CommitDeferredSettings(IDirectSound3DListener *iface)
{
        IDirectSoundBufferImpl *This = impl_from_IDirectSound3DListener(iface);

	TRACE("\n");
	DSOUND_ChangeListener(This);
	return DS_OK;
}

const IDirectSound3DListenerVtbl ds3dlvt =
{
	/* IUnknown methods */
	IDirectSound3DListenerImpl_QueryInterface,
	IDirectSound3DListenerImpl_AddRef,
	IDirectSound3DListenerImpl_Release,
	/* IDirectSound3DListener methods */
	IDirectSound3DListenerImpl_GetAllParameter,
	IDirectSound3DListenerImpl_GetDistanceFactor,
	IDirectSound3DListenerImpl_GetDopplerFactor,
	IDirectSound3DListenerImpl_GetOrientation,
	IDirectSound3DListenerImpl_GetPosition,
	IDirectSound3DListenerImpl_GetRolloffFactor,
	IDirectSound3DListenerImpl_GetVelocity,
	IDirectSound3DListenerImpl_SetAllParameters,
	IDirectSound3DListenerImpl_SetDistanceFactor,
	IDirectSound3DListenerImpl_SetDopplerFactor,
	IDirectSound3DListenerImpl_SetOrientation,
	IDirectSound3DListenerImpl_SetPosition,
	IDirectSound3DListenerImpl_SetRolloffFactor,
	IDirectSound3DListenerImpl_SetVelocity,
	IDirectSound3DListenerImpl_CommitDeferredSettings,
};
