⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 sound.c

📁 使用tapi实现的用语音modem进行接电话并播放wav文件的程序
💻 C
字号:
// MESSAGE.C
#include "comdial.h"

/* quick and dirty RIFF chunk */
BYTE ab_riffchunk[] = {'R','I','F','F',  0,0,0,0, 'W','A','V','E'};
/* quick and dirty format chunk tag */
BYTE ab_formatchunktag[] = {'f','m','t',' ',  0,0,0,0};
/* quick and dirty data chunk header */
BYTE ab_datachunktag[] = {'d','a','t','a',  0,0,0,0};

/* message headers */
WAVEHDR inMessageHeader = {NULL, 0, 0, 0, 0 /* no flags */, 0 /* no loops */,  
                           NULL, 0};

/* handle to main window */
extern HWND hTTYWnd;

/* format of in-message */
WAVEFORMATEX messageFormat = {WAVE_FORMAT_PCM, 1, 8000, 8000, 1, 16};

/****************************************************************************
    FUNCTION: recordMessage
    PURPOSE:  begin recording voice message
****************************************************************************/
/* record the voice message  - 60s max */
HWAVEIN recordMessage (DWORD dw_devid)
{
HWAVEIN h_wavein; 
LONG lrc;
DWORD dw_60sbufsz = 60L * (LONG)messageFormat.nSamplesPerSec * 
                            (LONG)messageFormat.wBitsPerSample/8L;
HANDLE hData;


 /* check support for format */
 if (lrc=waveInOpen( NULL, (WORD) dw_devid, &messageFormat,
                 (DWORD)hTTYWnd, 0, WAVE_FORMAT_QUERY)) {
     MessageBox (NULL, "Unsupported format.", "", MB_OK);
     return 0;
 }

 /* open recorder. */
 if (lrc=waveInOpen( &h_wavein, (WORD) dw_devid, &messageFormat,
                 (DWORD)hTTYWnd, 0, CALLBACK_WINDOW)) {
     MessageBox (NULL, "Error opening wave record device.", "", MB_OK);
     return 0;
 }

 /* allocate 60s message buffer */
 hData = GlobalAlloc (GPTR, dw_60sbufsz);
 if ((inMessageHeader.lpData = GlobalLock(hData)) == NULL) {
     MessageBox (NULL, "Not enough memory.", "", MB_OK);
     return 0;
 }
 
 inMessageHeader.dwBufferLength = dw_60sbufsz;
 if (lrc=waveInPrepareHeader(h_wavein, &inMessageHeader, sizeof(WAVEHDR))) {
	 GlobalFree (hData);
     MessageBox (NULL, "Error preparing message header.", "", MB_OK);
     return 0;
 }

 /* pass down a 60s buffer to record into */
 if (waveInAddBuffer (h_wavein, &inMessageHeader, sizeof(WAVEHDR))) {
	 GlobalFree (hData);
     MessageBox (NULL, "Error adding buffer.", "", MB_OK);
     return 0;
 }

 inMessageHeader.dwUser = (DWORD) hData;

 waveInStart (h_wavein); /* start recording */
 return h_wavein;
    
} /* end function (record message) */
/****************************************************************************
    FUNCTION: saveMessage
    PURPOSE:  save a recorded voice message
****************************************************************************/
/* save the message after the caller hangs up, or after 60s */
int saveMessage (char *name, LPWAVEHDR hdr)
{
HANDLE h_file;
DWORD n_written;

    h_file = CreateFile (name, GENERIC_READ|GENERIC_WRITE, 0, 
    					NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL,NULL);
    if (h_file == NULL) {
        MessageBox (NULL, "Error opening file.", "", MB_OK);
        return -1;
    }
  
    /* write out the RIFF chunk */
    *((DWORD *)&ab_riffchunk[4])=4 + sizeof(ab_formatchunktag) + 
                                 sizeof(messageFormat) + sizeof(ab_datachunktag) + 
                                 hdr->dwBytesRecorded;
    WriteFile (h_file, ab_riffchunk, sizeof(ab_riffchunk), &n_written, NULL);
    *((DWORD *)&ab_formatchunktag[4]) = sizeof(messageFormat); /* write  tag */
    WriteFile (h_file, ab_formatchunktag, sizeof(ab_formatchunktag), &n_written, NULL);

    /* write out the canned format header */
    WriteFile (h_file, &messageFormat, sizeof(messageFormat), &n_written, NULL);

    /* write out the data chunk tag */
    *((DWORD *)&ab_datachunktag[4]) = hdr->dwBytesRecorded;
    WriteFile (h_file, ab_datachunktag, sizeof(ab_datachunktag), &n_written, NULL);

    /* write out the data chunk */
    WriteFile (h_file, hdr->lpData, hdr->dwBytesRecorded, &n_written, NULL);
    CloseHandle (h_file); /* close message file */
    return 0;

} /* end function (save message) */

/****************************************************************************
    FUNCTION: 
    PURPOSE:  
****************************************************************************/
/* begin playing out the message */
HWAVEOUT playSound (DWORD dw_devid, char *szWaveFile, HWND hWnd)
{
HWAVEOUT        hWave;
HMMIO            hmmio;
MMCKINFO        mmckinfoParent;
MMCKINFO        mmckinfoSubchunk;
DWORD            dwFmtSize;
DWORD            dwDataSize;
HPSTR            lpWaveData;
WAVEHDR *    lpWaveHdr;
WAVEFORMATEX *lpWaveFormat;
    
    /* Open wave file */
    hmmio = mmioOpen(szWaveFile, NULL, MMIO_READ | MMIO_ALLOCBUF);
    if(!hmmio)
    {
        return 0;
    }

    /* Locate a 'RIFF' chunk with a 'WAVE' form type */
    mmckinfoParent.fccType = mmioFOURCC('W', 'A', 'V', 'E');
    if (mmioDescend(hmmio, (LPMMCKINFO) &mmckinfoParent, NULL, MMIO_FINDRIFF))
    {
        mmioClose(hmmio, 0);
        return 0;
    }
    
    /* Find the format chunk */
    mmckinfoSubchunk.ckid = mmioFOURCC('f', 'm', 't', ' ');
    if (mmioDescend(hmmio, &mmckinfoSubchunk, &mmckinfoParent, MMIO_FINDCHUNK))
    {
        mmioClose(hmmio, 0);
        return 0;
    }

    /* Get the size of the format chunk, allocate memory for it */
    dwFmtSize = mmckinfoSubchunk.cksize;
    lpWaveFormat = (WAVEFORMATEX *) calloc (1, dwFmtSize);
    if (!lpWaveFormat)
    {
        mmioClose(hmmio, 0);
        return 0;
    }

    /* Read the format chunk */
    if (mmioRead(hmmio, (LPSTR) lpWaveFormat, dwFmtSize) != (LONG) dwFmtSize)
    {
        free( lpWaveFormat );
        mmioClose(hmmio, 0);
        return 0;
    }
    
    /* Ascend out of the format subchunk */
    mmioAscend(hmmio, &mmckinfoSubchunk, 0);
    
    /* Find the data subchunk */
    mmckinfoSubchunk.ckid = mmioFOURCC('d', 'a', 't', 'a');
    if (mmioDescend(hmmio, &mmckinfoSubchunk, &mmckinfoParent, MMIO_FINDCHUNK))
    {
        free( lpWaveFormat );
        mmioClose(hmmio, 0);
        return 0;
    }
  

  
    /* Get the size of the data subchunk */
    dwDataSize = mmckinfoSubchunk.cksize;
    if (dwDataSize == 0L)
    {
        free( lpWaveFormat );
        mmioClose(hmmio, 0);
        return 0;
    }
        
    /* Allocate and lock memory for the waveform data. */
    lpWaveData = (LPSTR) calloc (1, dwDataSize );
    if (!lpWaveData)
    {
        free( lpWaveFormat );
        mmioClose(hmmio, 0);
        return 0;
    }

    /* Read the waveform data subchunk */
    if(mmioRead(hmmio, (HPSTR) lpWaveData, dwDataSize) != (LONG) dwDataSize)
    {
        free(lpWaveFormat);
        free(lpWaveData);
        mmioClose(hmmio, 0);
        return 0;
    }

    /* We're done with the file, close it */
    mmioClose(hmmio, 0);

    /* Allocate a waveform data header */
    lpWaveHdr = (WAVEHDR *) calloc (1,(DWORD)sizeof(WAVEHDR));
    if (!lpWaveHdr)
    {
        free(lpWaveData);
        free(lpWaveFormat);
        return 0;
    }

    /* Set up WAVEHDR structure and prepare it to be written to wave device */
    lpWaveHdr->lpData = lpWaveData;
    lpWaveHdr->dwBufferLength = dwDataSize;
    lpWaveHdr->dwFlags = 0L;
    lpWaveHdr->dwLoops = 0L;
    lpWaveHdr->dwUser  = 0L;

    /* make sure wave device can play our format */
    if (waveOutOpen((LPHWAVEOUT)NULL,
                    (WORD)dw_devid,
                    (LPWAVEFORMATEX)lpWaveFormat, 
                    0L, 0L, WAVE_FORMAT_QUERY)) {
        free( lpWaveFormat );
        free(lpWaveData);
        free(lpWaveHdr);
        MessageBox (NULL, "Unsupported wave format.", "", MB_OK);
        return 0;
    }

    /* open the wave device corresponding to the line */
    if (waveOutOpen (    &hWave, 
                        (WORD)dw_devid, 
                        (LPWAVEFORMATEX)lpWaveFormat, 
                        (DWORD)hWnd, 
                        0L, 
                        CALLBACK_WINDOW))
    {
        free( lpWaveFormat );
        free(lpWaveData);
        free(lpWaveHdr);
        MessageBox (NULL, "Error opening wave device.", "", MB_OK);
        return 0;
    }
  
    free( lpWaveFormat );

     /* prepare the message header for playing */
    if (waveOutPrepareHeader (hWave, lpWaveHdr, sizeof(WAVEHDR))) {
       MessageBox (NULL, "Error preparing message header.", "", MB_OK);
        free(lpWaveData);
        free(lpWaveHdr);
        return 0;
    }

    /* play the message right from the data segment;  set the play message flag */
    if (waveOutWrite (hWave, lpWaveHdr, sizeof (WAVEHDR))) {
        MessageBox (NULL, "Error writing wave message.", "", MB_OK);
        free(lpWaveData);
        free(lpWaveHdr);
        return 0;
    }


    return hWave;

} /* end function (play message) */

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -