⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 dct.cpp

📁 一个可用于多平台的旋转180度 jpg的源代码。大家可以进一步的改进。
💻 CPP
字号:
#include <stdio.h>
#include "DCT.h"

//亮度量化表,教材<<多媒体技术原理及应用>>p28表2.2
BYTE g_lumQuantTableDef[DCT_SIZE][DCT_SIZE] = { 
						{ 16, 11, 10, 16, 24, 40, 51, 61 },
    					{ 12, 12, 14, 19, 26, 58, 60, 55 },
						{ 14, 13, 16, 24, 40, 57, 69, 56 },
						{ 14, 17, 22, 29, 51, 87, 80, 62 },
						{ 18, 22, 37, 56, 68, 109,103,77 },
						{ 24, 35, 55, 64, 81, 104,113,92 },
						{ 49, 64, 78, 87, 103,121,120,101},
						{ 72, 92, 95, 98, 112,100,103,99 } };

//色度量化表,教材<<多媒体技术原理及应用>>p28表2.3						    
BYTE g_chrQuantTableDef[DCT_SIZE][DCT_SIZE] = { 
						{ 17,18,24,47,99,99,99,99 },
						{ 18,21,26,66,99,99,99,99 },
						{ 24,26,56,99,99,99,99,99 },
						{ 47,66,99,99,99,99,99,99 },
						{ 99,99,99,99,99,99,99,99 },
						{ 99,99,99,99,99,99,99,99 },
						{ 99,99,99,99,99,99,99,99 },
						{ 99,99,99,99,99,99,99,99 } };

//亮度系数表
BYTE g_lumQuantTable[DCT_SIZE][DCT_SIZE];

//色度系数表
BYTE g_chrQuantTable[DCT_SIZE][DCT_SIZE];

//z型扫描表,教材<<多媒体技术原理及应用>>p29图2.12
BYTE g_rleZigZagTable[DCT_SIZE][DCT_SIZE] = { 
							{ 0, 1, 5, 6, 14,15,27,28 },
							{ 2, 4, 7, 13,16,26,29,42 },
							{ 3, 8, 12,17,25,30,41,43 },
							{ 9, 11,18,24,31,40,44,53 },
							{ 10,19,23,32,39,45,52,54 },
							{ 20,22,33,38,46,51,55,60 },
							{ 21,34,37,47,50,56,59,61 },
							{ 35,36,48,49,57,58,62,63 } };

//离散余弦变换函数,公式教材<<多媒体技术原理及应用>>p27
void DCT_AAN(double dct[], double pic[])
{
	static double x01, x11, x21, x31, x41, x51, x61, x71;
	static double x0, x1, x2, x3;
	x01 = pic[0]+pic[7];
	x11 = pic[1]+pic[6];
	x21 = pic[2]+pic[5];
	x31 = pic[3]+pic[4];
	x41 = pic[3]-pic[4];
	x51 = pic[2]-pic[5];
	x61 = pic[1]-pic[6];
	x71 = pic[0]-pic[7];

	x0 = x01+x31;
	x1 = x11+x21;
	x2 = x11-x21;
	x3 = x01-x31;

	dct[0] = 0.35355339*(x0+x1);	
	dct[4] = 0.35355339*(x0-x1);	
	x2 = 0.707106781*(x2+x3);	
	dct[2] = 0.27059805*(x2+x3);	
	dct[6] = 0.653281482*(x3-x2);	

	x0 = x41+x51;
	x1 = x51+x61;
	x2 = x61+x71;
	x3 = 0.382683432*(x0-x2);	

	x41 = 0.541196100*x0+x3;	
	x51 = 0.707106781*x1;		
	x61 = 1.306562965*x2+x3;	

	x1 = x51+x71;
	x3 = x71-x51;
	dct[5] = 0.449988111*(x41+x3);	
	dct[1] = 0.254897789*(x1+x61);	
	dct[7] = 1.281457724*(x1-x61);	
	dct[3] = 0.300672443*(x3-x41);	
}

//离散余弦变换调用函数
void DCT_8x8(double dct[][DCT_SIZE], double pic[][DCT_SIZE])
{
	static int i, j;
	static double res[DCT_SIZE][DCT_SIZE], out[DCT_SIZE], in[DCT_SIZE];
	for (i=0; i<DCT_SIZE; i++)
	{
		for (j=0; j<DCT_SIZE; j++)
			in[j] = pic[i][j]-128;	//注意此处
 		DCT_AAN(res[i], in);
	}
	for (i=0; i<DCT_SIZE; i++)
	{
		for (j=0; j<DCT_SIZE; j++)
			in[j] = res[j][i];
		DCT_AAN(out, in);
		for (j=0; j<DCT_SIZE; j++)
			dct[j][i] = out[j];
	}
}

//建立量化表
void InitQuantTable( BYTE compQuantTablePtr[][DCT_SIZE],const BYTE compQuantTableDef[][DCT_SIZE], int QValue )
{
	int i, j, val;
	if (QValue < 1)
 		QValue = 1;
	if (QValue > 100)
 		QValue = 100;
	if (QValue < 50)         //nonlinear mapping 1->5000, 10->500, 25->200, 50->100, 75->50, 100->0
		QValue = 5000/QValue;
	else
		QValue = 200-QValue*2;
	for (i=0; i<DCT_SIZE; i++)
		for (j=0; j<DCT_SIZE; j++)
		{
			val = (compQuantTableDef[i][j]*QValue+50)/100;
			if (val < 1)
				val = 1;
			if (val > 255)
				val = 255;
   			compQuantTablePtr[i][j] = val;
		}
}

//量化处理函数
void QuantDCTValue(int quant[][DCT_SIZE], double dct[][DCT_SIZE], BYTE compQuantTable[][DCT_SIZE])
{
	int i, j;
	for (i=0; i<DCT_SIZE; i++)
		for (j=0; j<DCT_SIZE; j++)
		{
			if(dct[i][j] >= 0)
				quant[i][j] = (int)(dct[i][j]/compQuantTable[i][j]+0.5);
			else
				quant[i][j] = (int)(dct[i][j]/compQuantTable[i][j]-0.5);
		}
}

//z型扫描函数					 
void ZigZagScan(int scan[], int quant[][DCT_SIZE])
{
	int i, j;
	for (i=0; i<DCT_SIZE; i++)
		for (j=0; j<DCT_SIZE; j++)
			scan[g_rleZigZagTable[i][j]] = quant[i][j];
}

//行程编码函数
void RunLengthEncode(int zlen[], int num[], int *cnt, int scan[])
{
	int k = 0, z = 0;
	(*cnt) = 0;
 	do {
 		k++;
 		if (scan[k] == 0)
 		{
 			if (k == 63)
 			{
 				zlen[*cnt] = 0;
 				num[*cnt] = 0;
 				(*cnt)++;
			}
			else
				z++;
		}
		else
		{
			while (z > 15)
			{
				zlen[*cnt] = 15;
				num[*cnt] = 0;
				(*cnt)++;
				z -= 16;
    			}
			zlen[*cnt] = z;
			num[*cnt] = scan[k];
			(*cnt)++;
			z = 0;
  		}
  	} while(k < 63);
}


⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -