簡體   English   中英

如何通過UVC支持硬件編碼H264

[英]How to support hardware encoded H264 though UVC

我在使用DirectShow創建的視頻應用程序中使用Logitech C930e網絡攝像頭。 到目前為止,我能夠在YUY2或mJPEG中使用原始流。 無論如何,我發現網絡攝像頭通過UVC接口支持硬件H264編碼。

現在我使用標准方法來獲取可能的網絡攝像頭捕獲引腳配置,但那里沒有H264引腳。

void list_cameras {
    ICreateDevEnum *pDevEnum = nullptr;
    IEnumMoniker *pEnum = nullptr;

    // Create the System Device Enumerator.
    HRESULT hr = CoCreateInstance(CLSID_SystemDeviceEnum, nullptr,
                                  CLSCTX_INPROC_SERVER, IID_ICreateDevEnum,
                                  reinterpret_cast<void**>(&pDevEnum));
    if (SUCCEEDED(hr)) {
        // Create an enumerator for the video capture category.
        hr = pDevEnum->CreateClassEnumerator(
            CLSID_VideoInputDeviceCategory,
            &pEnum, 0);
        if (hr == S_FALSE) {
            return;
        }
    }

    IMoniker *pMoniker = nullptr; // IMoniker is the device
    int index = 0;

    // for each device
    while (pEnum->Next(1, &pMoniker, nullptr) == S_OK) {

        // bind camera to filter to be able to use it
        if (cam.device->BindToObject(nullptr, nullptr, IID_IBaseFilter, reinterpret_cast<void**>(&_pCapture)) != S_OK) {
            continue;
        }

        // fetch the configuration interface
        IAMStreamConfig *pConfig = nullptr;
        HRESULT hr = _capture->FindInterface(
            &PIN_CATEGORY_CAPTURE, // Preview pin.
            nullptr, // Any media type.
            _pCapture, // Pointer to the capture filter.
            IID_IAMStreamConfig, reinterpret_cast<void**>(&pConfig));

        if (FAILED(hr)) {
            continue;
        }

        // fetch possible configurations
        int iCount = 0, iSize = 0;
        if (pConfig->GetNumberOfCapabilities(&iCount, &iSize) != S_OK) {
            continue;
        }

        // store each configuration
        AM_MEDIA_TYPE *pmtConfig;
        for (int iFormat = 0; iFormat < iCount; iFormat++) {
            // get config
            VIDEO_STREAM_CONFIG_CAPS scc;
            if (pConfig->GetStreamCaps(iFormat, &pmtConfig, reinterpret_cast<BYTE*>(&scc)) != S_OK) {
                continue;
            }

            // copy config data
            VIDEOINFOHEADER *pVih = new VIDEOINFOHEADER(); // deleted afterwards
            *pVih = *reinterpret_cast<VIDEOINFOHEADER *>(pmtConfig->pbFormat);

            AM_MEDIA_TYPE mt;
            mt = *pmtConfig;
            mt.pbFormat = reinterpret_cast<BYTE *>(pVih);
            auto fcc = FOURCCMap(pVih->bmiHeader.biCompression);

            // wrap it
            CameraConfig config = { mt, pVih->bmiHeader.biWidth, pVih->bmiHeader.biHeight, 1000 / (static_cast<float>(pVih->AvgTimePerFrame) / 10000), fcc };

            // if resolution is bad (or unsupported), skip this configuration
            if (config.width == 0 || config.height == 0 ) // bad
                continue;

            cam.configurations.push_back(config);
        }
        _cameras.push_back(cam);

        pConfig->Release();
        _pCapture->Release();
    }

    pEnum->Release();
    pDevEnum->Release();
}

_cameras是Camera的矢量,定義如下:

typedef struct {
    //! Pointer to DirectShow device.
    DSDevice device; 

    //! Camera name
    string name;

    //! List of supported configurations.
    vector<CameraConfig> configurations; // list of all available configurations

    //! Index of selected configuration.
    int selected;
} Camera;

_pCapture是指向創建的捕獲過濾器的指針。 CameraConfig定義如下:

typedef struct {
    //! Media type.
    AM_MEDIA_TYPE _mediaType;

    //! Output width.
    int width;

    //! Outpus height.
    int height;

    //! Output framerate.
    float fps;

    //! Compression algoritm. YUY2 and mJPEG are supported for now.
    FOURCCMap compression;
} CameraConfig;

如何實現對UVC設備的支持? 可以控制哪些硬件編碼器參數?

謝謝。

我能夠在Windows 8.x下獲得該流的唯一方法是不使用LOGITECH驅動程序。 這是兼容UVC 1.5的相機,它將由操作系統自動配置。 使用該驅動程序(來自Microsoft),使用引腳1(而不是0),您將獲得大量的H264格式。

我認為在Windows 7下,Logitech的一些驅動程序也提供了許多H264格式。

如果您使用的是Windows 8.x並且已經安裝了Logitech驅動程序,則必須將其刪除。 這很難。 我通常通過編寫這樣的結構(以管理員身份運行)來實現:

BOOL res;
res = SetupUninstallOEMInf(TEXT("oem131.inf"), SUOI_FORCEDELETE, nullptr );

至於你刪除的內容很簡單:轉到Windows \\ Inf文件夾並搜索Logitech。 然后檢查每個文件o看看究竟是什么(你可能有一個鼠標或其他你想保留的東西)。 通常它不止一個。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM