Microsoft DirectX 8.0

CSourceSeeking Class

CSourceSeeking class hierarchy

Abstract class for implementing seeking in source filters with one output pin.

Declaration: Ctlutil.h.

This class supports the IMediaSeeking interface. It provides default implementations for all of the IMediaSeeking methods. Protected member variables store the start time, stop time, and current rate. By default, the only time format supported by the class is TIME_FORMAT_MEDIA_TIME (100-nanosecond units).

Whenever the start position, stop position, or playback rate changes, the CSourceSeeking object calls a corresponding pure virtual method:

The derived class must implement these methods. After any seek operation, a filter must do the following:

  1. Call the IPin::BeginFlush method on the downstream input pin.
  2. Halt the worker thread that is delivering data.
  3. Call the IPin::EndFlush method on the input pin.
  4. Restart the worker thread.
  5. Call the IPin::NewSegment method on the input pin.
  6. Set the discontinuity property on the first sample. Call the IMediaSample::SetDiscontinuity method.

The call to BeginFlush frees the worker thread, if the thread is blocked waiting to deliver a sample.

In step 2, make sure that the thread has stopped sending data. Depending on the implementation, you might need to wait for the thread to exit, or for the thread to signal a response of some kind. If your filter uses the CSourceStream class, the CSourceStream::Stop method blocks until the worker thread replies.

Ideally, the new segment (step 5) should be delivered from the worker thread. It can also be done by the CSourceSeeking object, as long as the filter serializes it with the samples.

The following example shows a possible implementation. It assumes that the source filter's output pin is derived from CSourceSeeking and CSourceStream. This example defines a helper method, UpdateFromSeek, that performs steps 1–4. The CSourceStream::OnThreadStartPlay method is overridden to send the new segment, and to set a flag indicating the discontinuity. The worker thread picks up this flag and calls the IMediaSample::SetDiscontinuity method:

void CMyStream::UpdateFromSeek()
{
    if (ThreadExists()) 
    {
        DeliverBeginFlush();
        Stop();
        DeliverEndFlush();
        Run();
    }
}

HRESULT CMyStream::OnThreadStartPlay()
{
    m_bDiscontinuity = TRUE;
    return DeliverNewSegment(m_rtStart, m_rtStop, m_dRateSeeking);
}
Protected Member Variables
m_rtDurationDuration of the stream.
m_rtStartStart time.
m_rtStopStop time.
m_dRateSeekingPlayback rate.
m_dwSeekingCapsSeeking capabilities.
m_pLockPointer to a critical section object for locking.
Protected Methods
CSourceSeekingConstructor method.
Pure Virtual Methods
ChangeRateCalled when the playback rate changes.
ChangeStartCalled when the start position changes.
ChangeStopCalled when the stop position changes.
IMediaSeeking Methods
IsFormatSupportedDetermines whether a specified time format is supported.
QueryPreferredFormatRetrieves the object's preferred time format.
SetTimeFormatSets the time format.
IsUsingTimeFormatDetermines whether a specified time format is the format currently in use.
GetTimeFormatRetrieves the current time format.
GetDurationRetrieves the duration of the stream.
GetStopPositionRetrieves the time at which the playback will stop, relative to the duration of the stream.
GetCurrentPositionRetrieves the current position, relative to the total duration of the stream.
GetCapabilitiesRetrieves all the seeking capabilities of the stream.
CheckCapabilitiesQueries whether the stream has specified seeking capabilities.
ConvertTimeFormatConverts from one time format to another.
SetPositionsSets the current position and the stop position.
GetPositionsRetrieves the current position and the stop position.
GetAvailableRetrieves the range of times in which seeking is efficient.
SetRateSets the playback rate.
GetRateRetrieves the playback rate.
GetPrerollRetrieves the preroll time.

CSourceSeeking.m_rtDuration

CSourceSeeking Class

Duration of the stream. By default, the value is set to the value of the m_rtStop member variable.

Syntax

CRefTime m_rtDuration;

CSourceSeeking.m_rtStart

CSourceSeeking Class

Start time. By default, the value is set to zero.

Syntax

CRefTime m_rtStart;

CSourceSeeking.m_rtStop

CSourceSeeking Class

Stop time. By default, the value is set to a very large number. The derived class can reset the value in its constructor, or when the filter is initialized.

Syntax

CRefTime m_rtStop;

CSourceSeeking.m_dRateSeeking

CSourceSeeking Class

Playback rate. By default, the value is set to 1.0.

Syntax

double m_dRateSeeking;

CSourceSeeking.m_dwSeekingCaps

CSourceSeeking Class

Seeking capabilities.

Syntax

DWORD m_dwSeekingCaps;

Remarks

By default, the value is set to the bitwise combination of the following flags:

If the filter supports a different set of capabilities, it should override this value.

CSourceSeeking.m_pLock

CSourceSeeking Class

Pointer to a critical section object for locking.

Syntax

CCritSec *m_pLock;

CSourceSeeking::ChangeRate

CSourceSeeking Class

Called when the playback rate changes.

Syntax

virtual HRESULT ChangeRate(void) PURE;

Return Value

Returns an HRESULT value.

Remarks

The SetRate method calls this method, which the derived class must implement. The SetRate method updates the m_dRateSeeking member variable, but does not validate the new value. A rate of zero should always be rejected. Rates less than zero indicate negative playback. Most filters do not support negative rates.

The following example shows a possible implementation:

HRESULT CMyStream::ChangeRate( )
{
    {
        CAutoLock cAutoLockSeeking(CSourceSeeking::m_pLock);
        if( m_dRateSeeking <= 0 ) {
            m_dRateSeeking = 1.0;  // Reset to a reasonable value.
            return E_FAIL;
        }
    }
    UpdateFromSeek();
    return S_OK;
}

CSourceSeeking::ChangeStart

CSourceSeeking Class

Called when the start position changes.

Syntax

virtual HRESULT ChangeStart(void) PURE;

Return Value

Returns an HRESULT value.

Remarks

The SetPositions method calls this method if the start position changes. This method is pure virtual; the derived class must implement it. After a seek operation, time stamps should restart from zero. Media times should reflect the new start time. The following example shows a possible implementation:

HRESULT CMyStream::ChangeStart( )
{
    m_rtSampleTime = 0;          // Reset the time stamps.
    m_rtMediaTime = m_rtStart;   // Reset the media times.
    UpdateFromSeek();
    return S_OK;
}

CSourceSeeking::ChangeStop

CSourceSeeking Class

Called when the stop position changes.

Syntax

virtual HRESULT ChangeStop(void) PURE;

Return Value

Returns an HRESULT value.

Remarks

The SetPositions method calls this method if the stop position changes. This method is pure virtual; the derived class must implement it. The following example shows a possible implementation:

HRESULT CMyStream::ChangeStop( )
{
    UpdateFromSeek();
    return S_OK;
}

CSourceSeeking::CheckCapabilities

CSourceSeeking Class

Queries whether the stream has specified seeking capabilities. Implements the IMediaSeeking::CheckCapabilities method.

Syntax

HRESULT CheckCapabilities(
    DWORD *pCapabilities
);

Parameters

pCapabilities
Pointer to a bitwise combination of one or more AM_SEEKING_SEEKING_CAPABILITIES attributes.

Return Value

Returns one of the HRESULT values listed in the following table.

S_FALSENot all of the capabilities in pCapabilities are present.
S_OKAll capabilities in pCapabilities are present.
E_POINTERNULL pointer argument.

Remarks

As implemented, this method checks the value of *pCapabilities against the m_dwSeekingCaps member variable. However, it does not set *pCapabilities equal to m_dwSeekingCaps, as described for the IMediaSeeking::CheckCapabilities method. Also, in the case where none of the specified capabilities are available, the method does not return E_FAIL. A more complete implementation would be as follows:

DWORD dwCaps;
HRESULT hr = GetCapabilities(&dwCaps);
if (SUCCEEDED(hr))
{
    dwCaps &= *pCapabilities;
    hr =  dwCaps ? ( dwCaps == *pCapabilities ? S_OK : S_FALSE ) : E_FAIL;
    *pCapabilities = dwCaps;
}
else *pCapabilities = 0;
return hr;

CSourceSeeking::ConvertTimeFormat

CSourceSeeking Class

Converts from one time format to another. Implements the IMediaSeeking::ConvertTimeFormat method.

Syntax

HRESULT ConvertTimeFormat(
    LONGLONG *pTarget,
    const GUID *pTargetFormat,
    LONGLONG Source,
    const GUID *pSourceFormat
);

Parameters

pTarget
Pointer to a variable that receives the converted time.
pTargetFormat
Pointer to the time format GUID of the target format. If NULL, the current format is used.
Source
Time value to be converted.
pSourceFormat
Pointer to the time format GUID of the format to convert. If NULL, the current format is used.

Return Value

Returns one of the HRESULT values listed in the following table.

S_OKSuccess
E_INVALIDARGInvalid argument
E_POINTERNULL pointer argument

Remarks

The only time format supported by the base class is TIME_FORMAT_MEDIA_TIME (100-nanosecond units). This method returns E_INVALIDARG, except in the trivial case where pTargetFormat and pSourceFormat both specify TIME_FORMAT_MEDIA_TIME.

CSourceSeeking::CSourceSeeking

CSourceSeeking Class

Constructor method.

Syntax

CSourceSeeking(
    const TCHAR *pName,
    LPUNKNOWN pUnk,
    HRESULT *phr,
    CCritSec *pLock
);

Parameters

pName
Pointer to a string containing the name of the object. For more information, see CBaseObject.
pUnk
Pointer to the owner of this object. If the object is aggregated, pass a pointer to the aggregating object's IUnknown interface. Otherwise, set this parameter to NULL.
phr
Pointer to an HRESULT value. Ignored.
pLock
Pointer to a CCritSec object that protects shared data used by this class.

CSourceSeeking::GetAvailable

CSourceSeeking Class

Retrieves the range of times in which seeking is efficient. Implements the IMediaSeeking::GetAvailable method.

Syntax

HRESULT GetAvailable(
    LONGLONG *pEarliest,
    LONGLONG *pLatest
);

Parameters

pEarliest
Pointer to a variable that receives the earliest time for efficient seeking. The variable is set to zero.
pLatest
Pointer to a variable that receives the latest time for efficient seeking. The variable is set to the value of the m_rtDuration member variable.

Return Value

Returns S_OK.

CSourceSeeking::GetCapabilities

CSourceSeeking Class

Retrieves all the seeking capabilities of the stream. Implements the IMediaSeeking::GetCapabilities method.

Syntax

HRESULT GetCapabilities(
    DWORD *pCapabilities
);

Parameters

pCapabilities
Pointer to a variable that receives a bitwise combination of AM_SEEKING_SEEKING_CAPABILITIES flags.

Return Value

Returns one of the HRESULT values listed in the following table.

S_OKSuccess
E_POINTERNULL pointer value

Remarks

The seeking capabilities are specified by the m_dwSeekingCaps member variable.

CSourceSeeking::GetCurrentPosition

CSourceSeeking Class

Retrieves the current position, relative to the total duration of the stream. Not implemented.

Syntax

HRESULT GetCurrentPosition(
  LONGLONG *pCurrent
);

Parameters

pCurrent
Pointer to a variable that receives the current position, in units of the current time format.

Return Value

Returns E_NOTIMPL.

Remarks

Source filters typically do not support this method. Instead, renderer filters report the current position through the CRendererPosPassThru class.

CSourceSeeking::GetDuration

CSourceSeeking Class

Retrieves the duration of the stream. Implements the IMediaSeeking::GetDuration method.

Syntax

HRESULT GetDuration(
    LONGLONG *pDuration
);

Parameters

pDuration
Pointer to a variable that receives the duration, in units of the current time format.

Return Value

Returns one of the HRESULT values listed in the following table.

S_OKSuccess
E_POINTERNULL pointer value

Remarks

The duration is specified by the m_rtDuration member variable.

CSourceSeeking::GetPositions

CSourceSeeking Class

Retrieves the current position and the stop position. Implements the IMediaSeeking::GetPositions method.

Syntax

HRESULT GetPositions(
    LONGLONG *pCurrent,
    LONGLONG *pStop
);

Parameters

pCurrent
Pointer to a variable that receives the start position.
pStop
Pointer to a variable that receives the stop position.

Return Value

Returns S_OK.

Remarks

For the pCurrent parameter, this method returns the value of the m_rtStart member variable, which represents the latest seek time, not the current streaming position. However, when an application calls IMediaSeeking::GetPositions through the filter graph manager, the values typically come from a renderer filter, not a source filter.

CSourceSeeking::GetPreroll

CSourceSeeking Class

Retrieves the preroll time. Implements the IMediaSeeking::GetPreroll method.

Syntax

HRESULT GetPreroll(
    LONGLONG *pPreroll
);

Parameters

pPreroll
Pointer to a variable that receives the preroll time. The value is set to zero.

Return Value

Returns one of the HRESULT values listed in the following table.

S_OKSuccess
E_POINTERNULL pointer value

CSourceSeeking::GetRate

CSourceSeeking Class

Retrieves the playback rate. Implements the IMediaSeeking::GetRate method.

Syntax

HRESULT GetRate(
    double *pdRate
);

Parameters

pdRate
Pointer to a variable that receives the playback rate.

Return Value

Returns one of the HRESULT values listed in the following table.

S_OKSuccess
E_POINTERNULL pointer value

Remarks

The playback rate is specified by the m_dRateSeeking member variable.

CSourceSeeking::GetStopPosition

CSourceSeeking Class

Retrieves the time at which the playback will stop, relative to the duration of the stream. Implements the IMediaSeeking::GetStopPosition method.

