现在的位置: 首页 > 综合 > 正文

DirectSound开发

2018年02月08日 ⁄ 综合 ⁄ 共 5588字 ⁄ 字号 评论关闭

获取语音设备并创建Interface

    DirectSound开发中常常需要获取系统当前可用的语音设备列表,在SDK Samples中最先介绍了它。DirectX将它封装成函数DirectSoundEnumerate/DirectSoundCaptureEnumerate,我们所要做的只是以DSEnumCallback作为接口模板,添加一个自定义的回调函数,然后简单的调用一下即可。
    获取设备列表后,创建DirectSound环境使用函数DirectSoundCreate8/DirectSoundCaptureCreate8。

 

下面是示例源代码:

/*----------------------------------------------------------------------------------
* File: EnumDevices.cpp
*
* Desc: This sample shows how to enumerate DirectSound sound and capture devices.
*
* Copyright (c) Microsoft Corp. All rights reserved.
*
*
* DirectSoundEnumerate
* DirectSoundCaptureEnumerate
* DirectSoundCreate8
* DirectSoundCaptureCreate8
* DXTRACE_ERR_MSGBOX : 在DEBUG模式下用来显示错误信息
* DSEnumCallback     : 用来枚举设备的回调函数
*-----------------------------------------------------------------------------------*/

#include <windows.h>
#include <dxerr9.h>
#include <dsound.h>
#include "resource.h"

#pragma comment( lib,"Dsound.lib" )
#ifdef _DEBUG
    #pragma comment( lib,"dxerr9.lib" )
#endif

INT_PTR CALLBACK MainDlgProc( HWND,UINT,WPARAM,LPARAM );
INT_PTR CALLBACK DSoundEnumCallback( GUID*,LPSTR, LPSTR,VOID* );
HRESULT OnInitDialog( HWND );
HRESULT InitDirectSound( HWND );
HRESULT FreeDirectSound();

#define SAFE_DELETE(p) { if(p) { delete (p);     (p)=NULL; } }
#define SAFE_RELEASE(p) { if(p) { (p)->Release(); (p)=NULL; } }

LPDIRECTSOUND8        g_pDS        = NULL; //用来存放IDirectSound8 interface地址
LPDIRECTSOUNDCAPTURE8 g_pDSCapture = NULL; //用来存放IDirectSoundCapture8 interface地址

int WINAPI WinMain (HINSTANCE hInstance, HINSTANCE hPrevInstance, PSTR pszCmdLine, int iCmdShow)
{
    //初始化COM, 可参考DirectX开发文档中创建COM对象部分(Creating a COM Object)
    CoInitialize( NULL );

    // Display the main dialog box.
    DialogBox( hInstance, MAKEINTRESOURCE(IDD_MAIN), NULL,
  

MainDlgProc );

    //释放COM
    CoUninitialize();

    return TRUE;
}

//主窗口回调函数
INT_PTR CALLBACK MainDlgProc( HWND hDlg, UINT msg, WPARAM wParam, LPARAM lParam )
{
    HRESULT hr;

    switch( msg )
    {
        case WM_INITDIALOG:
            if( FAILED( hr = OnInitDialog( hDlg ) ) )
            {
                DXTRACE_ERR_MSGBOX( TEXT("OnInitDialog"), hr );
                MessageBox( hDlg, "枚举DirectSound设备错误,程序退出.", "EnumDevices", MB_OK | MB_ICONERROR );
                EndDialog( hDlg, IDABORT );
            }
            break;

        case WM_COMMAND:
            switch( LOWORD(wParam) )
            {
                case IDC_BUTTON_CREATE:
                    //尝试创建
                    if( SUCCEEDED( hr = InitDirectSound( hDlg ) ) )
                        MessageBox( hDlg, TEXT("创建DirectSound interface成功."), TEXT("EnumDevices"), MB_OK );
                    else
      &nbs

p;              {
                        DXTRACE_ERR_MSGBOX( TEXT("InitDirectSound"), hr );
                        MessageBox( hDlg, TEXT("创建DirectSound interface失败."), TEXT("EnumDevices"), MB_OK | MB_ICONERROR );
                    }
                    break;

                case IDOK:
                    EndDialog( hDlg, IDCANCEL );
                    break;

                default:
                    return FALSE;
            }
            break;

        case WM_DESTROY:
            FreeDirectSound(); //不要忘记释放设备
            break;

        default:
            return FALSE;
    }
    return TRUE;
}

