⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 teletextoutputpin.cpp

📁 Teletext module usually used in the DVB area.
💻 CPP
📖 第 1 页 / 共 2 页
字号:
					    hr = mix_config->SetBlendingParameter(255);
					    hr = mix_config->SetAspectRatioMode(AM_ARMODE_STRETCHED_AS_PRIMARY);
					    hr = mix_config->SetRelativePosition(0, 0, 10000, 10000);
				    }

				    break;
			    }
		    }
        }

		HDC hdc = GetDC(NULL);
		m_DC = CreateCompatibleDC(hdc);
		if (m_DC == NULL)
		{
			return S_OK;
		}

		m_Bitmap = CreateCompatibleBitmap(hdc, m_nWidth, m_nHeight);
		if (m_Bitmap == NULL)
		{
			return S_OK;
		}

		ReleaseDC(NULL, hdc);

		m_OldObject = SelectObject(m_DC, m_Bitmap);
		if (m_OldObject == NULL)
		{
			return S_OK;
		}

		m_CurrentFont = CreateFont
		(
			row_height * 2,
			column_width - 1,
			0, 0, FW_BOLD, 0, 0, 0, 0, 0, 0, PROOF_QUALITY, FIXED_PITCH, 
			"Lucinda Console"
		);

		if (m_CurrentFont != NULL)
		{
			m_OldFont = (HFONT)SelectObject(m_DC, m_CurrentFont);
		}

		m_SupplementaryFont = CreateFont(14, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, PROOF_QUALITY, FIXED_PITCH, 
			"Lucinda Console");
	}

    //
    // Fill the background with m_Colours[Colour_Key].
    //
	int old_mode = SetBkMode(m_DC, m_TextMode);
	COLORREF old_bk_colour = SetBkColor(m_DC, ((CDVBTeletextSubtitles*)m_pFilter)->m_Colours[Colour_Key]);
	RECT rc;
	rc.left = 0;
	rc.top = 0;
	rc.right = m_nWidth;
	rc.bottom = m_nHeight;
	ExtTextOut(m_DC, 0, 0, ETO_OPAQUE, &rc, NULL, 0, NULL);

	//
    // Default text background colour
    //
    SetBkColor(m_DC, ((CDVBTeletextSubtitles*)m_pFilter)->m_Colours[Colour_Background]);

    //
    // Get the current reference time in milliseconds.
    //
    __int64 reference_time_milliseconds = 0;

	CComQIPtr<IMediaFilter> media_filter = ((CDVBTeletextSubtitles*)m_pFilter)->m_pGraph;
	if (media_filter != NULL)
	{
        CComPtr<IReferenceClock> reference_clock;
	    media_filter->GetSyncSource(&reference_clock);
	    if (reference_clock != NULL)
	    {
		    REFERENCE_TIME reference_time;
		    reference_clock->GetTime(&reference_time);

		    reference_time_milliseconds = ConvertToMilliseconds(reference_time);

			if (m_FirstReferenceTimeMilliseconds == 0)
			{
				m_FirstReferenceTimeMilliseconds = reference_time_milliseconds;
			}

			reference_time_milliseconds -= m_FirstReferenceTimeMilliseconds;
        }
    }

	std::vector<SMagazineSubPage*> results;
	((CDVBTeletextSubtitles*)m_pFilter)->GetSubPagesAt(reference_time_milliseconds, results);

#define MODE 1
#if MODE==0
	HFONT OldFont = (HFONT)SelectObject(m_DC, m_SupplementaryFont);
#endif

	COLORREF old_text_colour = SetTextColor(m_DC, RGB(255,255,255));
	COLORREF old_text_bkcolour = SetBkColor(m_DC, RGB(0,0,0));

#if MODE==0
	SIZE size;
	GetTextExtentPoint(m_DC, "x", 1, &size);
	int pos = m_nHeight - size.cy;
#endif

#if MODE==0
	char buff[512];
#endif

	std::vector<SMagazineSubPage*>::iterator magazine_sub_page_it = results.begin();
	while (magazine_sub_page_it != results.end())
	{
		SMagazineSubPage* sub_page = *magazine_sub_page_it;

		//
		// Draw the text!!!
		//
		vector<STeletextSubtitleLine> texts;
		// SMagazineSubPage* sub_page = ((CDVBTeletextSubtitles*)m_pFilter)->GetSubPageAt(reference_time_milliseconds);
		__int64 start_milliseconds = 0;
		__int64 end_milliseconds = 0;

		if ((sub_page != NULL) && sub_page->m_Valid)
		{
			sub_page->GenerateIsoTextLines
			(
				texts,
				((CDVBTeletextSubtitles*)m_pFilter)->m_DisplayHeadingLine,
				((CDVBTeletextSubtitles*)m_pFilter)->m_nLastLine
			);

			start_milliseconds = sub_page->m_StartMilliseconds;
			end_milliseconds = sub_page->m_EndMilliseconds;

			sub_page->m_Displayed = true;
		}

		// ((CDVBTeletextSubtitles*)m_pFilter)->ClearSubPages();

		unsigned int sh = (unsigned int)(start_milliseconds/(1000*60*60));
		unsigned int sm = (unsigned int)((start_milliseconds/(1000*60))-(sh*60));
		unsigned int ss = (unsigned int)((start_milliseconds/1000)-(sh*3600)-(sm*60));
		unsigned int su = (unsigned int)(start_milliseconds-(sh*1000*60*60)-(sm*1000*60)-(ss*1000));

		unsigned int eh = (unsigned int)(end_milliseconds/(1000*60*60));
		unsigned int em = (unsigned int)((end_milliseconds/(1000*60))-(eh*60));
		unsigned int es = (unsigned int)((end_milliseconds/1000)-(eh*3600)-(em*60));
		unsigned int eu = (unsigned int)(end_milliseconds-(eh*1000*60*60)-(em*1000*60)-(es*1000));

		vector<STeletextSubtitleLine>::iterator it = texts.begin();
		for (;it != texts.end(); it++)
		{
			STeletextSubtitleLine subtitle_line = *it;

			COLORREF old_text_colour = SetTextColor(m_DC, ((CDVBTeletextSubtitles*)m_pFilter)->m_Colours[subtitle_line.m_Colour]);
			COLORREF old_text_bkcolour = SetBkColor(m_DC, ((CDVBTeletextSubtitles*)m_pFilter)->m_Colours[subtitle_line.m_BackgroundColour]);

#if MODE!=0
			int length = _tcslen(subtitle_line.text);

			char buffer[200];
			memset(&buffer, _T(' '), sizeof(buffer) - 1);
			memcpy(&buffer[subtitle_line.column - 1], subtitle_line.text, length);
			buffer[40] = _T('\0');

			TextOut
			(
				m_DC,
				0,
				subtitle_line.row * row_height,
				buffer, 40
			);
#else
			sprintf(buff, "%d:%02d:%02d.%03d end=%d:%02d:%02d.%03d (%d,%d) %s"/*" ref=%d:%02d:%02d.%03d"*/, sh, sm, ss, su, eh, em, es, eu, subtitle_line.row, subtitle_line.column, subtitle_line.text);
			TextOut
			(
				m_DC,
				200,
				pos,
				buff,
				_tcslen(buff)
			);

			pos -= size.cy;
#endif

			SetBkColor(m_DC, old_text_bkcolour);
			SetTextColor(m_DC, old_text_colour);
		}

		// SetBkMode(m_DC, OPAQUE);

		/*
		TextOut
		(
			m_DC,
			0,
			pos, // + 70,
			buff,
			_tcslen(buff)
		);
		*/

		magazine_sub_page_it++;

#if MODE==0
		if (pos < 0)
		{
			break;
		}
#endif
	}

#if MODE==0

	DWORD subtitle_delay_time = 0;
	((CDVBTeletextSubtitles*)m_pFilter)->get_SubtitleDelayTime(&subtitle_delay_time);

	DWORD subtitle_delay_range = 0;
	((CDVBTeletextSubtitles*)m_pFilter)->get_SubtitleDelayRange(&subtitle_delay_range);

	{
		unsigned int rh = (unsigned int)(reference_time_milliseconds/(1000*60*60));
		unsigned int rm = (unsigned int)((reference_time_milliseconds/(1000*60))-(rh*60));
		unsigned int rs = (unsigned int)((reference_time_milliseconds/1000)-(rh*3600)-(rm*60));
		unsigned int ru = (unsigned int)(reference_time_milliseconds-(rh*1000*60*60)-(rm*1000*60)-(rs*1000));

		sprintf(buff, "T=%d R=%d ref=%d:%02d:%02d.%03d", subtitle_delay_time, subtitle_delay_range, rh, rm, rs, ru);
		TextOut
		(
			m_DC,
			0,
			m_nHeight - size.cy * 4,
			buff,
			_tcslen(buff)
		);
	}

	{
		__int64 reference_time_milliseconds_begin = reference_time_milliseconds - subtitle_delay_time;
		reference_time_milliseconds_begin -= subtitle_delay_range;
		unsigned int rbh = (unsigned int)(reference_time_milliseconds_begin/(1000*60*60));
		unsigned int rbm = (unsigned int)((reference_time_milliseconds_begin/(1000*60))-(rbh*60));
		unsigned int rbs = (unsigned int)((reference_time_milliseconds_begin/1000)-(rbh*3600)-(rbm*60));
		unsigned int rbu = (unsigned int)(reference_time_milliseconds_begin-(rbh*1000*60*60)-(rbm*1000*60)-(rbs*1000));

		sprintf(buff, "refb=%d:%02d:%02d.%03d", rbh, rbm, rbs, rbu);
		TextOut
		(
			m_DC,
			0,
			m_nHeight - size.cy * 3,
			buff,
			_tcslen(buff)
		);
	}

	{
		__int64 reference_time_milliseconds_end = reference_time_milliseconds - subtitle_delay_time;
		reference_time_milliseconds_end += subtitle_delay_range;

		unsigned int reh = (unsigned int)(reference_time_milliseconds_end/(1000*60*60));
		unsigned int rem = (unsigned int)((reference_time_milliseconds_end/(1000*60))-(reh*60));
		unsigned int res = (unsigned int)((reference_time_milliseconds_end/1000)-(reh*3600)-(rem*60));
		unsigned int reu = (unsigned int)(reference_time_milliseconds_end-(reh*1000*60*60)-(rem*1000*60)-(res*1000));

		sprintf(buff, "refe=%d:%02d:%02d.%03d", reh, rem, res, reu);
		TextOut
		(
			m_DC,
			0,
			m_nHeight - size.cy * 2,
			buff,
			_tcslen(buff)
		);
	}

	SelectObject(m_DC, OldFont);
