Home | Info | Community | Development | myReactOS | Contact Us
ReactOS Development > Doxygencontrol.c
Go to the documentation of this file.
00001 /* 00002 * Filter Seeking and Control Interfaces 00003 * 00004 * Copyright 2003 Robert Shearman 00005 * 00006 * This library is free software; you can redistribute it and/or 00007 * modify it under the terms of the GNU Lesser General Public 00008 * License as published by the Free Software Foundation; either 00009 * version 2.1 of the License, or (at your option) any later version. 00010 * 00011 * This library is distributed in the hope that it will be useful, 00012 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00013 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 00014 * Lesser General Public License for more details. 00015 * 00016 * You should have received a copy of the GNU Lesser General Public 00017 * License along with this library; if not, write to the Free Software 00018 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA 00019 */ 00020 /* FIXME: critical sections */ 00021 00022 #include "quartz_private.h" 00023 #include "control_private.h" 00024 00025 #include "uuids.h" 00026 #include "wine/debug.h" 00027 00028 #include <assert.h> 00029 00030 WINE_DEFAULT_DEBUG_CHANNEL(quartz); 00031 00032 static const IMediaSeekingVtbl IMediaSeekingPassThru_Vtbl; 00033 00034 typedef struct PassThruImpl { 00035 const ISeekingPassThruVtbl *IPassThru_vtbl; 00036 const IUnknownVtbl *IInner_vtbl; 00037 const IMediaSeekingVtbl *IMediaSeeking_vtbl; 00038 00039 LONG ref; 00040 IUnknown * pUnkOuter; 00041 IPin * pin; 00042 BOOL bUnkOuterValid; 00043 BOOL bAggregatable; 00044 BOOL renderer; 00045 } PassThruImpl; 00046 00047 static HRESULT WINAPI SeekInner_QueryInterface(IUnknown * iface, 00048 REFIID riid, 00049 LPVOID *ppvObj) { 00050 ICOM_THIS_MULTI(PassThruImpl, IInner_vtbl, iface); 00051 TRACE("(%p)->(%s (%p), %p)\n", This, debugstr_guid(riid), riid, ppvObj); 00052 00053 if (This->bAggregatable) 00054 This->bUnkOuterValid = TRUE; 00055 00056 if (IsEqualGUID(&IID_IUnknown, riid)) 00057 { 00058 *ppvObj = &(This->IInner_vtbl); 00059 TRACE(" returning IUnknown interface (%p)\n", *ppvObj); 00060 } else if (IsEqualGUID(&IID_ISeekingPassThru, riid)) { 00061 *ppvObj = &(This->IPassThru_vtbl); 00062 TRACE(" returning ISeekingPassThru interface (%p)\n", *ppvObj); 00063 } else if (IsEqualGUID(&IID_IMediaSeeking, riid)) { 00064 *ppvObj = &(This->IMediaSeeking_vtbl); 00065 TRACE(" returning IMediaSeeking interface (%p)\n", *ppvObj); 00066 } else { 00067 *ppvObj = NULL; 00068 FIXME("unknown interface %s\n", debugstr_guid(riid)); 00069 return E_NOINTERFACE; 00070 } 00071 00072 IUnknown_AddRef((IUnknown *)(*ppvObj)); 00073 return S_OK; 00074 } 00075 00076 static ULONG WINAPI SeekInner_AddRef(IUnknown * iface) { 00077 ICOM_THIS_MULTI(PassThruImpl, IInner_vtbl, iface); 00078 ULONG ref = InterlockedIncrement(&This->ref); 00079 00080 TRACE("(%p)->(): new ref = %d\n", This, ref); 00081 00082 return ref; 00083 } 00084 00085 static ULONG WINAPI SeekInner_Release(IUnknown * iface) { 00086 ICOM_THIS_MULTI(PassThruImpl, IInner_vtbl, iface); 00087 ULONG ref = InterlockedDecrement(&This->ref); 00088 00089 TRACE("(%p)->(): new ref = %d\n", This, ref); 00090 00091 if (ref == 0) 00092 { 00093 CoTaskMemFree(This); 00094 } 00095 return ref; 00096 } 00097 00098 static const IUnknownVtbl IInner_VTable = 00099 { 00100 SeekInner_QueryInterface, 00101 SeekInner_AddRef, 00102 SeekInner_Release 00103 }; 00104 00105 /* Generic functions for aggregation */ 00106 static HRESULT SeekOuter_QueryInterface(PassThruImpl *This, REFIID riid, LPVOID *ppv) 00107 { 00108 if (This->bAggregatable) 00109 This->bUnkOuterValid = TRUE; 00110 00111 if (This->pUnkOuter) 00112 { 00113 if (This->bAggregatable) 00114 return IUnknown_QueryInterface(This->pUnkOuter, riid, ppv); 00115 00116 if (IsEqualIID(riid, &IID_IUnknown)) 00117 { 00118 HRESULT hr; 00119 00120 IUnknown_AddRef((IUnknown *)&(This->IInner_vtbl)); 00121 hr = IUnknown_QueryInterface((IUnknown *)&(This->IInner_vtbl), riid, ppv); 00122 IUnknown_Release((IUnknown *)&(This->IInner_vtbl)); 00123 This->bAggregatable = TRUE; 00124 return hr; 00125 } 00126 00127 *ppv = NULL; 00128 return E_NOINTERFACE; 00129 } 00130 00131 return IUnknown_QueryInterface((IUnknown *)&(This->IInner_vtbl), riid, ppv); 00132 } 00133 00134 static ULONG SeekOuter_AddRef(PassThruImpl *This) 00135 { 00136 if (This->pUnkOuter && This->bUnkOuterValid) 00137 return IUnknown_AddRef(This->pUnkOuter); 00138 return IUnknown_AddRef((IUnknown *)&(This->IInner_vtbl)); 00139 } 00140 00141 static ULONG SeekOuter_Release(PassThruImpl *This) 00142 { 00143 if (This->pUnkOuter && This->bUnkOuterValid) 00144 return IUnknown_Release(This->pUnkOuter); 00145 return IUnknown_Release((IUnknown *)&(This->IInner_vtbl)); 00146 } 00147 00148 static HRESULT WINAPI SeekingPassThru_QueryInterface(ISeekingPassThru *iface, REFIID riid, LPVOID *ppvObj) 00149 { 00150 ICOM_THIS_MULTI(PassThruImpl, IPassThru_vtbl, iface); 00151 00152 TRACE("(%p/%p)->(%s (%p), %p)\n", This, iface, debugstr_guid(riid), riid, ppvObj); 00153 00154 return SeekOuter_QueryInterface(This, riid, ppvObj); 00155 } 00156 00157 static ULONG WINAPI SeekingPassThru_AddRef(ISeekingPassThru *iface) 00158 { 00159 ICOM_THIS_MULTI(PassThruImpl, IPassThru_vtbl, iface); 00160 00161 TRACE("(%p/%p)->()\n", This, iface); 00162 00163 return SeekOuter_AddRef(This); 00164 } 00165 00166 static ULONG WINAPI SeekingPassThru_Release(ISeekingPassThru *iface) 00167 { 00168 ICOM_THIS_MULTI(PassThruImpl, IPassThru_vtbl, iface); 00169 00170 TRACE("(%p/%p)->()\n", This, iface); 00171 00172 return SeekOuter_Release(This); 00173 } 00174 00175 static HRESULT WINAPI SeekingPassThru_Init(ISeekingPassThru *iface, BOOL renderer, IPin *pin) 00176 { 00177 ICOM_THIS_MULTI(PassThruImpl, IPassThru_vtbl, iface); 00178 00179 TRACE("(%p/%p)->(%d, %p)\n", This, iface, renderer, pin); 00180 00181 if (This->pin) 00182 FIXME("Re-initializing?\n"); 00183 00184 This->renderer = renderer; 00185 This->pin = pin; 00186 00187 return S_OK; 00188 } 00189 00190 static const ISeekingPassThruVtbl ISeekingPassThru_Vtbl = 00191 { 00192 SeekingPassThru_QueryInterface, 00193 SeekingPassThru_AddRef, 00194 SeekingPassThru_Release, 00195 SeekingPassThru_Init 00196 }; 00197 00198 HRESULT SeekingPassThru_create(IUnknown *pUnkOuter, LPVOID *ppObj) 00199 { 00200 PassThruImpl *fimpl; 00201 00202 TRACE("(%p,%p)\n", pUnkOuter, ppObj); 00203 00204 *ppObj = fimpl = CoTaskMemAlloc(sizeof(*fimpl)); 00205 if (!fimpl) 00206 return E_OUTOFMEMORY; 00207 00208 fimpl->pUnkOuter = pUnkOuter; 00209 fimpl->bUnkOuterValid = FALSE; 00210 fimpl->bAggregatable = FALSE; 00211 fimpl->IInner_vtbl = &IInner_VTable; 00212 fimpl->IPassThru_vtbl = &ISeekingPassThru_Vtbl; 00213 fimpl->IMediaSeeking_vtbl = &IMediaSeekingPassThru_Vtbl; 00214 fimpl->ref = 1; 00215 fimpl->pin = NULL; 00216 return S_OK; 00217 } 00218 00219 typedef HRESULT (*SeekFunc)( IMediaSeeking *to, LPVOID arg ); 00220 00221 static HRESULT ForwardCmdSeek( PCRITICAL_SECTION crit_sect, IBaseFilter* from, SeekFunc fnSeek, LPVOID arg ) 00222 { 00223 HRESULT hr = S_OK; 00224 HRESULT hr_return = S_OK; 00225 IEnumPins *enumpins = NULL; 00226 BOOL foundend = FALSE, allnotimpl = TRUE; 00227 00228 hr = IBaseFilter_EnumPins( from, &enumpins ); 00229 if (FAILED(hr)) 00230 goto out; 00231 00232 hr = IEnumPins_Reset( enumpins ); 00233 while (hr == S_OK) { 00234 IPin *pin = NULL; 00235 hr = IEnumPins_Next( enumpins, 1, &pin, NULL ); 00236 if (hr == VFW_E_ENUM_OUT_OF_SYNC) 00237 { 00238 hr = IEnumPins_Reset( enumpins ); 00239 continue; 00240 } 00241 if (pin) 00242 { 00243 PIN_DIRECTION dir; 00244 00245 IPin_QueryDirection( pin, &dir ); 00246 if (dir == PINDIR_INPUT) 00247 { 00248 IPin *connected = NULL; 00249 00250 IPin_ConnectedTo( pin, &connected ); 00251 if (connected) 00252 { 00253 HRESULT hr_local; 00254 IMediaSeeking *seek = NULL; 00255 00256 hr_local = IPin_QueryInterface( connected, &IID_IMediaSeeking, (void**)&seek ); 00257 if (hr_local == S_OK) 00258 { 00259 foundend = TRUE; 00260 if (crit_sect) 00261 { 00262 LeaveCriticalSection( crit_sect ); 00263 hr_local = fnSeek( seek , arg ); 00264 EnterCriticalSection( crit_sect ); 00265 } 00266 else 00267 hr_local = fnSeek( seek , arg ); 00268 00269 if (hr_local != E_NOTIMPL) 00270 allnotimpl = FALSE; 00271 00272 hr_return = updatehres( hr_return, hr_local ); 00273 IMediaSeeking_Release( seek ); 00274 } 00275 IPin_Release(connected); 00276 } 00277 } 00278 IPin_Release( pin ); 00279 } 00280 } 00281 IEnumPins_Release( enumpins ); 00282 00283 if (foundend && allnotimpl) 00284 hr = E_NOTIMPL; 00285 else 00286 hr = hr_return; 00287 00288 out: 00289 TRACE("Returning: %08x\n", hr); 00290 return hr; 00291 } 00292 00293 00294 HRESULT MediaSeekingImpl_Init(IBaseFilter *pUserData, CHANGEPROC fnChangeStop, CHANGEPROC fnChangeCurrent, CHANGEPROC fnChangeRate, MediaSeekingImpl * pSeeking, PCRITICAL_SECTION crit_sect) 00295 { 00296 assert(fnChangeStop && fnChangeCurrent && fnChangeRate); 00297 00298 pSeeking->refCount = 1; 00299 pSeeking->pUserData = pUserData; 00300 pSeeking->fnChangeRate = fnChangeRate; 00301 pSeeking->fnChangeStop = fnChangeStop; 00302 pSeeking->fnChangeCurrent = fnChangeCurrent; 00303 pSeeking->dwCapabilities = AM_SEEKING_CanSeekForwards | 00304 AM_SEEKING_CanSeekBackwards | 00305 AM_SEEKING_CanSeekAbsolute | 00306 AM_SEEKING_CanGetStopPos | 00307 AM_SEEKING_CanGetDuration; 00308 pSeeking->llCurrent = 0; 00309 pSeeking->llStop = ((ULONGLONG)0x80000000) << 32; 00310 pSeeking->llDuration = pSeeking->llStop; 00311 pSeeking->dRate = 1.0; 00312 pSeeking->timeformat = TIME_FORMAT_MEDIA_TIME; 00313 pSeeking->crst = crit_sect; 00314 00315 return S_OK; 00316 } 00317 00318 struct pos_args { 00319 LONGLONG* current, *stop; 00320 DWORD curflags, stopflags; 00321 }; 00322 00323 static HRESULT fwd_setposition(IMediaSeeking *seek, LPVOID pargs) 00324 { 00325 struct pos_args *args = (void*)pargs; 00326 00327 return IMediaSeeking_SetPositions(seek, args->current, args->curflags, args->stop, args->stopflags); 00328 } 00329 00330 static HRESULT fwd_checkcaps(IMediaSeeking *iface, LPVOID pcaps) 00331 { 00332 DWORD *caps = pcaps; 00333 return IMediaSeeking_CheckCapabilities(iface, caps); 00334 } 00335 00336 static HRESULT fwd_settimeformat(IMediaSeeking *iface, LPVOID pformat) 00337 { 00338 const GUID *format = pformat; 00339 return IMediaSeeking_SetTimeFormat(iface, format); 00340 } 00341 00342 static HRESULT fwd_getduration(IMediaSeeking *iface, LPVOID pdur) 00343 { 00344 LONGLONG *duration = pdur; 00345 LONGLONG mydur = *duration; 00346 HRESULT hr; 00347 00348 hr = IMediaSeeking_GetDuration(iface, &mydur); 00349 if (FAILED(hr)) 00350 return hr; 00351 00352 if ((mydur < *duration) || (*duration < 0 && mydur > 0)) 00353 *duration = mydur; 00354 return hr; 00355 } 00356 00357 static HRESULT fwd_getstopposition(IMediaSeeking *iface, LPVOID pdur) 00358 { 00359 LONGLONG *duration = pdur; 00360 LONGLONG mydur = *duration; 00361 HRESULT hr; 00362 00363 hr = IMediaSeeking_GetStopPosition(iface, &mydur); 00364 if (FAILED(hr)) 00365 return hr; 00366 00367 if ((mydur < *duration) || (*duration < 0 && mydur > 0)) 00368 *duration = mydur; 00369 return hr; 00370 } 00371 00372 static HRESULT fwd_getcurposition(IMediaSeeking *iface, LPVOID pdur) 00373 { 00374 LONGLONG *duration = pdur; 00375 LONGLONG mydur = *duration; 00376 HRESULT hr; 00377 00378 hr = IMediaSeeking_GetCurrentPosition(iface, &mydur); 00379 if (FAILED(hr)) 00380 return hr; 00381 00382 if ((mydur < *duration) || (*duration < 0 && mydur > 0)) 00383 *duration = mydur; 00384 return hr; 00385 } 00386 00387 static HRESULT fwd_setrate(IMediaSeeking *iface, LPVOID prate) 00388 { 00389 double *rate = prate; 00390 00391 HRESULT hr; 00392 00393 hr = IMediaSeeking_SetRate(iface, *rate); 00394 if (FAILED(hr)) 00395 return hr; 00396 00397 return hr; 00398 } 00399 00400 00401 HRESULT WINAPI MediaSeekingImpl_GetCapabilities(IMediaSeeking * iface, DWORD * pCapabilities) 00402 { 00403 MediaSeekingImpl *This = (MediaSeekingImpl *)iface; 00404 00405 TRACE("(%p)\n", pCapabilities); 00406 00407 *pCapabilities = This->dwCapabilities; 00408 00409 return S_OK; 00410 } 00411 00412 HRESULT WINAPI MediaSeekingImpl_CheckCapabilities(IMediaSeeking * iface, DWORD * pCapabilities) 00413 { 00414 MediaSeekingImpl *This = (MediaSeekingImpl *)iface; 00415 HRESULT hr; 00416 DWORD dwCommonCaps; 00417 00418 TRACE("(%p)\n", pCapabilities); 00419 00420 if (!pCapabilities) 00421 return E_POINTER; 00422 00423 EnterCriticalSection(This->crst); 00424 hr = ForwardCmdSeek(This->crst, This->pUserData, fwd_checkcaps, pCapabilities); 00425 LeaveCriticalSection(This->crst); 00426 if (FAILED(hr) && hr != E_NOTIMPL) 00427 return hr; 00428 00429 dwCommonCaps = *pCapabilities & This->dwCapabilities; 00430 00431 if (!dwCommonCaps) 00432 hr = E_FAIL; 00433 else 00434 hr = (*pCapabilities == dwCommonCaps) ? S_OK : S_FALSE; 00435 *pCapabilities = dwCommonCaps; 00436 00437 return hr; 00438 } 00439 00440 HRESULT WINAPI MediaSeekingImpl_IsFormatSupported(IMediaSeeking * iface, const GUID * pFormat) 00441 { 00442 TRACE("(%s)\n", qzdebugstr_guid(pFormat)); 00443 00444 return (IsEqualIID(pFormat, &TIME_FORMAT_MEDIA_TIME) ? S_OK : S_FALSE); 00445 } 00446 00447 HRESULT WINAPI MediaSeekingImpl_QueryPreferredFormat(IMediaSeeking * iface, GUID * pFormat) 00448 { 00449 TRACE("(%s)\n", qzdebugstr_guid(pFormat)); 00450 00451 *pFormat = TIME_FORMAT_MEDIA_TIME; 00452 return S_OK; 00453 } 00454 00455 HRESULT WINAPI MediaSeekingImpl_GetTimeFormat(IMediaSeeking * iface, GUID * pFormat) 00456 { 00457 MediaSeekingImpl *This = (MediaSeekingImpl *)iface; 00458 TRACE("(%s)\n", qzdebugstr_guid(pFormat)); 00459 00460 EnterCriticalSection(This->crst); 00461 *pFormat = This->timeformat; 00462 LeaveCriticalSection(This->crst); 00463 00464 return S_OK; 00465 } 00466 00467 HRESULT WINAPI MediaSeekingImpl_IsUsingTimeFormat(IMediaSeeking * iface, const GUID * pFormat) 00468 { 00469 MediaSeekingImpl *This = (MediaSeekingImpl *)iface; 00470 HRESULT hr = S_OK; 00471 00472 TRACE("(%s)\n", qzdebugstr_guid(pFormat)); 00473 00474 EnterCriticalSection(This->crst); 00475 if (!IsEqualIID(pFormat, &This->timeformat)) 00476 hr = S_FALSE; 00477 LeaveCriticalSection(This->crst); 00478 00479 return hr; 00480 } 00481 00482 00483 HRESULT WINAPI MediaSeekingImpl_SetTimeFormat(IMediaSeeking * iface, const GUID * pFormat) 00484 { 00485 MediaSeekingImpl *This = (MediaSeekingImpl *)iface; 00486 TRACE("(%s)\n", qzdebugstr_guid(pFormat)); 00487 00488 EnterCriticalSection(This->crst); 00489 ForwardCmdSeek(This->crst, This->pUserData, fwd_settimeformat, (LPVOID)pFormat); 00490 LeaveCriticalSection(This->crst); 00491 00492 return (IsEqualIID(pFormat, &TIME_FORMAT_MEDIA_TIME) ? S_OK : S_FALSE); 00493 } 00494 00495 00496 HRESULT WINAPI MediaSeekingImpl_GetDuration(IMediaSeeking * iface, LONGLONG * pDuration) 00497 { 00498 MediaSeekingImpl *This = (MediaSeekingImpl *)iface; 00499 00500 TRACE("(%p)\n", pDuration); 00501 00502 EnterCriticalSection(This->crst); 00503 *pDuration = This->llDuration; 00504 ForwardCmdSeek(This->crst, This->pUserData, fwd_getduration, pDuration); 00505 LeaveCriticalSection(This->crst); 00506 00507 return S_OK; 00508 } 00509 00510 HRESULT WINAPI MediaSeekingImpl_GetStopPosition(IMediaSeeking * iface, LONGLONG * pStop) 00511 { 00512 MediaSeekingImpl *This = (MediaSeekingImpl *)iface; 00513 00514 TRACE("(%p)\n", pStop); 00515 00516 EnterCriticalSection(This->crst); 00517 *pStop = This->llStop; 00518 ForwardCmdSeek(This->crst, This->pUserData, fwd_getstopposition, pStop); 00519 LeaveCriticalSection(This->crst); 00520 00521 return S_OK; 00522 } 00523 00524 /* FIXME: Make use of the info the filter should expose */ 00525 HRESULT WINAPI MediaSeekingImpl_GetCurrentPosition(IMediaSeeking * iface, LONGLONG * pCurrent) 00526 { 00527 MediaSeekingImpl *This = (MediaSeekingImpl *)iface; 00528 00529 TRACE("(%p)\n", pCurrent); 00530 00531 EnterCriticalSection(This->crst); 00532 *pCurrent = This->llCurrent; 00533 ForwardCmdSeek(This->crst, This->pUserData, fwd_getcurposition, pCurrent); 00534 LeaveCriticalSection(This->crst); 00535 00536 return S_OK; 00537 } 00538 00539 HRESULT WINAPI MediaSeekingImpl_ConvertTimeFormat(IMediaSeeking * iface, LONGLONG * pTarget, const GUID * pTargetFormat, LONGLONG Source, const GUID * pSourceFormat) 00540 { 00541 if (IsEqualIID(pTargetFormat, &TIME_FORMAT_MEDIA_TIME) && IsEqualIID(pSourceFormat, &TIME_FORMAT_MEDIA_TIME)) 00542 { 00543 *pTarget = Source; 00544 return S_OK; 00545 } 00546 /* FIXME: clear pTarget? */ 00547 return E_INVALIDARG; 00548 } 00549 00550 static inline LONGLONG Adjust(LONGLONG value, const LONGLONG * pModifier, DWORD dwFlags) 00551 { 00552 switch (dwFlags & AM_SEEKING_PositioningBitsMask) 00553 { 00554 case AM_SEEKING_NoPositioning: 00555 return value; 00556 case AM_SEEKING_AbsolutePositioning: 00557 return *pModifier; 00558 case AM_SEEKING_RelativePositioning: 00559 case AM_SEEKING_IncrementalPositioning: 00560 return value + *pModifier; 00561 default: 00562 assert(FALSE); 00563 return 0; 00564 } 00565 } 00566 00567 HRESULT WINAPI MediaSeekingImpl_SetPositions(IMediaSeeking * iface, LONGLONG * pCurrent, DWORD dwCurrentFlags, LONGLONG * pStop, DWORD dwStopFlags) 00568 { 00569 MediaSeekingImpl *This = (MediaSeekingImpl *)iface; 00570 BOOL bChangeCurrent = FALSE, bChangeStop = FALSE; 00571 LONGLONG llNewCurrent, llNewStop; 00572 struct pos_args args; 00573 00574 TRACE("(%p, %x, %p, %x)\n", pCurrent, dwCurrentFlags, pStop, dwStopFlags); 00575 00576 args.current = pCurrent; 00577 args.stop = pStop; 00578 args.curflags = dwCurrentFlags; 00579 args.stopflags = dwStopFlags; 00580 00581 EnterCriticalSection(This->crst); 00582 00583 llNewCurrent = Adjust(This->llCurrent, pCurrent, dwCurrentFlags); 00584 llNewStop = Adjust(This->llStop, pStop, dwStopFlags); 00585 00586 if (pCurrent) 00587 bChangeCurrent = TRUE; 00588 if (llNewStop != This->llStop) 00589 bChangeStop = TRUE; 00590 00591 TRACE("Old: %u, New: %u\n", (DWORD)(This->llCurrent/10000000), (DWORD)(llNewCurrent/10000000)); 00592 00593 This->llCurrent = llNewCurrent; 00594 This->llStop = llNewStop; 00595 00596 if (pCurrent && (dwCurrentFlags & AM_SEEKING_ReturnTime)) 00597 *pCurrent = llNewCurrent; 00598 if (pStop && (dwStopFlags & AM_SEEKING_ReturnTime)) 00599 *pStop = llNewStop; 00600 00601 ForwardCmdSeek(This->crst, This->pUserData, fwd_setposition, &args); 00602 LeaveCriticalSection(This->crst); 00603 00604 if (bChangeCurrent) 00605 This->fnChangeCurrent(This->pUserData); 00606 if (bChangeStop) 00607 This->fnChangeStop(This->pUserData); 00608 00609 return S_OK; 00610 } 00611 00612 HRESULT WINAPI MediaSeekingImpl_GetPositions(IMediaSeeking * iface, LONGLONG * pCurrent, LONGLONG * pStop) 00613 { 00614 MediaSeekingImpl *This = (MediaSeekingImpl *)iface; 00615 00616 TRACE("(%p, %p)\n", pCurrent, pStop); 00617 00618 EnterCriticalSection(This->crst); 00619 *pCurrent = This->llCurrent; 00620 *pStop = This->llStop; 00621 LeaveCriticalSection(This->crst); 00622 00623 return S_OK; 00624 } 00625 00626 HRESULT WINAPI MediaSeekingImpl_GetAvailable(IMediaSeeking * iface, LONGLONG * pEarliest, LONGLONG * pLatest) 00627 { 00628 MediaSeekingImpl *This = (MediaSeekingImpl *)iface; 00629 00630 TRACE("(%p, %p)\n", pEarliest, pLatest); 00631 00632 EnterCriticalSection(This->crst); 00633 *pEarliest = 0; 00634 *pLatest = This->llDuration; 00635 LeaveCriticalSection(This->crst); 00636 00637 return S_OK; 00638 } 00639 00640 HRESULT WINAPI MediaSeekingImpl_SetRate(IMediaSeeking * iface, double dRate) 00641 { 00642 MediaSeekingImpl *This = (MediaSeekingImpl *)iface; 00643 BOOL bChangeRate = (dRate != This->dRate); 00644 HRESULT hr = S_OK; 00645 00646 TRACE("(%e)\n", dRate); 00647 00648 if (dRate > 100 || dRate < .001) 00649 { 00650 FIXME("Excessive rate %e, ignoring\n", dRate); 00651 return VFW_E_UNSUPPORTED_AUDIO; 00652 } 00653 00654 EnterCriticalSection(This->crst); 00655 This->dRate = dRate; 00656 if (bChangeRate) 00657 hr = This->fnChangeRate(This->pUserData); 00658 ForwardCmdSeek(This->crst, This->pUserData, fwd_setrate, &dRate); 00659 LeaveCriticalSection(This->crst); 00660 00661 return hr; 00662 } 00663 00664 HRESULT WINAPI MediaSeekingImpl_GetRate(IMediaSeeking * iface, double * dRate) 00665 { 00666 MediaSeekingImpl *This = (MediaSeekingImpl *)iface; 00667 00668 TRACE("(%p)\n", dRate); 00669 00670 EnterCriticalSection(This->crst); 00671 /* Forward? */ 00672 *dRate = This->dRate; 00673 LeaveCriticalSection(This->crst); 00674 00675 return S_OK; 00676 } 00677 00678 HRESULT WINAPI MediaSeekingImpl_GetPreroll(IMediaSeeking * iface, LONGLONG * pPreroll) 00679 { 00680 TRACE("(%p)\n", pPreroll); 00681 00682 *pPreroll = 0; 00683 return S_OK; 00684 } 00685 00686 static HRESULT WINAPI MediaSeekingPassThru_QueryInterface(IMediaSeeking *iface, REFIID riid, LPVOID *ppvObj) 00687 { 00688 ICOM_THIS_MULTI(PassThruImpl, IMediaSeeking_vtbl, iface); 00689 00690 TRACE("(%p/%p)->(%s (%p), %p)\n", This, iface, debugstr_guid(riid), riid, ppvObj); 00691 00692 return SeekOuter_QueryInterface(This, riid, ppvObj); 00693 } 00694 00695 static ULONG WINAPI MediaSeekingPassThru_AddRef(IMediaSeeking *iface) 00696 { 00697 ICOM_THIS_MULTI(PassThruImpl, IMediaSeeking_vtbl, iface); 00698 00699 TRACE("(%p/%p)->()\n", iface, This); 00700 00701 return SeekOuter_AddRef(This); 00702 } 00703 00704 static ULONG WINAPI MediaSeekingPassThru_Release(IMediaSeeking *iface) 00705 { 00706 ICOM_THIS_MULTI(PassThruImpl, IMediaSeeking_vtbl, iface); 00707 00708 TRACE("(%p/%p)->()\n", iface, This); 00709 00710 return SeekOuter_Release(This); 00711 } 00712 00713 static HRESULT WINAPI MediaSeekingPassThru_GetCapabilities(IMediaSeeking * iface, DWORD * pCapabilities) 00714 { 00715 ICOM_THIS_MULTI(PassThruImpl, IMediaSeeking_vtbl, iface); 00716 00717 TRACE("(%p/%p)->(%p)\n", iface, This, pCapabilities); 00718 00719 FIXME("stub\n"); 00720 return E_NOTIMPL; 00721 } 00722 00723 static HRESULT WINAPI MediaSeekingPassThru_CheckCapabilities(IMediaSeeking * iface, DWORD * pCapabilities) 00724 { 00725 ICOM_THIS_MULTI(PassThruImpl, IMediaSeeking_vtbl, iface); 00726 00727 TRACE("(%p/%p)->(%p)\n", iface, This, pCapabilities); 00728 00729 if (!pCapabilities) 00730 return E_POINTER; 00731 00732 FIXME("stub\n"); 00733 return E_NOTIMPL; 00734 } 00735 00736 static HRESULT WINAPI MediaSeekingPassThru_IsFormatSupported(IMediaSeeking * iface, const GUID * pFormat) 00737 { 00738 ICOM_THIS_MULTI(PassThruImpl, IMediaSeeking_vtbl, iface); 00739 TRACE("(%p/%p)->(%s)\n", iface, This, qzdebugstr_guid(pFormat)); 00740 00741 FIXME("stub\n"); 00742 return E_NOTIMPL; 00743 } 00744 00745 static HRESULT WINAPI MediaSeekingPassThru_QueryPreferredFormat(IMediaSeeking * iface, GUID * pFormat) 00746 { 00747 ICOM_THIS_MULTI(PassThruImpl, IMediaSeeking_vtbl, iface); 00748 TRACE("(%p/%p)->(%p)\n", iface, This, pFormat); 00749 00750 FIXME("stub\n"); 00751 return E_NOTIMPL; 00752 } 00753 00754 static HRESULT WINAPI MediaSeekingPassThru_GetTimeFormat(IMediaSeeking * iface, GUID * pFormat) 00755 { 00756 ICOM_THIS_MULTI(PassThruImpl, IMediaSeeking_vtbl, iface); 00757 TRACE("(%p/%p)->(%p)\n", iface, This, pFormat); 00758 00759 FIXME("stub\n"); 00760 return E_NOTIMPL; 00761 } 00762 00763 static HRESULT WINAPI MediaSeekingPassThru_IsUsingTimeFormat(IMediaSeeking * iface, const GUID * pFormat) 00764 { 00765 ICOM_THIS_MULTI(PassThruImpl, IMediaSeeking_vtbl, iface); 00766 00767 TRACE("(%p/%p)->(%s)\n", iface, This, qzdebugstr_guid(pFormat)); 00768 00769 FIXME("stub\n"); 00770 return E_NOTIMPL; 00771 } 00772 00773 00774 static HRESULT WINAPI MediaSeekingPassThru_SetTimeFormat(IMediaSeeking * iface, const GUID * pFormat) 00775 { 00776 ICOM_THIS_MULTI(PassThruImpl, IMediaSeeking_vtbl, iface); 00777 TRACE("(%p/%p)->(%s)\n", iface, This, qzdebugstr_guid(pFormat)); 00778 00779 FIXME("stub\n"); 00780 return E_NOTIMPL; 00781 } 00782 00783 00784 static HRESULT WINAPI MediaSeekingPassThru_GetDuration(IMediaSeeking * iface, LONGLONG * pDuration) 00785 { 00786 ICOM_THIS_MULTI(PassThruImpl, IMediaSeeking_vtbl, iface); 00787 PIN_INFO info; 00788 HRESULT hr; 00789 00790 TRACE("(%p/%p)->(%p)\n", iface, This, pDuration); 00791 00792 IPin_QueryPinInfo(This->pin, &info); 00793 00794 hr = ForwardCmdSeek(NULL, info.pFilter, fwd_getduration, pDuration); 00795 IBaseFilter_Release(info.pFilter); 00796 00797 return hr; 00798 } 00799 00800 static HRESULT WINAPI MediaSeekingPassThru_GetStopPosition(IMediaSeeking * iface, LONGLONG * pStop) 00801 { 00802 ICOM_THIS_MULTI(PassThruImpl, IMediaSeeking_vtbl, iface); 00803 00804 TRACE("(%p/%p)->(%p)\n", iface, This, pStop); 00805 00806 FIXME("stub\n"); 00807 return E_NOTIMPL; 00808 } 00809 00810 /* FIXME: Make use of the info the filter should expose */ 00811 static HRESULT WINAPI MediaSeekingPassThru_GetCurrentPosition(IMediaSeeking * iface, LONGLONG * pCurrent) 00812 { 00813 ICOM_THIS_MULTI(PassThruImpl, IMediaSeeking_vtbl, iface); 00814 00815 TRACE("(%p/%p)->(%p)\n", iface, This, pCurrent); 00816 00817 FIXME("stub\n"); 00818 return E_NOTIMPL; 00819 } 00820 00821 static HRESULT WINAPI MediaSeekingPassThru_ConvertTimeFormat(IMediaSeeking * iface, LONGLONG * pTarget, const GUID * pTargetFormat, LONGLONG Source, const GUID * pSourceFormat) 00822 { 00823 ICOM_THIS_MULTI(PassThruImpl, IMediaSeeking_vtbl, iface); 00824 00825 TRACE("(%p/%p)->(%p,%s,%x%08x,%s)\n", iface, This, pTarget, debugstr_guid(pTargetFormat), (DWORD)(Source>>32), (DWORD)Source, debugstr_guid(pSourceFormat)); 00826 00827 FIXME("stub\n"); 00828 return E_NOTIMPL; 00829 } 00830 00831 static HRESULT WINAPI MediaSeekingPassThru_SetPositions(IMediaSeeking * iface, LONGLONG * pCurrent, DWORD dwCurrentFlags, LONGLONG * pStop, DWORD dwStopFlags) 00832 { 00833 ICOM_THIS_MULTI(PassThruImpl, IMediaSeeking_vtbl, iface); 00834 struct pos_args args; 00835 PIN_INFO info; 00836 HRESULT hr; 00837 00838 TRACE("(%p/%p)->(%p, %p)\n", iface, This, pCurrent, pStop); 00839 args.current = pCurrent; 00840 args.stop = pStop; 00841 args.curflags = dwCurrentFlags; 00842 args.stopflags = dwStopFlags; 00843 00844 IPin_QueryPinInfo(This->pin, &info); 00845 00846 hr = ForwardCmdSeek(NULL, info.pFilter, fwd_setposition, &args); 00847 IBaseFilter_Release(info.pFilter); 00848 return hr; 00849 } 00850 00851 static HRESULT WINAPI MediaSeekingPassThru_GetPositions(IMediaSeeking * iface, LONGLONG * pCurrent, LONGLONG * pStop) 00852 { 00853 ICOM_THIS_MULTI(PassThruImpl, IMediaSeeking_vtbl, iface); 00854 00855 TRACE("(%p/%p)->(%p, %p)\n", iface, This, pCurrent, pStop); 00856 00857 FIXME("stub\n"); 00858 return E_NOTIMPL; 00859 } 00860 00861 static HRESULT WINAPI MediaSeekingPassThru_GetAvailable(IMediaSeeking * iface, LONGLONG * pEarliest, LONGLONG * pLatest) 00862 { 00863 ICOM_THIS_MULTI(PassThruImpl, IMediaSeeking_vtbl, iface); 00864 00865 TRACE("(%p/%p)->(%p,%p)\n", iface, This, pEarliest, pLatest); 00866 00867 FIXME("stub\n"); 00868 return E_NOTIMPL; 00869 } 00870 00871 static HRESULT WINAPI MediaSeekingPassThru_SetRate(IMediaSeeking * iface, double dRate) 00872 { 00873 ICOM_THIS_MULTI(PassThruImpl, IMediaSeeking_vtbl, iface); 00874 00875 TRACE("(%p/%p)->(%e)\n", iface, This, dRate); 00876 00877 FIXME("stub\n"); 00878 return E_NOTIMPL; 00879 } 00880 00881 static HRESULT WINAPI MediaSeekingPassThru_GetRate(IMediaSeeking * iface, double * dRate) 00882 { 00883 ICOM_THIS_MULTI(PassThruImpl, IMediaSeeking_vtbl, iface); 00884 00885 TRACE("(%p/%p)->(%p)\n", iface, This, dRate); 00886 00887 FIXME("stub\n"); 00888 return E_NOTIMPL; 00889 } 00890 00891 static HRESULT WINAPI MediaSeekingPassThru_GetPreroll(IMediaSeeking * iface, LONGLONG * pPreroll) 00892 { 00893 TRACE("(%p)\n", pPreroll); 00894 00895 FIXME("stub\n"); 00896 return E_NOTIMPL; 00897 } 00898 00899 static const IMediaSeekingVtbl IMediaSeekingPassThru_Vtbl = 00900 { 00901 MediaSeekingPassThru_QueryInterface, 00902 MediaSeekingPassThru_AddRef, 00903 MediaSeekingPassThru_Release, 00904 MediaSeekingPassThru_GetCapabilities, 00905 MediaSeekingPassThru_CheckCapabilities, 00906 MediaSeekingPassThru_IsFormatSupported, 00907 MediaSeekingPassThru_QueryPreferredFormat, 00908 MediaSeekingPassThru_GetTimeFormat, 00909 MediaSeekingPassThru_IsUsingTimeFormat, 00910 MediaSeekingPassThru_SetTimeFormat, 00911 MediaSeekingPassThru_GetDuration, 00912 MediaSeekingPassThru_GetStopPosition, 00913 MediaSeekingPassThru_GetCurrentPosition, 00914 MediaSeekingPassThru_ConvertTimeFormat, 00915 MediaSeekingPassThru_SetPositions, 00916 MediaSeekingPassThru_GetPositions, 00917 MediaSeekingPassThru_GetAvailable, 00918 MediaSeekingPassThru_SetRate, 00919 MediaSeekingPassThru_GetRate, 00920 MediaSeekingPassThru_GetPreroll 00921 }; Generated on Mon May 28 2012 04:16:36 for ReactOS by
1.7.6.1
|