www.pudn.com > src.rar > DirectVobSubFilter.h


#pragma once 
 
#include  
#include  
 
#include "DirectVobSub.h" 
 
#include "../vobsub/vobsub.h" 
 
#include "MyCustomAllocator.h" 
 
#define MAXSUBIMAGECACHE 10 
 
// ms 
#define LOOKAHEADSIZE 60000 
#define LOOKAHEADSTEPSIZE 10 
 
class CDirectVobSubFilter; 
 
typedef struct  
{ 
public: 
	HBITMAP hbm; 
	int start, stop; 
 
	void Clear(uint c); 
	void ConvertToYUY2(); 
} SubImage; 
 
typedef struct 
{ 
	HWND hSystrayWnd; 
	IFilterGraph* graph; 
	IDirectVobSub* dvs; 
	bool fRunOnce, fShowIcon; 
} SystrayIconData; 
 
/* This is for graphedit */ 
 
class CDirectVobSubFilter :  
		public CTransformFilter, 
		public CDirectVobSub, 
		public ISpecifyPropertyPages, 
		public IAMStreamSelect, 
		public CAMThread 
{ 
    friend class CDirectVobSubInputPin; 
    friend class CDirectVobSubOutputPin; 
    friend class CTextInputPin; 
 
#ifdef DEBUG 
	DWORD dwRegister; 
#endif 
 
public: 
    DECLARE_IUNKNOWN; 
    static CUnknown* WINAPI CreateInstance(LPUNKNOWN punk, HRESULT* phr); 
 
    STDMETHODIMP NonDelegatingQueryInterface(REFIID riid, void** ppv); 
 
	HRESULT InitializeOutputSample(IMediaSample* pSample, IMediaSample** ppOutSample); 
 
    // Overriden from CTransformFilter base class 
	HRESULT Receive(IMediaSample* pSample), 
			Transform(IMediaSample* pIn, IMediaSample* pOut), 
			CheckInputType(const CMediaType* mtIn), 
			CheckTransform(const CMediaType* mtIn, const CMediaType* mtOut), 
			DecideBufferSize(IMemAllocator* pAlloc, ALLOCATOR_PROPERTIES* pProperties), 
			GetMediaType(int iPosition, CMediaType* pMediaType), 
			SetMediaType(PIN_DIRECTION direction, const CMediaType* pMediaType), 
			CheckConnect(PIN_DIRECTION direction, IPin* pPin), 
			CompleteConnect(PIN_DIRECTION direction, IPin* pReceivePin), 
			BreakConnect(PIN_DIRECTION direction), 
			StartStreaming(),  
			StopStreaming(), 
			NewSegment(REFERENCE_TIME tStart, REFERENCE_TIME tStop, double dRate); 
 
	HRESULT CheckOutputType(const CMediaType* mtOut); 
 
    // Overriden from CBaseFilter base class 
	STDMETHODIMP JoinFilterGraph(IFilterGraph* pGraph, LPCWSTR pName); 
	STDMETHODIMP SetSyncSource(IReferenceClock* pClock); 
	STDMETHODIMP QueryFilterInfo(FILTER_INFO* pInfo); 
 
    CArray m_pTextInput; 
 
	CMyCustomAllocator m_Allocator; 
	bool m_fUsingOwnAllocator; 
 
	CBasePin* GetPin(int n); 
	int GetPinCount(); 
 
    // IDirectVobSub 
    STDMETHODIMP put_FileName(WCHAR* fn); 
	STDMETHODIMP get_LanguageCount(int* nLangs); 
	STDMETHODIMP get_LanguageName(int iLanguage, WCHAR** ppName); 
	STDMETHODIMP put_SelectedLanguage(int iSelected); 
	STDMETHODIMP put_PreBuffering(bool fDoPreBuffering); 
    STDMETHODIMP put_Placement(bool fOverridePlacement, int xperc, int yperc); 
    STDMETHODIMP put_VobSubSettings(bool fBuffer, bool fOnlyShowForcedSubs, bool fPolygonize); 
    STDMETHODIMP put_TextSettings(void* lf, int lflen, COLORREF color, bool fShadow, bool fOutline, bool fAdvancedRenderer); 
    STDMETHODIMP put_SubtitleTiming(int delay, int speedmul, int speeddiv); 
    STDMETHODIMP get_MediaFPS(bool* fEnabled, double* fps); 
    STDMETHODIMP put_MediaFPS(bool fEnabled, double fps); 
    STDMETHODIMP get_ZoomRect(NORMALIZEDRECT* rect); 
    STDMETHODIMP put_ZoomRect(NORMALIZEDRECT* rect); 
    STDMETHODIMP get_ColorFormat(int* iPosition); 
    STDMETHODIMP put_ColorFormat(int iPosition); 
	STDMETHODIMP HasConfigDialog(int iSelected); 
	STDMETHODIMP ShowConfigDialog(int iSelected, HWND hWndParent); 
 
    // ISpecifyPropertyPages 
    STDMETHODIMP GetPages(CAUUID* pPages); 
 
	// IAMStreamSelect 
	STDMETHODIMP Count(DWORD* pcStreams);  
	STDMETHODIMP Enable(long lIndex, DWORD dwFlags);  
	STDMETHODIMP Info(long lIndex, AM_MEDIA_TYPE** ppmt, DWORD* pdwFlags, LCID* plcid, DWORD* pdwGroup, WCHAR** ppszName, IUnknown** ppObject, IUnknown** ppUnk);   
 
    // CPersistStream 
	STDMETHODIMP GetClassID(CLSID* pClsid); 
 
protected: 
    CDirectVobSubFilter(TCHAR* tszName, LPUNKNOWN punk, HRESULT* phr, const GUID& guid); 
	virtual ~CDirectVobSubFilter(); 
 
protected: 
	BITMAPINFOHEADER m_bihIn, m_bihSub, m_bihOut; 
 
	HRESULT ChangeMediaType(int iPosition); 
 
	bool AdjustFrameSize(int& w, int& h); 
	HRESULT ConvertMediaTypeInputToOutput(CMediaType* pmt, int iVIHTemplate = -1, bool fVIH2 = false); 
 
	HRESULT Copy(BYTE* pOut, BYTE* pIn, SubImage* img); 
	HRESULT CopyYV12(BYTE* pOut, BYTE* pIn, SubImage* img); 
 
	HDC m_hdc; 
	HBITMAP m_hbm; 
	HFONT m_hfont; 
	void PrintMessages(BYTE* pOut); 
 
/* ResX2 */ 
	BYTE* m_pTempPicBuff; 
	bool m_fResX2Active; 
	void Scale2x(BYTE* pOut, BYTE* pIn); 
 
	// segment start time, absolute time 
	CRefTime m_tOff, m_tPrev; 
	int CalcCurrentTime(); 
 
	double m_fps; 
 
	// needed when opening a saved .grp  
	// without reconnecting we may not start playing 
	bool m_fAudioReconnected; 
 
	// 3.x- versions of microsoft's mpeg4 codec output flipped image 
	bool m_fMSMpeg4Fix; 
 
	// DivxPlus puts our picture upside-down on the tv 
	bool m_fDivxPlusFix; 
 
	// don't set the "hide subtitles" stream until we are finished with loading 
	bool m_fLoading; 
 
	bool Open(); 
 
	typedef enum {NONE, VOBSUB, TEXT} smode; 
	smode m_mode; 
 
	// lock for all subtitle sources (m_file, m_textlangs) 
	CCritSec m_fileLock; 
 
	int FindPreferedLanguage(bool fHideToo = true); 
	void UpdatePreferedLanguages(CString lang); 
 
//	int m_curIndex; 
 
	// vobsub file 
	CVobSubFile* m_file; 
 
	typedef CArray  TextLangs; 
	TextLangs m_textlangs; 
	int m_textidx; 
 
	bool InitRTSStreams(bool fApplyDefStyle = true); 
 
	// the text input pin is using these 
	void AddTextStream(CString name); 
	void AddNewEntryToTextStream(CString name, CString str, int start, int end); 
	void ChangeName(CString oldname, CString newname, bool fUnicode); 
	void ChangeName(CString oldname, CString newname); 
	void RemoveEntriesFromTextStream(CString name); 
	void RemoveTextStream(CString name); 
	void OpenRawTextSubtitle(CString name, BYTE* data, int len); 
 
	// Whether the text output pins of AVI splitter get connected to our input pins  
	// depends on their rendering order. Since I haven't found a better way yet, we  
	// just simply reconnect them to ours... 
	bool m_fTextStreamWorkaroundDone; 
	void HookTextStreams(); 
 
	// support for EC_OLE_EVENT 
	void Post_EC_OLE_EVENT(); 
	int m_iLastSegmentPosted; 
 
protected: 
	class SubImageCache 
	{ 
		HDC hdc; 
		HFONT hfont; 
		SubImage imgs[MAXSUBIMAGECACHE]; 
		 
		int pos, size, start, stop; 
 
		void RemoveOldest(); 
 
	public: 
		int w, h; 
 
		SubImageCache(); 
		virtual ~SubImageCache(); 
 
		void Init(int width, int heigth), DeInit(); 
		void SetFont(LOGFONT* lf); 
 
		void Update(int PTS); 
		void RemoveAll(); 
		void FreeExtra(int PTS); 
 
		void MarkAsStart(int PTS), MarkAsEnd(int PTS); 
 
		int SeekToEnd(int PTS); 
 
		bool CachedEnough(), CachedEnough(int PTS); 
 
		SubImage 
			* LookupSubImage(int PTS), 
			* GetSubImage(int i), // i is a logical value ((pos+i)%MAXSUBIMAGECACHE) 
			* GetLast(),  
			* GetNextFree(); // returns a pointer to the first free slot in the queue (or NULL when full) 
 
		// call this after being ready with setting up what GetNextFree() returned 
		// it will also do a stop = imgs['next'].stop 
		void MarkNextAsOccupied();  
 
		void GetStats(int& start, int& stop, int& pos, int& size); 
		int GetSize() {return(size);} 
 
		HDC GetDC() {return(hdc);} // we would need a lock on hdc and a ReleaseDC() too, but it works just fine without it... 
		HFONT GetFont() {return(hfont);} 
 
		CCritSec m_csAccessLock; 
	}; 
 
	SubImageCache m_sic; 
 
	enum {CMD_EXIT, CMD_INIT, CMD_RESET, CMD_BREAK, CMD_SETFONT, CMD_SETPTS}; 
 
    DWORD ThreadProc(); 
	bool m_fThreadActive, m_fBreakBuffering; 
 
	SubImage* GetSubImage(); 
 
	void AddVobSub(SubImage* img, int start, int stop); 
	void AddText(SubImage* img, int start, int stop, int PTS); 
 
private: 
	class CFileReloaderData 
	{ 
	public: 
		HANDLE hThread, hEndThreadEvent, hRefreshEvent; 
		CStringArray files; 
		CArray mtime; 
		CDirectVobSubFilter* pFilter; 
	} m_frd; 
 
	static void SetupFRD(CFileReloaderData* frd, CStringArray& paths, CArray& handles); 
	static DWORD WINAPI FileReloaderThreadProc(LPVOID lpParameter); 
 
private: 
	HANDLE m_hSystrayThread; 
	SystrayIconData m_tbid; 
 
private: 
	bool m_fVMRFilter, m_fVMRFilterActive; 
 
/* 
private: 
	CComPtr m_pDD; 
*/ 
}; 
 
/* The "auto-loading" version */ 
 
class CDirectVobSubFilter2 :  
		public CDirectVobSubFilter 
{ 
	bool ShouldWeAutoload(IFilterGraph* pGraph); 
	void GetRidOfInternalScriptRenderer(); 
 
public: 
    static CUnknown* WINAPI CreateInstance(LPUNKNOWN punk, HRESULT* phr); 
 
	// Overriden from CTransformFilter base class 
	HRESULT CheckConnect(PIN_DIRECTION dir, IPin* pPin); 
	STDMETHODIMP JoinFilterGraph(IFilterGraph* pGraph, LPCWSTR pName); 
    HRESULT CheckInputType(const CMediaType* mtIn); 
 
    STDMETHODIMP GetClassID(CLSID* pClsid); 
 
private: 
    CDirectVobSubFilter2(TCHAR* tszName, LPUNKNOWN punk, HRESULT* phr, const GUID& guid); 
};