Can't navigate to frame 0

Peter Meier
2012-02-10
2012-10-29
  • Peter Meier
    Peter Meier
    2012-02-10

    Hello everyone,

    I have a WinForms application which uses the DirectShow.NET library to play
    media files. But whenever I load a file and play it (using Run() from
    IMediaControl), the 1st frame (indexed with 0) is being skipped. I included
    the SampleGrabber filter with its Callback Events and the first time a
    callback event is triggered it's already frame 1. The same is true when I try
    to seek to the beginning by using IMediaSeeking.

    It happens even if I have a raw RGB24 avi. Also Media Player Classic is able
    show me frame 0, even though the graphs are almost identical.
    My graph: Haali MS 1.11.96.14 --> SampleGrabber --> Color Space Converter -->
    VMR Renderer
    MPC graph is the same except for a different source filter. The renderer is
    set to "System Default", so it should be the same one, I guess.

    Regards
    Squall

     
  • Peter Meier
    Peter Meier
    2012-02-13

    I am one step further. Apparently, GraphEdit has the very same problem. Choose
    any media file where you painted the frame numbers or something like that on
    each frame, open it with GraphEdit and you're probably going to see the very
    same effect.

    However, MPC does not have this problem, like I mentioned above.

    Also, if you don't use a Renderer, but a file writer instead, then all frames
    will be written to the file. This is also true for both GraphEdit and my
    application which uses the DirectShow.NET library.

     
  • Peter Meier
    Peter Meier
    2012-02-15

    I found out that the problem doesn't happen in the C++ application found here:
    http://www.flipcode.com/archives/DirectShow_For_Media_Playback_In_Windows-
    Part_I_Basics.shtml

    When I created a WinForms C++/CLI app and copied the code from the main
    function into it, I was able to see the 1st frame, too.

    Could it be that GraphEdit was written in C# as well and that this is a
    general C# problem?

     
  • snarfle
    snarfle
    2012-02-16

    Umm. I can say, with a very high degree of confidence, that GraphEdt was NOT
    written in c# (or any .Net language).

    Also, while I cannot positively say that this behavior doesn't somehow stem
    from .Net, I will say that it seems unlikely. You have to understand that
    there is (almost) no executable code in the DS.Net library. It is (almost) all
    just definitions: Enums, Structs and Interfaces.

    Have you tried translating that exact c++ code into c#? If you want to compare
    behaviors, starting with the same code seems like a place to start.

     
  • Peter Meier
    Peter Meier
    2012-02-16

    Ok, it's good to hear that the DS.Net lib is unlikely to have anything to do
    with it. That way I can keep using C#. :-) Indeed I can see the first frame if
    I put a button in my GUI that does the following:

    private void buttonTest_Click(object sender, EventArgs e)
    {
    int hr;
    IGraphBuilder pGraphBuilder = (IGraphBuilder)new FilterGraph();
    IMediaControl pMediaControl;
    hr = pGraphBuilder.RenderFile("D:/Video/testvideoRgb24.avi", null);
    pMediaControl = pGraphBuilder as IMediaControl;
    hr = pMediaControl.Run();
    pMediaControl.Pause();
    }

    I guess I have to look through my code after all. When I saw GraphEdit had the
    same problem I just kind of assumed it had to do with DS. I'll post again once
    I know more.

    Thanks for the help! This forum would be dead without you.

     
  • Peter Meier
    Peter Meier
    2012-02-16

    Well, there seems to be a problem with the seeking function. Since the
    stop()-command doesn't rewind the graph I have to do it via a seek-call

    IMediaSeeking pMS = pGraphBuilder as IMediaSeeking;
    pMS.GetDuration(out length);
    pMS.SetPositions(0, AMSeekingSeekingFlags.AbsolutePositioning, length,
    AMSeekingSeekingFlags.AbsolutePositioning);

    and this is what causes my problem. This happens in C++ as well, when I use
    this code:

    System::Void Form1::buttonTest_Click(System::Object^ sender,
    System::EventArgs^ e)
    {
    HRESULT hr;
    IGraphBuilder pGraphBuilder;
    IMediaControl
    pMediaControl;
    IMediaSeeking* pMS;
    WCHAR MediaFile; // MAX_PATH is defined as 260 in WinDef.h
    LPSTR lpCmdLine = "D:/Video/testvideoRgb24.avi";
    MultiByteToWideChar(CP_ACP, 0, lpCmdLine, -1, MediaFile, MAX_PATH);

    // Creation of the graph, rendering and linking the control and seek
    interfaces to it.
    hr = CoCreateInstance(CLSID_FilterGraph, NULL, CLSCTX_ALL, IID_IGraphBuilder,
    (void)&pGraphBuilder);
    hr = pGraphBuilder->RenderFile(MediaFile, NULL);
    hr = pGraphBuilder->QueryInterface(IID_IMediaControl, (void
    )&pMediaControl);
    hr = pGraphBuilder->QueryInterface(IID_IMediaSeeking, (void**)&pMS);

    pMediaControl->Pause();

    // calling the seek function
    LONGLONG duration;
    LONGLONG start = 0;
    pMS->GetDuration(&duration);
    pMS->SetPositions(&start, 0, &duration, 0);

    Sleep(2000);
    pMediaControl->Stop();
    pMediaControl->Release();
    pGraphBuilder->Release();
    }

    So I guess it's because of the seeking-function. Am I using this function in a
    wrong manner or do I have to work around this problem?

     
  • snarfle
    snarfle
    2012-02-17

    While you can't ever say absolutely that .Net didn't introduce some behavior,
    that hasn't usually been my experience with DS .Net (.Net v4.0 being an
    exception). Glad to hear your observations bear this out.

    Looking at your c# code, I would probably do this as:

    pMS.SetPositions(0, AMSeekingSeekingFlags.AbsolutePositioning, 0, AMSeekingSeekingFlags.NoPositioning);
    

    It might also be interesting to experiment with the modifiers (NoFlush and
    ReturnTime).

    Looking at your c++ code, I wouldn't expect the SetPositions call to do
    anything. Isn't NoPositioning == 0? If you were going to be doing a c++
    solution, I'd probably have a few other comments about your Release calls.

     
  • Peter Meier
    Peter Meier
    2012-02-17

    Was .net 4.0 an exception in some parts that are important to the DS.NET lib?
    .net framework 4.0 is the most recent one and therefore I have it installed.
    If there's a serious problem I'm switching back to 3.5.

    The release-calls are part of the code from flipcode (see above) which was in
    a main function. I just copied it and made a few small changes where necessary
    in order to have a quick result. I didn't care at all whether or not I
    released anything properly.

    According to the documentation, "NoPositioning" means "don't change anything".
    But in fact, putting it into the stop position didn't give me a different
    behaviour. I then used

    int result = m_objMediaSeeking.SetPositions(lTime,
    AMSeekingSeekingFlags.AbsolutePositioning,
    0, AMSeekingSeekingFlags.NoPositioning | AMSeekingSeekingFlags.NoFlush);

    in order to test the flush function, but to no avail. Concerning Return_Time I
    have the problem that in the documentation it says that the time is being
    returned in one of the time parameters I pass to the function. But in C#
    they're not passed as pointers but as values.

     
  • Peter Meier
    Peter Meier
    2012-05-10

    I finally found the answer:
    It's Haali Media Splitter's fault. If I uninstall it, then I can see frame 0
    just fine. Probably MPC and Zoom Player use different source filters, while in
    GraphEdit Haali is my default one as well.