Articles Technology Blog News Company

Basic graph editing

GraphEditPlus starts with an empty graph window open, you can open multiple such windows and work with several DirectShow graphs simultaneously. Each graph has is displayed and edited in its own window, but all of them work in one OS process.

This is a graph window with a simple DirectShow graph built:

DirectShow graph consists of nodes called filters and edges called connections. Each filter may have one or more pins and it's these pins that are really getting connected, each connection connects two pins. Pins on the left side of a filter's box are input pins, on the right side - output pins.

You can add filters to a graph in several ways: by double-clicking filters in Filters window on your left, or dragging them to a graph window, or by selecting some filter from Favorites menu, or by inserting some source filter for a file or URL, or by rendering some file or pin.

You can move filters around by dragging them with left mouse button pressed. GraphEditPlus will make sure filters don't overlap so they don't hide each other.

You can select a filter with a left click. If you hold Shift and click on more filters you can select several filters and move them together.

Left clicking on some empty space and dragging the mouse allows you to select several filters by a rectangle you draw this way.

Clicking on a filter brings information about this filter to the Properties window on your left. You'll see its name, category, CLSID, in what file it's implemented, information about this file (path, size, creation/modification dates etc.).

Press Del button to remove selected filter(s) from the graph.

Click a non-connected pin to see what media types it can accept (if it's an input pin) or can provide (for an output pin). List of media types is provided by the pin via IEnumMediaTypes interface, so it's not fixed nor stored anywhere in metadata, it's what this particular filter instance and its pin in their current state are willing to tell. This means list of media types for a filter's output pin might be different depending on what is connected to input pin of this filter.

There are two ways to connect two filters: direct connect and intelligent connect. The former connects two pins directly and fails if they don't agree to connect. Intelligent connect will try to insert some intermediate filters if the initial connecting pins refuse to connect directly. For example, if one filter produces some compressed video you cannot connect it directly to a video renderer (who needs uncompressed video), so direct connect will fail, however intelligent connect will try to find proper decoder and insert it to the graph.

To use intelligent connect use left mouse button to click one pin, then drag to the other pin and release the button. To use direct connect, do the same operation with right mouse button instead.

After a connection is established you can click on it to see what kind of data would flow through it: media type information will be displayed in the Properties window.

To disconnect two filters select a connection (by clicking it) and press Del button.

Running a graph

On the top of each graph window there are three buttons: Play, Pause and Stop. They correspond to Run(), Pause() and Stop() methods of IMediaControl interface exposed by the DirectShow graph object. Current graph state, as reported by IMediaControl::GetState(), is displayed as text near those buttons. Each filter of the graph has its own state and it's always shown in the filter's box as an icon.

The graph object also exposes IMediaSeeking interface and its method GetPositions() reports current position and total expected length of playback. These are shown in text near the graph state and position can be changed using seek bar on the top of graph window.

Turning clocks off an on:
by default each graph uses some reference clock (often provided by a renderer filter) and playback goes with normal speed. However via Options menu (in the main GraphEditPlus window) you can disable this clock by unchecking "Use clock in this graph". This equivalent to calling SetSyncSource(NULL) to the graph object (via IMediaFilter interface it exposes). With clock disabled renderers don't wait for the time to come to display next frame and show everything as fast as possible, so there are no artificial delays in the graph and the data flows as fast as it can be processed.

Operations via context menus

Right clicking on a filter, pin, or empty space in graph window brings corresponding context menus.

Graph operations:
  • Render file - select a file on your disk and use IGraphBuilder::RenderFile() to add necessary filters and build a graph automatically that plays this file.
  • Add source filter - select a file and call IGraphBuilder::AddSourceFilter() to add proper filter for reading this kind of file.
  • Load graph - select a .grf file from your disk and load it to this graph window.
  • Save graph (as) - save current graph to a .grf file.
  • See event log - open event log window and watch the graph events, see Watching graph event log.
  • Arrange filters - choose positions for filter boxes in the window automatically to display them in neatly ordered graph.
  • Refresh graph - re-scan the graph object to see if any new filters appeared or some filters changed their states and number of their pins.

Filter's context menu

 

 
  • Property page - show filter's propery page window if it exposes ISpecifyPropertyPages interface. Some filters allow to be configured this way.
  • Scan interfaces - show a list of DirectShow interfaces this filter exposes. See Scanning for interfaces.
  • Add to favorites - add this filter to global list of Favorites so that you can quickly add such filter to graphs in the future without having to search for it in the Filters window. Good for working with often needed filters like your camera or sample grabber.
  • Find this filter in the list - find and highlight this filter's entry in the Filters window on your left.
  • Save state to code - get current state (usually settings) of this filter and generate a chunk of C++ code for setting this state in your app. Available for filters exposing IPersistStream interface.
  • VfW compressor: Config - show configuration window for a Video-for-Windows codec.
  • VfW compressor: About - show About window for a Video-for-Windows codec.
  • Set media type - (only for Sample Grabber filter) set media type that Sample Grabber would prefer on its input pin. Use this when some decoder or camera can produce media in different formats and you want to select a particular one to pass downstream. See Using Sample Grabber.
  • Watch grabbed samples - show a special window where all samples going through this Sample Grabber instance will be logged with their info. See Using Sample Grabber.

Pin's context menu
  • Pin category - shows pin category (Capture / Preview / etc.) if the pin exposes it via IKsPropertySet interface.
  • Render pin - use IGraphBuilder::Render() to add and connect necessary filters to render this pin (display video or play audio).
  • Property page - show pin's property page window. Some filters (like cameras) can be configured through this window.
  • Scan interfaces - show what DirectShow interfaces this pin supports. See Scanning for interfaces.
  • Show matching filters - show list of filters that are expected to be able to connect to this pin. This is like one step of intelligent connect or pin rendering. See Displaying matching filters.
  • IAMStreamConfig::SetFormat - if the pin can provide media in different formats and supports IAMStreamConfig interface you select a particular format for it to produce.
  • IAMStreamConfig::GetStreamCaps - calls this method and shows the returned values in the Properties window on your left.
  • See allocator properties - for pins supporting IMemInputPin interface, show its allocator properties in the Properties window on your left.
  • See allocator requirements - same for the pins allocator requirements.