Я нашел этот хороший пример в интернете, объясняющий, как работает DirectShow.
В этом примере есть два примера грабберов. Один называется не RGB-граббер, а другой называется RGB-граббер.
Первый: (NON-RGB)
#pragma region Non-RGB Sample Grabber
{
CComPtr<IBaseFilter> pBaseFilter;
ATLENSURE_SUCCEEDED(pBaseFilter.CoCreateInstance(__uuidof(SampleGrabber)));
ATLENSURE_SUCCEEDED(pFilterGraph->AddFilter(pBaseFilter, L"Non-RGB Sample Grabber")); // This will connect in MJPG format
const CComQIPtr<ISampleGrabber> pSampleGrabber = pBaseFilter;
ATLASSERT(pSampleGrabber);
#if TRUE
// NOTE: IFilterGraph::Connect would do just fine, but with a real capture device, if we prefer having Smart Tee added, we need to use
// Capture Graph Builder (only here)
CComPtr<ICaptureGraphBuilder2> pCaptureGraphBuilder;
ATLENSURE_SUCCEEDED(pCaptureGraphBuilder.CoCreateInstance(CLSID_CaptureGraphBuilder2));
ATLENSURE_SUCCEEDED(pCaptureGraphBuilder->SetFiltergraph(pFilterGraph));
ATLENSURE_SUCCEEDED(pCaptureGraphBuilder->RenderStream(&PIN_CATEGORY_CAPTURE, NULL, pCurrentOutputPin, NULL, pBaseFilter));
#else
ATLENSURE_SUCCEEDED(pFilterGraph->Connect(pCurrentOutputPin, GetPin(pBaseFilter, 0)));
#endif
MessageBox(GetActiveWindow(), _T("After Non-RGB Sample Grabber Connected"), _T("Debug"), MB_OK);
pCurrentOutputPin = GetPin(pBaseFilter, 1);
}
#pragma endregion
второй: (RGB)
#pragma region RGB Sample Grabber
{
CComPtr<IBaseFilter> pBaseFilter;
ATLENSURE_SUCCEEDED(pBaseFilter.CoCreateInstance(__uuidof(SampleGrabber)));
ATLENSURE_SUCCEEDED(pFilterGraph->AddFilter(pBaseFilter, L"RGB Sample Grabber"));
const CComQIPtr<ISampleGrabber> pSampleGrabber = pBaseFilter;
ATLASSERT(pSampleGrabber);
AM_MEDIA_TYPE MediaType;
ZeroMemory(&MediaType, sizeof MediaType);
MediaType.majortype = MEDIATYPE_Video;
MediaType.subtype = MEDIASUBTYPE_RGB24;
ATLENSURE_SUCCEEDED(pSampleGrabber->SetMediaType(&MediaType));
ATLENSURE_SUCCEEDED(pFilterGraph->Connect(pCurrentOutputPin, GetPin(pBaseFilter, 0)));
MessageBox(GetActiveWindow(), _T("After RGB Sample Grabber Connected"), _T("Debug"), MB_OK);
pCurrentOutputPin = GetPin(pBaseFilter, 1);
}
#pragma endregion
Метод «setmediatype ()» используется только в версии «RGB». Но мне интересно. На странице MSDN указано, что setmediatype () сообщает, к какому типу данных можно получить входной контакт фильтра выборки. И если возможно использовать образец граббер без установки типа носителя, почему я должен установить его на что-нибудь?
Вопросы:
Делает ли образец граббер какой-либо тип конвертации медиа?
Почему я должен установить тип носителя для захвата образца?
Что произойдет, если в медиатайпе формы кулачка установлено значение MJPG, а в типе grabber я установил тип носителя RGB24?
Может ли быть разница в производительности при использовании одного над другим? Чтобы повысить производительность (fps) программного обеспечения, я должен удалить один из захватчиков образца?
Спасибо!
Sample Grabber Filter не выполняет никаких преобразований. Вот почему можно гибко принимать различные форматы, включая видео и аудио, не зная о конкретных форматах.
Когда вы устанавливаете тип носителя для Sample Grabber, вы заставляете его использовать только этот тип. Только принять этот тип и отклонить другой. Вместе с Интеллектуальное соединение, это работает так, что DirectShow может предоставить дополнительные фильтры для преобразования в запрошенный формат, если это возможно. Обычно это возможно с 24-битным RGB, потому что это своего рода «универсальный несжатый видеоформат». Вот почему безопасно установить тип мультимедиа на 24-битный RGB, и в то же время он потерпит неудачу практически с любым форматом сжатого видео (если источник уже не может обеспечить точное совпадение).
Обратите внимание, что если Intelligent Connect предоставляет дополнительные фильтры преобразования, они подключаются в восходящем направлении к Sample Grabber, а не внутри него.
Других решений пока нет …