quartz/filtergraph: Implement IMediaControl state functions on top of IMediaFilter.
Signed-off-by: Zebediah Figura <z.figura12@gmail.com> Signed-off-by: Alexandre Julliard <julliard@winehq.org>
This commit is contained in:
parent
0c0606cd1b
commit
093a32ec7b
|
@ -2228,114 +2228,34 @@ static HRESULT SendFilterMessage(IFilterGraphImpl *This, fnFoundFilter FoundFilt
|
||||||
return S_FALSE;
|
return S_FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*** IMediaControl methods ***/
|
|
||||||
static HRESULT WINAPI MediaControl_Run(IMediaControl *iface)
|
static HRESULT WINAPI MediaControl_Run(IMediaControl *iface)
|
||||||
{
|
{
|
||||||
IFilterGraphImpl *This = impl_from_IMediaControl(iface);
|
IFilterGraphImpl *graph = impl_from_IMediaControl(iface);
|
||||||
|
|
||||||
TRACE("(%p/%p)->()\n", This, iface);
|
return IMediaFilter_Run(&graph->IMediaFilter_iface, 0);
|
||||||
|
|
||||||
EnterCriticalSection(&This->cs);
|
|
||||||
if (This->state == State_Running)
|
|
||||||
goto out;
|
|
||||||
This->EcCompleteCount = 0;
|
|
||||||
|
|
||||||
if (This->defaultclock && !This->refClock)
|
|
||||||
IFilterGraph2_SetDefaultSyncSource(&This->IFilterGraph2_iface);
|
|
||||||
|
|
||||||
if (This->refClock)
|
|
||||||
{
|
|
||||||
REFERENCE_TIME now;
|
|
||||||
IReferenceClock_GetTime(This->refClock, &now);
|
|
||||||
if (This->state == State_Stopped)
|
|
||||||
This->start_time = now + 500000;
|
|
||||||
else if (This->pause_time >= 0)
|
|
||||||
This->start_time += now - This->pause_time;
|
|
||||||
else
|
|
||||||
This->start_time = now;
|
|
||||||
}
|
|
||||||
else This->start_time = 0;
|
|
||||||
|
|
||||||
SendFilterMessage(This, SendRun, (DWORD_PTR)&This->start_time);
|
|
||||||
This->state = State_Running;
|
|
||||||
out:
|
|
||||||
LeaveCriticalSection(&This->cs);
|
|
||||||
return S_FALSE;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static HRESULT WINAPI MediaControl_Pause(IMediaControl *iface)
|
static HRESULT WINAPI MediaControl_Pause(IMediaControl *iface)
|
||||||
{
|
{
|
||||||
IFilterGraphImpl *This = impl_from_IMediaControl(iface);
|
IFilterGraphImpl *graph = impl_from_IMediaControl(iface);
|
||||||
|
|
||||||
TRACE("(%p/%p)->()\n", This, iface);
|
return IMediaFilter_Pause(&graph->IMediaFilter_iface);
|
||||||
|
|
||||||
EnterCriticalSection(&This->cs);
|
|
||||||
if (This->state == State_Paused)
|
|
||||||
goto out;
|
|
||||||
|
|
||||||
if (This->defaultclock && !This->refClock)
|
|
||||||
IFilterGraph2_SetDefaultSyncSource(&This->IFilterGraph2_iface);
|
|
||||||
|
|
||||||
if (This->state == State_Running && This->refClock && This->start_time >= 0)
|
|
||||||
IReferenceClock_GetTime(This->refClock, &This->pause_time);
|
|
||||||
else
|
|
||||||
This->pause_time = -1;
|
|
||||||
|
|
||||||
SendFilterMessage(This, SendPause, 0);
|
|
||||||
This->state = State_Paused;
|
|
||||||
out:
|
|
||||||
LeaveCriticalSection(&This->cs);
|
|
||||||
return S_FALSE;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static HRESULT WINAPI MediaControl_Stop(IMediaControl *iface)
|
static HRESULT WINAPI MediaControl_Stop(IMediaControl *iface)
|
||||||
{
|
{
|
||||||
IFilterGraphImpl *This = impl_from_IMediaControl(iface);
|
IFilterGraphImpl *graph = impl_from_IMediaControl(iface);
|
||||||
|
|
||||||
TRACE("(%p/%p)->()\n", This, iface);
|
return IMediaFilter_Stop(&graph->IMediaFilter_iface);
|
||||||
|
|
||||||
if (This->state == State_Stopped) return S_OK;
|
|
||||||
|
|
||||||
EnterCriticalSection(&This->cs);
|
|
||||||
if (This->state == State_Running) SendFilterMessage(This, SendPause, 0);
|
|
||||||
SendFilterMessage(This, SendStop, 0);
|
|
||||||
This->state = State_Stopped;
|
|
||||||
LeaveCriticalSection(&This->cs);
|
|
||||||
return S_OK;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static HRESULT WINAPI MediaControl_GetState(IMediaControl *iface, LONG msTimeout,
|
static HRESULT WINAPI MediaControl_GetState(IMediaControl *iface, LONG timeout, OAFilterState *state)
|
||||||
OAFilterState *pfs)
|
|
||||||
{
|
{
|
||||||
IFilterGraphImpl *This = impl_from_IMediaControl(iface);
|
IFilterGraphImpl *graph = impl_from_IMediaControl(iface);
|
||||||
DWORD end;
|
|
||||||
|
|
||||||
TRACE("(%p/%p)->(%d, %p)\n", This, iface, msTimeout, pfs);
|
if (timeout < 0) timeout = INFINITE;
|
||||||
|
|
||||||
if (!pfs)
|
return IMediaFilter_GetState(&graph->IMediaFilter_iface, timeout, (FILTER_STATE *)state);
|
||||||
return E_POINTER;
|
|
||||||
|
|
||||||
EnterCriticalSection(&This->cs);
|
|
||||||
|
|
||||||
*pfs = This->state;
|
|
||||||
if (msTimeout > 0)
|
|
||||||
{
|
|
||||||
end = GetTickCount() + msTimeout;
|
|
||||||
}
|
|
||||||
else if (msTimeout < 0)
|
|
||||||
{
|
|
||||||
end = INFINITE;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
end = 0;
|
|
||||||
}
|
|
||||||
if (end)
|
|
||||||
SendFilterMessage(This, SendGetState, end);
|
|
||||||
|
|
||||||
LeaveCriticalSection(&This->cs);
|
|
||||||
|
|
||||||
return S_OK;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static HRESULT WINAPI MediaControl_RenderFile(IMediaControl *iface, BSTR strFilename)
|
static HRESULT WINAPI MediaControl_RenderFile(IMediaControl *iface, BSTR strFilename)
|
||||||
|
@ -5454,34 +5374,119 @@ static HRESULT WINAPI MediaFilter_GetClassID(IMediaFilter *iface, CLSID * pClass
|
||||||
|
|
||||||
static HRESULT WINAPI MediaFilter_Stop(IMediaFilter *iface)
|
static HRESULT WINAPI MediaFilter_Stop(IMediaFilter *iface)
|
||||||
{
|
{
|
||||||
IFilterGraphImpl *This = impl_from_IMediaFilter(iface);
|
IFilterGraphImpl *graph = impl_from_IMediaFilter(iface);
|
||||||
|
|
||||||
return MediaControl_Stop(&This->IMediaControl_iface);
|
TRACE("graph %p.\n", graph);
|
||||||
|
|
||||||
|
EnterCriticalSection(&graph->cs);
|
||||||
|
|
||||||
|
if (graph->state == State_Stopped)
|
||||||
|
{
|
||||||
|
LeaveCriticalSection(&graph->cs);
|
||||||
|
return S_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (graph->state == State_Running)
|
||||||
|
SendFilterMessage(graph, SendPause, 0);
|
||||||
|
SendFilterMessage(graph, SendStop, 0);
|
||||||
|
graph->state = State_Stopped;
|
||||||
|
|
||||||
|
LeaveCriticalSection(&graph->cs);
|
||||||
|
return S_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
static HRESULT WINAPI MediaFilter_Pause(IMediaFilter *iface)
|
static HRESULT WINAPI MediaFilter_Pause(IMediaFilter *iface)
|
||||||
{
|
{
|
||||||
IFilterGraphImpl *This = impl_from_IMediaFilter(iface);
|
IFilterGraphImpl *graph = impl_from_IMediaFilter(iface);
|
||||||
|
|
||||||
return MediaControl_Pause(&This->IMediaControl_iface);
|
TRACE("graph %p.\n", graph);
|
||||||
|
|
||||||
|
EnterCriticalSection(&graph->cs);
|
||||||
|
|
||||||
|
if (graph->state == State_Paused)
|
||||||
|
{
|
||||||
|
LeaveCriticalSection(&graph->cs);
|
||||||
|
return S_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (graph->defaultclock && !graph->refClock)
|
||||||
|
IFilterGraph2_SetDefaultSyncSource(&graph->IFilterGraph2_iface);
|
||||||
|
|
||||||
|
if (graph->state == State_Running && graph->refClock && graph->start_time >= 0)
|
||||||
|
IReferenceClock_GetTime(graph->refClock, &graph->pause_time);
|
||||||
|
else
|
||||||
|
graph->pause_time = -1;
|
||||||
|
|
||||||
|
SendFilterMessage(graph, SendPause, 0);
|
||||||
|
graph->state = State_Paused;
|
||||||
|
|
||||||
|
LeaveCriticalSection(&graph->cs);
|
||||||
|
return S_FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
static HRESULT WINAPI MediaFilter_Run(IMediaFilter *iface, REFERENCE_TIME tStart)
|
static HRESULT WINAPI MediaFilter_Run(IMediaFilter *iface, REFERENCE_TIME start)
|
||||||
{
|
{
|
||||||
IFilterGraphImpl *This = impl_from_IMediaFilter(iface);
|
IFilterGraphImpl *graph = impl_from_IMediaFilter(iface);
|
||||||
|
|
||||||
if (tStart)
|
TRACE("graph %p, start %s.\n", graph, wine_dbgstr_longlong(start));
|
||||||
FIXME("Run called with non-null tStart: %s\n", wine_dbgstr_longlong(tStart));
|
|
||||||
|
|
||||||
return MediaControl_Run(&This->IMediaControl_iface);
|
EnterCriticalSection(&graph->cs);
|
||||||
|
|
||||||
|
if (graph->state == State_Running)
|
||||||
|
{
|
||||||
|
LeaveCriticalSection(&graph->cs);
|
||||||
|
return S_OK;
|
||||||
|
}
|
||||||
|
graph->EcCompleteCount = 0;
|
||||||
|
|
||||||
|
if (graph->defaultclock && !graph->refClock)
|
||||||
|
IFilterGraph2_SetDefaultSyncSource(&graph->IFilterGraph2_iface);
|
||||||
|
|
||||||
|
if (!start && graph->refClock)
|
||||||
|
{
|
||||||
|
REFERENCE_TIME now;
|
||||||
|
IReferenceClock_GetTime(graph->refClock, &now);
|
||||||
|
if (graph->state == State_Stopped)
|
||||||
|
graph->start_time = now + 500000;
|
||||||
|
else if (graph->pause_time >= 0)
|
||||||
|
graph->start_time += now - graph->pause_time;
|
||||||
|
else
|
||||||
|
graph->start_time = now;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
graph->start_time = start;
|
||||||
|
|
||||||
|
SendFilterMessage(graph, SendRun, (DWORD_PTR)&graph->start_time);
|
||||||
|
graph->state = State_Running;
|
||||||
|
|
||||||
|
LeaveCriticalSection(&graph->cs);
|
||||||
|
return S_FALSE;
|
||||||
}
|
}
|
||||||
|
|
||||||
static HRESULT WINAPI MediaFilter_GetState(IMediaFilter *iface, DWORD dwMsTimeout,
|
static HRESULT WINAPI MediaFilter_GetState(IMediaFilter *iface, DWORD timeout, FILTER_STATE *state)
|
||||||
FILTER_STATE *pState)
|
|
||||||
{
|
{
|
||||||
IFilterGraphImpl *This = impl_from_IMediaFilter(iface);
|
IFilterGraphImpl *graph = impl_from_IMediaFilter(iface);
|
||||||
|
DWORD end;
|
||||||
|
|
||||||
return MediaControl_GetState(&This->IMediaControl_iface, dwMsTimeout, (OAFilterState*)pState);
|
TRACE("graph %p, timeout %u, state %p.\n", graph, timeout, state);
|
||||||
|
|
||||||
|
if (!state)
|
||||||
|
return E_POINTER;
|
||||||
|
|
||||||
|
EnterCriticalSection(&graph->cs);
|
||||||
|
|
||||||
|
*state = graph->state;
|
||||||
|
if (timeout > 0)
|
||||||
|
end = GetTickCount() + timeout;
|
||||||
|
else if (timeout == INFINITE)
|
||||||
|
end = INFINITE;
|
||||||
|
else
|
||||||
|
end = 0;
|
||||||
|
if (end)
|
||||||
|
SendFilterMessage(graph, SendGetState, end);
|
||||||
|
|
||||||
|
LeaveCriticalSection(&graph->cs);
|
||||||
|
return S_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
static HRESULT WINAPI MediaFilter_SetSyncSource(IMediaFilter *iface, IReferenceClock *pClock)
|
static HRESULT WINAPI MediaFilter_SetSyncSource(IMediaFilter *iface, IReferenceClock *pClock)
|
||||||
|
|
|
@ -2698,10 +2698,8 @@ todo_wine
|
||||||
todo_wine
|
todo_wine
|
||||||
ok(hr == S_OK, "Got hr %#x.\n", hr);
|
ok(hr == S_OK, "Got hr %#x.\n", hr);
|
||||||
check_filter_state(graph, State_Running);
|
check_filter_state(graph, State_Running);
|
||||||
todo_wine {
|
|
||||||
ok(source.start_time == 0xdeadbeef, "Got time %s.\n", wine_dbgstr_longlong(source.start_time));
|
ok(source.start_time == 0xdeadbeef, "Got time %s.\n", wine_dbgstr_longlong(source.start_time));
|
||||||
ok(sink.start_time == 0xdeadbeef, "Got time %s.\n", wine_dbgstr_longlong(sink.start_time));
|
ok(sink.start_time == 0xdeadbeef, "Got time %s.\n", wine_dbgstr_longlong(sink.start_time));
|
||||||
}
|
|
||||||
|
|
||||||
hr = IMediaFilter_Pause(filter);
|
hr = IMediaFilter_Pause(filter);
|
||||||
todo_wine
|
todo_wine
|
||||||
|
|
Loading…
Reference in New Issue