www.pudn.com > PCMsdgl.rar > PCMSelect.cpp


 
#include     
 
#include    
 
#include "resource.h" 
 
DEFINE_GUID(CLSID_PCMSelect, 
	0x18bf6fde, 0xb42c, 0x4df0, 0x8d, 0xeb, 0x22, 0x66, 0x2b, 0xb0, 0xac, 0x48); 
 
DEFINE_GUID(CLSID_PCMSelectProp, 
	0x7f2c122e, 0x957f, 0x49e3, 0xab, 0xc1, 0x7f, 0x4, 0x70, 0xad, 0x14, 0x3d); 
 
DEFINE_GUID(IID_IPCMSELECT, 
	0x9dc7617b, 0x1d1f, 0x44dc, 0xac, 0xd8, 0x91, 0x5b, 0xaa, 0x5b, 0x13, 0x24); 
 
    DECLARE_INTERFACE_(IPCMSELECT, IUnknown) 
    { 
        STDMETHOD(get_PCMChannel) (THIS_ int *channel) PURE; 
 
        STDMETHOD(put_PCMChannel) (THIS_ int channel) PURE; 
    }; 
 
class CPCMSelect : public CTransInPlaceFilter, public IPCMSELECT, public ISpecifyPropertyPages 
{ 
public: 
    static CUnknown *WINAPI CreateInstance(LPUNKNOWN punk, HRESULT *phr); 
 
    DECLARE_IUNKNOWN; 
 
public: 
	int m_wbits; 
	int m_channel; 
 
private: 
 
    CPCMSelect(TCHAR *tszName, LPUNKNOWN punk, HRESULT *phr)  
		: CTransInPlaceFilter (tszName, punk, CLSID_PCMSelect, phr) 
    { 
		m_channel = 0; 
		m_wbits =16; 
	} 
 
	STDMETHODIMP get_PCMChannel(int *channel) 
	{ 
		*channel = m_channel; 
 
		return NOERROR; 
	} 
 
    STDMETHODIMP put_PCMChannel(int  channel) 
	{ 
		m_channel = channel; 
 
		return NOERROR; 
	} 
 
    STDMETHODIMP NonDelegatingQueryInterface(REFIID riid, void ** ppv) 
	{	    
		CheckPointer(ppv,E_POINTER); 
    
		if (riid == IID_IPCMSELECT)  
			return GetInterface((IPCMSELECT *) this, ppv); 
		else if (riid == IID_ISpecifyPropertyPages)  
			return GetInterface((ISpecifyPropertyPages *) this, ppv); 
		else  
			return CTransformFilter::NonDelegatingQueryInterface(riid, ppv); 
	} 
 
    STDMETHODIMP GetPages(CAUUID * pPages) 
	{	    
		pPages->cElems = 1; 
		pPages->pElems = (GUID *) CoTaskMemAlloc(sizeof(GUID)); 
		if (pPages->pElems == NULL)  
		{ 
			return E_OUTOFMEMORY; 
		} 
		*(pPages->pElems) = CLSID_PCMSelectProp; 
 
		return NOERROR; 
	} 
 
    HRESULT Transform(IMediaSample *pSample) 
	{  
		BYTE* buf; 
		pSample->GetPointer(&buf); 
		int len=pSample->GetActualDataLength(); 
		if(len <= 0) 
			return NOERROR; 
 
		if( m_channel == 0 ) // left 
		{ 
			if( m_wbits == 16 ) 
			{ 
				__asm 
				{ 
					cld 
					mov  ecx, len 
					shr  ecx, 2 
 
					mov  esi, buf 
					mov  edi, esi 
					add  edi, 2 
 
					mov  eax, 2 
			loop1: 
					movsw  
					add esi, eax 
					add edi, eax 
 
					dec ecx 
					jg loop1	 
				} 
			} 
			else //if( m_wbits == 8 ) 
			{ 
				__asm 
				{ 
					cld 
					mov  ecx, len 
					shr  ecx, 1 
 
					mov  esi, buf 
					mov  edi, esi 
					add  edi, 1 
 
					mov  eax, 1 
			loop2: 
					movsb  
					add esi, eax 
					add edi, eax 
 
					dec ecx 
					jg loop2	 
				} 
 
			} 
		} 
		else if( m_channel == 1 ) 
		{ 
			if( m_wbits == 16 ) 
			{ 
				__asm 
				{ 
					cld  
					mov  ecx, len 
					shr  ecx, 2 
 
					mov  edi, buf 
					mov  esi, edi 
					add  esi, 2 
 
					mov  eax, 2 
			loop3: 
					movsw  
					add esi, eax 
					add edi, eax 
 
					dec ecx 
					jg loop3	 
				} 
			} 
			else //if( m_wbits == 8 ) 
			{ 
				__asm 
				{ 
					cld  
					mov  ecx, len 
					shr  ecx, 1 
 
					mov  edi, buf 
					mov  esi, edi 
					add  esi, 1 
 
					mov  eax, 1 
			loop4: 
					movsw  
					add esi, eax 
					add edi, eax 
 
					dec ecx 
					jg loop4	 
				} 
			} 
		} 
 
		return NOERROR;  
	} 
 
    HRESULT CheckInputType(const CMediaType* mtIn)  
	{ 
		if (mtIn->majortype != MEDIATYPE_Audio)  
			return VFW_E_TYPE_NOT_ACCEPTED; 
 
		if (mtIn->subtype != MEDIASUBTYPE_PCM) 
			return VFW_E_TYPE_NOT_ACCEPTED; 
 
		WAVEFORMATEX *pwfx = (WAVEFORMATEX *) mtIn->pbFormat; 
		m_wbits=pwfx->wBitsPerSample; 
 
		if(m_wbits==8 || m_wbits==16) 
			return S_OK;  
		else 
			return VFW_E_TYPE_NOT_ACCEPTED; 
	} 
}; 
 
class CPCMSelectProp : public CBasePropertyPage 
{ 
public: 
    static CUnknown * WINAPI CreateInstance(LPUNKNOWN lpunk, HRESULT *phr); 
	 
    BOOL m_bIsInitialized;      
    IPCMSELECT *m_pIPCMSelect;    
	int  m_channel; 
 
public: 
	CPCMSelectProp(LPUNKNOWN lpunk, HRESULT *phr) 
		: CBasePropertyPage( NAME("Tinck PCM Select Prop"), lpunk, IDD_PCMSELECTPROP, IDS_NAME) 
	{ 
	} 
 
	~CPCMSelectProp() 
	{ 
	} 
 
    BOOL OnReceiveMessage(HWND hwnd,UINT uMsg,WPARAM wParam,LPARAM lParam) 
	{ 
		if( uMsg == WM_COMMAND && m_bIsInitialized ) 
		{ 
            m_bDirty = TRUE; 
            if (m_pPageSite) 
            { 
                m_pPageSite->OnStatusChange(PROPPAGESTATUS_DIRTY); 
            } 
 
            return (LRESULT) 1; 
        } 
 
        return CBasePropertyPage::OnReceiveMessage(hwnd,uMsg,wParam,lParam); 
	} 
 
    HRESULT OnConnect(IUnknown *pUnknown) 
	{   
		HRESULT hr = pUnknown->QueryInterface(IID_IPCMSELECT, (void **) &m_pIPCMSelect); 
		if (FAILED(hr))  
		{ 
			return E_NOINTERFACE; 
		} 
 
		m_pIPCMSelect->get_PCMChannel(&m_channel); 
 
		m_bIsInitialized = FALSE ; 
		return NOERROR; 
	} 
 
    HRESULT OnDisconnect() 
	{ 
		if(m_pIPCMSelect) 
		{ 
			m_pIPCMSelect->Release(); 
			m_pIPCMSelect = NULL; 
		} 
		return NOERROR; 
	} 
 
    HRESULT OnActivate() 
	{ 
		CheckRadioButton(m_Dlg, IDC_RADIO1, IDC_RADIO3, IDC_RADIO1+m_channel); 
 
		m_bIsInitialized = TRUE; 
 
		return NOERROR; 
	} 
 
