timgfilterchroma.cpp
来自「从FFMPEG转换而来的H264解码程序,VC下编译..」· C++ 代码 · 共 96 行
CPP
96 行
/*
* Copyright (c) 2002-2006 Milan Cutka
* based on AviSynth filter by Donald A. Graft
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
#include "stdafx.h"
#include "TimgFilterChroma.h"
#include "TpictPropSettings.h"
#include "simd.h"
#include "Tconfig.h"
TimgFilterChroma::TimgFilterChroma(IffdshowBase *Ideci,Tfilters *Iparent):TimgFilter(Ideci,Iparent)
{
#ifdef __SSE2__
if (Tconfig::cpu_flags&FF_CPU_SSE2)
chromaFc=&TimgFilterChroma::chroma<Tsse2>;
else
#endif
chromaFc=&TimgFilterChroma::chroma<Tmmx>;
for (int i=-180,ii=0;i<=180;ii++,i++)
{
double Hue=(i*3.1415926)/180.0;
hueSin[ii]=short(sin(Hue)*128);
hueCos[ii]=short(cos(Hue)*128);
}
}
bool TimgFilterChroma::is(const TffPictBase &pict,const TfilterSettingsVideo *cfg0)
{
const TpictPropSettings *cfg=(const TpictPropSettings*)cfg0;
return super::is(pict,cfg) && (cfg->hue!=cfg->hueDef || cfg->saturation!=cfg->saturationDef);
}
template<class _mm> void TimgFilterChroma::chroma(const TpictPropSettings *cfg,const unsigned char *srcU,const unsigned char *srcV,unsigned char *dstU,unsigned char *dstV)
{
typename _mm::__m Sin64=_mm::set1_pi16(hueSin[cfg->hue+180]);
typename _mm::__m Cos64=_mm::set1_pi16(hueCos[cfg->hue+180]);
typename _mm::__m Sat64=_mm::set1_pi16((short)cfg->saturation);
typename _mm::__m m0=_mm::setzero_si64(),m128=_mm::set1_pi16(128);
for (const unsigned char *srcUend=srcU+stride1[1]*dy1[1];srcU!=srcUend;srcU+=stride1[1],srcV+=stride1[2],dstU+=stride2[1],dstV+=stride2[2])
{
int x=0;
const int dx113=dx1[1]-_mm::size/2+1;
for (;x<dx113;x+=_mm::size/2)
{
typename _mm::__m u=_mm::subs_pi16(_mm::unpacklo_pi8(_mm::load2(srcU+x),m0),m128);
typename _mm::__m v=_mm::subs_pi16(_mm::unpacklo_pi8(_mm::load2(srcV+x),m0),m128);
typename _mm::__m u1=_mm::add_pi16(_mm::srai_pi16(_mm::mullo_pi16(_mm::add_pi16(_mm::srai_pi16(_mm::mullo_pi16(u,Cos64),7),_mm::srai_pi16(_mm::mullo_pi16(v,Sin64),7)),Sat64),6),m128);
typename _mm::__m v1=_mm::add_pi16(_mm::srai_pi16(_mm::mullo_pi16(_mm::sub_pi16(_mm::srai_pi16(_mm::mullo_pi16(v,Cos64),7),_mm::srai_pi16(_mm::mullo_pi16(u,Sin64),7)),Sat64),6),m128);
_mm::store2(dstU+x,_mm::packs_pu16(u1,m0));
_mm::store2(dstV+x,_mm::packs_pu16(v1,m0));
}
for (;x<(int)dx1[1];x++)
{
int u=srcU[x]-128;
int v=srcV[x]-128;
int u2=((u*hueCos[cfg->hue+180])>>7)+((v*hueSin[cfg->hue+180])>>7);
int v2=((v*hueCos[cfg->hue+180])>>7)-((u*hueSin[cfg->hue+180])>>7);
u=((u2*cfg->saturation)>>6)+128;
v=((v2*cfg->saturation)>>6)+128;
dstU[x]=limit_uint8(u);
dstV[x]=limit_uint8(v);
}
}
_mm::empty();
}
HRESULT TimgFilterChroma::process(TfilterQueue::iterator it,TffPict &pict,const TfilterSettingsVideo *cfg0)
{
if (is(pict,cfg0))
{
const TpictPropSettings *cfg=(const TpictPropSettings*)cfg0;
init(pict,cfg->full,cfg->half);
const unsigned char *srcU,*srcV;
getCur(FF_CSPS_MASK_YUV_PLANAR,pict,cfg->full,NULL,&srcU,&srcV,NULL);
unsigned char *dstU,*dstV;
getCurNext(csp1,pict,cfg->full,COPYMODE_NO,NULL,&dstU,&dstV,NULL);
(this->*chromaFc)(cfg,srcU,srcV,dstU,dstV);
}
return parent->deliverSample(++it,pict);
}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?