Что нового

Как изменить iAudioEndPoint

VadimKHL

Новичок
Сообщения
155
Репутация
0
Добрый вечер!
В интернете много примеров, как управлять громкостью и выводить уровень громкости при помощи интерфейса iAudioEndPointVolume. Все работает отлично.
Не могу разобраться, как можно выбрать другую звуковую конечную точку для этого интерфейса, допустим микрофон/линейный вход/твтюнер?
Приведенный ниже код работает непосредственно для конечной точки вывода звука по умолчанию:
Код:
; ===============================================================================================================================
; ===============================================================================================================================
; ===============================================================================================================================
; =========================================== Интерфейсы EndPointVolume =========================================================
; ===============================================================================================================================
; ===============================================================================================================================
; ===============================================================================================================================
; https://learn.microsoft.com/ru-ru/windows/win32/api/endpointvolume/
; ===============================================================================================================================

; Пример PeakMeter.
Func _MakePeakMeterInWindow()
    Local $hGUI = GUICreate("PeakMeter", 80, 300)
    Local $PeakBar = GUICtrlCreateProgress(20, 20, 40, 260, 0x04)
    Local $iPeak, $iCurrentRead, $S_OK = 0
    Local $oAudioMeterInformation = _GetAudioMeterInformationObject()
    GUISetState(@SW_SHOW, $hGUI)
    While GUIGetMsg() <> -3 ; $GUI_EVENT_CLOSE
        If $oAudioMeterInformation.GetPeakValue($iPeak) = $S_OK Then
            $iCurrentRead = 100 * $iPeak
            GUICtrlSetData($PeakBar, $iCurrentRead + 1)
            GUICtrlSetData($PeakBar, $iCurrentRead)
        EndIf
        Sleep(20)
    WEnd
    Exit
EndFunc

; ===============================================================================================================================
; Интерфейс IAudioMeterInformation.
; https://learn.microsoft.com/ru-ru/windows/win32/api/endpointvolume/nn-endpointvolume-iaudiometerinformation
; ===============================================================================================================================
Func _GetAudioMeterInformationObject()
    Local Const $CLSCTX_INPROC_SERVER = 0x1
    Local Const $sCLSID_MMDeviceEnumerator = "{BCDE0395-E52F-467C-8E3D-C4579291692E}"
    Local Const $sIID_IMMDeviceEnumerator = "{A95664D2-9614-4F35-A746-DE8DB63617E6}"
    Local Const $tagIMMDeviceEnumerator = "EnumAudioEndpoints hresult(dword;dword;ptr*);" & _
                                          "GetDefaultAudioEndpoint hresult(dword;dword;ptr*);" & _
                                          "GetDevice hresult(wstr;ptr*);" & _
                                          "RegisterEndpointNotificationCallback hresult(ptr);" & _
                                          "UnregisterEndpointNotificationCallback hresult(ptr);"
    Local Const $sIID_IMMDevice = "{D666063F-1587-4E43-81F1-B948E807363F}"
    Local Const $tagIMMDevice = "Activate hresult(clsid;dword;variant*;ptr*);" & _
                                "OpenPropertyStore hresult(dword;ptr*);" & _
                                "GetId hresult(ptr*);" & _
                                "GetState hresult(dword*);"
    Local Const $sIID_IAudioMeterInformation = "{C02216F6-8C67-4B5B-9D00-D008E73E0064}"
    Local Const $tagIAudioMeterInformation = "GetPeakValue hresult(float*);" & _
                                             "GetMeteringChannelCount hresult(dword*);" & _
                                             "GetChannelsPeakValues hresult(dword;float*);" & _
                                             "QueryHardwareSupport hresult(dword*);"
    ; MMDeviceEnumerator.
    Local $oMMDeviceEnumerator = ObjCreateInterface($sCLSID_MMDeviceEnumerator, $sIID_IMMDeviceEnumerator, $tagIMMDeviceEnumerator)
    If @error Then Return SetError(1, 0, 0)
    ; DefaultAudioEndpoint.
    Local Const $eRender = 0
    Local Const $eConsole = 0
    Local $pDefaultDevice
    $oMMDeviceEnumerator.GetDefaultAudioEndpoint($eRender, $eConsole, $pDefaultDevice)
    If Not $pDefaultDevice Then Return SetError(2, 0, 0)
    ; Turn that pointer into object.
    Local $oDefaultDevice = ObjCreateInterface($pDefaultDevice, $sIID_IMMDevice, $tagIMMDevice)
    If @error Then Return SetError(3, 0, 0)
    If Not IsObj($oDefaultDevice) Then Return SetError(3, 0, 0)
    ; AudioMeterInformation.
    Local $pAudioMeterInformation
    $oDefaultDevice.Activate($sIID_IAudioMeterInformation, $CLSCTX_INPROC_SERVER, 0, $pAudioMeterInformation)
    If Not $pAudioMeterInformation Then Return SetError(4, 0, 0)
    Local $oAudioMeterInformation = ObjCreateInterface($pAudioMeterInformation, $sIID_IAudioMeterInformation, $tagIAudioMeterInformation)
    If Not IsObj($oAudioMeterInformation) Then Return SetError(5, 0, 0)
    Return $oAudioMeterInformation
EndFunc

; ===============================================================================================================================
; Интерфейс IAudioEndpointVolume.
; https://learn.microsoft.com/ru-ru/windows/win32/api/endpointvolume/nn-endpointvolume-iaudioendpointvolume
; ===============================================================================================================================
Func _GetAudioEndpointVolumeObject()
    Local Const $CLSCTX_INPROC_SERVER = 0x1
    Local Const $sCLSID_MMDeviceEnumerator = "{BCDE0395-E52F-467C-8E3D-C4579291692E}"
    Local Const $sIID_IMMDeviceEnumerator = "{A95664D2-9614-4F35-A746-DE8DB63617E6}"
    Local Const $tagIMMDeviceEnumerator = "EnumAudioEndpoints hresult(dword;dword;ptr*);" & _
                                          "GetDefaultAudioEndpoint hresult(dword;dword;ptr*);" & _
                                          "GetDevice hresult(wstr;ptr*);" & _
                                          "RegisterEndpointNotificationCallback hresult(ptr);" & _
                                          "UnregisterEndpointNotificationCallback hresult(ptr);"
    Local Const $sIID_IMMDevice = "{D666063F-1587-4E43-81F1-B948E807363F}"
    Local Const $tagIMMDevice = "Activate hresult(clsid;dword;variant*;ptr*);" & _
                                "OpenPropertyStore hresult(dword;ptr*);" & _
                                "GetId hresult(ptr*);" & _
                                "GetState hresult(dword*);"
    Local Const $sIID_IAudioEndpointVolume = "{5CDF2C82-841E-4546-9722-0CF74078229A}"
    Local Const $tagIAudioEndpointVolume = "RegisterControlChangeNotify hresult(ptr);" & _
                                           "UnregisterControlChangeNotify hresult(ptr);" & _
                                           "GetChannelCount hresult(uint*);" & _
                                           "SetMasterVolumeLevel hresult(float;ptr);" & _
                                           "SetMasterVolumeLevelScalar hresult(float;ptr);" & _
                                           "GetMasterVolumeLevel hresult(float*);" & _
                                           "GetMasterVolumeLevelScalar hresult(float*);" & _
                                           "SetChannelVolumeLevel hresult(uint;float;ptr);" & _
                                           "SetChannelVolumeLevelScalar hresult(uint;float;ptr);" & _
                                           "GetChannelVolumeLevel hresult(uint;float*);" & _
                                           "GetChannelVolumeLevelScalar hresult(uint;float*);" & _
                                           "SetMute hresult(int;ptr);" & _
                                           "GetMute hresult(int*);" & _
                                           "GetVolumeStepInfo hresult(uint*;uint*);" & _
                                           "VolumeStepUp hresult(ptr);" & _
                                           "VolumeStepDown hresult(ptr);" & _
                                           "QueryHardwareSupport hresult(dword*);" & _
                                           "GetVolumeRange hresult(float*;float*;float*)"
    ; MMDeviceEnumerator.
    Local $oMMDeviceEnumerator = ObjCreateInterface($sCLSID_MMDeviceEnumerator, $sIID_IMMDeviceEnumerator, $tagIMMDeviceEnumerator)
    If @error Then Return SetError(1, 0, 0)
    ; DefaultAudioEndpoint.
    Local Const $eRender = 0
    Local Const $eConsole = 0
    Local $pDefaultDevice
    $oMMDeviceEnumerator.GetDefaultAudioEndpoint($eRender, $eConsole, $pDefaultDevice)
    If Not $pDefaultDevice Then Return SetError(2, 0, 0)
    ; Turn that pointer into object.
    Local $oDefaultDevice = ObjCreateInterface($pDefaultDevice, $sIID_IMMDevice, $tagIMMDevice)
    If @error Then Return SetError(3, 0, 0)
    If Not IsObj($oDefaultDevice) Then Return SetError(3, 0, 0)
    ; AudioEndpointVolume.
    Local $pAudioEndpointVolume
    $oDefaultDevice.Activate($sIID_IAudioEndpointVolume, $CLSCTX_INPROC_SERVER, 0, $pAudioEndpointVolume)
    If Not $pAudioEndpointVolume Then Return SetError(4, 0, 0)
    Local $oAudioEndpointVolume = ObjCreateInterface($pAudioEndpointVolume, $sIID_IAudioEndpointVolume, $tagIAudioEndpointVolume)
    If Not IsObj($oAudioEndpointVolume) Then Return SetError(5, 0, 0)
    Return $oAudioEndpointVolume
EndFunc

Сообщение автоматически объединено:

Получилось переключиться на устройство ввода звука по умолчанию! Уже какое то движение к цели)
Код:
; EDataFlow enumeration:
Global Enum $eRender = 0, $eCapture, $eAll, $EDataFlow_enum_count
; https://learn.microsoft.com/en-us/windows/win32/api/mmdeviceapi/ne-mmdeviceapi-edataflow

; ERole enumeration:
Global $eConsole = 0, $eMultimedia, $eCommunications, $ERole_enum_count
; https://learn.microsoft.com/en-us/windows/win32/api/mmdeviceapi/ne-mmdeviceapi-erole

_MakePeakMeterInWindow()
Exit

; ===============================================================================================================================
; ===============================================================================================================================
; ===============================================================================================================================
; =========================================== Интерфейсы EndPointVolume =========================================================
; ===============================================================================================================================
; ===============================================================================================================================
; ===============================================================================================================================
; https://learn.microsoft.com/ru-ru/windows/win32/api/endpointvolume/
; ===============================================================================================================================

; Пример PeakMeter.
Func _MakePeakMeterInWindow()
    Local $hGUI = GUICreate("PeakMeter", 80, 300)
    Local $PeakBar = GUICtrlCreateProgress(20, 20, 40, 260, 0x04)
    Local $iPeak, $iCurrentRead, $S_OK = 0
    Local $oAudioMeterInformation = _GetAudioMeterInformationObject($eCapture)
    GUISetState(@SW_SHOW, $hGUI)
    While GUIGetMsg() <> -3 ; $GUI_EVENT_CLOSE
        If $oAudioMeterInformation.GetPeakValue($iPeak) = $S_OK Then
            $iCurrentRead = 100 * $iPeak
            GUICtrlSetData($PeakBar, $iCurrentRead + 1)
            GUICtrlSetData($PeakBar, $iCurrentRead)
        EndIf
        Sleep(50)
    WEnd
    Exit
EndFunc

; ===============================================================================================================================
; Интерфейс IAudioMeterInformation.
; https://learn.microsoft.com/ru-ru/windows/win32/api/endpointvolume/nn-endpointvolume-iaudiometerinformation
; ===============================================================================================================================
Func _GetAudioMeterInformationObject($EDF = $eRender, $ERLE = $eConsole)
    Local Const $CLSCTX_INPROC_SERVER = 0x1
    Local Const $sCLSID_MMDeviceEnumerator = "{BCDE0395-E52F-467C-8E3D-C4579291692E}"
    Local Const $sIID_IMMDeviceEnumerator = "{A95664D2-9614-4F35-A746-DE8DB63617E6}"
    Local Const $tagIMMDeviceEnumerator = "EnumAudioEndpoints hresult(dword;dword;ptr*);" & _
                                          "GetDefaultAudioEndpoint hresult(dword;dword;ptr*);" & _
                                          "GetDevice hresult(wstr;ptr*);" & _
                                          "RegisterEndpointNotificationCallback hresult(ptr);" & _
                                          "UnregisterEndpointNotificationCallback hresult(ptr);"
    Local Const $sIID_IMMDevice = "{D666063F-1587-4E43-81F1-B948E807363F}"
    Local Const $tagIMMDevice = "Activate hresult(clsid;dword;variant*;ptr*);" & _
                                "OpenPropertyStore hresult(dword;ptr*);" & _
                                "GetId hresult(ptr*);" & _
                                "GetState hresult(dword*);"
    Local Const $sIID_IAudioMeterInformation = "{C02216F6-8C67-4B5B-9D00-D008E73E0064}"
    Local Const $tagIAudioMeterInformation = "GetPeakValue hresult(float*);" & _
                                             "GetMeteringChannelCount hresult(dword*);" & _
                                             "GetChannelsPeakValues hresult(dword;float*);" & _
                                             "QueryHardwareSupport hresult(dword*);"
    ; MMDeviceEnumerator.
    Local $oMMDeviceEnumerator = ObjCreateInterface($sCLSID_MMDeviceEnumerator, $sIID_IMMDeviceEnumerator, $tagIMMDeviceEnumerator)
    If @error Then Return SetError(1, 0, 0)
    ; DefaultAudioEndpoint.
    Local $pDefaultDevice
    $oMMDeviceEnumerator.GetDefaultAudioEndpoint($EDF, $ERLE, $pDefaultDevice)
    If Not $pDefaultDevice Then Return SetError(2, 0, 0)
    ; Turn that pointer into object.
    Local $oDefaultDevice = ObjCreateInterface($pDefaultDevice, $sIID_IMMDevice, $tagIMMDevice)
    If @error Then Return SetError(3, 0, 0)
    If Not IsObj($oDefaultDevice) Then Return SetError(3, 0, 0)
    ; AudioMeterInformation.
    Local $pAudioMeterInformation
    $oDefaultDevice.Activate($sIID_IAudioMeterInformation, $CLSCTX_INPROC_SERVER, 0, $pAudioMeterInformation)
    If Not $pAudioMeterInformation Then Return SetError(4, 0, 0)
    Local $oAudioMeterInformation = ObjCreateInterface($pAudioMeterInformation, $sIID_IAudioMeterInformation, $tagIAudioMeterInformation)
    If Not IsObj($oAudioMeterInformation) Then Return SetError(5, 0, 0)
    Return $oAudioMeterInformation
EndFunc

; ===============================================================================================================================
; Интерфейс IAudioEndpointVolume.
; https://learn.microsoft.com/ru-ru/windows/win32/api/endpointvolume/nn-endpointvolume-iaudioendpointvolume
; ===============================================================================================================================
Func _GetAudioEndpointVolumeObject($EDF = $eRender, $ERLE = $eConsole)
    Local Const $CLSCTX_INPROC_SERVER = 0x1
    Local Const $sCLSID_MMDeviceEnumerator = "{BCDE0395-E52F-467C-8E3D-C4579291692E}"
    Local Const $sIID_IMMDeviceEnumerator = "{A95664D2-9614-4F35-A746-DE8DB63617E6}"
    Local Const $tagIMMDeviceEnumerator = "EnumAudioEndpoints hresult(dword;dword;ptr*);" & _
                                          "GetDefaultAudioEndpoint hresult(dword;dword;ptr*);" & _
                                          "GetDevice hresult(wstr;ptr*);" & _
                                          "RegisterEndpointNotificationCallback hresult(ptr);" & _
                                          "UnregisterEndpointNotificationCallback hresult(ptr);"
    Local Const $sIID_IMMDevice = "{D666063F-1587-4E43-81F1-B948E807363F}"
    Local Const $tagIMMDevice = "Activate hresult(clsid;dword;variant*;ptr*);" & _
                                "OpenPropertyStore hresult(dword;ptr*);" & _
                                "GetId hresult(ptr*);" & _
                                "GetState hresult(dword*);"
    Local Const $sIID_IAudioEndpointVolume = "{5CDF2C82-841E-4546-9722-0CF74078229A}"
    Local Const $tagIAudioEndpointVolume = "RegisterControlChangeNotify hresult(ptr);" & _
                                           "UnregisterControlChangeNotify hresult(ptr);" & _
                                           "GetChannelCount hresult(uint*);" & _
                                           "SetMasterVolumeLevel hresult(float;ptr);" & _
                                           "SetMasterVolumeLevelScalar hresult(float;ptr);" & _
                                           "GetMasterVolumeLevel hresult(float*);" & _
                                           "GetMasterVolumeLevelScalar hresult(float*);" & _
                                           "SetChannelVolumeLevel hresult(uint;float;ptr);" & _
                                           "SetChannelVolumeLevelScalar hresult(uint;float;ptr);" & _
                                           "GetChannelVolumeLevel hresult(uint;float*);" & _
                                           "GetChannelVolumeLevelScalar hresult(uint;float*);" & _
                                           "SetMute hresult(int;ptr);" & _
                                           "GetMute hresult(int*);" & _
                                           "GetVolumeStepInfo hresult(uint*;uint*);" & _
                                           "VolumeStepUp hresult(ptr);" & _
                                           "VolumeStepDown hresult(ptr);" & _
                                           "QueryHardwareSupport hresult(dword*);" & _
                                           "GetVolumeRange hresult(float*;float*;float*)"
    ; MMDeviceEnumerator.
    Local $oMMDeviceEnumerator = ObjCreateInterface($sCLSID_MMDeviceEnumerator, $sIID_IMMDeviceEnumerator, $tagIMMDeviceEnumerator)
    If @error Then Return SetError(1, 0, 0)
    ; DefaultAudioEndpoint.
    Local $pDefaultDevice
    $oMMDeviceEnumerator.GetDefaultAudioEndpoint($EDF, $ERLE, $pDefaultDevice)
    If Not $pDefaultDevice Then Return SetError(2, 0, 0)
    ; Turn that pointer into object.
    Local $oDefaultDevice = ObjCreateInterface($pDefaultDevice, $sIID_IMMDevice, $tagIMMDevice)
    If @error Then Return SetError(3, 0, 0)
    If Not IsObj($oDefaultDevice) Then Return SetError(3, 0, 0)
    ; AudioEndpointVolume.
    Local $pAudioEndpointVolume
    $oDefaultDevice.Activate($sIID_IAudioEndpointVolume, $CLSCTX_INPROC_SERVER, 0, $pAudioEndpointVolume)
    If Not $pAudioEndpointVolume Then Return SetError(4, 0, 0)
    Local $oAudioEndpointVolume = ObjCreateInterface($pAudioEndpointVolume, $sIID_IAudioEndpointVolume, $tagIAudioEndpointVolume)
    If Not IsObj($oAudioEndpointVolume) Then Return SetError(5, 0, 0)
    Return $oAudioEndpointVolume
EndFunc


Но интерфейс AudioMeterInformation работает только тогда, когда кто то микрофон слушает. К примеру панель управления звука Windows:
1681599718103.png

Если закрыть панель звук, все перестает работать. Подскажите, как можно заставить работать интерфейс IAudioMeterInformation?

Для интерйфеса AudioEndpointVolume все работает без проблем, громкость микрофона регулируется.
Сообщение автоматически объединено:

Всем привет. Получилось одолеть микрофон. Требуется создать еще интерфейсы IAudioClient и IAudioCaptureClient.
Теперь все работает как надо:
 

Вложения

  • iAudio_V4.au3
    13.7 КБ · Просмотры: 5
Последнее редактирование:
Верх