    HRESULT OnDeactivate() 
	{  
		m_bIsInitialized = FALSE; 
     
		GetControlValues(); 
 
		return NOERROR; 
	} 
 
    HRESULT OnApplyChanges() 
	{ 
		GetControlValues(); 
 
		m_pIPCMSelect->put_PCMChannel(m_channel); 
 
		return NOERROR; 
	} 
 
    void    GetControlValues() 
	{ 
		if (IsDlgButtonChecked(m_Dlg, IDC_RADIO1))  
		{ 
			m_channel = 0; 
		} 
		else if (IsDlgButtonChecked(m_Dlg, IDC_RADIO2))  
		{ 
			m_channel = 1; 
		} 
		else //if (IsDlgButtonChecked(m_Dlg, IDC_RADIO3))  
		{ 
			m_channel = 2; 
		} 
	} 
};   
 
//----------------------------------------------------------------------------- 
 
const AMOVIESETUP_MEDIATYPE sudPinTypes = 
{ 
	&MEDIATYPE_Audio, &MEDIASUBTYPE_PCM 
}; 
 
const AMOVIESETUP_PIN psudPins[] = 
{ 
	{ L"Input"            // strName 
	, FALSE               // bRendered 
	, FALSE               // bOutput 
	, FALSE               // bZero 
	, FALSE               // bMany 
	, &CLSID_NULL         // clsConnectsToFilter 
	, L""                 // strConnectsToPin 
	, 1                   // nTypes 
	, &sudPinTypes        // lpTypes 
	} 
	, { L"Output"           // strName 
	, FALSE               // bRendered 
	, TRUE                // bOutput 
	, FALSE               // bZero 
	, FALSE               // bMany 
	, &CLSID_NULL         // clsConnectsToFilter 
	, L""                 // strConnectsToPin 
	, 1                   // nTypes 
	, &sudPinTypes        // lpTypes 
	} 
}; 
 
const AMOVIESETUP_FILTER sudNullNull = 
{  
	&CLSID_PCMSelect	// clsID 
	, L"Tinck PCM Select"	// strName 
	, MERIT_DO_NOT_USE  // dwMerit 
	, 2                 // nPins 
	, psudPins          // lpPin 
}; 
 
CFactoryTemplate g_Templates[2]=  
{  
	{ L"Tinck PCM Select" 
       , &CLSID_PCMSelect 
       , CPCMSelect::CreateInstance 
       , NULL 
       , &sudNullNull 
    } 
    ,  
	{ L"Tinck PCM Select Prop" 
       , &CLSID_PCMSelectProp 
       , CPCMSelectProp::CreateInstance 
    } 
}; 
 
int g_cTemplates = sizeof(g_Templates)/sizeof(g_Templates[0]); 
 
CUnknown * WINAPI CPCMSelect::CreateInstance(LPUNKNOWN punk, HRESULT *phr)  
{ 
    CheckPointer(phr,NULL); 
     
    CPCMSelect *pNewObject = new CPCMSelect(NAME("Tinck PCM Select"), punk, phr ); 
 
    if (pNewObject == NULL)  
        *phr = E_OUTOFMEMORY; 
 
    return pNewObject; 
}  
 
CUnknown * WINAPI CPCMSelectProp::CreateInstance(LPUNKNOWN lpunk, HRESULT *phr) 
{ 
    CUnknown *punk = new CPCMSelectProp(lpunk, phr); 
  
    return punk; 
}  
 
STDAPI DllRegisterServer() 
{ 
	return AMovieDllRegisterServer2( TRUE ); 
} 
 
STDAPI DllUnregisterServer() 
{ 
	return AMovieDllRegisterServer2( FALSE ); 
} 
 
extern "C" BOOL WINAPI DllEntryPoint(HINSTANCE, ULONG, LPVOID); 
 
BOOL APIENTRY DllMain(HANDLE hModule, DWORD  dwReason, LPVOID lpReserved) 
{ 
	return DllEntryPoint((HINSTANCE)(hModule), dwReason, lpReserved); 
} 
 
#pragma warning( disable:4514)