#endif

	SetBkColor(m_DC, old_bk_colour);
	SetBkMode(m_DC, old_mode);
	SetBkColor(m_DC, old_text_bkcolour);

	VIDEOINFOHEADER *pVih = (VIDEOINFOHEADER*)m_mt.pbFormat;

	// Copy the DIB bits over into our filter's output buffer.

	// Access the sample's data buffer
	BYTE *pData;
	pSample->GetPointer(&pData);

	// Copy the bitmap data into the provided BYTE buffer
	GetDIBits
	(
		m_DC,
		m_Bitmap,
		0,
		m_nHeight,
		pData,
		(BITMAPINFO*)&(pVih->bmiHeader),
		DIB_RGB_COLORS
	);

	// pSample->SetActualDataLength();

	// Set the timestamps that will govern playback frame rate.
	// If this file is getting written out as an AVI,
	// then you'll also need to configure the AVI Mux filter to 
	// set the Average Time Per Frame for the AVI Header.
	// The current time is the sample's start.
	REFERENCE_TIME rtStart = m_iFrameNumber * m_rtFrameLength;
	REFERENCE_TIME rtStop  = rtStart + m_rtFrameLength;

	// pSample->SetTime(&rtStart, &rtStop);
	m_iFrameNumber++;

    return S_OK;
}

HRESULT
CTeletextOutputPin::DoBufferProcessingLoop(void)
{
    // too bad CheckRequest wasn't virtual ;(

    Command com;

    OnThreadStartPlay();

    do
    {
    	while (1)
        {
            HANDLE requests[2] =
            {
                GetRequestHandle(),
                m_EventDataReady
            };

            DWORD timeout = 100; // ((CDVBTeletextSubtitles*)m_pFilter)->GetIntervalToNextEvent();

            DWORD result = WaitForMultipleObjects(sizeof(requests) / sizeof(requests[0]), requests, FALSE, timeout);
            if (result == WAIT_OBJECT_0)
            {
                if (CheckRequest(&com))
                {
                    break;
                }
            }
            else if (result == (WAIT_OBJECT_0 + 1))
            {
				m_EventDataReady.Reset();
            }
            else if (result == (WAIT_TIMEOUT)) // some data needs to be sent now
            {
                CComPtr<IMediaSample> sample;

                HRESULT hr = GetDeliveryBuffer(&sample, NULL, NULL, 0);

                if (FAILED(hr))
                {
                    Sleep(1);
                    continue;
                    // go round again. Perhaps the error will go away
                    // or the allocator is decommited & we will be asked to
                    // exit soon.
                }

                hr = FillBuffer(sample);

                if (hr == S_OK)
                {
                    m_EventDataReady.Reset();

                    hr = Deliver(sample);
                    sample.Release();

                    // downstream filter returns S_FALSE if it wants us to
                    // stop or an error if it's reporting an error.
                    if (hr != S_OK)
                    {
                        DbgLog((LOG_TRACE, 2, TEXT("Deliver() returned %08x; stopping"), hr));
                        return S_OK;
                    }

                }
                else if (hr == S_FALSE)
                {
                    // derived class wants us to stop pushing data
                    DeliverEndOfStream();
                    return S_OK;
                }
                else
                {
                    // derived class encountered an error
                    DbgLog((LOG_ERROR, 1, TEXT("Error %08lX from FillBuffer!!!"), hr));
                    DeliverEndOfStream();
                    m_pFilter->NotifyEvent(EC_ERRORABORT, hr, 0);
                    return hr;
                }
            }
        }


        // For all commands sent to us there must be a Reply call!

        if (com == CMD_RUN || com == CMD_PAUSE)
        {
            Reply(NOERROR);
        }
        else if (com != CMD_STOP)
        {
            Reply((DWORD) E_UNEXPECTED);
            DbgLog((LOG_ERROR, 1, TEXT("Unexpected command!!!")));
        }
    } while (com != CMD_STOP);

    return S_FALSE;
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -