2010-12-05 95 views
2

因此,要獲得相機列表,讓用戶選擇一個(C++,升壓,DSHOW,窗戶)我用這樣的代碼:Windows:如何獲得相機支持的分辨率?

#include "StdAfx.h" 
#include "list.h" 
#include <windows.h> 
#include <dshow.h> 
#include <boost/lexical_cast.hpp> 

HRESULT CamerasList::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; 
} 

int CamerasList::SelectFromList() 
{ int i = 0; 
    int SelectedIndex; 
    IEnumMoniker *pEnum; 
    printf("\nLet us select video device\n"); 
    printf("Available Capture Devices are:\n"); 
    HRESULT hr; 
    hr = EnumerateDevices(CLSID_VideoInputDeviceCategory, &pEnum); 
    if (SUCCEEDED(hr)) 
    { 
     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)) 
      { 
       std::cout << i; 
       printf(") %S\n", var.bstrVal); 
       i++; 
       VariantClear(&var); 
      } 

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

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

     } 
     SelectedIndex = 999; 
    if (i <= 0) 
    { 
     cout <<"No devices found. \n " << endl; 
     //cout <<"Please restart application." << endl; 
     //cin.get(); 
     //Sleep(999999); 
    return 999; 

    }else if(i == 1){ 
      cout <<"Default device will be used\n" << std::endl; 
      SelectedIndex = 0; 
     }else{ 
     while(SelectedIndex > i-1 || SelectedIndex < 0) 
     { 
      try{   
      std::string s; 
      std::getline(cin, s, '\n'); 
      SelectedIndex = boost::lexical_cast<int>(s); 
      } 
      catch(std::exception& e){ 
       std::cout <<"please input index from 0 to " << i-1 << std::endl; 
       SelectedIndex = 999; 
      } 
     }} 
     pEnum->Release(); 
    }else 
    { 
     printf("no Video Devices found. \n") ; 
     //cout <<"Please restart application." << endl; 
     //cin.get(); 
     //Sleep(999999); 
     return 999; 
    } 
    return SelectedIndex; 
} 

我需要以某種方式獲得相機的列表支持選定的攝像頭分辨率。如何做這樣的事情?

回答

4

假設你已經添加了捕捉源過濾器到圖形: 一種方法是讓捕獲過濾器的輸出引腳的IAMStreamConfig接口,然後調用IAMStreamConfig :: GetNumberOfCapabilities獲得由支持的格式的功能數量裝置。您可以通過使用適當的索引調用IAMStreamConfig :: GetStreamCaps來遍歷所有格式。

+0

不,我實際上只是用它來獲取相機列表 - 我使用OpenCV進行拍攝。所以如果我不創建一個圖表如何做這樣的事情?或者如何爲這樣的porpus創建圖表? – Rella 2010-12-05 21:00:30

+0

我不知道有沒有其他的方式來做到這一點,而不需要添加捕獲源到圖表來查詢IAMStreamConfig接口的輸出引腳等等。只要將它添加到圖表中,查詢它等等,然後一旦你得到所需的信息,發佈圖表和資源? – Ralf 2011-03-01 11:32:45

3

無需將捕獲源添加到過濾器圖即可獲得支持的分辨率。您需要

  • 綁定的設備moniker到基地filter
  • 從過濾器得到的輸出pin
  • 枚舉該輸出引腳

這裏是如何枚舉媒體media types給定的類型media type enumerator

AM_MEDIA_TYPE* mediaType = NULL; 
VIDEOINFOHEADER* videoInfoHeader = NULL; 
while (S_OK == mediaTypesEnumerator->Next(1, &mediaType, NULL)) 
{ 
    if ((mediaType->formattype == FORMAT_VideoInfo) && 
     (mediaType->cbFormat >= sizeof(VIDEOINFOHEADER)) && 
     (mediaType->pbFormat != NULL)) 
    { 
     videoInfoHeader = (VIDEOINFOHEADER*)mediaType->pbFormat; 
     videoInfoHeader->bmiHeader.biWidth; // Supported width 
     videoInfoHeader->bmiHeader.biHeight; // Supported height 
    } 
    FreeMediaType(*mediaType); 
}