www.pudn.com > VOIP_server_client.rar > peer1_sound_play.cpp


#include "peer1_sound_play.h" 
#include "dsound.h" 
#include "peer1_main.h" 
#include "peer1_resource.h" 
#include "peer1_sound_cap.h" 
 
// TYPE Defines================================================================= 
typedef unsigned short USHORT; 
typedef unsigned short WORD; 
typedef unsigned char  UCHAR; 
typedef unsigned char  BYTE; 
 
// Global Variables ============================================================ 
LPDIRECTSOUND		lpds;           // directsound interface pointer 
DSBUFFERDESC		dsbd;           // directsound description 
DSCAPS			dscaps;         // directsound caps 
HRESULT			dsresult;       // general directsound result 
DSBCAPS                 dsbcaps;        // directsound buffer caps 
WAVEFORMATEX            pcmwf;          // generic waveformat structure 
LPDIRECTSOUNDBUFFER     sound_buffer; 
UCHAR                   *tmp_snd_buffer; // Temp buffer for fill data 
WAVEFORMATEX            wfmtx;           // wave format structure 
DSBPOSITIONNOTIFY*      aPosNotify     = NULL; 
LPDIRECTSOUNDNOTIFY     pDSNotify      = NULL; 
HANDLE                  g_hNotificationEvent_play    = NULL; 
 
 
// External Global Variables =================================================== 
extern HWND g_hwndDlg; 
struct play_buffer{ 
                   char play_data[PLAY_LENGTH]; 
                   }; 
extern struct play_buffer my_play_buffer[PLAY_BUF_LEN]; 
 
 
//------------------------------------------------------------------------------ 
//**************************** Pr ********************************************** 
//------------------------------------------------------------------------------ 
void pr(HWND hwndDlg, char *st) 
{ 
   
  Display(st); 
} 
 
//------------------------------------------------------------------------------ 
//*************************** Play Sound Init ********************************** 
//------------------------------------------------------------------------------ 
int Play_Sound_Init(HWND hwndDlg,HWND main_window_handle) 
{ 
  // all the initialization 
  tmp_snd_buffer = (UCHAR *)malloc(PLAY_LENGTH); 
  ZeroMemory( my_play_buffer, sizeof(struct play_buffer)*PLAY_BUF_LEN); 
  g_hNotificationEvent_play = CreateEvent( NULL, FALSE, FALSE, NULL ); 
 
  // create a directsound object 
  if (DirectSoundCreate(NULL, &lpds, NULL)!=DS_OK ) 
        { 
        pr(hwndDlg,"DS Creation failed!\r\n"); 
	return(0); 
        } 
  // set cooperation level 
  if (lpds->SetCooperativeLevel(main_window_handle,DSSCL_NORMAL)!=DS_OK) 
	return(0); 
 
  memset(&pcmwf, 0, sizeof(WAVEFORMATEX)); 
  pcmwf.wFormatTag	  = WAVE_FORMAT_PCM;  // pulse code modulation 
  pcmwf.nChannels	  = 1;                // mono 
  pcmwf.nSamplesPerSec    = SAMPLE_RATE;             //  11205 or 8000 
  pcmwf.nBlockAlign	  = 1; 
  pcmwf.nAvgBytesPerSec   = pcmwf.nSamplesPerSec * pcmwf.nBlockAlign; 
  pcmwf.wBitsPerSample    = 8; 
  pcmwf.cbSize		  = 0; 
 
  // prepare to create sounds buffer 
  dsbd.dwSize		= sizeof(DSBUFFERDESC); 
  dsbd.dwFlags		= DSBCAPS_GLOBALFOCUS | DSBCAPS_CTRLPOSITIONNOTIFY | 
                          DSBCAPS_GETCURRENTPOSITION2 ; 
  dsbd.dwBufferBytes	= PLAY_LENGTH * play_buffer_size; 
  dsbd.lpwfxFormat	= &pcmwf; 
 
  // create the sound buffer 
  if (FAILED(lpds->CreateSoundBuffer(&dsbd,&sound_buffer,NULL))) 
   { 
   // release memory 
    free(tmp_snd_buffer); 
    pr(hwndDlg, "CreateSoundBuffer failed.\r\n"); 
   // return error 
   return 0; 
   } // end if 
 
   if( FAILED( sound_buffer->QueryInterface( IID_IDirectSoundNotify, 
                                                (VOID**)&pDSNotify ) ) ) 
    { 
        free( aPosNotify ); 
        return 0; 
    } 
 
    aPosNotify = new DSBPOSITIONNOTIFY[play_buffer_size]; 
    if( aPosNotify == NULL ) 
     pr(hwndDlg,"aPosNotify == NULL!\r\n"); 
 
    for( DWORD i = 0; i < play_buffer_size; i++ ) 
    { 
        aPosNotify[i].dwOffset     = (PLAY_LENGTH * i) + PLAY_LENGTH-1; 
        aPosNotify[i].hEventNotify = g_hNotificationEvent_play;              
    } 
 
    if( FAILED( pDSNotify->SetNotificationPositions( play_buffer_size, aPosNotify ) ) ) 
    { 
        free( pDSNotify ); 
        free( aPosNotify ); 
        pr(hwndDlg,"SetNotificationPositions failed!\r\n"); 
        return 0; 
    } 
 
// return success 
return(1); 
} 
//------------------------------------------------------------------------------ 
//************************** Play_Sound **************************************** 
//------------------------------------------------------------------------------ 
int Play_Sound(HWND hwndDlg) 
{ 
   sound_buffer->Restore(); 
   sound_buffer->Play(0,0,DSBPLAY_LOOPING); 
   return (1); 
} 
//------------------------------------------------------------------------------ 
//*********************** Sound_Shutdown *************************************** 
//------------------------------------------------------------------------------ 
 
int Sound_Shutdown(HWND hwndDlg) 
{ 
// release the sound buffer 
if (sound_buffer) 
  sound_buffer->Release(); 
 
// release the directsoundobject 
if (lpds!=NULL) 
   lpds->Release(); 
 
// return success 
return(1); 
} 
//------------------------------------------------------------------------------ 
//**************************** Copy Play Data ********************************** 
//------------------------------------------------------------------------------ 
int Copy_Play_Data(char *play_buffer_p, HWND hwndDlg) 
{ 
  memset( tmp_snd_buffer, 0, PLAY_LENGTH); 
  if(FAILED(memcpy( tmp_snd_buffer, play_buffer_p, PLAY_LENGTH))) 
     { 
      pr(hwndDlg,"Error copying buffer.\r\n\r\n" ); 
      return (-1); 
     } 
  return (1); 
} 
 
//------------------------------------------------------------------------------ 
//******************* fill data ************************************************ 
//------------------------------------------------------------------------------ 
int fill_data(HWND hwndDlg, DWORD dwOffset, DWORD dwBytes) 
{ 
UCHAR      *audio_ptr_1=NULL, // data ptr to first write buffer 
	   *audio_ptr_2=NULL; // data ptr to second write buffer 
DWORD      audio_length_1=0,  // length of first write buffer 
	   audio_length_2=0;  // length of second write buffer 
 
// copy data into sound buffer 
if (FAILED(sound_buffer->Lock(dwOffset,dwBytes,(void **) &audio_ptr_1, 
                                                      &audio_length_1, 
                                                (void **)&audio_ptr_2, 
                                                      &audio_length_2, 
                                              DSBLOCK_FROMWRITECURSOR))) 
    return(0); 
 
// copy first section of circular buffer 
memcpy(audio_ptr_1, tmp_snd_buffer, audio_length_1); 
 
// copy last section of circular buffer 
memcpy(audio_ptr_2, (tmp_snd_buffer+audio_length_1),audio_length_2); 
 
// unlock the buffer 
if (FAILED(sound_buffer->Unlock(audio_ptr_1, 
                              audio_length_1, 
                                 audio_ptr_2, 
                              audio_length_2))) 
        return(0); 
 
// release the temp buffer 
if(tmp_snd_buffer) 
free(tmp_snd_buffer); 
 
return (1); 
 
} // end DSound_Load_WAV 
 
//------------------------------------------------------------------------------ 
//*************************** Sound_stop *************************************** 
//------------------------------------------------------------------------------ 
int Sound_stop(HWND hwndDlg) 
{ 
  sound_buffer->Stop(); 
  return (1); 
} 
 
//------------------------------------------------------------------------------ 
//************************* Get Current Position (not used) ******************** 
//------------------------------------------------------------------------------ 
void Get_Current_Position(HWND hwndDlg) 
{ 
      DWORD play_pos, write_pos; 
      sound_buffer->GetCurrentPosition(&play_pos, &write_pos); 
 
      char st10[40]; 
      sprintf(st10, "Play_pos = %d\r\n ->Write_pos = %d\r\n",play_pos, write_pos); 
      pr(hwndDlg, st10); 
}