// Create the topology. HRESULT CreateTopology(IMFMediaSource *pSource, IMFActivate *pSinkActivate, IMFTopology **ppTopo) { IMFTopology *pTopology = NULL; IMFPresentationDescriptor *pPD = NULL; IMFStreamDescriptor *pSD = NULL; IMFMediaTypeHandler *pHandler = NULL; IMFTopologyNode *pNode1 = NULL; IMFTopologyNode *pNode2 = NULL; HRESULT hr = S_OK; DWORD cStreams = 0; CHECK_HR(hr = MFCreateTopology(&pTopology)); CHECK_HR(hr = pSource->CreatePresentationDescriptor(&pPD)); CHECK_HR(hr = pPD->GetStreamDescriptorCount(&cStreams)); for (DWORD i = 0; i < cStreams; i++) { // In this example, we look for audio streams and connect them to the sink. BOOL fSelected = FALSE; GUID majorType; CHECK_HR(hr = pPD->GetStreamDescriptorByIndex(i, &fSelected, &pSD)); CHECK_HR(hr = pSD->GetMediaTypeHandler(&pHandler)); CHECK_HR(hr = pHandler->GetMajorType(&majorType)); if (majorType == MFMediaType_Video && fSelected) { CHECK_HR(hr = AddSourceNode(pTopology, pSource, pPD, pSD, &pNode1)); CHECK_HR(hr = AddOutputNode(pTopology, pSinkActivate, 0, &pNode2)); CHECK_HR(hr = pNode1->ConnectOutput(0, pNode2, 0)); break; } else { CHECK_HR(hr = pPD->DeselectStream(i)); } SafeRelease(&pSD); SafeRelease(&pHandler); } *ppTopo = pTopology; (*ppTopo)->AddRef(); done: SafeRelease(&pTopology); SafeRelease(&pNode1); SafeRelease(&pNode2); SafeRelease(&pPD); SafeRelease(&pSD); SafeRelease(&pHandler); return hr; }
/** Set playback topology */ FIntPoint FImfVideoPlayer::SetPlaybackTopology( FImfSampleGrabberCallback* SampleGrabberCallback ) { FIntPoint OutDimensions = FIntPoint( ForceInit ); HRESULT HResult = S_OK; IMFPresentationDescriptor* PresentationDesc = NULL; HResult = MediaSource->CreatePresentationDescriptor( &PresentationDesc ); check( SUCCEEDED( HResult ) ); IMFTopology* Topology = NULL; HResult = MFCreateTopology( &Topology ); check( SUCCEEDED( HResult ) ); DWORD StreamCount = 0; HResult = PresentationDesc->GetStreamDescriptorCount( &StreamCount ); check( SUCCEEDED( HResult ) ); for( uint32 i = 0; i < StreamCount; i++ ) { BOOL bSelected = 0; IMFStreamDescriptor* StreamDesc = NULL; HResult = PresentationDesc->GetStreamDescriptorByIndex( i, &bSelected, &StreamDesc ); check( SUCCEEDED( HResult ) ); if( bSelected ) { FIntPoint VideoDimensions = AddStreamToTopology( Topology, PresentationDesc, StreamDesc, SampleGrabberCallback ); if( VideoDimensions != FIntPoint( ForceInit ) ) OutDimensions = VideoDimensions; } StreamDesc->Release( ); } HResult = MediaSession->SetTopology( 0, Topology ); check( SUCCEEDED( HResult ) ); Topology->Release( ); PresentationDesc->Release( ); return OutDimensions; }
HRESULT CPlayer::CreateTopologyFromSource(IMFTopology **ppTopology) { TRACE((L"CPlayer::CreateTopologyFromSource\n")); assert(m_pSession != NULL); assert(m_pSource != NULL); HRESULT hr = S_OK; IMFTopology *pTopology = NULL; IMFPresentationDescriptor* pSourcePD = NULL; DWORD cSourceStreams = 0; // Create a new topology. CHECK_HR(hr = MFCreateTopology(&pTopology)); // Create the presentation descriptor for the media source. CHECK_HR(hr = m_pSource->CreatePresentationDescriptor(&pSourcePD)); // Get the number of streams in the media source. CHECK_HR(hr = pSourcePD->GetStreamDescriptorCount(&cSourceStreams)); TRACE((L"Stream count: %d\n", cSourceStreams)); // For each stream, create the topology nodes and add them to the topology. for (DWORD i = 0; i < cSourceStreams; i++) { CHECK_HR(hr = AddBranchToPartialTopology(pTopology, pSourcePD, i)); } // Return the IMFTopology pointer to the caller. if (SUCCEEDED(hr)) { *ppTopology = pTopology; (*ppTopology)->AddRef(); } done: SAFE_RELEASE(pTopology); SAFE_RELEASE(pSourcePD); return hr; }
//---------------------------------------------------------------------------- long MediaFoundationVideoDevice::EnumerateCaptureFormats(IMFMediaSource *pSource) { IMFPresentationDescriptor *pPD = NULL; IMFStreamDescriptor *pSD = NULL; IMFMediaTypeHandler *pHandler = NULL; HRESULT hr=-1; if (pSource==NULL) { goto done; } hr = pSource->CreatePresentationDescriptor(&pPD); if (FAILED(hr)) { goto done; } DWORD descriptorCount = 0; hr = pPD->GetStreamDescriptorCount(&descriptorCount); if (FAILED(hr)) { goto done; } for (DWORD streamIndex = 0; streamIndex<descriptorCount; streamIndex++) { std::vector<MediaType> formats; BOOL fSelected = false; hr = pPD->GetStreamDescriptorByIndex(streamIndex, &fSelected, &pSD); if (FAILED(hr)) { goto done; } DWORD streamId=0; hr = pSD->GetStreamIdentifier(&streamId); if (FAILED(hr)) { goto done; } hr = pSD->GetMediaTypeHandler(&pHandler); if (FAILED(hr)) { goto done; } DWORD cTypes = 0; hr = pHandler->GetMediaTypeCount(&cTypes); if (FAILED(hr)) { continue; } for (DWORD i = 0; i < cTypes; i++) { IMFMediaType *pType = NULL; hr = pHandler->GetMediaTypeByIndex(i, &pType); if (SUCCEEDED(hr)) { MediaType mt = FormatReader::Read(pType);\ mt.StreamId = streamId; formats.push_back(mt); } SafeRelease(&pType); } this->CurrentFormats.push_back(formats); } done: SafeRelease(&pPD); SafeRelease(&pSD); SafeRelease(&pHandler); return hr; }