00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022 #pragma once
00023
00024 #include <atlcoll.h>
00025 #include <afxtempl.h>
00026 #include <Videoacc.h>
00027 #include "IMpeg2DecFilter.h"
00028 #include "..\..\..\decss\DeCSSInputPin.h"
00029 #include "..\BaseVideoFilter\BaseVideoFilter.h"
00030
00031 class CSubpicInputPin;
00032 class CClosedCaptionOutputPin;
00033 class CMpeg2Dec;
00034
00035 [uuid("39F498AF-1A09-4275-B193-673B0BA3D478")]
00036 class CMpeg2DecFilter : public CBaseVideoFilter, public IMpeg2DecFilter
00037 {
00038 CSubpicInputPin* m_pSubpicInput;
00039 CClosedCaptionOutputPin* m_pClosedCaptionOutput;
00040 CAutoPtr<CMpeg2Dec> m_dec;
00041 REFERENCE_TIME m_AvgTimePerFrame;
00042 bool m_fWaitForKeyFrame;
00043 bool m_fFilm;
00044 struct framebuf
00045 {
00046 int w, h, pitch;
00047 BYTE* buf[6];
00048 REFERENCE_TIME rtStart, rtStop;
00049 DWORD flags;
00050 framebuf()
00051 {
00052 w = h = pitch = 0;
00053 memset(&buf, 0, sizeof(buf));
00054 rtStart = rtStop = 0;
00055 flags = 0;
00056 }
00057 ~framebuf() {free();}
00058 void alloc(int w, int h, int pitch)
00059 {
00060 this->w = w; this->h = h; this->pitch = pitch;
00061 buf[0] = (BYTE*)_aligned_malloc(pitch*h, 16); buf[3] = (BYTE*)_aligned_malloc(pitch*h, 16);
00062 buf[1] = (BYTE*)_aligned_malloc(pitch*h/4, 16); buf[4] = (BYTE*)_aligned_malloc(pitch*h/4, 16);
00063 buf[2] = (BYTE*)_aligned_malloc(pitch*h/4, 16); buf[5] = (BYTE*)_aligned_malloc(pitch*h/4, 16);
00064 }
00065 void free() {for(int i = 0; i < 6; i++) {_aligned_free(buf[i]); buf[i] = NULL;}}
00066 } m_fb;
00067
00068 AM_SimpleRateChange m_rate;
00069
00070 protected:
00071 void InputTypeChanged();
00072 HRESULT Transform(IMediaSample* pIn);
00073
00074 public:
00075 CMpeg2DecFilter(LPUNKNOWN lpunk, HRESULT* phr);
00076 virtual ~CMpeg2DecFilter();
00077
00078 DECLARE_IUNKNOWN
00079 STDMETHODIMP NonDelegatingQueryInterface(REFIID riid, void** ppv);
00080
00081 HRESULT Deliver(bool fRepeatLast);
00082
00083 int GetPinCount();
00084 CBasePin* GetPin(int n);
00085
00086 HRESULT EndOfStream();
00087 HRESULT BeginFlush();
00088 HRESULT EndFlush();
00089 HRESULT NewSegment(REFERENCE_TIME tStart, REFERENCE_TIME tStop, double dRate);
00090
00091 HRESULT CheckConnect(PIN_DIRECTION dir, IPin* pPin);
00092 HRESULT CheckInputType(const CMediaType* mtIn);
00093 HRESULT CheckTransform(const CMediaType* mtIn, const CMediaType* mtOut);
00094
00095 HRESULT StartStreaming();
00096 HRESULT StopStreaming();
00097
00098 bool m_fDropFrames;
00099 HRESULT AlterQuality(Quality q);
00100
00101 protected:
00102 CCritSec m_csProps;
00103 ditype m_di;
00104 double m_bright, m_cont, m_hue, m_sat;
00105 BYTE m_YTbl[256], m_UTbl[256*256], m_VTbl[256*256];
00106 bool m_fForcedSubs;
00107 bool m_fPlanarYUV;
00108
00109 static void CalcBrCont(BYTE* YTbl, double bright, double cont);
00110 static void CalcHueSat(BYTE* UTbl, BYTE* VTbl, double hue, double sat);
00111 void ApplyBrContHueSat(BYTE* srcy, BYTE* srcu, BYTE* srcv, int w, int h, int pitch);
00112
00113 public:
00114
00115
00116 STDMETHODIMP SetDeinterlaceMethod(ditype di);
00117 STDMETHODIMP_(ditype) GetDeinterlaceMethod();
00118
00119 STDMETHODIMP SetBrightness(double bright);
00120 STDMETHODIMP SetContrast(double cont);
00121 STDMETHODIMP SetHue(double hue);
00122 STDMETHODIMP SetSaturation(double sat);
00123 STDMETHODIMP_(double) GetBrightness();
00124 STDMETHODIMP_(double) GetContrast();
00125 STDMETHODIMP_(double) GetHue();
00126 STDMETHODIMP_(double) GetSaturation();
00127
00128 STDMETHODIMP EnableForcedSubtitles(bool fEnable);
00129 STDMETHODIMP_(bool) IsForcedSubtitlesEnabled();
00130
00131 STDMETHODIMP EnablePlanarYUV(bool fEnable);
00132 STDMETHODIMP_(bool) IsPlanarYUVEnabled();
00133 };
00134
00135 class CMpeg2DecInputPin : public CDeCSSInputPin
00136 {
00137 LONG m_CorrectTS;
00138
00139 public:
00140 CMpeg2DecInputPin(CTransformFilter* pFilter, HRESULT* phr, LPWSTR pName);
00141
00142 CCritSec m_csRateLock;
00143 AM_SimpleRateChange m_ratechange;
00144
00145
00146 STDMETHODIMP Set(REFGUID PropSet, ULONG Id, LPVOID InstanceData, ULONG InstanceLength, LPVOID PropertyData, ULONG DataLength);
00147 STDMETHODIMP Get(REFGUID PropSet, ULONG Id, LPVOID InstanceData, ULONG InstanceLength, LPVOID PropertyData, ULONG DataLength, ULONG* pBytesReturned);
00148 STDMETHODIMP QuerySupported(REFGUID PropSet, ULONG Id, ULONG* pTypeSupport);
00149 };
00150
00151 class CSubpicInputPin : public CMpeg2DecInputPin
00152 {
00153 CCritSec m_csReceive;
00154
00155 AM_PROPERTY_COMPOSIT_ON m_spon;
00156 AM_DVD_YUV m_sppal[16];
00157 bool m_fsppal;
00158 CAutoPtr<AM_PROPERTY_SPHLI> m_sphli;
00159
00160 struct spu
00161 {
00162 bool m_fForced;
00163 REFERENCE_TIME m_rtStart, m_rtStop;
00164 CArray<BYTE> m_pData;
00165 DWORD m_offset[2];
00166 AM_PROPERTY_SPHLI m_sphli;
00167 CAutoPtr<AM_PROPERTY_SPHLI> m_psphli;
00168 struct spu() {memset(&m_sphli, 0, sizeof(m_sphli)); m_fForced = false; m_rtStart = m_rtStop = 0;}
00169 virtual bool Parse() = 0;
00170 virtual void Render(BYTE** p, int w, int h, AM_DVD_YUV* sppal, bool fsppal) = 0;
00171 };
00172
00173 struct dvdspu : public spu
00174 {
00175 bool Parse();
00176 void Render(BYTE** p, int w, int h, AM_DVD_YUV* sppal, bool fsppal);
00177 };
00178
00179 struct cvdspu : public spu
00180 {
00181 AM_DVD_YUV m_sppal[2][4];
00182 struct cvdspu() {memset(m_sppal, 0, sizeof(m_sppal));}
00183 bool Parse();
00184 void Render(BYTE** p, int w, int h, AM_DVD_YUV* sppal, bool fsppal);
00185 };
00186
00187 struct svcdspu : public spu
00188 {
00189 AM_DVD_YUV m_sppal[4];
00190 struct svcdspu() {memset(m_sppal, 0, sizeof(m_sppal));}
00191 bool Parse();
00192 void Render(BYTE** p, int w, int h, AM_DVD_YUV* sppal, bool fsppal);
00193 };
00194
00195 CAutoPtrList<spu> m_sps;
00196
00197 protected:
00198 HRESULT Transform(IMediaSample* pSample);
00199
00200 public:
00201 CSubpicInputPin(CTransformFilter* pFilter, HRESULT* phr);
00202
00203 bool HasAnythingToRender(REFERENCE_TIME rt);
00204 void RenderSubpics(REFERENCE_TIME rt, BYTE** p, int w, int h);
00205
00206 HRESULT CheckMediaType(const CMediaType* mtIn);
00207 HRESULT SetMediaType(const CMediaType* mtIn);
00208
00209
00210 STDMETHODIMP EndOfStream() {return S_OK;}
00211 STDMETHODIMP BeginFlush() {return S_OK;}
00212 STDMETHODIMP EndFlush();
00213 STDMETHODIMP NewSegment(REFERENCE_TIME tStart, REFERENCE_TIME tStop, double dRate) {return S_OK;}
00214
00215
00216 STDMETHODIMP Set(REFGUID PropSet, ULONG Id, LPVOID InstanceData, ULONG InstanceLength, LPVOID PropertyData, ULONG DataLength);
00217 STDMETHODIMP QuerySupported(REFGUID PropSet, ULONG Id, ULONG* pTypeSupport);
00218 };
00219
00220 class CClosedCaptionOutputPin : public CBaseOutputPin
00221 {
00222 public:
00223 CClosedCaptionOutputPin(CBaseFilter* pFilter, CCritSec* pLock, HRESULT* phr);
00224
00225 HRESULT CheckMediaType(const CMediaType* mtOut);
00226 HRESULT GetMediaType(int iPosition, CMediaType* pmt);
00227 HRESULT DecideBufferSize(IMemAllocator* pAllocator, ALLOCATOR_PROPERTIES* pProperties);
00228
00229 CMediaType& CurrentMediaType() {return m_mt;}
00230 };