From 416f17d7ead0818bede36c479996f152527a2708 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Micha=C3=ABl=20Lemaire?= Date: Fri, 13 Jul 2018 16:52:59 +0200 Subject: [PATCH] WIP --- TODO.md | 1 + src/core/Battle.spec.ts | 27 ++++++++++++++++++++++++++- src/core/Battle.ts | 11 +++++++++++ src/core/MoveFireSimulator.spec.ts | 2 +- src/core/actions/MoveAction.spec.ts | 12 ++++++------ src/core/actions/MoveAction.ts | 14 ++++++++++++-- 6 files changed, 57 insertions(+), 10 deletions(-) diff --git a/TODO.md b/TODO.md index 0a28d0e..a1b7c69 100644 --- a/TODO.md +++ b/TODO.md @@ -111,6 +111,7 @@ Common UI * If ProgressiveMessage animation performance is bad, show the text directly * Add caret/focus and configurable background to text input * Release keybord grabbing when UITextInput is hidden or loses focus +* UI parents should only be containers, not images * Mobile: think UI layout so that fingers do not block the view (right and left handed) * Mobile: display tooltips larger and on the side of screen where the finger is not * Mobile: targetting in two times, using a draggable target indicator diff --git a/src/core/Battle.spec.ts b/src/core/Battle.spec.ts index ee13c15..b014bac 100644 --- a/src/core/Battle.spec.ts +++ b/src/core/Battle.spec.ts @@ -378,6 +378,31 @@ module TK.SpaceTac { check.equals(ship.getValue("hull"), 0, "hull=0"); check.equals(battle.log.count(), 0, "log count=0"); }); - }) + }); + + test.case("checks whether a location is occupied or not", check => { + let battle = new Battle(); + + check.in("no ships", check => { + check.equals(battle.isOccupied({ x: 0, y: 0 }), false); + }); + + battle.fleets[0].addShip().setArenaPosition(0, 0); + check.in("one ship", check => { + check.equals(battle.isOccupied({ x: 0, y: 0 }), true, "0,0"); + check.equals(battle.isOccupied({ x: 10, y: 0 }), true, "10,0"); + check.equals(battle.isOccupied({ x: 50, y: 0 }), true, "50,0"); + check.equals(battle.isOccupied({ x: 51, y: 0 }), false, "51,0"); + }); + + let s2 = battle.fleets[0].addShip(); + s2.setArenaPosition(0, 40); + check.in("two ships", check => { + check.equals(battle.isOccupied({ x: 0, y: 30 }), true, "0,30"); + check.equals(battle.isOccupied({ x: 0, y: 60 }), true, "0,60"); + check.equals(battle.isOccupied({ x: 0, y: 30 }, [s2]), true, "0,30 ignore second"); + check.equals(battle.isOccupied({ x: 0, y: 60 }, [s2]), false, "0,60 ignore second"); + }); + }); }); } diff --git a/src/core/Battle.ts b/src/core/Battle.ts index e69c89d..5cca012 100644 --- a/src/core/Battle.ts +++ b/src/core/Battle.ts @@ -346,6 +346,17 @@ module TK.SpaceTac { return flatten(drone_effects.concat(ships_effects)); } + /** + * Check if a specific location is occupied + */ + isOccupied(location: IArenaLocation, exclude: Ship[] = []): boolean { + let ships = this.ships.list().filter(ship => ship.alive); + if (exclude.length) { + ships = difference(ships, exclude); + } + return any(ships, ship => arenaDistance(ship.location, location) <= 50.1); + } + /** * Perform all battle checks to ensure the state is consistent * diff --git a/src/core/MoveFireSimulator.spec.ts b/src/core/MoveFireSimulator.spec.ts index cd0fa75..9d70d09 100644 --- a/src/core/MoveFireSimulator.spec.ts +++ b/src/core/MoveFireSimulator.spec.ts @@ -124,7 +124,7 @@ module TK.SpaceTac.Specs { ]); }); - test.case("accounts for exclusion areas for the approach", check => { + test.case("does not make approach on an occupied location", check => { let [ship, simulator, action] = simpleWeaponCase(100, 5, 1, 50); ship.setArenaPosition(300, 200); let battle = new Battle(); diff --git a/src/core/actions/MoveAction.spec.ts b/src/core/actions/MoveAction.spec.ts index a8fd1b2..f434eec 100644 --- a/src/core/actions/MoveAction.spec.ts +++ b/src/core/actions/MoveAction.spec.ts @@ -69,19 +69,19 @@ module TK.SpaceTac.Specs { var action = new MoveAction("Engine", { distance_per_power: 1000 }); var result = action.checkTarget(ship, Target.newFromLocation(700, 500)); - check.equals(result, true); + check.equals(result, true, "700"); result = action.checkTarget(ship, Target.newFromLocation(800, 500)); - check.equals(result, true); + check.equals(result, true, "800"); - result = action.checkTarget(ship, Target.newFromLocation(900, 500)); - check.equals(result, false); + result = action.checkTarget(ship, Target.newFromLocation(950, 500)); + check.equals(result, false, "950"); result = action.checkTarget(ship, Target.newFromLocation(1000, 500)); - check.equals(result, false); + check.equals(result, false, "1000"); result = action.checkTarget(ship, Target.newFromLocation(1200, 500)); - check.equals(result, true); + check.equals(result, true, "1200"); }); test.case("builds a textual description", check => { diff --git a/src/core/actions/MoveAction.ts b/src/core/actions/MoveAction.ts index f5fdfd2..b59f235 100644 --- a/src/core/actions/MoveAction.ts +++ b/src/core/actions/MoveAction.ts @@ -91,11 +91,21 @@ module TK.SpaceTac { } protected checkLocationTarget(ship: Ship, target: Target, from: IArenaLocation): boolean { - if (!ship.grid.check(target) || ship.grid.measure(from, target) < 1e-8) { + // Check the location is on the grid + if (!ship.grid.check(target)) { return false; } - // TODO Check the space is not occupied + // Check that we move at least a unit + if (ship.grid.measure(from, target) < 1) { + return false; + } + + // Check the space is not occupied + let battle = ship.getBattle(); + if (battle && battle.isOccupied(target, [ship])) { + return false; + } return true; }