nuclear@0: #include nuclear@0: #include nuclear@0: nuclear@0: #include "engine3d.h" nuclear@0: #include "generate3d.h" nuclear@0: #include "render3d.h" nuclear@0: #include "main.h" nuclear@0: nuclear@0: point3d fpts[MAXDATA]; nuclear@0: point3d norms[MAXDATA]; nuclear@0: point3d pt_norms[MAXDATA]; nuclear@0: point2d spts[MAXDATA]; nuclear@0: point3d spls[MAXDATA]; nuclear@0: nuclear@0: unsigned short swp[MAXDATA]; nuclear@0: nuclear@0: int lightcalc = LIGHTVIEW; nuclear@0: nuclear@0: #define fp_mul 256 nuclear@0: #define fp_shr 8 nuclear@0: #define proj_shr 8 nuclear@0: nuclear@0: nuclear@0: vector3d CrossProduct(vector3d v1, vector3d v2) nuclear@0: { nuclear@0: vector3d v; nuclear@0: v.x=v1.y*v2.z-v1.z*v2.y; nuclear@0: v.y=v1.z*v2.x-v1.x*v2.z; nuclear@0: v.z=v1.x*v2.y-v1.y*v2.x; nuclear@0: return v; nuclear@0: } nuclear@0: nuclear@0: nuclear@0: int DotProduct(vector3d v1, vector3d v2) nuclear@0: { nuclear@0: return v1.x*v2.x + v1.y*v2.y + v1.z*v2.z; nuclear@0: } nuclear@0: nuclear@0: nuclear@0: vector3d Normalize(vector3d v) nuclear@0: { nuclear@0: int d=(int)(sqrt(v.x*v.x+v.y*v.y+v.z*v.z)); nuclear@0: if (d!=0) nuclear@0: { nuclear@0: v.x=(v.x<pos.x * fp_mul); nuclear@0: int objposy = (int)(obj->pos.y * fp_mul); nuclear@0: int objposz = (int)(obj->pos.z * fp_mul); nuclear@0: nuclear@0: for (i=0; inpts; i++) nuclear@0: { nuclear@0: fpts[i].x += objposx; nuclear@0: fpts[i].y += objposy; nuclear@0: fpts[i].z += objposz; nuclear@0: } nuclear@0: } nuclear@0: nuclear@0: void rotate3d (object3d *obj) nuclear@0: { nuclear@0: float cosxr = cos(obj->rot.x); float cosyr = cos(obj->rot.y); float coszr = cos(obj->rot.z); nuclear@0: float sinxr = sin(obj->rot.x); float sinyr = sin(obj->rot.y); float sinzr = sin(obj->rot.z); nuclear@0: nuclear@0: int xvx = (int)((cosyr * coszr) * fp_mul); int xvy = (int)((sinxr * sinyr * coszr - cosxr * sinzr) * fp_mul); int xvz = (int)((cosxr * sinyr * coszr + sinxr * sinzr) * fp_mul); nuclear@0: int yvx = (int)((cosyr * sinzr) * fp_mul); int yvy = (int)((cosxr * coszr + sinxr * sinyr * sinzr) * fp_mul); int yvz = (int)((-sinxr * coszr + cosxr * sinyr * sinzr) * fp_mul); nuclear@0: int zvx = (int)((-sinyr) * fp_mul); int zvy = (int)((sinxr * cosyr) * fp_mul); int zvz = (int)((cosxr * cosyr) * fp_mul); nuclear@0: nuclear@0: int x, y, z; nuclear@0: int i; nuclear@0: for (i=0; inpts; i++) nuclear@0: { nuclear@0: x = obj->point[i].x; nuclear@0: y = obj->point[i].y; nuclear@0: z = obj->point[i].z; nuclear@0: fpts[i].x = x * xvx + y * xvy + z * xvz; nuclear@0: fpts[i].y = x * yvx + y * yvy + z * yvz; nuclear@0: fpts[i].z = x * zvx + y * zvy + z * zvz; nuclear@0: } nuclear@0: } nuclear@0: nuclear@0: nuclear@0: void rotate3d_normals (object3d *obj) nuclear@0: { nuclear@0: float cosxr = cos(obj->rot.x); float cosyr = cos(obj->rot.y); float coszr = cos(obj->rot.z); nuclear@0: float sinxr = sin(obj->rot.x); float sinyr = sin(obj->rot.y); float sinzr = sin(obj->rot.z); nuclear@0: nuclear@0: int xvx = (int)((cosyr * coszr) * fp_mul); int xvy = (int)((sinxr * sinyr * coszr - cosxr * sinzr) * fp_mul); int xvz = (int)((cosxr * sinyr * coszr + sinxr * sinzr) * fp_mul); nuclear@0: int yvx = (int)((cosyr * sinzr) * fp_mul); int yvy = (int)((cosxr * coszr + sinxr * sinyr * sinzr) * fp_mul); int yvz = (int)((-sinxr * coszr + cosxr * sinyr * sinzr) * fp_mul); nuclear@0: int zvx = (int)((-sinyr) * fp_mul); int zvy = (int)((sinxr * cosyr) * fp_mul); int zvz = (int)((cosxr * cosyr) * fp_mul); nuclear@0: nuclear@0: int x, y, z; nuclear@0: int i; nuclear@0: for (i=0; inpls; i++) nuclear@0: { nuclear@0: x = obj->normal[i].x; nuclear@0: y = obj->normal[i].y; nuclear@0: z = obj->normal[i].z; nuclear@0: norms[i].x = x * xvx + y * xvy + z * xvz; nuclear@0: norms[i].y = x * yvx + y * yvy + z * yvz; nuclear@0: norms[i].z = x * zvx + y * zvy + z * zvz; nuclear@0: } nuclear@0: } nuclear@0: nuclear@0: nuclear@0: void rotate3d_pt_normals (object3d *obj) nuclear@0: { nuclear@0: float cosxr = cos(obj->rot.x); float cosyr = cos(obj->rot.y); float coszr = cos(obj->rot.z); nuclear@0: float sinxr = sin(obj->rot.x); float sinyr = sin(obj->rot.y); float sinzr = sin(obj->rot.z); nuclear@0: nuclear@0: int xvx = (int)((cosyr * coszr) * fp_mul); int xvy = (int)((sinxr * sinyr * coszr - cosxr * sinzr) * fp_mul); int xvz = (int)((cosxr * sinyr * coszr + sinxr * sinzr) * fp_mul); nuclear@0: int yvx = (int)((cosyr * sinzr) * fp_mul); int yvy = (int)((cosxr * coszr + sinxr * sinyr * sinzr) * fp_mul); int yvz = (int)((-sinxr * coszr + cosxr * sinyr * sinzr) * fp_mul); nuclear@0: int zvx = (int)((-sinyr) * fp_mul); int zvy = (int)((sinxr * cosyr) * fp_mul); int zvz = (int)((cosxr * cosyr) * fp_mul); nuclear@0: nuclear@0: int x, y, z; nuclear@0: int i; nuclear@0: for (i=0; inpts; i++) nuclear@0: { nuclear@0: x = obj->pt_normal[i].x; nuclear@0: y = obj->pt_normal[i].y; nuclear@0: z = obj->pt_normal[i].z; nuclear@0: pt_norms[i].x = x * xvx + y * xvy + z * xvz; nuclear@0: pt_norms[i].y = x * yvx + y * yvy + z * yvz; nuclear@0: pt_norms[i].z = x * zvx + y * zvy + z * zvz; nuclear@0: } nuclear@0: } nuclear@0: nuclear@0: void project3d (object3d *obj) nuclear@0: { nuclear@0: int i; nuclear@0: int smul = 1; nuclear@0: nuclear@0: for (i=0; inpts; i++) nuclear@0: if (fpts[i].z > 0) nuclear@0: { nuclear@0: spts[i].x = ((fpts[i].x << proj_shr) / (fpts[i].z/smul)) + (ScreenWidth>>1); nuclear@0: spts[i].y = ((fpts[i].y << proj_shr) / (fpts[i].z/smul)) + (ScreenHeight>>1); nuclear@0: } nuclear@0: } nuclear@0: nuclear@0: void CalcPolyColorStatic(object3d *obj) nuclear@0: { nuclear@0: int i, c; nuclear@0: for (i=0; inpls; i++) nuclear@0: { nuclear@0: c = norms[i].z>>8; nuclear@0: if (c<0) c=0; nuclear@0: if (c>255) c=255; nuclear@0: spls[i].c = c; nuclear@0: } nuclear@0: } nuclear@0: nuclear@0: void CalcPointColorStatic(object3d *obj) nuclear@0: { nuclear@0: int i, c; nuclear@0: for (i=0; inpts; i++) nuclear@0: { nuclear@0: c = pt_norms[i].z>>8; nuclear@0: if (c<0) c=0; nuclear@0: if (c>255) c=255; nuclear@0: spts[i].c = c; nuclear@0: } nuclear@0: } nuclear@0: nuclear@0: void CalcPolyColorDynamic(object3d *obj) nuclear@0: { nuclear@0: vector3d light, v; nuclear@0: light.x = 0; nuclear@0: light.y = 0; nuclear@0: light.z = 256; nuclear@0: float c; nuclear@0: nuclear@0: int i; nuclear@0: for (i=0; inpls; i++) nuclear@0: { nuclear@0: v.x = norms[i].x; nuclear@0: v.y = norms[i].y; nuclear@0: v.z = norms[i].z; nuclear@0: c = DotProduct(v,light); nuclear@0: spls[i].c = (int)c; nuclear@0: if (c<0) spls[i].c = 0; nuclear@0: if (spls[i].c>255) spls[i].c = 255; nuclear@0: } nuclear@0: } nuclear@0: nuclear@0: void CalcPointColorDynamic(object3d *obj) nuclear@0: { nuclear@0: vector3d light, v; nuclear@0: light.x = 0; nuclear@0: light.y = 0; nuclear@0: light.z = 256; nuclear@0: float c; nuclear@0: nuclear@0: int i; nuclear@0: for (i=0; inpts; i++) nuclear@0: { nuclear@0: v.x = pt_norms[i].x; nuclear@0: v.y = pt_norms[i].y; nuclear@0: v.z = pt_norms[i].z; nuclear@0: c = DotProduct(v,light); nuclear@0: if (c<0) c = 0; nuclear@0: if (c>255) c = 255; nuclear@0: spts[i].c = (int)c; nuclear@0: } nuclear@0: } nuclear@0: nuclear@0: void CalcPointColor(object3d *obj) nuclear@0: { nuclear@0: if (lightcalc==LIGHTVIEW) CalcPointColorStatic(obj); nuclear@0: if (lightcalc==LIGHTMOVE) CalcPointColorDynamic(obj); nuclear@0: } nuclear@0: nuclear@0: void CalcPolyColor(object3d *obj) nuclear@0: { nuclear@0: if (lightcalc==LIGHTVIEW) CalcPolyColorStatic(obj); nuclear@0: if (lightcalc==LIGHTMOVE) CalcPolyColorDynamic(obj); nuclear@0: } nuclear@0: nuclear@0: void Calc3d(object3d *obj) nuclear@0: { nuclear@0: rotate3d(obj); nuclear@0: translate3d(obj); nuclear@0: project3d(obj); nuclear@0: } nuclear@0: nuclear@0: void quicksort (int lo, int hi, int data[]) nuclear@0: { nuclear@0: int m1 = lo; nuclear@0: int m2 = hi; nuclear@0: int temp0; nuclear@0: unsigned short temp1; nuclear@0: nuclear@0: int mp = data[(lo + hi)>>1]; nuclear@0: nuclear@0: while (m1<=m2) nuclear@0: { nuclear@0: while (data[m1] < mp) m1++; nuclear@0: while (mp < data[m2]) m2--; nuclear@0: nuclear@0: if (m1<=m2) nuclear@0: { nuclear@0: temp0 = data[m1]; data[m1] = data[m2]; data[m2] = temp0; nuclear@0: temp1 = swp[m1]; swp[m1] = swp[m2]; swp[m2] = temp1; nuclear@0: m1++; nuclear@0: m2--; nuclear@0: } nuclear@0: } nuclear@0: nuclear@0: if (m2>lo) quicksort(lo, m2, data); nuclear@0: if (m1