summaryrefslogtreecommitdiff
path: root/src/LivingVillage.Kernel/Occupation.fs
diff options
context:
space:
mode:
Diffstat (limited to 'src/LivingVillage.Kernel/Occupation.fs')
-rw-r--r--src/LivingVillage.Kernel/Occupation.fs53
1 files changed, 53 insertions, 0 deletions
diff --git a/src/LivingVillage.Kernel/Occupation.fs b/src/LivingVillage.Kernel/Occupation.fs
new file mode 100644
index 0000000..28008f5
--- /dev/null
+++ b/src/LivingVillage.Kernel/Occupation.fs
@@ -0,0 +1,53 @@
+namespace LivingVillage.Kernel
+
+/// Occupation system first slice (design §1/§2, docs/design/occupation-system-design.md).
+/// Data lives beside the player only — NPCs are never occupied.
+/// Nothing here runs inside Sim.step; WorldBootstrap stamps the profile onto the
+/// world's avatar at creation time, which keeps the numeric state path untouched.
+module Occupation =
+
+ type Kind =
+ | Farmer
+ | Fisher
+ | Peddler
+ | Scholar
+
+ /// Chinese labels, shared for a later UI slice (农夫 / 渔夫 / 货郎 / 书生).
+ let nameOf (kind: Kind) : string =
+ match kind with
+ | Farmer -> "农夫"
+ | Fisher -> "渔夫"
+ | Peddler -> "货郎"
+ | Scholar -> "书生"
+
+ let saveToken (kind: Kind) : string =
+ match kind with
+ | Farmer -> "farmer"
+ | Fisher -> "fisher"
+ | Peddler -> "peddler"
+ | Scholar -> "scholar"
+
+ let all : Kind list = [ Farmer; Fisher; Peddler; Scholar ]
+
+ type Profile =
+ { Kind: Kind
+ InitialMoney: int
+ InitialEnergy: float32
+ InitialInventory: (Sim.ItemKind * int) list }
+
+ /// Initial values straight from the approved design §1 table.
+ let profileOf (kind: Kind) : Profile =
+ match kind with
+ | Farmer -> { Kind = Farmer; InitialMoney = 60; InitialEnergy = 100.0f; InitialInventory = [ Sim.Food, 12 ] }
+ | Fisher -> { Kind = Fisher; InitialMoney = 45; InitialEnergy = 95.0f; InitialInventory = [ Sim.Food, 8; Sim.Fish, 3 ] }
+ | Peddler -> { Kind = Peddler; InitialMoney = 90; InitialEnergy = 100.0f; InitialInventory = [ Sim.Food, 6; Sim.Spice, 4 ] }
+ | Scholar -> { Kind = Scholar; InitialMoney = 70; InitialEnergy = 100.0f; InitialInventory = [ Sim.Food, 10; Sim.Scroll, 2 ] }
+
+ /// Placeholder carried in save v3 until the task-system slice lands (design §3).
+ type State =
+ { Profile: Profile
+ TaskToken: int
+ StoryStage: int }
+
+ let stateOf (kind: Kind) : State =
+ { Profile = profileOf kind; TaskToken = 0; StoryStage = 0 }