/* sub_5D676 */ internal static void localSteppingPathInit(Point target, Point caster, SteppingPath path) { path.attacker = caster; path.target = target; path.CalculateDeltas(); }
/* sub_5D702 */ static int find_players_on_path(SteppingPath path, List<int> player_list) { int dir = 0; while (path.Step()) { int playerIndex = ovr033.PlayerIndexAtMapXY(path.current.y, path.current.x); if (playerIndex > 0) { if (player_list.Contains(playerIndex) == false) { player_list.Add(playerIndex); } } dir = path.direction; } return dir; }
// sub_5D7CF static void BuildAreaDamageTargets(int max_range, int playerSize, Point targetPos, Point casterPos) { List<int> players_on_path = new List<int>(); bool finished; SteppingPath path = new SteppingPath(); localSteppingPathInit(targetPos, casterPos, path); byte[] directions = new byte[0x32]; int index = 0; while (!path.Step()) { directions[index] = path.direction; index++; } int count = index - 1; index = 0; max_range *= 2; int tmp_range = path.steps; finished = false; var tmpPos = new Point(targetPos); while (tmp_range < max_range && finished == false) { if (tmpPos.x < 0x31 && tmpPos.x > 0 && tmpPos.y < 0x18 && tmpPos.y > 0) { switch (directions[index]) { case 0: case 2: case 4: case 6: tmp_range += 2; break; case 1: case 3: case 5: case 7: tmp_range += 3; break; } tmpPos += gbl.MapDirectionDelta[directions[index]]; if (index == count) { index = 0; } else { index++; } } else { finished = true; } } targetPos.MapBoundaryTrunc(); ovr032.canReachTarget(ref targetPos, casterPos); localSteppingPathInit(targetPos, casterPos, path); int var_76 = find_players_on_path(path, players_on_path); if (playerSize > 1) { Point map_b = targetPos + unk_16D32[var_76]; map_b.MapBoundaryTrunc(); localSteppingPathInit(map_b, casterPos, path); find_players_on_path(path, players_on_path); if (playerSize > 2) { Point map_a = targetPos + unk_16D22[var_76]; map_a.MapBoundaryTrunc(); localSteppingPathInit(map_a, casterPos, path); find_players_on_path(path, players_on_path); } } gbl.spellTargets.Clear(); foreach (var idx in players_on_path) { var player = gbl.player_array[idx]; if (player != gbl.SelectedPlayer) { gbl.spellTargets.Add(player); } } }
internal static void sub_5FA44(byte arg_0, SaveVerseType bonusType, int damage, byte arg_6) { int var_3A = 0; /* Simeon */ bool var_36 = false; ovr025.load_missile_icons(0x13); int var_39; int groundTile; ovr033.AtMapXY(out groundTile, out var_39, gbl.targetPos); int var_3D = 0; int var_35 = 1; var playerPos = ovr033.PlayerMapPos(gbl.SelectedPlayer); byte var_38 = arg_0; if (playerPos != gbl.targetPos) { int var_3C = arg_6 * 2; gbl.byte_1D2C7 = true; while (var_3C > 0) { var path_a = new SteppingPath(); path_a.attacker = gbl.targetPos; path_a.target = gbl.targetPos + ((gbl.targetPos - playerPos) * var_35 * var_3C); path_a.CalculateDeltas(); do { var tmppos = path_a.current; if (path_a.attacker != path_a.target) { bool stepping; do { stepping = path_a.Step(); ovr033.AtMapXY(out groundTile, out var_3A, path_a.current); if (gbl.BackGroundTiles[groundTile].move_cost == 1) { var_36 = false; } } while (stepping == true && (var_3A <= 0 || var_3A == var_39) && groundTile != 0 && gbl.BackGroundTiles[groundTile].move_cost <= 1 && path_a.steps < var_3C); } if (groundTile == 0) { var_3C = 0; } ovr025.draw_missile_attack(0x32, 4, path_a.current, tmppos); var_36 = DoElecDamage(var_36, var_39, bonusType, damage, path_a.current); var_39 = var_3A; if (var_36 == true) { gbl.targetPos = path_a.current; var path_b = new SteppingPath(); path_b.attacker = gbl.targetPos; path_b.target = playerPos; path_b.CalculateDeltas(); while (path_b.Step() == true) { /* empty */ } if (var_38 != 0 && path_b.steps <= 8) { path_a.steps += 8; } var_35 = -var_35; var_38 = 0; var_39 = 0; } var_3D = (byte)(path_a.steps - var_3D); if (var_3D < var_3C) { var_3C -= var_3D; } else { var_3C = 0; } var_3D = path_a.steps; } while (var_36 == false && var_3C != 0); } gbl.byte_1D2C7 = false; } }
/* sub_733F1 */ static MapReach canReachTargetCalc(Struct_1D1BC groundTilesMap, Point outPos, Point attacker) { SteppingPath var_31 = new SteppingPath(); SteppingPath var_19 = new SteppingPath(); int max_range = (256 * 2) + 1; var_19.attacker = attacker; var_19.target = outPos; var_19.CalculateDeltas(); var_31.attacker.x = 0; var_31.attacker.y = gbl.BackGroundTiles[groundTilesMap[attacker]].field_1; if (var_19.diff_x > var_19.diff_y) { var_31.target.x = var_19.diff_x; } else { var_31.target.x = var_19.diff_y; } var_31.target.y = gbl.BackGroundTiles[groundTilesMap[attacker]].field_1; var_31.CalculateDeltas(); bool finished = false; do { int gt = groundTilesMap[var_19.current]; Struct_189B4 s189 = gbl.BackGroundTiles[gt]; if (groundTilesMap.ignoreWalls == false && s189.field_2 > var_31.current.y) { return new MapReach(false, var_19.steps, var_19.current); } // range is for cache hard coded to 256, thus max_range = 513, so skip this. if (var_19.steps > max_range) { return new MapReach(false, var_19.steps, var_19.current); } var_31.Step(); finished = !var_19.Step(); } while (finished == false); return new MapReach(true, var_19.steps, outPos); }
/* sub_67AA4 */ internal static void draw_missile_attack(int delay, int frameCount, Point target, Point attacker) { Point center; bool var_B4; bool var_B3; SteppingPath path = new SteppingPath(); byte[] pathDir = new byte[0x94]; seg051.FillChar(8, 0x94, pathDir); int var_AF = 0; int frame = 0; path.attacker = attacker * 3; path.target = target * 3; path.CalculateDeltas(); do { var_B4 = !path.Step(); pathDir[var_AF] = path.direction; var_AF++; } while (var_B4 == false); int var_B0 = var_AF - 2; if (var_B0 < 2 || var_AF < 2) { return; } var diff = target - attacker; if (ovr033.CoordOnScreen(attacker - gbl.mapToBackGroundTile.mapScreenTopLeft) == false || ovr033.CoordOnScreen(target - gbl.mapToBackGroundTile.mapScreenTopLeft) == false) { if (System.Math.Abs(diff.x) <= 6 && System.Math.Abs(diff.y) <= 6) { var_B3 = true; center = (diff / 2) + attacker; } else { var_B3 = false; center = gbl.mapToBackGroundTile.mapScreenTopLeft + Point.ScreenCenter; } } else { var_B3 = true; center = gbl.mapToBackGroundTile.mapScreenTopLeft + Point.ScreenCenter; } ovr033.redrawCombatArea(8, 0xFF, center); var_AF = 0; Point delta = new Point(0, 0); do { Point cur = ((attacker - gbl.mapToBackGroundTile.mapScreenTopLeft) * 3) + delta; var_B4 = false; do { Point var_C6 = gbl.MapDirectionDelta[pathDir[var_AF]]; cur += var_C6; if (delay > 0 || (cur.x % 3) == 0 || (cur.y % 3) == 0) { Display.SaveVidRam(); seg040.OverlayBounded(gbl.missile_dax, 5, frame, cur.y, cur.x); seg040.DrawOverlay(); seg049.SysDelay(delay); Display.RestoreVidRam(); frame++; if (frame >= frameCount) { frame = 0; } } var_AF++; if (cur.x < 0 || cur.x > 0x12 || cur.y < 0 || cur.y > 0x12) { var_B4 = true; } if (var_B4 == false && var_AF < var_B0) { delta += var_C6; if (Math.Abs(delta.x) == 3) { attacker.x += Math.Sign(delta.x); center.x += Math.Sign(delta.x); delta.x = 0; } if (Math.Abs(delta.y) == 3) { attacker.y += Math.Sign(delta.y); center.y += Math.Sign(delta.y); delta.y = 0; } } } while (var_AF < var_B0 && var_B4 == false); if (var_AF < var_B0) { int var_CE = 0; int var_D0 = 0; delta = new Point(0, 0); attacker = target; if ((target.x + Point.ScreenHalfX) > Point.MapMaxX) { var_CE = target.x - Point.MapMaxX; } else if (target.x < Point.ScreenHalfX) { var_CE = Point.ScreenHalfX - target.x; } if ((target.y + Point.ScreenHalfY) > Point.MapMaxY) { var_D0 = target.y - Point.MapMaxY; } else if (target.y < Point.ScreenHalfY) { var_D0 = Point.ScreenHalfY - target.y; } center.x = target.x + var_CE; center.y = target.y + var_D0; ovr033.redrawCombatArea(8, 0xff, center); cur = (target - gbl.mapToBackGroundTile.mapScreenTopLeft) * 3; var_AF = var_B0; var_B4 = false; do { Point var_C6 = new Point(0, 0) - gbl.MapDirectionDelta[pathDir[var_AF]]; cur += var_C6; if (cur.x > 18) { attacker.x = gbl.mapToBackGroundTile.mapScreenTopLeft.x + Point.ScreenMaxX; } else if (cur.x < 0) { attacker.x = gbl.mapToBackGroundTile.mapScreenTopLeft.x; } if (cur.y > 18) { attacker.y = gbl.mapToBackGroundTile.mapScreenTopLeft.y + Point.ScreenMaxY; } else if (cur.y < 0) { attacker.y = gbl.mapToBackGroundTile.mapScreenTopLeft.y; } if (cur.x < 0 || cur.x > 18 || cur.y < 0 || cur.y > 18) { var_B4 = true; } if (var_B4 == false) { delta += var_C6; if (System.Math.Abs(delta.x) == Point.ScreenHalfX) { attacker.x += Math.Sign(delta.x); center.x += Math.Sign(delta.x); delta.x = 0; } if (System.Math.Abs(delta.y) == Point.ScreenHalfY) { attacker.y += Math.Sign(delta.y); center.y += Math.Sign(delta.y); delta.y = 0; } var_AF -= 1; } } while (var_B4 == false); } else { var_B3 = true; if (ovr033.CoordOnScreen(target - gbl.mapToBackGroundTile.mapScreenTopLeft) == false) { ovr033.redrawCombatArea(8, 3, target); } cur = (target - gbl.mapToBackGroundTile.mapScreenTopLeft) * 3; Display.SaveVidRam(); seg040.OverlayBounded(gbl.missile_dax, 5, frame, cur.y, cur.x); if (delay > 0) { seg040.DrawOverlay(); seg049.SysDelay(delay); Display.RestoreVidRam(); } } } while (var_B3 == false); seg040.DrawOverlay(); }