diff --git a/src/engine/math_util.c b/src/engine/math_util.c index 6e6f0c23..a8642a29 100644 --- a/src/engine/math_util.c +++ b/src/engine/math_util.c @@ -140,7 +140,7 @@ void mtxf_translate(Mat4 dest, Vec3f b) { * at the position 'to'. The up-vector is assumed to be (0, 1, 0), but the 'roll' * angle allows a bank rotation of the camera. */ -void mtxf_lookat(Mat4 mtx, Vec3f from, Vec3f to, s16 roll) { +void mtxf_lookat(Mat4 mtx, Vec3f from, Vec3f to, s32 roll) { Vec3f colX, colY, colZ; f32 dx = to[0] - from[0]; @@ -263,7 +263,7 @@ void mtxf_rotate_xyz_and_translate(Mat4 dest, Vec3f b, Vec3s c) { * 'position' is the position of the object in the world * 'angle' rotates the object while still facing the camera. */ -void mtxf_billboard(Mat4 dest, Mat4 mtx, Vec3f position, s16 angle) { +void mtxf_billboard(Mat4 dest, Mat4 mtx, Vec3f position, s32 angle) { if (angle == 0x0) { dest[0][0] = 1; dest[0][1] = 0; @@ -297,7 +297,7 @@ void mtxf_billboard(Mat4 dest, Mat4 mtx, Vec3f position, s16 angle) { * 'yaw' is the angle which it should face * 'pos' is the object's position in the world */ -void mtxf_align_terrain_normal(Mat4 dest, Vec3f upDir, Vec3f pos, s16 yaw) { +void mtxf_align_terrain_normal(Mat4 dest, Vec3f upDir, Vec3f pos, s32 yaw) { Vec3f lateralDir; Vec3f leftDir; Vec3f forwardDir; @@ -330,7 +330,7 @@ void mtxf_align_terrain_normal(Mat4 dest, Vec3f upDir, Vec3f pos, s16 yaw) { * 'pos' is the object's position in the world * 'radius' is the distance from each triangle vertex to the center */ -void mtxf_align_terrain_triangle(Mat4 mtx, Vec3f pos, s16 yaw, f32 radius) { +void mtxf_align_terrain_triangle(Mat4 mtx, Vec3f pos, s32 yaw, f32 radius) { struct Surface *floor; Vec3f point0, point1, point2; Vec3f forward; @@ -463,14 +463,19 @@ void mtxf_mul_vec3s(Mat4 mtx, Vec3s b) { * integer. If this doesn't fit, the N64 and iQue consoles will throw an * exception. On Wii and Wii U Virtual Console the value will simply be clamped * and no crashes occur. + + * Modified into a hybrid of the original function and the worldscale altered function. + * Will check if the worldscale is below what's considered safe in vanilla bounds and + * just run the faster vanilla function, otherwise it'll run the slower, but safer scale + * function, for extended boundaries. */ -void mtxf_to_mtx(Mtx *dest, Mat4 src) { +void mtxf_to_mtx_scale(Mtx *dest, Mat4 src) { Mat4 temp; register s32 i, j; for( i = 0; i < 4; i++ ) { for( j = 0; j < 3; j++ ) { - temp[i][j] = src[i][j] / gWorldScale; + temp[i][j] = src[i][j] / gWorldScale; } temp[i][3] = src[i][3]; } @@ -478,10 +483,29 @@ void mtxf_to_mtx(Mtx *dest, Mat4 src) { guMtxF2L( temp, dest ); } +void mtxf_to_mtx_constant(register s16 *dest, register f32 *src) { + s32 asFixedPoint; + s32 i; + for (i = 0; i < 16; i++) + { + asFixedPoint = src[i] * (1 << 16); + dest[i] = asFixedPoint >> 16; + dest[i + 16] = asFixedPoint & 0xFFFF; + } +} + +void mtxf_to_mtx(void *dest, void *src) +{ + if (gWorldScale > 2.0f) + mtxf_to_mtx_scale(dest, src); + else + mtxf_to_mtx_constant(dest, src); +} + /** * Set 'mtx' to a transformation matrix that rotates around the z axis. */ -void mtxf_rotate_xy(Mtx *mtx, s16 angle) { +void mtxf_rotate_xy(Mtx *mtx, s32 angle) { Mat4 temp; mtxf_identity(temp); @@ -529,7 +553,7 @@ void vec3f_get_dist_and_angle(Vec3f from, Vec3f to, f32 *dist, s16 *pitch, s16 * * Construct the 'to' point which is distance 'dist' away from the 'from' position, * and has the angles pitch and yaw. */ -void vec3f_set_dist_and_angle(Vec3f from, Vec3f to, f32 dist, s16 pitch, s16 yaw) { +void vec3f_set_dist_and_angle(Vec3f from, Vec3f to, f32 dist, s32 pitch, s32 yaw) { to[0] = from[0] + dist * coss(pitch) * sins(yaw); to[1] = from[1] + dist * sins(pitch); to[2] = from[2] + dist * coss(pitch) * coss(yaw); @@ -858,7 +882,7 @@ void find_surface_on_ray_list(struct SurfaceNode *list, Vec3f orig, Vec3f dir, f #endif } -void find_surface_on_ray_cell(s16 cellX, s16 cellZ, Vec3f orig, Vec3f normalized_dir, f32 dir_length, struct Surface **hit_surface, Vec3f hit_pos, f32 *max_length, s32 flags) { +void find_surface_on_ray_cell(s32 cellX, s32 cellZ, Vec3f orig, Vec3f normalized_dir, f32 dir_length, struct Surface **hit_surface, Vec3f hit_pos, f32 *max_length, s32 flags) { // Skip if OOB if (cellX >= 0 && cellX <= (NUM_CELLS - 1) && cellZ >= 0 && cellZ <= (NUM_CELLS - 1)) { // Iterate through each surface in this partition diff --git a/src/engine/math_util.h b/src/engine/math_util.h index a17b063b..6e37ea4e 100644 --- a/src/engine/math_util.h +++ b/src/engine/math_util.h @@ -357,20 +357,22 @@ void vec3f_normalize(Vec3f dest); void mtxf_copy(Mat4 dest, Mat4 src); void mtxf_identity(Mat4 mtx); void mtxf_translate(Mat4 dest, Vec3f b); -void mtxf_lookat(Mat4 mtx, Vec3f from, Vec3f to, s16 roll); +void mtxf_lookat(Mat4 mtx, Vec3f from, Vec3f to, s32 roll); void mtxf_rotate_zxy_and_translate(Mat4 dest, Vec3f translate, Vec3s rotate); void mtxf_rotate_xyz_and_translate(Mat4 dest, Vec3f b, Vec3s c); -void mtxf_billboard(Mat4 dest, Mat4 mtx, Vec3f position, s16 angle); -void mtxf_align_terrain_normal(Mat4 dest, Vec3f upDir, Vec3f pos, s16 yaw); -void mtxf_align_terrain_triangle(Mat4 mtx, Vec3f pos, s16 yaw, f32 radius); +void mtxf_billboard(Mat4 dest, Mat4 mtx, Vec3f position, s32 angle); +void mtxf_align_terrain_normal(Mat4 dest, Vec3f upDir, Vec3f pos, s32 yaw); +void mtxf_align_terrain_triangle(Mat4 mtx, Vec3f pos, s32 yaw, f32 radius); void mtxf_mul(Mat4 dest, Mat4 a, Mat4 b); void mtxf_scale_vec3f(Mat4 dest, Mat4 mtx, Vec3f s); void mtxf_mul_vec3s(Mat4 mtx, Vec3s b); -void mtxf_to_mtx(Mtx *dest, Mat4 src); -void mtxf_rotate_xy(Mtx *mtx, s16 angle); +void mtxf_to_mtx(void *dest, void *src); +void mtxf_to_mtx_constant(register s16 *dest, register f32 *src); +void mtxf_to_mtx_scale(Mtx *dest, Mat4 src); +void mtxf_rotate_xy(Mtx *mtx, s32 angle); void get_pos_from_transform_mtx(Vec3f dest, Mat4 objMtx, Mat4 camMtx); void vec3f_get_dist_and_angle(Vec3f from, Vec3f to, f32 *dist, s16 *pitch, s16 *yaw); -void vec3f_set_dist_and_angle(Vec3f from, Vec3f to, f32 dist, s16 pitch, s16 yaw); +void vec3f_set_dist_and_angle(Vec3f from, Vec3f to, f32 dist, s32 pitch, s32 yaw); s32 approach_s32(s32 current, s32 target, s32 inc, s32 dec); f32 approach_f32(f32 current, f32 target, f32 inc, f32 dec); s16 atan2s(f32 y, f32 x); diff --git a/src/game/puppyprint.c b/src/game/puppyprint.c index bc831fc9..53688027 100644 --- a/src/game/puppyprint.c +++ b/src/game/puppyprint.c @@ -383,7 +383,7 @@ void puppyprint_render_profiler(void) if (!ramViewer && !benchViewer && !logViewer) { print_fps(16,40); - sprintf(textBytes, "CPU: %dus (%d_)#RSP: %dus (%d_)#RDP: %dus (%d_)", (s32)cpuCount, (s32)OS_CYCLES_TO_USEC(cpuTime)/248, (s32)OS_CYCLES_TO_USEC(rspTime), (s32)OS_CYCLES_TO_USEC(rspTime)/333, (s32)OS_CYCLES_TO_USEC(rdpTime), (s32)OS_CYCLES_TO_USEC(rdpTime)/333); + sprintf(textBytes, "CPU: %dus (%d_)#RSP: %dus (%d_)#RDP: %dus (%d_)", (s32)cpuCount, (s32)(cpuCount/333), (s32)OS_CYCLES_TO_USEC(rspTime), (s32)OS_CYCLES_TO_USEC(rspTime)/333, (s32)OS_CYCLES_TO_USEC(rdpTime), (s32)OS_CYCLES_TO_USEC(rdpTime)/333); print_small_text(16, 52, textBytes, PRINT_TEXT_ALIGN_LEFT, PRINT_ALL); sprintf(textBytes, "OBJ: %d/%d", gObjectCounter, OBJECT_POOL_CAPACITY); diff --git a/src/game/rendering_graph_node.c b/src/game/rendering_graph_node.c index 22b3854f..10dc3f6d 100644 --- a/src/game/rendering_graph_node.c +++ b/src/game/rendering_graph_node.c @@ -208,7 +208,7 @@ LookAt lookAt; #if SILHOUETTE #define SIL_CVG_THRESHOLD 0x3F // 32..255, 63 seems to give best results -#define SCHWA (AA_EN | IM_RD | CLR_ON_CVG | CVG_DST_WRAP | CVG_X_ALPHA | FORCE_BL) +#define SCHWA (IM_RD | CLR_ON_CVG | CVG_DST_WRAP | CVG_X_ALPHA | FORCE_BL) #define SET_SILHOUETTE_F3D(gfx) { \ gDPSetRenderMode( (gfx)++, (SCHWA | GBL_c1(G_BL_CLR_FOG, G_BL_A_FOG, G_BL_CLR_MEM, G_BL_1MA)), \ (SCHWA | GBL_c2(G_BL_CLR_FOG, G_BL_A_FOG, G_BL_CLR_MEM, G_BL_1MA))); \ @@ -515,7 +515,7 @@ static void geo_process_switch(struct GraphNodeSwitchCase *node) { } } -static void make_roll_matrix(Mtx *mtx, s16 angle) { +static void make_roll_matrix(Mtx *mtx, s32 angle) { Mat4 temp; mtxf_identity(temp); @@ -1262,7 +1262,7 @@ void geo_try_process_children(struct GraphNode *node) { * be iterated over. */ void geo_process_node_and_siblings(struct GraphNode *firstNode) { - s16 iterateChildren = TRUE; + s32 iterateChildren = TRUE; struct GraphNode *curGraphNode = firstNode; struct GraphNode *parent = curGraphNode->parent;