public static void item_color(s_item hp, float[] c) { switch (hp.m_t) { case Solid.ITEM_COIN: if (hp.m_n >= 1) { c[0] = 1.0f; c[1] = 1.0f; c[2] = 0.2f; } if (hp.m_n >= 5) { c[0] = 1.0f; c[1] = 0.2f; c[2] = 0.2f; } if (hp.m_n >= 10) { c[0] = 0.2f; c[1] = 0.2f; c[2] = 1.0f; } break; case Solid.ITEM_GROW: c[0] = 0.00f; c[1] = 0.51f; c[2] = 0.80f; break; case Solid.ITEM_SHRINK: c[0] = 1.00f; c[1] = 0.76f; c[2] = 0.00f; break; default: c[0] = 1.0f; c[1] = 1.0f; c[2] = 1.0f; break; } }
public void item_draw(s_item hp, float r) { float[] c = new float[3]; s_file fp = null; switch (hp.m_t) { case Solid.ITEM_COIN: fp = item_coin_file; break; case Solid.ITEM_GROW: fp = item_grow_file; break; case Solid.ITEM_SHRINK: fp = item_shrink_file; break; } item_color(hp, c); Video.Color(c); fp.sol_draw(0, 1); }
public static void game_run_cmd(Command cmd) { /* * Neverball <= 1.5.1 does not send explicit tilt axes, rotation * happens directly around view vectors. So for compatibility if * at the time of receiving tilt angles we have not yet received * the tilt axes, we use the view vectors. */ float[] f = new float[3]; if (client_state != 0) { s_ball[] up; float dt; int i; switch (cmd.type) { case cmd_type.CMD_END_OF_UPDATE: game_run_cmd_got_tilt_axes = 0; if (first_update != 0) { first_update = 0; break; } /* Compute gravity for particle effects. */ if (status == (int)GAME.GAME_GOAL) { game_common.game_tilt_grav(f, game_run_cmd_gup, tilt); } else { game_common.game_tilt_grav(f, game_run_cmd_gdn, tilt); } /* Step particle, goal and jump effects. */ if (ups > 0) { dt = 1.0f / (float)ups; if (goal_e != 0 && goal_k < 1.0f) { goal_k += dt; } if (jump_b != 0) { jump_dt += dt; if (1.0f < jump_dt) { jump_b = 0; } } Part.part_step(f, dt); } break; case cmd_type.CMD_MAKE_BALL: /* Allocate a new ball and mark it as the current ball. */ up = new s_ball[file.m_uc + 1]; { for (i = 0; i < file.m_uc; i++) { up[i] = file.m_uv[i]; } up[file.m_uc] = new s_ball(); } { file.m_uv = up; curr_ball = file.m_uc; file.m_uc++; } break; case cmd_type.CMD_MAKE_ITEM: /* Allocate and initialise a new item. */ { s_item[] hp = new s_item[file.m_hc + 1]; { for (i = 0; i < file.m_hc; i++) { hp[i] = file.m_hv[i]; } } { s_item h = new s_item(); Vec3.v_cpy(h.m_p, cmd.mkitem.p); h.m_t = cmd.mkitem.t; h.m_n = cmd.mkitem.n; file.m_hv = hp; file.m_hv[file.m_hc] = h; file.m_hc++; } } break; case cmd_type.CMD_PICK_ITEM: /* Set up particle effects and discard the item. */ { s_item hp = file.m_hv[cmd.pkitem.hi]; Item.item_color(hp, f); Part.part_burst(hp.m_p, f); hp.m_t = Solid.ITEM_NONE; } break; case cmd_type.CMD_TILT_ANGLES: if (game_run_cmd_got_tilt_axes == 0) { game_common.game_tilt_axes(tilt, view_e); } tilt.rx = cmd.tiltangles.x; tilt.rz = cmd.tiltangles.z; break; case cmd_type.CMD_SOUND: /* Play the sound, then free its file name. */ if (cmd.sound.n != null) { Audio.audio_play(cmd.sound.n, cmd.sound.a); /* * FIXME Command memory management should be done * elsewhere and done properly. */ cmd.sound.n = null; } break; case cmd_type.CMD_TIMER: timer = cmd.timer.t; break; case cmd_type.CMD_STATUS: status = cmd.status.t; break; case cmd_type.CMD_COINS: coins = cmd.coins.n; break; case cmd_type.CMD_JUMP_ENTER: jump_b = 1; jump_e = 0; jump_dt = 0.0f; break; case cmd_type.CMD_JUMP_EXIT: jump_e = 1; break; case cmd_type.CMD_BODY_PATH: file.m_bv[cmd.bodypath.bi].m_pi = cmd.bodypath.pi; break; case cmd_type.CMD_BODY_TIME: file.m_bv[cmd.bodytime.bi].m_t = cmd.bodytime.t; break; case cmd_type.CMD_GOAL_OPEN: /* * Enable the goal and make sure it's fully visible if * this is the first update. */ if (goal_e == 0) { goal_e = 1; goal_k = first_update != 0 ? 1.0f : 0.0f; } break; case cmd_type.CMD_SWCH_ENTER: file.m_xv[cmd.swchenter.xi].m_e = 1; break; case cmd_type.CMD_SWCH_TOGGLE: file.m_xv[cmd.swchtoggle.xi].m_f = file.m_xv[cmd.swchtoggle.xi].m_f == 0 ? 1 : 0; break; case cmd_type.CMD_SWCH_EXIT: file.m_xv[cmd.swchexit.xi].m_e = 0; break; case cmd_type.CMD_UPDATES_PER_SECOND: ups = cmd.ups.n; break; case cmd_type.CMD_BALL_RADIUS: file.m_uv[curr_ball].m_r = cmd.ballradius.r; break; case cmd_type.CMD_CLEAR_ITEMS: if (file.m_hv != null) { file.m_hv = null; } file.m_hc = 0; break; case cmd_type.CMD_CLEAR_BALLS: if (file.m_uv != null) { file.m_uv = null; } file.m_uc = 0; break; case cmd_type.CMD_BALL_POSITION: Vec3.v_cpy(file.m_uv[curr_ball].m_p, cmd.ballpos.p); break; case cmd_type.CMD_BALL_BASIS: Vec3.v_cpy(file.m_uv[curr_ball].m_e[0], cmd.ballbasis.e[0]); Vec3.v_cpy(file.m_uv[curr_ball].m_e[1], cmd.ballbasis.e[1]); Vec3.v_crs(file.m_uv[curr_ball].m_e[2], file.m_uv[curr_ball].m_e[0], file.m_uv[curr_ball].m_e[1]); break; case cmd_type.CMD_VIEW_POSITION: Vec3.v_cpy(view_p, cmd.viewpos.p); break; case cmd_type.CMD_VIEW_CENTER: Vec3.v_cpy(view_c, cmd.viewcenter.c); break; case cmd_type.CMD_VIEW_BASIS: Vec3.v_cpy(view_e[0], cmd.viewbasis.e[0]); Vec3.v_cpy(view_e[1], cmd.viewbasis.e[1]); Vec3.v_crs(view_e[2], view_e[0], view_e[1]); break; case cmd_type.CMD_CURRENT_BALL: curr_ball = cmd.currball.ui; break; case cmd_type.CMD_PATH_FLAG: file.m_pv[cmd.pathflag.pi].m_f = cmd.pathflag.f; break; case cmd_type.CMD_STEP_SIMULATION: /* * Simulate body motion. * * This is done on the client side due to replay file size * concerns and isn't done as part of cmd_type.CMD_END_OF_UPDATE to * match the server state as closely as possible. Body * time is still synchronised with the server on a * semi-regular basis and path indices are handled through * cmd_type.CMD_BODY_PATH, thus this code doesn't need to be as * sophisticated as sol_body_step. */ dt = cmd.stepsim.dt; for (i = 0; i < file.m_bc; i++) { s_body bp = file.m_bv[i]; // + i; if (bp.m_pi >= 0) { s_path pp = file.m_pv[bp.m_pi]; if (pp.m_f != 0) { bp.m_t += dt; } } } break; case cmd_type.CMD_MAP: /* * Note if the loaded map matches the server's * expectations. (No, this doesn't actually load a map, * yet. Something else somewhere else does.) */ cmd.map.name = null; game_compat_map = version_x == cmd.map.version.x ? 1 : 0; break; case cmd_type.CMD_TILT_AXES: game_run_cmd_got_tilt_axes = 1; Vec3.v_cpy(tilt.x, cmd.tiltaxes.x); Vec3.v_cpy(tilt.z, cmd.tiltaxes.z); break; case cmd_type.CMD_NONE: case cmd_type.CMD_MAX: break; } } }
public static void sol_load_item(IntPtr fin, s_item hp) { Binary.get_array(fin, hp.m_p, 3); Binary.get_index(fin, ref hp.m_t); Binary.get_index(fin, ref hp.m_n); }
public static int game_update_state(int bt) { s_file fp = file; s_goal zp; int hi; float[] p = new float[3]; /* Test for an item. */ if (bt != 0 && (hi = solid_phys.sol_item_test(fp, p, Item.ITEM_RADIUS)) != -1) { s_item hp = file.m_hv[hi]; game_cmd_pkitem(hi); grow_init(fp, hp.m_t); if (hp.m_t == Solid.ITEM_COIN) { coins += hp.m_n; game_cmd_coins(); } audio_play(Common.AUD_COIN, 1); /* Discard item. */ hp.m_t = Solid.ITEM_NONE; } /* Test for a switch. */ if (solid_phys.sol_swch_test(fp, 0) != 0) { audio_play(Common.AUD_SWITCH, 1); } /* Test for a jump. */ if (jump_e == 1 && jump_b == 0 && solid_phys.sol_jump_test(fp, jump_p, 0) == 1) { jump_b = 1; jump_e = 0; jump_dt = 0; Vec3.v_sub(jump_w, jump_p, fp.m_uv[0].m_p); Vec3.v_add(jump_w, view_p, jump_w); audio_play(Common.AUD_JUMP, 1); game_cmd_jump(1); } if (jump_e == 0 && jump_b == 0 && solid_phys.sol_jump_test(fp, jump_p, 0) == 0) { jump_e = 1; game_cmd_jump(0); } /* Test for a goal. */ if (bt != 0 && goal_e != 0 && (zp = solid_phys.sol_goal_test(fp, p, 0)) != null) { audio_play(Common.AUD_GOAL, 1.0f); return((int)GAME.GAME_GOAL); } /* Test for time-out. */ if (bt != 0 && timer_down != 0 && timer <= 0) { audio_play(Common.AUD_TIME, 1.0f); return((int)GAME.GAME_TIME); } /* Test for fall-out. */ if (bt != 0 && fp.m_uv[0].m_p[1] < fp.m_vv[0].m_p[1]) { audio_play(Common.AUD_FALL, 1.0f); return((int)GAME.GAME_FALL); } return((int)GAME.GAME_NONE); }