//初始化窗体
HRESULT OnInitDialog( HWND hDlg )
{
    HRESULT hr;

    //枚举sound devices并添加到组合框中
    HWND hSoundDeviceCombo = GetDlgItem( hDlg,

IDC_COMBO_SOUND_DEVICE );
    if( FAILED( hr = DirectSoundEnumerate( (LPDSENUMCALLBACK)DSoundEnumCallback, (VOID*)hSoundDeviceCombo ) ) )
        return DXTRACE_ERR_MSGBOX( TEXT("DirectSoundEnumerate"), hr );

    //枚举capture devices并添加到组合框中
    HWND hCaptureDeviceCombo = GetDlgItem( hDlg, IDC_COMBO_CAPTURE_DEVICE );
    if( FAILED( hr = DirectSoundCaptureEnumerate( (LPDSENUMCALLBACK)DSoundEnumCallback, (VOID*)hCaptureDeviceCombo ) ) )
        return DXTRACE_ERR_MSGBOX( TEXT("DirectSoundCaptureEnumerate"), hr );

    //选中组合框中的第一个设备
    SendMessage( hSoundDeviceCombo,   CB_SETCURSEL, 0, 0 );
    SendMessage( hCaptureDeviceCombo, CB_SETCURSEL, 0, 0 );

    return S_OK;
}

//供枚举函数使用的回调函数
INT_PTR CALLBACK DSoundEnumCallback( GUID* pGUID, LPSTR strDesc, LPSTR strDrvName, VOID* pContext )
{
    //注意定义为静态变量
    static GUID AudioDriverGUIDs[20]; //预留20个设备的存储空间
    static DWORD dwAudioDriverIndex = 0;

    GUID* pTemp = NULL;

    if( pGUID )
    {
        if( dwAudioDriverIndex >= 20 )
            return TRUE;

        pTemp = &AudioDriverGUIDs[dwAudioDriverIndex++];
        memcpy( pTemp, pGUID, sizeof(GUID) );
    }

    HWND hSoundDeviceCombo = (HWND)pContext;

    //把设备名称添加到组合框中
    SendMessage( hSoundDeviceCombo, CB_ADDSTRING, 0, (LPARAM)(LPCTSTR)strDesc );

    //获取当前设备名称在组合框中的索引值
    int nIndex = (int)SendMessage( hSoundDeviceCombo, CB_FINDSTRING, 0, (LPARAM) (LPCTSTR) strDesc );

    //将存储在AudioDriverGUIDs设备数组中的GUID保存到对应项中
    SendMessage( hSoundDeviceCombo, CB_SETITEMDATA, nIndex, (LPARAM) pTemp );
return TRUE;
}

//创建IDirectSound
HRESULT InitDirectSound( HWND hDlg )
{
    HRESULT hr;

    //首先释放当前可能使用的DirectSound对象
    FreeDirectSound();

    HWND hSoundDeviceCombo   = GetDlgItem( hDlg, IDC_COMBO_SOUND_DEVICE );
    HWND hCaptureDeviceCombo = GetDlgItem( hDlg, IDC_COMBO_CAPTURE_DEVICE );

    int nSoundIndex   = (int)SendMessage( hSoundDeviceCombo,   CB_GETCURSEL, 0, 0 );
    int nCaptureIndex = (int)SendMessage( hCaptureDeviceCombo, CB_GETCURSEL, 0, 0 );

    //获取当前选择项所对应的GUID数据
    GUID* pSoundGUID   = (GUID*) SendMessage( hSoundDeviceCombo, CB_GETITEMDATA, nSoundIndex, 0 );
    GUID* pCaptureGUID = (GUID*) SendMessage( hCaptureDeviceCombo, CB_GETITEMDATA, nCaptureIndex, 0 );

    //使用所选设备创建IDirectSound
    if( FAILED( hr = DirectSoundCreate8( pSoundGUID, &g_pDS, NULL ) ) )
        return DXTRACE_ERR_MSGBOX( TEXT("DirectSoundCreate"), hr );

    //作为一个示例,我们尝试创建后马上释放掉.
    SAFE_RELEASE( g_pDS );

    //使用所选设备创建IDirectSoundCapture
    if( FAILED( hr = DirectSoundCaptureCreate8( pCaptureGUID, &g_pDSCapture, NULL ) ) )
        return DXTRACE_ERR_MSGBOX( TEXT("DirectSoundCaptureCreate"), hr );

    //释放
    SAFE_RELEASE( g_pDSCapture );

    return S_OK;
}

//释放对象
HRESULT FreeDirectSound()
{
    SAFE_RELEASE( g_pDSCapture );
    SAFE_RELEASE( g_pDS );

    return S_OK;

}

 

 

更多技术文章请参看施昌权的个人网站: http://www.joyvc.cn

 

 

抱歉!评论已关闭.