15 #pragma warning(disable:4355)
20 if (rt < - (50 *
UNITS)) {
23 if (rt > 50 *
UNITS) {
25 }
else return (
int)rt;
31 __in_opt LPCTSTR
pName,
32 __inout_opt LPUNKNOWN pUnk,
33 __inout HRESULT *phr) :
36 m_evComplete(TRUE, phr),
37 m_RenderEvent(FALSE, phr),
40 m_ThreadSignal(TRUE, phr),
43 m_bEOSDelivered(FALSE),
48 m_bRepaintStatus(TRUE),
53 if (SUCCEEDED(*phr)) {
56 m_idBaseStamp =
MSR_REGISTER(TEXT(
"BaseRenderer: sample time stamp"));
57 m_idBaseRenderTime =
MSR_REGISTER(TEXT(
"BaseRenderer: draw time (msec)"));
58 m_idBaseAccuracy =
MSR_REGISTER(TEXT(
"BaseRenderer: Accuracy (msec)"));
108 return E_OUTOFMEMORY;
111 HRESULT
hr = NOERROR;
123 return E_OUTOFMEMORY;
129 return E_NOINTERFACE;
141 if (
riid == IID_IMediaPosition ||
riid == IID_IMediaSeeking) {
157 if (bCanWait == TRUE) {
173 void CBaseRenderer::DisplayRendererState()
221 CRefTime CurrentTime,StartTime,EndTime;
222 m_pClock->GetTime((REFERENCE_TIME*) &CurrentTime);
235 m_pMediaSample->GetTime((REFERENCE_TIME*)&StartTime, (REFERENCE_TIME*)&EndTime);
236 DbgLog((
LOG_TIMING, 1, TEXT(
"Next sample stream times (Start %d End %d ms)"),
237 StartTime.Millisecs(),EndTime.Millisecs()));
252 #define RENDER_TIMEOUT 10000
257 DWORD Result = WAIT_TIMEOUT;
262 while (Result == WAIT_TIMEOUT) {
263 Result = WaitForMultipleObjects(2,WaitObjects,FALSE,
RENDER_TIMEOUT);
266 if (Result == WAIT_TIMEOUT) DisplayRendererState();
274 if (Result == WAIT_OBJECT_0) {
275 return VFW_E_STATE_CHANGED;
299 PeekMessage(&msg,
NULL, WM_NULL, WM_NULL, PM_NOREMOVE);
308 if (HIWORD(GetQueueStatus(QS_POSTMESSAGE)) & QS_POSTMESSAGE) {
310 PostThreadMessage(GetCurrentThreadId(), WM_NULL, 0, 0);
346 return VFW_S_STATE_INTERMEDIATE;
379 if (OldState != State_Stopped) {
403 if (
m_State == State_Stopped) {
410 NOTE(
"Input pin is not connected");
457 FILTER_STATE OldState =
m_State;
469 NOTE(
"Input pin is not connected");
478 NOTE(
"Pause failed");
510 if (OldState == State_Stopped) {
530 FILTER_STATE OldState =
m_State;
534 if (
m_State == State_Running) {
541 NotifyEvent(EC_COMPLETE,S_OK,(LONG_PTR)(IBaseFilter *)
this);
581 if (OldState == State_Stopped) {
621 HRESULT
hr = NOERROR;
644 if (0==lstrcmpW(Id,L
"In")) {
649 return E_OUTOFMEMORY;
653 return VFW_E_NOT_FOUND;
668 if (
m_State == State_Stopped) {
810 return VFW_E_NOT_STOPPED;
818 if (State_Running ==
m_State) {
832 __out REFERENCE_TIME *pStartTime,
833 __out REFERENCE_TIME *pEndTime)
842 if (SUCCEEDED(pMediaSample->GetTime(pStartTime, pEndTime))) {
843 if (*pEndTime < *pStartTime) {
844 return VFW_E_START_TIME_AFTER_END;
867 __out REFERENCE_TIME *ptrStart,
868 __out REFERENCE_TIME *ptrEnd)
908 return (dwAdvise ? S_OK : S_FALSE);
919 REFERENCE_TIME StartSample, EndSample;
923 if (pMediaSample ==
NULL) {
985 if (pMediaSample ==
NULL) {
1049 HRESULT
hr =
m_pInputPin->CBaseInputPin::Receive(pMediaSample);
1051 if (
hr != NOERROR) {
1086 return E_UNEXPECTED;
1098 return VFW_E_SAMPLE_REJECTED;
1135 if (
hr == VFW_E_SAMPLE_REJECTED) {
1143 if (
m_State == State_Paused) {
1223 NOTE1(
"EndOfStreamTimer called (%d)",uID);
1249 #define TIMEOUT_DELIVERYWAIT 50
1250 #define TIMEOUT_RESOLUTION 10
1267 REFERENCE_TIME CurrentTime;
1269 LONG Delay = LONG((Signal - CurrentTime) / 10000);
1273 NOTE1(
"Delay until end of stream delivery %d",Delay);
1274 NOTE1(
"Current %s",(LPCTSTR)
CDisp((LONGLONG)CurrentTime));
1275 NOTE1(
"Signal %s",(LPCTSTR)
CDisp((LONGLONG)Signal));
1322 NOTE(
"Sending EC_COMPLETE...");
1323 return NotifyEvent(EC_COMPLETE,S_OK,(LONG_PTR)(IBaseFilter *)
this);
1438 IMediaEventSink *pSink;
1441 HRESULT
hr = pPin->QueryInterface(IID_IMediaEventSink,(
void **)&pSink);
1442 if (SUCCEEDED(
hr)) {
1443 pSink->Notify(EC_NOTIFY_WINDOW,LONG_PTR(hwnd),0);
1457 #define RLOG(_x_) DbgLog((LOG_TRACE,1,TEXT(_x_)));
1479 RLOG(
"Sending repaint");
1503 RLOG(
"Notification of EC_DISPLAY_CHANGE");
1509 NotifyEvent(EC_DISPLAY_CHANGED,(LONG_PTR) pPin,0);
1525 REFERENCE_TIME trStart, trEnd;
1526 pMediaSample->GetTime(&trStart, &trEnd);
1530 m_pClock->GetTime(&m_trRenderStart);
1532 REFERENCE_TIME trStream;
1533 trStream = m_trRenderStart-
m_tStart;
1536 const int trLate = (int)(trStream - trStart);
1549 REFERENCE_TIME trNow;
1552 int t = (int)((trNow - m_trRenderStart)/10000);
1563 __inout HRESULT *phr,
1564 __in_opt LPCWSTR pPinName) :
1567 &pRenderer->m_InterfaceLock,
1586 if (
hr != NOERROR) {
1593 if (SUCCEEDED(
hr)) {
1626 if (SUCCEEDED(
hr)) {
1707 const WCHAR szIn[] = L
"In";
1709 *Id = (LPWSTR)CoTaskMemAlloc(
sizeof(szIn));
1711 return E_OUTOFMEMORY;
1771 REFCLSID RenderClass,
1772 __in_opt LPCTSTR
pName,
1773 __inout_opt LPUNKNOWN pUnk,
1774 __inout HRESULT *phr) :
1777 m_cFramesDropped(0),
1779 m_bSupplierHandlingQuality(FALSE)
1784 m_idTimeStamp =
MSR_REGISTER(TEXT(
"Frame time stamp"));
1787 m_idSchLateTime =
MSR_REGISTER(TEXT(
"mSec late when scheduled"));
1788 m_idDecision =
MSR_REGISTER(TEXT(
"Scheduler decision code"));
1789 m_idQualityRate =
MSR_REGISTER(TEXT(
"Quality rate sent"));
1790 m_idQualityTime =
MSR_REGISTER(TEXT(
"Quality time sent"));
1793 m_idFrameAccuracy =
MSR_REGISTER(TEXT(
"Frame accuracy (msecs)"));
1797 m_idRenderAvg =
MSR_REGISTER(TEXT(
"Render draw time Avg"));
1801 m_idThrottle =
MSR_REGISTER(TEXT(
"Audio-video throttle wait"));
1863 m_trRememberFrameForPerf = 0;
1915 REFERENCE_TIME trRealStream;
1922 REFERENCE_TIME tr = timeGetTime()*10000;
1923 trRealStream = tr + m_llTimeOffset;
1935 int trFrame = (int)(tr - m_trRememberFrameForPerf);
1938 m_trRememberFrameForPerf = tr;
1968 int tLate = trLate/10000;
1979 if (tLate>1000 || tLate<-1000) {
1982 }
else if (tLate>0) {
1998 int tFrame = trFrame/10000;
2003 if (tFrame>1000||tFrame<0) tFrame = 1000;
2128 m_trThrottle = -330000 + (388880000/(q.Proportion+167));
2171 REFERENCE_TIME trRealStream)
2188 q.TimeStamp = (REFERENCE_TIME)trRealStream;
2200 q.Proportion = 1000;
2205 else if ( trLate> 0 ) {
2210 q.Proportion = 1000 - (int)((trLate)/(
UNITS/1000));
2211 if (q.Proportion<500) {
2225 q.Proportion = 2000;
2235 q.Proportion = 2000;
2239 if (q.Proportion>2000) {
2240 q.Proportion = 2000;
2261 MSR_INTEGER( m_idQualityTime, (
int)q.Late / 10000 );
2270 IQualityControl *pQC =
NULL;
2276 hr = pOutputPin->QueryInterface(IID_IQualityControl,(
void**) &pQC);
2277 if (SUCCEEDED(
hr)) {
2301 __inout REFERENCE_TIME *ptrStart,
2302 __inout REFERENCE_TIME *ptrEnd)
2308 MSR_INTEGER(m_idTimeStamp, (
int)((*ptrStart)>>32));
2316 if (*ptrStart>=80000) {
2326 REFERENCE_TIME trRealStream;
2333 m_llTimeOffset = trRealStream-timeGetTime()*10000;
2344 const int trTrueLate =
TimeDiff(trRealStream - *ptrStart);
2345 const int trLate = trTrueLate;
2356 const int trDuration = (int)(*ptrEnd - *ptrStart);
2382 if (S_OK==pMediaSample->IsDiscontinuity()) {
2392 BOOL bJustDroppedFrame
2396 && (S_OK == pMediaSample->IsDiscontinuity())
2416 int trL = trLate<0 ? -trLate : 0;
2440 ? (trLate <= trDuration*4)
2441 : (trLate+trLate < trDuration)
2462 BOOL bPlayASAP = FALSE;
2467 if ( bJustDroppedFrame) {
2480 && (trLate > - trDuration*10)
2487 else if ( (trLate + trDuration > 0)
2498 if (trLate<-9000000) {
2551 int Delay = -trTrueLate;
2552 Result = Delay<=0 ? S_OK : S_FALSE;
2558 if (Result==S_FALSE) {
2572 iAccuracy = trTrueLate;
2588 if (m_bDrawLateFrames) {
2617 if (bDrawImage == FALSE) {
2674 *piAvgFrameRate = 0;
2731 if (x > 0x40000000) {
2743 if (s>=0) s = (s*s+x)/(2*s);
2744 if (s>=0) s = (s*s+x)/(2*s);
2756 __out
int *piResult,
2782 x = llSumSq -
llMulDiv(iTot, iTot, nSamples, 0);
2783 x = x / (nSamples-1);
2785 *piResult =
isqrt((LONG)x);
2826 if (
riid == IID_IQualProp) {
2828 }
else if (
riid == IID_IQualityControl) {
2848 IBaseFilter* pFilter =
this;
2849 NotifyEvent(EC_WINDOW_DESTROYED, (LPARAM) pFilter, 0);
2857 #pragma warning(disable: 4514)