|
发表于 2011-6-8 12:34:49
|
显示全部楼层
这是改后的程序,如是float radians; 定义成s32图就不会转动。
#define MAX(a,b) ((a) > (b) ? (a) : (b))
#define MIN(a,b) ((a) > (b) ? (b) : (a))
typedef struct
{
u16 Width;
u16 Height;
u16 Data[];
}IMAGE;
/*******************************************************************************
函数:
功能: 图片旋转
参数: u16 x, u16 y,
返回: x,y: ,hImg : 图片,angle:角度
********************************************************************************/
void RotateImage(int x,int y,IMAGE *hImg,int angle)
{
float radians;
s32 cos_a,sin_a,cos_ay,sin_ay;
s32 point1x,point1y,point2x,point2y,point3x,point3y;
s32 minx,miny,maxx,maxy;
s32 xx,yy,xx0,yy0,xx1,yy1,cx,cy,src_dx,src_dy,dst_dx,dst_dy;
u16 color;
IMAGE *img;
///////////
//算法优化思路:小数除法->整数除法->乘法->加法
img=hImg;
src_dx = img->Width;
src_dy = img->Height;
angle %= 360;
//计算外接矩形坐标
radians = (2*(float)3.1415*angle)/(float)360.0;
cos_a = (s32)(cos(radians)*(float)65536.0);
sin_a = (s32)(sin(radians)*(float)65536.0);
point1x = (-src_dy*sin_a)>>16;
point1y = (src_dy*cos_a)>>16;
point2x = (src_dx*cos_a-src_dy*sin_a)>>16;
point2y = (src_dy*cos_a+src_dx*sin_a)>>16;
point3x = (src_dx*cos_a)>>16;
point3y = (src_dx*sin_a)>>16;
minx = MIN(0,MIN(point1x,MIN(point2x,point3x)));
miny = MIN(0,MIN(point1y,MIN(point2y,point3y)));
maxx = MAX(point1x,MAX(point2x,point3x));
maxy = MAX(point1y,MAX(point2y,point3y));
// 取得最小整数
if(angle>90&&angle<180)
{
dst_dx=(int)ceil(-minx);
}
else
{
dst_dx=(int)ceil(maxx-minx);
}
if(angle>180&&angle<270)
{
dst_dy=(int)ceil(-miny);
}
else
{
dst_dy=(int)ceil(maxy-miny);
}
cx =(dst_dx>>1); //目标位置中心点的x偏移
cy =(dst_dy>>1); //目标位置中心点的y偏移
cos_ay =(miny*cos_a)>>16;
sin_ay =(miny*sin_a)>>16;
////////////
//-------------------------------------------------------------
/* if(((IMAGE*)hImg)->Bpp==32)
{
//ARGB 8888格式(带Alpha通道)
for(yy=0;yy<dst_dy;yy++)
{
cos_ay =((yy+miny)*cos_a)>>16;
sin_ay =((yy+miny)*sin_a)>>16;
////
yy0 =y+yy-cy;
if(yy0<0) continue;
if(yy0>pdc->ymax) return;
for(xx=0;xx<dst_dx;xx++)
{
////
xx1 =((((xx+minx)*cos_a)>>16)+sin_ay); //计算坐标
yy1 =(cos_ay-(((xx+minx)*sin_a)>>16));
////
xx0 =x+xx-cx;
if(xx1>=0&&xx1<src_dx&&yy1>=0&&yy1<src_dy&&xx0>0&&xx0<pdc->xmax)
{
color =img->Data[yy1*img->Width+xx1];
pdc->PutPixel(pdc,xx0,yy0,AlphaBlendColor(color,GetPixel(hdc,xx0,yy0),img->AlphaData[yy1*img->Width+xx1]));
}
}
}
}
else
{
*/
//其它格式(不带Alpha通道)
for(yy=0;yy<dst_dy;yy++)
{
cos_ay =((yy+miny)*cos_a)>>16;
sin_ay =((yy+miny)*sin_a)>>16;
////
yy0 =y+yy-cy;
if(yy0<0) continue;
if(yy0>LCD_Ymax) return;
for(xx=0;xx<dst_dx;xx++)
{
xx1 =((((xx+minx)*cos_a)>>16)+sin_ay); //计算坐标
yy1 =(cos_ay-(((xx+minx)*sin_a)>>16));
////
xx0 =x+xx-cx;
if(xx1>=0&&xx1<src_dx&&yy1>=0&&yy1<src_dy&&xx0>0&&xx0<LCD_Xmax)
{
color = img->Data[yy1*img->Width+xx1];
LCD_SetCursor(xx0,yy0);
TFT_DRAW_Point(color); // 1
}
}
}
// }
} |
|