windows-nt/Source/XPSP1/NT/multimedia/directx/dplay/dvoice/dxvoice/dvsndt.h

148 lines
6.1 KiB
C
Raw Permalink Normal View History

2020-09-26 03:20:57 -05:00
/*==========================================================================
*
* Copyright (C) 1999 Microsoft Corporation. All Rights Reserved.
*
* File: dvsndt.h
* Content: definition of CSoundTarget class
*
* History:
* Date By Reason
* ==== == ======
* 09/02/99 rodtoll Created
* 09/08/99 rodtoll Updated to provide lockup detection
* 09/14/99 rodtoll Added WriteAheadSilence()
* 09/20/99 rodtoll Added handlers for buffer loss
* 11/12/99 rodtoll Updated to use new abstractions for playback (allows use
* of waveOut with this class).
* 01/24/2000 rodtoll Fix: Bug #129427 - Destroying transport before calling Delete3DSound
* 01/27/2000 rodtoll Bug #129934 - Update SoundTargets to take DSBUFFERDESC
* 02/17/2000 rodtoll Bug #133691 - Choppy audio - queue was not adapting
* Added instrumentation
* 04/17/2000 rodtoll Fix: Bug #32215 - Session Lost after resuming from hibernation
* 06/21/2000 rodtoll Fix: Bug #35767 - Must implement ability for dsound effects on voice buffers
* Added new constructor/init that takes pre-built buffers
* 07/09/2000 rodtoll Added signature bytes
*
***************************************************************************/
#ifndef __DVSNDT_H
#define __DVSNDT_H
// CSoundTarget
//
// This class represents a single mixer target within the DirectPlayClient system. Normally there
// is only a single mixer target ("main") for all incoming audio. However, using the CreateUserBuffer and
// DeleteUserBuffer APIs the developer can specify that they wish to seperate a group or a player
// from the main mixer target. In this manner they can control the 3d spatialization of the group/player's
// incoming audio stream.
//
// This class handles all the details related to a mixer target. It encapsulates the mixing of single
// or multiple source audio frames and then commiting them to the corresponding directsound buffer. It also
// handles timing errors in the directsoundbuffer.
//
// For example, if the directsoundbuffer stops running, it will attempt to reset the buffer.
//
// If the directsoundbuffer slows down (because of high CPU), it moves the read pointer forward. In short
// it ensures that there is always 1 or 2 frames of mixed audio present in the buffer in advance of the
// read pointer.
//
// In addition the class provides reference counting to prevent premature deletion of the class. If you
// wish to take a reference to the class, call AddRef and you MUST then call Release when you are done.
//
// Do not destroy the object directly. When the last reference to the object is released the object will
// destroy itself.
//
// This class is not multithread safe (except for AddRef and Release). Only one thread should be
// accessing it.
//
#define VSIG_SOUNDTARGET 'TNSV'
#define VSIG_SOUNDTARGET_FREE 'TNS_'
volatile struct CSoundTarget
{
public:
CSoundTarget( DVID dvidTarget, CAudioPlaybackDevice *lpads, LPDSBUFFERDESC lpdsBufferDesc, DWORD dwPriority, DWORD dwFlags, DWORD dwFrameSize );
CSoundTarget( DVID dvidTarget, CAudioPlaybackDevice *lpads, CAudioPlaybackBuffer *lpdsBuffer, LPDSBUFFERDESC lpdsBufferDesc, DWORD dwPriority, DWORD dwFlags, DWORD dwFrameSize );
CSoundTarget( DVID dvidTarget, CAudioPlaybackDevice *lpads, LPDIRECTSOUNDBUFFER lpdsBuffer, BOOL fEightBit, DWORD dwPriority, DWORD dwFlags, DWORD dwFrameSize );
~CSoundTarget();
HRESULT StartMix();
HRESULT MixInSingle( LPBYTE lpbBuffer );
HRESULT MixIn( LPBYTE lpbBuffer );
HRESULT Commit();
inline HRESULT GetInitResult() { return m_hrInitResult; };
LPDIRECTSOUND3DBUFFER Get3DBuffer();
inline CAudioPlaybackBuffer *GetBuffer() { return m_lpAudioPlaybackBuffer; };
CSoundTarget *m_lpstNext; // Next entry in the list
inline DVID GetTarget() { return m_dvidTarget; };
inline LONG GetRefCount() { return m_lRefCount; };
LONG AddRef();
LONG Release();
void GetStats( PlaybackStats *statPlayback );
HRESULT GetCurrentLead( PDWORD pdwLead );
protected:
HRESULT Initialize( DVID dvidTarget, CAudioPlaybackBuffer *lpdsBuffer, BOOL fEightBit, DWORD dwPriority, DWORD dwFlags, DWORD dwFrameSize );
HRESULT RestoreLostBuffer();
HRESULT AdjustWritePtr();
HRESULT WriteAheadSilence();
void Stats_Init();
void Stats_Begin();
void Stats_End();
public:
DWORD m_dwSignature;
protected:
CAudioPlaybackBuffer *m_lpAudioPlaybackBuffer;
LPDIRECTSOUND3DBUFFER m_lpds3dBuffer; // 3d buffer interface for this sound target
DWORD m_dwNextWritePos; // Next byte position in the directsound buffer we'll
// be writing to.
DWORD m_dwBufferSize; // Size of directsound buffer in bytes
BOOL m_bGroup; // Does this buffer represent a group?
LPLONG m_lpMixBuffer; // High resolution mixing buffer
BOOL m_bCommited; // Has the data in the latest mix been commited to the buffer
BOOL m_fEightBit; // Is the buffer 8-bit?
HRESULT m_hrInitResult; // Contains result of the initializatio of this object
DWORD m_dwMixSize; // # of samples per frame
DWORD m_dwFrameSize; // Size of a frame in bytes
BOOL m_fMixed; // Set to TRUE as soon as a single source has been mixed
// Set to FALSE whenever the mix is commited.
LONG m_lRefCount; // Reference count on the object
DWORD m_dwLastWritePos; // Byte position that the last write occured at.
DWORD m_dwNumResets; // # of times buffer has been reset
BOOL m_fLastFramePushed; // Did the last frame push the read pointer forward?
DWORD m_dwNumSinceMove; // How many frames since no movement was detected?
DWORD m_dwLastWriteTime; // GetTickCount() at last call to AdjustWritePtr
BOOL m_fIgnoreFrame; // This frame will cross the boundary of where the write pointer is.
// Do NOT write to the buffer
DWORD m_dwWritePos;
DNCRITICAL_SECTION m_csGuard; // Guard for reference counts
DWORD m_dwPlayFlags;
DWORD m_dwPriority;
DVID m_dvidTarget; // DVID this buffer is for.
// DVID_REMAINING for the global one
PlaybackStats m_statPlay; // Playback Statistics
LPVOID m_lpDummy;
};
#endif