Firekeeping: shared guild fires
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
parent
c64e28fc38
commit
54ae3ae641
6 changed files with 657 additions and 34 deletions
|
|
@ -741,7 +741,7 @@ class TierTest(unittest.TestCase):
|
|||
world = world_with(("kay", "miner"))
|
||||
p = world["players"]["kay"]
|
||||
p["xp"]["smithing"] = game.XP_TABLE[30]
|
||||
p["bank"] = {"iron_ore": 5, "coal": 10}
|
||||
p["bank"] = {"iron_ore": 5, "coal": 10, "willow_logs": 5}
|
||||
self.assertEqual(game.start_action(world, p, "smith_steel_bar", T0), "Needs Smithy level 2")
|
||||
world["city"]["buildings"]["smithy"]["level"] = 2
|
||||
self.assertIsNone(game.start_action(world, p, "smith_steel_bar", T0))
|
||||
|
|
@ -903,7 +903,7 @@ class HerbloreTest(unittest.TestCase):
|
|||
game.start_action(world, p, "grow_guam_leaf", T0)
|
||||
game.process_player(world, p, T0 + 450, random.Random(1))
|
||||
self.assertEqual(p["bank"]["guam_leaf"], 10)
|
||||
p["bank"]["logs"] = 3
|
||||
p["bank"]["logs"] = 6 # one a potion, one to burn under the still
|
||||
self.assertIsNone(game.start_action(world, p, "brew_woodcutting_potion_1", T0 + 450)) # tier I needs no Herblore
|
||||
game.process_player(world, p, T0 + 1000, random.Random(1))
|
||||
self.assertEqual(p["bank"]["woodcutting_potion_1"], 3)
|
||||
|
|
@ -1818,7 +1818,7 @@ class StationAndStorageTest(unittest.TestCase):
|
|||
self.assertEqual(game.action_time(self.world, self.bob, labour), bare)
|
||||
|
||||
def test_stations_move_out_of_the_tool_slot(self):
|
||||
self.world["version"] = game.WORLD_VERSION - 1
|
||||
self.world["version"] = 22
|
||||
self.bob["equip"]["tool_smithing"] = "oak_anvil_stand"
|
||||
del self.bob["equip"]["station_smithing"]
|
||||
game.migrate(self.world, T0)
|
||||
|
|
@ -1847,3 +1847,108 @@ class StationAndStorageTest(unittest.TestCase):
|
|||
self.assertEqual(app.Handler.equip(handler, self.bob, "wooden_strongbox", None), "Bank too full for that")
|
||||
self.assertEqual(self.bob["equip"]["storage"], "oak_strongbox")
|
||||
self.assertEqual(self.bob["bank"]["wooden_strongbox"], 1)
|
||||
|
||||
|
||||
class FirekeepingTest(unittest.TestCase):
|
||||
def setUp(self):
|
||||
self.world = world_with(("kai", "commoner"), ("sam", "commoner"))
|
||||
self.kai, self.sam = self.world["players"]["kai"], self.world["players"]["sam"]
|
||||
self.fires = self.world["city"]["fires"]
|
||||
|
||||
def tend(self, player, fire, log, at, seconds):
|
||||
self.assertIsNone(game.start_action(self.world, player, f"tend_{fire}_{log}", at))
|
||||
return game.process_player(self.world, player, at + seconds, random.Random(1))
|
||||
|
||||
def test_tending_feeds_only_that_fire_and_pays_by_the_minute(self):
|
||||
self.kai["bank"] = {"logs": 3}
|
||||
self.tend(self.kai, "forge", "logs", T0, 95)
|
||||
level = game.skill_level(self.kai, "firekeeping")
|
||||
self.assertEqual(self.kai["bank"].get("logs", 0), 0)
|
||||
self.assertEqual(game.heat(self.world, "forge"), 0)
|
||||
self.assertEqual(game.heat(self.world, "kitchen"), -1)
|
||||
self.assertAlmostEqual(self.kai["xp"]["firekeeping"], 3 * game.TEND_XP[0] * game.fire_minutes(level))
|
||||
|
||||
def test_better_logs_need_the_level(self):
|
||||
self.kai["bank"] = {"maple_logs": 3}
|
||||
self.assertEqual(game.start_action(self.world, self.kai, "tend_forge_maple_logs", T0), "Needs level 45")
|
||||
|
||||
def test_a_full_fire_stops_tending_and_pays_nothing(self):
|
||||
self.kai["bank"] = {"logs": 100}
|
||||
summary = self.tend(self.kai, "forge", "logs", T0, 3000)
|
||||
self.assertEqual(summary["stopped"], "The forge is full")
|
||||
left = sum(chunk["left"] for chunk in self.fires["forge"]["fuel"])
|
||||
self.assertGreater(left + game.fire_minutes(1) * 60, game.fire_bank(1) * 60) # no room for another log
|
||||
xp = self.kai["xp"]["firekeeping"]
|
||||
self.assertEqual(game.start_action(self.world, self.kai, "tend_forge_logs", T0 + 3000), "The forge is full")
|
||||
self.assertEqual(self.kai["xp"]["firekeeping"], xp)
|
||||
|
||||
def test_a_better_log_pushes_cheaper_fuel_out_but_not_the_reverse(self):
|
||||
bank = game.fire_bank(15) * 60
|
||||
self.fires["kiln"].update(fuel=[{"tier": 0, "left": bank, "by": "sam"}], at=T0) # full of plain logs
|
||||
self.kai["xp"]["firekeeping"] = game.XP_TABLE[15]
|
||||
self.kai["bank"] = {"oak_logs": 1, "logs": 1}
|
||||
self.assertEqual(game.start_action(self.world, self.kai, "tend_kiln_logs", T0), "The kiln is full")
|
||||
self.assertIsNone(game.start_action(self.world, self.kai, "tend_kiln_oak_logs", T0)) # a better log still fits
|
||||
game.feed_fire(self.world, self.kai, "kiln", 1)
|
||||
self.assertEqual(game.heat(self.world, "kiln"), 1)
|
||||
self.assertAlmostEqual(sum(chunk["left"] for chunk in self.fires["kiln"]["fuel"]), bank)
|
||||
self.assertEqual(game.start_action(self.world, self.kai, "tend_kiln_logs", T0), "The kiln is full")
|
||||
|
||||
def test_fuel_burns_hottest_first_on_game_time(self):
|
||||
fire = self.fires["still"]
|
||||
fire["fuel"] = [{"tier": 0, "left": 600, "by": "sam"}, {"tier": 2, "left": 300, "by": "kai"}]
|
||||
fire["at"] = T0
|
||||
game.burn_fires(self.world, T0 + 200)
|
||||
self.assertEqual(game.heat(self.world, "still"), 2)
|
||||
game.burn_fires(self.world, T0 + 400)
|
||||
self.assertEqual(game.heat(self.world, "still"), 0)
|
||||
self.assertAlmostEqual(fire["fuel"][0]["left"], 500)
|
||||
game.burn_fires(self.world, T0 + 100) # never backwards
|
||||
self.assertEqual(fire["at"], T0 + 400)
|
||||
|
||||
def test_a_hot_forge_pays_the_log_and_a_coal_but_never_the_last(self):
|
||||
steel, copper = game.ACTION_BY_ID["smith_steel_bar"], game.ACTION_BY_ID["smith_copper_bar"]
|
||||
self.assertEqual(game.fire_inputs(self.world, steel), {"iron_ore": 1, "coal": 2, "willow_logs": 1})
|
||||
self.fires["forge"]["fuel"] = [{"tier": 1, "left": 600, "by": "kai"}]
|
||||
self.assertEqual(game.fire_inputs(self.world, steel), {"iron_ore": 1, "coal": 2, "willow_logs": 1}) # too cool
|
||||
self.assertEqual(game.fire_inputs(self.world, copper), {"copper_ore": 1})
|
||||
self.fires["forge"]["fuel"] = [{"tier": 3, "left": 600, "by": "kai"}]
|
||||
self.assertEqual(game.fire_inputs(self.world, steel), {"iron_ore": 1, "coal": 1})
|
||||
self.assertEqual(game.fire_inputs(self.world, game.ACTION_BY_ID["smith_mithril_bar"]), {"mithril_ore": 1, "coal": 2})
|
||||
|
||||
def test_a_potion_brewed_from_logs_keeps_its_ingredient_log(self):
|
||||
brew = game.ACTION_BY_ID["brew_woodcutting_potion_1"]
|
||||
self.fires["still"]["fuel"] = [{"tier": 0, "left": 600, "by": "kai"}]
|
||||
self.assertEqual(game.fire_inputs(self.world, brew), {"guam_leaf": 1, "logs": 1})
|
||||
|
||||
def test_warmth_goes_to_whoever_fed_the_fire(self):
|
||||
self.fires["kitchen"]["fuel"] = [{"tier": 0, "left": 6000, "by": "kai"}]
|
||||
self.fires["kitchen"]["at"] = T0
|
||||
self.sam["bank"] = {"raw_shrimp": 4}
|
||||
game.start_action(self.world, self.sam, "cook_shrimp", T0)
|
||||
game.process_player(self.world, self.sam, T0 + 85, random.Random(1))
|
||||
self.assertEqual(self.sam["bank"]["cooked_shrimp"], 4)
|
||||
self.assertNotIn("logs", self.sam["bank"])
|
||||
self.assertAlmostEqual(self.kai["xp"]["firekeeping"], 4 * 6 * game.WARMTH)
|
||||
self.assertAlmostEqual(self.kai["away"]["xp"]["firekeeping"], 4 * 6 * game.WARMTH)
|
||||
self.assertEqual(self.fires["kitchen"]["saved"], 4)
|
||||
self.assertEqual(self.sam["xp"]["firekeeping"], 0)
|
||||
|
||||
def test_catch_up_runs_everyone_and_keeps_what_they_missed(self):
|
||||
game.start_action(self.world, self.sam, "mine_stone", T0)
|
||||
self.assertTrue(game.catch_up(self.world, T0 + 100, random.Random(1)))
|
||||
game.catch_up(self.world, T0 + 200, random.Random(1))
|
||||
self.assertEqual(self.sam["away"]["done"], 10)
|
||||
summary = game.take_summary(self.sam, game.process_player(self.world, self.sam, T0 + 220, random.Random(1)))
|
||||
self.assertEqual(summary["done"], 11)
|
||||
self.assertEqual(summary["items"], {"stone": 11})
|
||||
self.assertNotIn("away", self.sam)
|
||||
|
||||
def test_old_worlds_get_their_fires(self):
|
||||
del self.world["city"]["fires"]
|
||||
del self.kai["xp"]["firekeeping"]
|
||||
self.world["version"] = 23
|
||||
game.migrate(self.world, T0)
|
||||
self.assertEqual(set(self.world["city"]["fires"]), set(game.FIRES))
|
||||
self.assertEqual(self.kai["xp"]["firekeeping"], 0)
|
||||
self.assertIn("tool_firekeeping", self.kai["equip"])
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue