如何获取 Windows 上的视频捕获设备(网络摄像头)列表?(C++)

时间:2023-03-08
本文介绍了如何获取 Windows 上的视频捕获设备(网络摄像头)列表?(C++)的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着跟版网的小编来一起学习吧!

问题描述

所以我们有一个简单的 C++ win32 控制台应用程序.我们想要的只是打印可用的网络摄像机和其他视频捕获设备的列表.我们想尽可能多地使用 windows api - 没有外部库 - 毕竟 - 我们想要的只是打印出一个列表 - 而不是飞上月球!)如何做这样的事情?

So we have a simple C++ win32 console app. All we want is to print list of web cameras and other video capture devices that are avaliable. We want to use windows apis as much as possible - no external libs - after all - all we want is to print out a a list - not to fly onto the moon!) How to do such thing?

我自己的研究:我找到了这个 official msdn sample 但我仍然不知道如何将设备列表输出到屏幕上=((抱歉 - 我是 C++ 新手)

My own reserch: I found this official msdn sample but I still do not get how to output device list onto screen=( (sorry - I am new to C++)

...更多的研究...

... some more reserch...

在最简单的 ms 主题示例之一中发现了这个

In one of simpliest ms samples on topic found this

HRESULT OnInitDialog(HWND hwnd, ChooseDeviceParam *pParam)
{
    HRESULT hr = S_OK;

    HWND hList = GetDlgItem(hwnd, IDC_DEVICE_LIST);

    // Display a list of the devices.

    for (DWORD i = 0; i < pParam->count; i++)
    {
        WCHAR *szFriendlyName = NULL;

        hr = pParam->ppDevices[i]->GetAllocatedString(
            MF_DEVSOURCE_ATTRIBUTE_FRIENDLY_NAME,
            &szFriendlyName,
            NULL
            );

        if (FAILED(hr))
        {
            break;
        }

        int index = ListBox_AddString(hList, szFriendlyName);

        ListBox_SetItemData(hList, index, i);

        CoTaskMemFree(szFriendlyName);
    }

看起来应该可以完成这项工作,但我不知道如何将其包含在简单的命令行应用程序中以输出数据...

looks like it should do the job but I do not get how to include this into simple command line app so to output data...

也来自这个系列:

  • 如何在 Linux 上获取视频捕获设备列表? 和 有关获取相机名称的特殊详细信息 并提供正确的、经过测试的答案
  • 如何在 Mac OS 上获取视频捕获设备的列表?正确的,尚未经过我的回答测试
  • 如何获取 Windows 上的视频捕获设备列表? 提供正确的、经过测试的答案
  • 如何使用 Qt(跨平台)获取视频捕获设备名称列表?
  • How to get a list of video capture devices on linux? and special details on getting cameras NAMES with correct, tested answers
  • How to get a list of video capture devices on Mac OS? with correct, not yet tested by my answers
  • How to get a list of video capture devices on windows? with correct, tested answers
  • How to get a list video capture devices NAMES using Qt (crossplatform)?

推荐答案

从显示的示例中,将以下代码复制到 dev.c 中.然后打开设置了所有 SDK 变量的命令行.在命令行链接到 ole32.lib 和 oleaut32.lib.然后它会显示所有设备.

From the examples shown, copy the following code into dev.c. Then open the command line with all the SDK variables set. At the command line link to ole32.lib and oleaut32.lib. It will then show you all the devices.

cl dev.c ole32.lib oleaut32.lib

cl dev.c ole32.lib oleaut32.lib

dev.exe 会在命令行中给出列表.

dev.exe will give out the list on the command line.

#include <windows.h>
#include <dshow.h>

#pragma comment(lib, "strmiids")

HRESULT EnumerateDevices(REFGUID category, IEnumMoniker **ppEnum)
{
    // Create the System Device Enumerator.
    ICreateDevEnum *pDevEnum;
    HRESULT hr = CoCreateInstance(CLSID_SystemDeviceEnum, NULL,  
        CLSCTX_INPROC_SERVER, IID_PPV_ARGS(&pDevEnum));

    if (SUCCEEDED(hr))
    {
        // Create an enumerator for the category.
        hr = pDevEnum->CreateClassEnumerator(category, ppEnum, 0);
        if (hr == S_FALSE)
        {
            hr = VFW_E_NOT_FOUND;  // The category is empty. Treat as an error.
        }
        pDevEnum->Release();
    }
    return hr;
}


void DisplayDeviceInformation(IEnumMoniker *pEnum)
{
    IMoniker *pMoniker = NULL;

    while (pEnum->Next(1, &pMoniker, NULL) == S_OK)
    {
        IPropertyBag *pPropBag;
        HRESULT hr = pMoniker->BindToStorage(0, 0, IID_PPV_ARGS(&pPropBag));
        if (FAILED(hr))
        {
            pMoniker->Release();
            continue;  
        } 

        VARIANT var;
        VariantInit(&var);

        // Get description or friendly name.
        hr = pPropBag->Read(L"Description", &var, 0);
        if (FAILED(hr))
        {
            hr = pPropBag->Read(L"FriendlyName", &var, 0);
        }
        if (SUCCEEDED(hr))
        {
            printf("%S
", var.bstrVal);
            VariantClear(&var); 
        }

        hr = pPropBag->Write(L"FriendlyName", &var);

        // WaveInID applies only to audio capture devices.
        hr = pPropBag->Read(L"WaveInID", &var, 0);
        if (SUCCEEDED(hr))
        {
            printf("WaveIn ID: %d
", var.lVal);
            VariantClear(&var); 
        }

        hr = pPropBag->Read(L"DevicePath", &var, 0);
        if (SUCCEEDED(hr))
        {
            // The device path is not intended for display.
            printf("Device path: %S
", var.bstrVal);
            VariantClear(&var); 
        }

        pPropBag->Release();
        pMoniker->Release();
    }
}

void main()
{
    HRESULT hr = CoInitializeEx(NULL, COINIT_MULTITHREADED);
    if (SUCCEEDED(hr))
    {
        IEnumMoniker *pEnum;

        hr = EnumerateDevices(CLSID_VideoInputDeviceCategory, &pEnum);
        if (SUCCEEDED(hr))
        {
            DisplayDeviceInformation(pEnum);
            pEnum->Release();
        }
        hr = EnumerateDevices(CLSID_AudioInputDeviceCategory, &pEnum);
        if (SUCCEEDED(hr))
        {
            DisplayDeviceInformation(pEnum);
            pEnum->Release();
        }
        CoUninitialize();
    }
}

这篇关于如何获取 Windows 上的视频捕获设备(网络摄像头)列表?(C++)的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持跟版网!

上一篇:Visual Studio 2010 不会像应该的那样从属于依赖项的项目中自动链接静态库 下一篇:如何在程序执行的最开始设置断点

相关文章