📄 our_3d.c
字号:
/**************************************************************************
Copyright (C) jianbo miao Corporation. All Rights Released.
this is a 3d engin named our_3d_engin.
our_3d_engin feature:
1:there is no float.
2:it do the 3d things all by softwear.
3:base on 1 and 2 , it can execution on arm which have no 3d hardwear accelerate.
if you have any suggestion or question,pls contact with me
mail:miaojb@126.com
msn:miaojianbo@hotmail.com
qq:30209027
2008/01/01
***************************************************************************/
#include "our_math.h"
#include "our_3d.h"
#include "our_draw32.h"
#include "our_draw16.h"
#include "math.h"
UINT OUR_D_FrameTH;
UINT OUR_D_point_changed_num;
UINT OUR_D_triangle_drawed_num;
UINT OUR_D_screem_w;
UINT OUR_D_screem_h;
//-----------------------------
//FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF
//FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF
//MMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMM
//MMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMM
void OUR_Build_XYZ_Rotation_MATRIX3X3( FIXP16 theta_x, //60t 450t 850t
FIXP16 theta_y,
FIXP16 theta_z,
FIX_MATRIX_3X3_PTR mrot) // output
{
FIX_MATRIX_3X3 mx, my, mz, mtmp; // working matrices
FIXP16 sin_theta=0, cos_theta=0; // used to initialize matrices
sint32 rot_seq = 0; // 1 for x, 2 for y, 4 for z
// step 1: based on zero and non-zero rotation angles, determine
// rotation sequence
if (theta_x != 0) // x
rot_seq = rot_seq | 1;
if (theta_y != 0) // y
rot_seq = rot_seq | 2;
if (theta_z != 0) // z
rot_seq = rot_seq | 4;
switch(rot_seq) // now case on sequence
{
case 0: // no rotation
{
mrot->MM.M00=1<<FIXP15_SHIFT; mrot->MM.M01=0; mrot->MM.M02=0;
mrot->MM.M10=0; mrot->MM.M11=1<<FIXP15_SHIFT; mrot->MM.M12=0;
mrot->MM.M20=0; mrot->MM.M21=0; mrot->MM.M22=1<<FIXP15_SHIFT;
return;
}
case 1: // x rotation
{
// compute the sine and cosine of the angle
cos_theta = OUR_Fast_Cos(theta_x);
sin_theta = OUR_Fast_Sin(theta_x);
mrot->MM.M00=1<<FIXP15_SHIFT; mrot->MM.M01=0; mrot->MM.M02=0;
mrot->MM.M10=0; mrot->MM.M11=cos_theta; mrot->MM.M12=sin_theta;
mrot->MM.M20=0; mrot->MM.M21=-sin_theta; mrot->MM.M22=cos_theta;
return;
}
case 2: // y rotation
{
cos_theta = OUR_Fast_Cos(theta_y);
sin_theta = OUR_Fast_Sin(theta_y);
mrot->MM.M00=cos_theta; mrot->MM.M01=0; mrot->MM.M02=-sin_theta;
mrot->MM.M10=0; mrot->MM.M11=1<<FIXP15_SHIFT; mrot->MM.M12=0;
mrot->MM.M20=sin_theta; mrot->MM.M21=0; mrot->MM.M22=cos_theta;
return;
}
case 3: // xy rotation
{
cos_theta = OUR_Fast_Cos(theta_x);
sin_theta = OUR_Fast_Sin(theta_x);
mx.MM.M00=1<<FIXP15_SHIFT; mx.MM.M01=0; mx.MM.M02=0;
mx.MM.M10=0; mx.MM.M11=cos_theta; mx.MM.M12=sin_theta;
mx.MM.M20=0; mx.MM.M21=-sin_theta; mx.MM.M22=cos_theta;
cos_theta = OUR_Fast_Cos(theta_y);
sin_theta = OUR_Fast_Sin(theta_y);
my.MM.M00=cos_theta; my.MM.M01=0; my.MM.M02=-sin_theta;
my.MM.M10=0; my.MM.M11=1<<FIXP15_SHIFT; my.MM.M12=0;
my.MM.M20=sin_theta; my.MM.M21=0; my.MM.M22=cos_theta;
OUR_FIX_Mat_Mul_3X3(&mx, &my, mrot);
return;
}
case 4: // z rotation
{
cos_theta = OUR_Fast_Cos(theta_z);
sin_theta = OUR_Fast_Sin(theta_z);
mrot->MM.M00=cos_theta; mrot->MM.M01=sin_theta; mrot->MM.M02=0;
mrot->MM.M10=-sin_theta; mrot->MM.M11=cos_theta; mrot->MM.M12=0;
mrot->MM.M20=0; mrot->MM.M21=-0; mrot->MM.M22=1<<FIXP15_SHIFT;
return;
}
case 5: // xz rotation
{
cos_theta = OUR_Fast_Cos(theta_x);
sin_theta = OUR_Fast_Sin(theta_x);
mx.MM.M00=1<<FIXP15_SHIFT; mx.MM.M01=0; mx.MM.M02=0;
mx.MM.M10=0; mx.MM.M11=cos_theta; mx.MM.M12=sin_theta;
mx.MM.M20=0; mx.MM.M21=-sin_theta; mx.MM.M22=cos_theta;
cos_theta = OUR_Fast_Cos(theta_z);
sin_theta = OUR_Fast_Sin(theta_z);
mz.MM.M00=cos_theta; mz.MM.M01=sin_theta; mz.MM.M02=0;
mz.MM.M10=-sin_theta; mz.MM.M11=cos_theta; mz.MM.M12=0;
mz.MM.M20=0; mz.MM.M21=-0; mz.MM.M22=1<<FIXP15_SHIFT;
OUR_FIX_Mat_Mul_3X3(&mx, &mz, mrot);
return;
}
case 6: // yz rotation
{
cos_theta = OUR_Fast_Cos(theta_y);
sin_theta = OUR_Fast_Sin(theta_y);
my.MM.M00=cos_theta; my.MM.M01=0; my.MM.M02=-sin_theta;
my.MM.M10=0; my.MM.M11=1<<FIXP15_SHIFT; my.MM.M12=0;
my.MM.M20=sin_theta; my.MM.M21=0; my.MM.M22=cos_theta;
cos_theta = OUR_Fast_Cos(theta_z);
sin_theta = OUR_Fast_Sin(theta_z);
mz.MM.M00=cos_theta; mz.MM.M01=sin_theta; mz.MM.M02=0;
mz.MM.M10=-sin_theta; mz.MM.M11=cos_theta; mz.MM.M12=0;
mz.MM.M20=0; mz.MM.M21=-0; mz.MM.M22=1<<FIXP15_SHIFT;
OUR_FIX_Mat_Mul_3X3(&my, &mz, mrot);
return;
}
case 7: // xyz rotation
{
cos_theta = OUR_Fast_Cos(theta_x);
sin_theta = OUR_Fast_Sin(theta_x);
mx.MM.M00=1<<FIXP15_SHIFT; mx.MM.M01=0; mx.MM.M02=0;
mx.MM.M10=0; mx.MM.M11=cos_theta; mx.MM.M12=sin_theta;
mx.MM.M20=0; mx.MM.M21=-sin_theta; mx.MM.M22=cos_theta;
cos_theta = OUR_Fast_Cos(theta_y);
sin_theta = OUR_Fast_Sin(theta_y);
my.MM.M00=cos_theta; my.MM.M01=0; my.MM.M02=-sin_theta;
my.MM.M10=0; my.MM.M11=1<<FIXP15_SHIFT; my.MM.M12=0;
my.MM.M20=sin_theta; my.MM.M21=0; my.MM.M22=cos_theta;
cos_theta = OUR_Fast_Cos(theta_z);
sin_theta = OUR_Fast_Sin(theta_z);
mz.MM.M00=cos_theta; mz.MM.M01=sin_theta; mz.MM.M02=0;
mz.MM.M10=-sin_theta; mz.MM.M11=cos_theta; mz.MM.M12=0;
mz.MM.M20=0; mz.MM.M21=-0; mz.MM.M22=1<<FIXP15_SHIFT;
OUR_FIX_Mat_Mul_3X3(&mx, &my, &mtmp);
OUR_FIX_Mat_Mul_3X3(&mtmp, &mz, mrot);
return;
}
default: break;
}
return;
}
//--------------------------------------------------------------------
void OUR_XYZ_Rotation_OBJ( FIXP16 x, // 1300t
FIXP16 y,
FIXP16 z,
OUR_3D_OBJ_PTR obj)// output
{
obj->state_attr |= OBJ_CHANGED;
OUR_Build_XYZ_Rotation_MATRIX3X3(x, y, z,&obj->mrot);
OUR_Mat_Inverse_3X3(&obj->mrot,&obj->mrot_i);
}
//--------------------------------------------------------------------
//--------------------------------------------------------------------
void OUR_Build_CAM_Rotation_MATRIX3X3(OUR_3D_CAM_PTR cam)//1550
{
FIX_POINT3D v; //x
FIX_POINT3D u={0,1,0}; //y
FIX_POINT3D n; //z
OUR_FIX_VECTOR3D_SUB(&(cam->target),&(cam->pos),&n);
//OUR_VECTOR3D_Cross(&u, &n, &v);
v.MM.x=n.MM.z;//???
v.MM.y=0;
v.MM.z=-n.MM.x;
OUR_VECTOR3D_Cross( &n, &v,&u);
//OUR_VECTOR3D_Cross( &v, &u,&n);
OUR_VECTOR3D_Normalize(&n);
OUR_VECTOR3D_Normalize(&v);
OUR_VECTOR3D_Normalize(&u);
cam->mrot.MM.M00=v.MM.x;
cam->mrot.MM.M01=u.MM.x;
cam->mrot.MM.M02=n.MM.x;
cam->mrot.MM.M10=v.MM.y;
cam->mrot.MM.M11=u.MM.y;
cam->mrot.MM.M12=n.MM.y;
cam->mrot.MM.M20=v.MM.z;
cam->mrot.MM.M21=u.MM.z;
cam->mrot.MM.M22=n.MM.z;
}
//MMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMM
//MMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMMM
void OUR_POINT_CHANGE_OBJ(OUR_3D_OBJ_PTR obj,OUR_3D_CAM_PTR cam)//300t
{
uint32 i;
sint32 dvr;
FIX_POINT3D pos;
FIX_POINT3D pos_cam={0,0,1000};
FIX_POINT3D_PTR p_p;
FIX_MATRIX_3X3 mrot;
p_p=obj->pPoints;
OUR_FIX_Mat_Mul_3X3(&obj->mrot,&(cam->mrot),&mrot);
OUR_FIX_VECTOR3D_SUB(&obj->pos,&cam->pos,&pos); //20t
OUR_FIX_Mat_Mul_VECTOR3D_3X3(&pos, &(cam->mrot),&pos_cam); //100t
for(i=0;i<obj->point_num;i++)
{
if(OUR_D_FrameTH==obj->pPoints_changed[i])
{
OUR_FIX_Mat_Mul_VECTOR3D_3X3(&p_p[i], &mrot,&obj->pPoints_work[i]); //100t
obj->pPoints_work[i].MM.x=(obj->pPoints_work[i].MM.x *obj->scale)>>SCALE_1;
obj->pPoints_work[i].MM.y=(obj->pPoints_work[i].MM.y *obj->scale)>>SCALE_1;
obj->pPoints_work[i].MM.z=(obj->pPoints_work[i].MM.z *obj->scale)>>SCALE_1;
OUR_FIX_VECTOR3D_ADD(&obj->pPoints_work[i],&pos_cam,&obj->pPoints_work[i]); //20t
dvr=((cam->focus)<<15)/(obj->pPoints_work[i].MM.z);
obj->pPoints_work[i].MM.x=((obj->pPoints_work[i].MM.x*dvr)>>15)+cam->width;
obj->pPoints_work[i].MM.y=cam->hight-((obj->pPoints_work[i].MM.y*dvr)>>15);
OUR_D_point_changed_num++;
}
}
}
//--------------------------------------------------------------------
void OUR_INIT_Triangle_Normal( OUR_3D_OBJ_PTR obj ) //570*n t 需要优化
{
uint32 i;
sint32 n1,n2,n3;
FIX_POINT3D p1,p2;
uint32 num;
OUR_3D_TRAG_PTR triangle_list;
num=obj->triangle_num;
triangle_list=obj->pTriangle;
for(i=0;i<num;i++)
{
n1=triangle_list[i].p1;
n2=triangle_list[i].p2;
n3=triangle_list[i].p3;
OUR_FIX_VECTOR3D_SUB(&obj->pPoints[n2],&obj->pPoints[n1],&p1);
OUR_FIX_VECTOR3D_SUB(&obj->pPoints[n3],&obj->pPoints[n1],&p2);
OUR_VECTOR3D_Cross(&p1, &p2, &(triangle_list[i].NOR_P));
if(i==793)
n1++;
//OUR_FAST_Normalize(&(triangle_list[i].NOR_P));
OUR_VECTOR3D_Normalize(&(triangle_list[i].NOR_P));
}
}
//--------------------------------------------------------------------
void OUR_INIT_Point_Normal( OUR_3D_OBJ_PTR obj )//570*n t 需要优化
{
uint32 i,j;
FIX_POINT3D p_nor;
uint32 num_p,num_t;
OUR_3D_TRAG_PTR triangle_list;
FIX_POINT3D_PTR point_list;
num_p=obj->point_num;
num_t=obj->triangle_num;
triangle_list=obj->pTriangle;
point_list=obj->pPoints;
p_nor.MM.x=0;
p_nor.MM.y=0;
p_nor.MM.z=0;
for(j=0;j<num_p;j++)
{
for(i=0;i<num_t;i++)
{
if(j==triangle_list[i].p1 || j==triangle_list[i].p2 || j==triangle_list[i].p3)
{
OUR_FIX_VECTOR3D_ADD(&triangle_list[i].NOR_P,&p_nor,&p_nor);
}
}
//OUR_FAST_Normalize(&p_nor);
OUR_VECTOR3D_Normalize(&p_nor);
obj->pPoint_nor[j].MM.x=p_nor.MM.x;
obj->pPoint_nor[j].MM.y=p_nor.MM.y;
obj->pPoint_nor[j].MM.z=p_nor.MM.z;
}
}
//--------------------------------------------------------------------
void OUR_BACHFACE_OBJ_OBJ_LIT32( OUR_3D_OBJ_PTR obj,//100*n t 需要优化
OUR_3D_CAM_PTR cam,
OUR_3D_LIT_PTR lit)
{
OUR_3D_TRAG_PTR p_t;
FIX_POINT3D_PTR p_p;
FIX_POINT3D n,l;
uint32 i,j;
sint32 f;
CLR lihgt_clr0,lihgt_clr1;
OUR_3D_LIT_PTR lit_here;
lit_here=lit;
//take cam to the obj
OUR_FIX_VECTOR3D_SUB(&cam->pos,&obj->pos,&n);
OUR_FIX_Mat_Mul_VECTOR3D_3X3(&n, &obj->mrot_i,&(cam->pos_obj));//100t
cam->pos_obj.MM.x=((cam->pos_obj.MM.x))*obj->scale_i>>SCALE_1;
cam->pos_obj.MM.y=((cam->pos_obj.MM.y))*obj->scale_i>>SCALE_1;
cam->pos_obj.MM.z=((cam->pos_obj.MM.z))*obj->scale_i>>SCALE_1;
//take lits to the obj
while(lit)
{
if (lit->state_attr == LIT_point || lit->state_attr == LIT_parallel)
{
OUR_FIX_VECTOR3D_SUB(&lit->pos_dir,&obj->pos,&n);
OUR_FIX_Mat_Mul_VECTOR3D_3X3(&n, &obj->mrot_i,&(lit->pos_dir_obj));//100t
if (lit->state_attr == LIT_point )
{
lit->pos_dir_obj.MM.x=((lit->pos_dir_obj.MM.x))*obj->scale_i>>SCALE_1;
lit->pos_dir_obj.MM.y=((lit->pos_dir_obj.MM.y))*obj->scale_i>>SCALE_1;
lit->pos_dir_obj.MM.z=((lit->pos_dir_obj.MM.z))*obj->scale_i>>SCALE_1;
}
}
lit=lit->lit_next;
}
p_p = obj->pPoints;
p_t = obj->pTriangle;
for(i=0;i<obj->triangle_num;i++)
{
j=p_t[i].p1;
OUR_FIX_VECTOR3D_SUB(&(cam->pos_obj),&p_p[j],&l);
if(OUR_VECTOR3D_Dot(&l,&(p_t[i].NOR_P))>0) //need to change
{
obj->pTriangle_changed[i]=OUR_D_FrameTH;
//j=p_t[i].p1;
obj->pPoints_changed[j]=OUR_D_FrameTH;
j=p_t[i].p2;
obj->pPoints_changed[j]=OUR_D_FrameTH;
j=p_t[i].p3;
obj->pPoints_changed[j]=OUR_D_FrameTH;
//lighting
lihgt_clr0=0;
lihgt_clr1=0;
lit=lit_here;
//if(material_Triangle == obj->material )
//--------------------------------------------------
while(lit)
{
if (lit->state_attr == LIT_point) //点光源
{
j=p_t[i].p1;
OUR_FIX_VECTOR3D_SUB(&(lit->pos_dir_obj),&p_p[j],&n);
f=OUR_VECTOR3D_Dot(&n,&(p_t[i].NOR_P));
if(f>0)
{
j=OUR_FAST_Length(&n);//n为 灯到点
//j=OUR_Fast_division(f,j*j>>2);
j=f/(j*j>>2);
if(j>0x7f)
j=0x7f;
f=lit->clor[0] *j;
lihgt_clr0+=f;
f=lit->clor[1] *j;
lihgt_clr1+=f;
}
}
else if (lit->state_attr == LIT_parallel)//平行光
{
f=OUR_VECTOR3D_Dot(&(lit->pos_dir_obj),&(p_t[i].NOR_P));
if(f>0)
{
j=f>>23;
if(j>0x7f)
j=0x7f;
f=lit->clor[0] *j;
lihgt_clr0+=f;
f=lit->clor[1] *j;
lihgt_clr1+=f;
}
}
else if (lit->state_attr == LIT_condition)//环境光
{
lihgt_clr0+=lit->clor[0];
lihgt_clr1+=lit->clor[1];
}
//-----
lit=lit->lit_next;
}
//---------------------------------------------------
//blue
j=obj->CC.c[0]*(lihgt_clr1&0xffff);
if((j) >= (0x1<<21))
p_t[i].CC.clor=OUR_RGB_MASK0008;
else
p_t[i].CC.clor=(j)>>13;
//red
j=obj->CC.c[2]*(lihgt_clr1>>16);
if((j) >= (0x1<<21))
p_t[i].CC.clor+=OUR_RGB_MASK0800;
else
p_t[i].CC.clor+=((j)<<3)&OUR_RGB_MASK0800;
//green
j=obj->CC.c[1]*(lihgt_clr0&0xffff);
if((j) >= (0x1<<21))
p_t[i].CC.clor+=OUR_RGB_MASK0080;
else
p_t[i].CC.clor+=((j)>>5)&OUR_RGB_MASK0080;
/**/
}
}
}
//--------------------------------------------------------------------
void OUR_BACHFACE_OBJ_TRAG_LIT32( OUR_3D_OBJ_PTR obj,//100*n t 需要优化
OUR_3D_CAM_PTR cam,
OUR_3D_LIT_PTR lit)
{
OUR_3D_TRAG_PTR p_t;
FIX_POINT3D_PTR p_p;
FIX_POINT3D n,l;
uint32 i,j;
sint32 f;
CLR lihgt_clr0,lihgt_clr1;
OUR_3D_LIT_PTR lit_here;
lit_here=lit;
//take cam to the obj
OUR_FIX_VECTOR3D_SUB(&cam->pos,&obj->pos,&n);
OUR_FIX_Mat_Mul_VECTOR3D_3X3(&n, &obj->mrot_i,&(cam->pos_obj));//100t
cam->pos_obj.MM.x=((cam->pos_obj.MM.x))*obj->scale_i>>SCALE_1;
cam->pos_obj.MM.y=((cam->pos_obj.MM.y))*obj->scale_i>>SCALE_1;
cam->pos_obj.MM.z=((cam->pos_obj.MM.z))*obj->scale_i>>SCALE_1;
//take lits to the obj
while(lit)
{
if (lit->state_attr == LIT_point || lit->state_attr == LIT_parallel)
{
OUR_FIX_VECTOR3D_SUB(&lit->pos_dir,&obj->pos,&n);
OUR_FIX_Mat_Mul_VECTOR3D_3X3(&n, &obj->mrot_i,&(lit->pos_dir_obj));//100t
if (lit->state_attr == LIT_point )
{
lit->pos_dir_obj.MM.x=((lit->pos_dir_obj.MM.x))*obj->scale_i>>SCALE_1;
lit->pos_dir_obj.MM.y=((lit->pos_dir_obj.MM.y))*obj->scale_i>>SCALE_1;
lit->pos_dir_obj.MM.z=((lit->pos_dir_obj.MM.z))*obj->scale_i>>SCALE_1;
}
}
lit=lit->lit_next;
}
p_p = obj->pPoints;
p_t = obj->pTriangle;
for(i=0;i<obj->triangle_num;i++)
{
j=p_t[i].p1;
OUR_FIX_VECTOR3D_SUB(&(cam->pos_obj),&p_p[j],&l);
if(OUR_VECTOR3D_Dot(&l,&(p_t[i].NOR_P))>0) //need to change
{
obj->pTriangle_changed[i]=OUR_D_FrameTH;
//j=p_t[i].p1;
obj->pPoints_changed[j]=OUR_D_FrameTH;
j=p_t[i].p2;
obj->pPoints_changed[j]=OUR_D_FrameTH;
j=p_t[i].p3;
obj->pPoints_changed[j]=OUR_D_FrameTH;
//lighting
lihgt_clr0=0;
lihgt_clr1=0;
lit=lit_here;
//if(material_Triangle == obj->material )
//--------------------------------------------------
while(lit)
{
if (lit->state_attr == LIT_point) //点光源
{
j=p_t[i].p1;
OUR_FIX_VECTOR3D_SUB(&(lit->pos_dir_obj),&p_p[j],&n);
f=OUR_VECTOR3D_Dot(&n,&(p_t[i].NOR_P));
if(f>0)
{
j=OUR_FAST_Length(&n);//n为 灯到点
//j=OUR_Fast_division(f,j*j>>2);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -