I have an IMFSampleGrabberSinkCallback
in my Media Foundation application, which I create an activator for using MFCreateSampleGrabberSinkActivate
. The function receives only a partially filled media type. Within the sample grabber callback, an NVENC encoder is running (I know that there are out-of-the-box transforms for NVENC, but the software is not running on Windows 10). In order to use the encoder, I need to have the full media type that after topology resolution (mainly the size of the frames, which is not known when the sample grabber is created).
There seems to be no obvious way to obtain this information in the IMFSampleGrabberSinkCallback
, so the idea would be getting the full topology from the session once I receive MF_TOPOSTATUS_READY
.
First question: Is this the only way to get the full type the grabber will receive or did I miss something?
After getting the full topology, the idea is iterating all nodes, searching the one with the sample grabber and retrieving its input type.
Second question: What would be the best way of doing that? For me, there seems to be no way to retrieve my IMFSampleGabberSinkCallback
from the topology node.
I would solve that using the topo node ID, but I am not sure whether this would work in any case. The documentation of IMFTopologyNode::GetTopoNodeID
states that
When a node is first created, it is assigned an identifier. Node identifiers are unique within a topology, but can be reused across several topologies. The topology loader uses the identifier to look up nodes in the previous topology, so that it can reuse objects from the previous topology.
To me, it is not clear whether the ID will be reused or whether it can be reused.
Third question: Is it guaranteed that, if I obtain the topo node ID of the node I insert my IMFActivate
obtained from MFCreateSampleGrabberSinkActivate
(and as long as I do not change the ID manually using IMFTopologyNode::SetTopoNodeID
, the very same ID will be used for any subsequent topology created during the topology resolution process?
Thanks in advance, Christoph
Edit: The question is not on how to get NVENC working and resolve its input type, but the key questions are (1) whether the topo IDs are guaranteed to be preserved during the resolution process and (2) whether there is a better way to do that than the following (which is susceptible to users actively changing the topo ID): First, I create an activator for my grabber callback. Once I have added the node containing the activator as object to the topology, I retrieve its ID. When the session reports that the topology is ready, I retrieve the node with the ID saved before, obtain its object, query its IMFStreamSink
interface, retrieve its IMFMediaTypeHandler
, get the current media type and obtain the actual frame size and frame rate for NVENC. But: This only works if the ID cannot change and is not actively changed.
I have extracted the topology resolution stages from my test code:
The topology resolver finds out that a colour conversion is required and adds the blue transform to account for this. Coming back to the questions: In this case, they would be (1) whether it is guaranteed that the ID of the red node cannot change during resolution and (2) whether there is an alternative way to implement this which is not susceptible to someone using IMFTopologyNode::SetTopoNodeID
on the red node.