Microsoft DirectX 9.0 |
World Standard Teletext (WST) is encoded in the vertical blanking interval (VBI) of the analog television signal. The filter graph for previewing teletext is similar to the graph used to view closed captions.
This graph uses the following filters for WST display:
The Capture Graph Builder's RenderStream method does not support the WST filters directly, so your application must do some extra work.
IBaseFilter *pOvMix = NULL; // Pointer to the Overlay Mixer filter.
hr = AddFilterByCLSID(pGraph, CLSID_OverlayMixer, L"OVMix", &pOvMix);
if (FAILED(hr))
{
// Handle the error ...
}
hr = pBuild->RenderStream(&PIN_CATEGORY_PREVIEW, &MEDIATYPE_Video,
pCap, pOvMix, 0);
IBaseFilter* pKernelTee = NULL;
hr = CreateKernelFilter(AM_KSCATEGORY_SPLITTER,
OLESTR("Tee/Sink-to-Sink Converter"), &pKernelTee);
if (SUCCEEDED(hr))
{
hr = pGraph->AddFilter(pKernelTee, L"Kernel Tee");
}
IBaseFilter* pWstCodec = NULL;
hr = CreateKernelFilter(AM_KSCATEGORY_VBICODEC,
OLESTR("WST Codec"), &pWstCodec);
if (SUCCEEDED(hr))
{
hr = pGraph->AddFilter(pWstCodec, L"WST Codec");
}
hr = pBuild->RenderStream(&PIN_CATEGORY_VBI, 0, pCap,
pKernelTee, pWstCodec);
hr = pBuild->RenderStream(0, 0, pWstCodec, 0, pOvMix);
pOvMix->Release();
pKernelTee->Release();
pWstCodec->Release();
Note Currently, the WST Decoder filter does not support connections to the Video Mixing Renderer (VMR) filter. Therefore, you must use the legacy Video Renderer filter to view teletext.
If the capture filter has a video port VBI pin (PIN_CATEGPORY_VIDEOPORT_VBI), connect it to the VBI Surface Allocator filter. The graph will not run correctly otherwise. The following code example uses the AddFilterByCLSID function, described in Add a Filter by CLSID, and the FindPinByCategory function, described in Working with Pin Categories. (Neither function is a DirectShow API.)
// Look for a video port VBI pin on the capture filter.
IPin *pVPVBI = NULL;
hr = FindPinByCategory(pCap, PINDIR_OUTPUT,
PIN_CATEGORY_VIDEOPORT_VBI, &pVPVBI);
if (FAILED(hr))
{
// No video port VBI pin; nothing else to do. OK to run the graph.
}
else
{
// Found one. Connect it to the VBI Surface Allocator.
IBaseFilter *pSurf = NULL;
hr = AddFilterByCLSID(pGraph, CLSID_VBISurfaces, L"VBI Surf", &pSurf);
if (SUCCEEDED(hr))
{
hr = pBuild->RenderStream(NULL, NULL, pVPVBI, 0, pSurf);
pSurf->Release();
}
if (FAILED(hr))
{
// Handle the error (not shown). It is probably not safe to
// run the graph at this point.
}
pVPVBI->Release();
}