Syntax

HRESULT GetStopPosition(
    LONGLONG *pStop
);

Parameters

pStop
Pointer to a variable that receives the stop time, in units of the current time format.

Return Value

Returns one of the HRESULT values listed in the following table.

S_OKSuccess
E_POINTERNULL pointer value

Remarks

The stop time is specified by the m_rtStop member variable.

CSourceSeeking::GetTimeFormat

CSourceSeeking Class

Retrieves the current time format. Implements the IMediaSeeking::GetTimeFormat method.

Syntax

HRESULT GetTimeFormat(
    const GUID *pFormat
);

Parameters

pFormat
Pointer to a variable that receives a time format GUID.

Return Value

Returns one of the HRESULT values listed in the following table.

S_OKSuccess
E_POINTERNULL pointer value

Remarks

The only time format supported by the base class is TIME_FORMAT_MEDIA_TIME (100-nanosecond units).

CSourceSeeking::IsFormatSupported

CSourceSeeking Class

Determines whether a specified time format is supported. Implements the IMediaSeeking::IsFormatSupported method.

Syntax

HRESULT IsFormatSupported(
    const GUID *pFormat
);

Parameters

pFormat
Pointer to a time format GUID.

Return Value

Returns one of the HRESULT values listed in the following table.

S_FALSEThe format is not supported.
S_OKThe format is supported.
E_POINTERNULL pointer argument.

Remarks

The only time format supported by the base class is TIME_FORMAT_MEDIA_TIME (100-nanosecond units).

CSourceSeeking::IsUsingTimeFormat

CSourceSeeking Class

Determines whether a specified time format is the format currently in use.

Syntax

HRESULT IsUsingTimeFormat(
    const GUID *pFormat
);

Parameters

pFormat
Pointer to a time format GUID.

Return Value

Returns one of the HRESULT values listed in the following table.

S_FALSEThe specified format is not the current format.
S_OKThe specified format is the current format.
E_POINTERNULL pointer argument.

Remarks

The only time format supported by the base class is TIME_FORMAT_MEDIA_TIME (100-nanosecond units).

CSourceSeeking::QueryPreferredFormat

CSourceSeeking Class

Retrieves the object's preferred time format. Implements the IMediaSeeking::QueryPreferredFormat method.

Syntax

HRESULT QueryPreferredFormat(
    GUID *pFormat
);

Parameters

pFormat
Pointer to a variable that receives a time format GUID.

Return Value

Returns one of the HRESULT values listed in the following table.

S_OKSuccess
E_POINTERNULL pointer value

Remarks

The only time format supported by the base class is TIME_FORMAT_MEDIA_TIME (100-nanosecond units).

CSourceSeeking::SetPositions

CSourceSeeking Class

Sets the current position and the stop position. Implements the IMediaSeeking::SetPositions method.

Syntax

HRESULT SetPositions(
    LONGLONG *pCurrent,
    DWORD CurrentFlags,
    LONGLONG *pStop,
    DWORD StopFlags
);

Parameters

pCurrent
Pointer to a variable that specifies the current position.
CurrentFlags
Bitwise combination of flags. See Remarks.
pStop
Pointer to a variable that specifies the stop time, in units of the current time format.
StopFlags
Bitwise combination of flags. See Remarks.

Return Value

Returns an HRESULT value. Possible values include those listed in the following table.

S_OKSuccess
E_INVALIDARGInvalid flags
E_POINTERNULL pointer argument

Remarks

The following flags are supported:

For more information, see IMediaSeeking::SetPositions.

This method updates the values of the m_rtStart and m_rtStop member variables, and then calls the pure virtual methods ChangeStart and ChangeStop.

CSourceSeeking::SetRate

CSourceSeeking Class

Sets the playback rate. Implements the IMediaSeeking::SetRate method.

Syntax

HRESULT SetRate(
    double dRate
);

Parameters

dRate
Playback rate.

Return Value

Returns an HRESULT value.

Remarks

This method updates the value of the m_dRateSeeking member variable, and then calls the pure virtual method ChangeRate. The method does not validate the dRate parameter.

CSourceSeeking::SetTimeFormat

CSourceSeeking Class

Sets the time format. Implements the IMediaSeeking::SetTimeFormat method.

Syntax

HRESULT SetTimeFormat(
    const GUID *pFormat
);

Parameters

pFormat
Pointer to a time format GUID.

Return Value

Returns one of the HRESULT values listed in the following table.

S_OKSuccess.
E_INVALIDARGSpecified format is not supported.
E_POINTERNULL pointer argument.

Remarks

The only time format supported by the base class is TIME_FORMAT_MEDIA_TIME (100-nanosecond units).