refactor(packages): 0.R5 - the shop's week is rolled by its tick and asking reads it; needs start filled and vehicles start with their list; character, physics, vehicles and nativeecho's lazy starts are defaults; --tighten over all four

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
Orkun ÇAKILKAYA 2026-09-27 13:25:57 +03:00
parent 67d8079c47
commit 87259f989d
31 changed files with 104 additions and 111 deletions

View file

@ -1,13 +1,13 @@
# queries.ludic - what the world asks the body
export function needs_level(needs_st: mut NeedsState, k: int) -> float {
export function needs_level(needs_st: NeedsState, k: int) -> float {
if not nd_ok(k) { return 0.0 }
return nd_lv(needs_st)[k]
}
export function needs_warmth(needs_st: mut NeedsState) -> float { return nd_lv(needs_st)[NEED_WARMTH] }
export function needs_food(needs_st: mut NeedsState) -> float { return nd_lv(needs_st)[NEED_FOOD] }
export function needs_water(needs_st: mut NeedsState) -> float { return nd_lv(needs_st)[NEED_WATER] }
export function needs_energy(needs_st: mut NeedsState) -> float { return nd_lv(needs_st)[NEED_ENERGY] }
export function needs_warmth(needs_st: NeedsState) -> float { return nd_lv(needs_st)[NEED_WARMTH] }
export function needs_food(needs_st: NeedsState) -> float { return nd_lv(needs_st)[NEED_FOOD] }
export function needs_water(needs_st: NeedsState) -> float { return nd_lv(needs_st)[NEED_WATER] }
export function needs_energy(needs_st: NeedsState) -> float { return nd_lv(needs_st)[NEED_ENERGY] }
# seconds left before a collapse (0: no countdown), and the need it is for
export function needs_last_legs(needs_st: NeedsState) -> float { return needs_st.nd_legs }
@ -15,7 +15,7 @@ export function needs_last_need(needs_st: NeedsState) -> int { return needs_st.n
export function needs_collapses(needs_st: NeedsState) -> int { return needs_st.nd_collapses }
# the walk's pace, times: the ramp of each need, and 0.6 more on last legs
export function needs_pace(needs_st: mut NeedsState) -> float {
export function needs_pace(needs_st: NeedsState) -> float {
let lv = nd_lv(needs_st)
var m = nd_pace(lv[NEED_WARMTH]) * nd_pace(lv[NEED_FOOD])
if NeedsWorld.thirst() { m = m * nd_pace(lv[NEED_WATER]) }
@ -24,13 +24,13 @@ export function needs_pace(needs_st: mut NeedsState) -> float {
}
# running needs legs, calories and a body that is not already in trouble
export function needs_can_run(needs_st: mut NeedsState) -> bool {
export function needs_can_run(needs_st: NeedsState) -> bool {
let lv = nd_lv(needs_st)
return lv[NEED_ENERGY] > 8.0 and lv[NEED_FOOD] > 20.0 and lv[NEED_WARMTH] > 20.0 and lv[NEED_WATER] > 20.0
}
# the lowest of the four
export function needs_lowest(needs_st: mut NeedsState) -> float {
export function needs_lowest(needs_st: NeedsState) -> float {
let lv = nd_lv(needs_st)
return Math.min(Math.min(lv[NEED_WARMTH], lv[NEED_FOOD]), Math.min(lv[NEED_WATER], lv[NEED_ENERGY]))
}

View file

@ -1,10 +1,10 @@
# run.ludic - `gh` game hours of whatever the body is doing, taken out of the four bars
function nd_add(needs_st: mut NeedsState, k: int, d: float) -> void {
function nd_add(needs_st: NeedsState, k: int, d: float) -> void {
let lv = nd_lv(needs_st)
lv[k] = Math.clamp(lv[k] + d, 0.0, 100.0)
}
export function needs_run(needs_st: mut NeedsState, gh: float) -> void {
export function needs_run(needs_st: NeedsState, gh: float) -> void {
let a = NeedsWorld.activity()
nd_add(needs_st, NEED_FOOD, (NeedsWorld.bonus(NEED_FOOD) - nd_food_rate(a) * NeedsWorld.drain(NEED_FOOD)) * gh)
if NeedsWorld.thirst() {

View file

@ -51,21 +51,24 @@ export property NeedFact {
need: int = 0
}
# where a body starts: warm, fed well enough, watered, rested
function nd_start() -> []float {
let l = floats(NEED_COUNT)
l[NEED_WARMTH] = 100.0
l[NEED_FOOD] = 70.0
l[NEED_WATER] = 85.0
l[NEED_ENERGY] = 100.0
return l
}
export state NeedsState {
nd_level: []float = null
nd_level: []float = nd_start()
nd_legs: float = 0.0 # seconds left before a collapse, 0 = none
nd_last: int = 0 # the need the countdown is for
nd_collapses: int = 0
nd_facts: Queue<NeedFact> = nd_facts__new()
}
function nd_lv(needs_st: mut NeedsState) -> []float {
if needs_st.nd_level == null {
needs_st.nd_level = floats(NEED_COUNT)
nd_fill(needs_st)
}
return needs_st.nd_level
}
function nd_lv(needs_st: NeedsState) -> []float { return needs_st.nd_level }
function nd_fill(needs_st: mut NeedsState) -> void {
needs_st.nd_level[NEED_WARMTH] = 100.0

View file

@ -5,7 +5,7 @@ function needs_tick(needs_st: mut NeedsState, t: Tick) -> void {
needs_watch(needs_st, t.dt)
}
export function needs_save(needs_st: mut NeedsState) -> Val {
export function needs_save(needs_st: NeedsState) -> Val {
let v = Value.object()
sv_put_float(v, "warmth", needs_warmth(needs_st))
sv_put_float(v, "food", needs_food(needs_st))

View file

@ -45,7 +45,7 @@ program NeedsTest {
}
function fresh(needs_st: mut NeedsState) -> void { needs_reset(needs_st) }
function hours(needs_st: mut NeedsState, h: float) -> void { for i in 0 .. int(h * 10.0) { needs_run(needs_st, 0.1) } }
function hours(needs_st: NeedsState, h: float) -> void { for i in 0 .. int(h * 10.0) { needs_run(needs_st, 0.1) } }
function facts(needs_st: NeedsState) -> []NeedFact { return q_drain(needs_facts(needs_st)) }
test "a new body is warm, rested, fed and watered" (needs_st: mut NeedsState) {

View file

@ -1,27 +1,27 @@
# verbs.ludic - the only way the needs change from outside; each is held to 0..100
# `n` more of a need (less, when negative): a meal, a drink, a shove from a bear
export function needs_feed(needs_st: mut NeedsState, k: int, n: float) -> void {
export function needs_feed(needs_st: NeedsState, k: int, n: float) -> void {
if nd_ok(k) { nd_add(needs_st, k, n) }
}
# a meal: food, water and energy at once
export function needs_meal(needs_st: mut NeedsState, food: float, water: float, energy: float) -> void {
export function needs_meal(needs_st: NeedsState, food: float, water: float, energy: float) -> void {
nd_add(needs_st, NEED_FOOD, food)
nd_add(needs_st, NEED_WATER, water)
nd_add(needs_st, NEED_ENERGY, energy)
}
export function needs_set(needs_st: mut NeedsState, k: int, v: float) -> void {
export function needs_set(needs_st: NeedsState, k: int, v: float) -> void {
if nd_ok(k) { nd_lv(needs_st)[k] = Math.clamp(v, 0.0, 100.0) }
}
# at least `v`
export function needs_floor(needs_st: mut NeedsState, k: int, v: float) -> void {
export function needs_floor(needs_st: NeedsState, k: int, v: float) -> void {
if nd_ok(k) and nd_lv(needs_st)[k] < v { needs_set(needs_st, k, v) }
}
# a night: rested to what it was worth, hungrier and thirstier for it, but never empty
export function needs_after_night(needs_st: mut NeedsState, rested: float, food_lost: float, water_lost: float) -> void {
export function needs_after_night(needs_st: NeedsState, rested: float, food_lost: float, water_lost: float) -> void {
let lv = nd_lv(needs_st)
lv[NEED_ENERGY] = Math.clamp(rested, 0.0, 100.0)
lv[NEED_FOOD] = Math.max(lv[NEED_FOOD] - food_lost, 6.0)

View file

@ -3,7 +3,7 @@
const LAST_LEGS: float = 10.0
const GENTLE_FLOOR: float = 22.0
function nd_empty(needs_st: mut NeedsState) -> int {
function nd_empty(needs_st: NeedsState) -> int {
let lv = nd_lv(needs_st)
if lv[NEED_WARMTH] == 0.0 { return NEED_WARMTH }
if lv[NEED_FOOD] == 0.0 { return NEED_FOOD }
@ -11,7 +11,7 @@ function nd_empty(needs_st: mut NeedsState) -> int {
return -1
}
function nd_clear(needs_st: mut NeedsState) -> bool {
function nd_clear(needs_st: NeedsState) -> bool {
let lv = nd_lv(needs_st)
return lv[NEED_WARMTH] > 5.0 and lv[NEED_FOOD] > 5.0 and lv[NEED_WATER] > 5.0
}