timgfiltersmoother.cpp
来自「从FFMPEG转换而来的H264解码程序,VC下编译..」· C++ 代码 · 共 464 行 · 第 1/2 页
CPP
464 行
/*
* Copyright (c) 2002-2006 Milan Cutka
* based on VirtualDub Smoother filter by Avery Lee
*
* 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 "TimgFilterSmoother.h"
#include "TblurSettings.h"
//================================= TimgFilterSmootherLuma::Tblur =================================
void TimgFilterSmootherLuma::Tblur::avgrow(const unsigned char *src,unsigned char *dst,unsigned int width)
{
int r0=*src++;
int sum=r0*4;
unsigned int w=1;
do
{
unsigned char c=src[0];
sum+=c;
++src;
} while(--w);
w=3;
do
{
unsigned char c=src[0];
sum=sum+c-r0;
*dst++=(unsigned char)(sum/5);
++src;
} while(--w);
w=width-6;
do
{
unsigned char c=src[0],d=src[-5];
sum=sum+c-d;
*dst++=(unsigned char)(sum/5);
++src;
} while(--w);
r0=*src++;
w=3;
do
{
unsigned char d=src[-5];
sum=sum-d+r0;
*dst++=(unsigned char)(sum/5);
++src;
} while(--w);
}
void TimgFilterSmootherLuma::Tblur::filtrow_1(unsigned char *sum,const unsigned char *src,unsigned int dx,stride_t stride,int thresh)
{
long bitarray=0;
src=src-stride;
do
{
// Fetch surrounding pixels.
unsigned char pl=*((src-1)+stride);
unsigned char pr=*((src+1)+stride);
unsigned char pu=*src;
unsigned char pd=*(src+stride*2);
// Compute gradient at pixel.
int grad_x=pr-pl;
int grad_y=pu-pd;
bitarray >>=1;
// if (grad_x*grad_x+grad_y*grad_y > thresh) {
if (smoother_blur_square_table[765+grad_x]+smoother_blur_square_table[765+grad_y] > thresh)
bitarray |=16;
*sum++=smoother_blur_codes[bitarray];
++src;
} while(--dx>0);
*sum++=smoother_blur_codes[bitarray>>1];
*sum++=smoother_blur_codes[bitarray>>2];
}
TimgFilterSmootherLuma::Tblur::Tblur(unsigned int Idx,unsigned int Idy):dx(Idx),dy(Idy)
{
for (int i=0;i<5;i++) sum_row[i]=new unsigned char[dx+2];
for (int i=0;i<5;i++) avg_row[i]=new unsigned char[dx];
}
TimgFilterSmootherLuma::Tblur::~Tblur()
{
for(int i=0;i<5;i++) if (sum_row[i]) delete []sum_row[i];
for(int i=0;i<5;i++) if (avg_row[i]) delete []avg_row[i];
}
void TimgFilterSmootherLuma::Tblur::run(const unsigned char *src,stride_t srcStride,unsigned char *dst,stride_t dstStride,int g_thresh)
{
long w,h,x;
int next_row=0,next_avg_row=0;
unsigned char *avg_rows[5];
unsigned char *row[5];
int i;
const unsigned char *srcf;
unsigned char *avg;
srcf=src;
avgrow(src+0*srcStride,avg_row[1],dx);
memcpy(avg_row[2],avg_row[1],dx);
memcpy(avg_row[3],avg_row[1],dx);
avgrow(src+1*srcStride,avg_row[4],dx);
memset(sum_row[1],0,dx+2);
memset(sum_row[2],0,dx+2);
memset(sum_row[3],0,dx+2);
filtrow_1(sum_row[4],(srcf+1)+srcStride,dx-2,srcStride,g_thresh);
h=dy;
do
{
if (h>3)
filtrow_1(sum_row[next_row],(srcf+1)+srcStride*2,dx-2,srcStride,g_thresh);
else
memset(sum_row[next_row],0,dx+2);
avg=avg_row[next_avg_row];
if (h>2)
avgrow(src+2*srcStride,avg,dx);
else
memcpy(avg,avg_row[(next_avg_row+4)%5],dx);
if (++next_row>=5) next_row=0;
for(i=0;i<5;i++) row[i]=sum_row[(next_row+i)%5];
if (++next_avg_row>=5) next_avg_row=0;
for(i=0;i<5;i++) avg_rows[i]=avg_row[(next_avg_row+i)%5];
w=dx;
x=0;
do
{
int s=(int)(row[0][x]&0xe0)+(int)row[1][x]+(int)row[2][x]+(int)row[3][x]+(int)(row[4][x]&0xe0);
int A=s&31;
if (A>3)
*dst=*src;
else
{
int B=s>>5;
int p0=avg_rows[0][x];
int p1=avg_rows[1][x];
int p2=avg_rows[2][x];
int p3=avg_rows[3][x];
int p4=avg_rows[4][x];
int r=p0+p1*2+p2*2+p3*2+p4;
if (A>1)
{
int d=*src;
r+=d<<3;
*dst=(unsigned char)(r>>4);
}
else if (B>3)
{
int d=*src;
r=r*3+(d<<3);
*dst=(unsigned char)(r>>5);
}
else
*dst=(unsigned char)(r>>3);
}
++src;
++dst;
} while(++x<w);
src+=srcStride-dx;
dst+=dstStride-dx;
srcf+=srcStride;
} while(--h>0);
}
const int TimgFilterSmootherLuma::Tblur::smoother_blur_square_table[765*2+1]=
{
0x0008ee09,0x0008e810,0x0008e219,0x0008dc24,0x0008d631,0x0008d040,0x0008ca51,0x0008c464,
0x0008be79,0x0008b890,0x0008b2a9,0x0008acc4,0x0008a6e1,0x0008a100,0x00089b21,0x00089544,
0x00088f69,0x00088990,0x000883b9,0x00087de4,0x00087811,0x00087240,0x00086c71,0x000866a4,
0x000860d9,0x00085b10,0x00085549,0x00084f84,0x000849c1,0x00084400,0x00083e41,0x00083884,
0x000832c9,0x00082d10,0x00082759,0x000821a4,0x00081bf1,0x00081640,0x00081091,0x00080ae4,
0x00080539,0x0007ff90,0x0007f9e9,0x0007f444,0x0007eea1,0x0007e900,0x0007e361,0x0007ddc4,
0x0007d829,0x0007d290,0x0007ccf9,0x0007c764,0x0007c1d1,0x0007bc40,0x0007b6b1,0x0007b124,
0x0007ab99,0x0007a610,0x0007a089,0x00079b04,0x00079581,0x00079000,0x00078a81,0x00078504,
0x00077f89,0x00077a10,0x00077499,0x00076f24,0x000769b1,0x00076440,0x00075ed1,0x00075964,
0x000753f9,0x00074e90,0x00074929,0x000743c4,0x00073e61,0x00073900,0x000733a1,0x00072e44,
0x000728e9,0x00072390,0x00071e39,0x000718e4,0x00071391,0x00070e40,0x000708f1,0x000703a4,
0x0006fe59,0x0006f910,0x0006f3c9,0x0006ee84,0x0006e941,0x0006e400,0x0006dec1,0x0006d984,
0x0006d449,0x0006cf10,0x0006c9d9,0x0006c4a4,0x0006bf71,0x0006ba40,0x0006b511,0x0006afe4,
0x0006aab9,0x0006a590,0x0006a069,0x00069b44,0x00069621,0x00069100,0x00068be1,0x000686c4,
0x000681a9,0x00067c90,0x00067779,0x00067264,0x00066d51,0x00066840,0x00066331,0x00065e24,
0x00065919,0x00065410,0x00064f09,0x00064a04,0x00064501,0x00064000,0x00063b01,0x00063604,
0x00063109,0x00062c10,0x00062719,0x00062224,0x00061d31,0x00061840,0x00061351,0x00060e64,
0x00060979,0x00060490,0x0005ffa9,0x0005fac4,0x0005f5e1,0x0005f100,0x0005ec21,0x0005e744,
0x0005e269,0x0005dd90,0x0005d8b9,0x0005d3e4,0x0005cf11,0x0005ca40,0x0005c571,0x0005c0a4,
0x0005bbd9,0x0005b710,0x0005b249,0x0005ad84,0x0005a8c1,0x0005a400,0x00059f41,0x00059a84,
0x000595c9,0x00059110,0x00058c59,0x000587a4,0x000582f1,0x00057e40,0x00057991,0x000574e4,
0x00057039,0x00056b90,0x000566e9,0x00056244,0x00055da1,0x00055900,0x00055461,0x00054fc4,
0x00054b29,0x00054690,0x000541f9,0x00053d64,0x000538d1,0x00053440,0x00052fb1,0x00052b24,
0x00052699,0x00052210,0x00051d89,0x00051904,0x00051481,0x00051000,0x00050b81,0x00050704,
0x00050289,0x0004fe10,0x0004f999,0x0004f524,0x0004f0b1,0x0004ec40,0x0004e7d1,0x0004e364,
0x0004def9,0x0004da90,0x0004d629,0x0004d1c4,0x0004cd61,0x0004c900,0x0004c4a1,0x0004c044,
0x0004bbe9,0x0004b790,0x0004b339,0x0004aee4,0x0004aa91,0x0004a640,0x0004a1f1,0x00049da4,
0x00049959,0x00049510,0x000490c9,0x00048c84,0x00048841,0x00048400,0x00047fc1,0x00047b84,
0x00047749,0x00047310,0x00046ed9,0x00046aa4,0x00046671,0x00046240,0x00045e11,0x000459e4,
0x000455b9,0x00045190,0x00044d69,0x00044944,0x00044521,0x00044100,0x00043ce1,0x000438c4,
0x000434a9,0x00043090,0x00042c79,0x00042864,0x00042451,0x00042040,0x00041c31,0x00041824,
0x00041419,0x00041010,0x00040c09,0x00040804,0x00040401,0x00040000,0x0003fc01,0x0003f804,
0x0003f409,0x0003f010,0x0003ec19,0x0003e824,0x0003e431,0x0003e040,0x0003dc51,0x0003d864,
0x0003d479,0x0003d090,0x0003cca9,0x0003c8c4,0x0003c4e1,0x0003c100,0x0003bd21,0x0003b944,
0x0003b569,0x0003b190,0x0003adb9,0x0003a9e4,0x0003a611,0x0003a240,0x00039e71,0x00039aa4,
0x000396d9,0x00039310,0x00038f49,0x00038b84,0x000387c1,0x00038400,0x00038041,0x00037c84,
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?