Soul layer: imprints, warmth echoes, and consequences
Ports the Unity POC soul systems into the sim: - Warmth echoes: villagers remember who fed them (+0.15) and who turned them away (-0.25). Ask-for-food targeting runs on memory, not omniscience; the remembered-cold are not asked. Echoes fade daily. - Refusing the hungry while holding food marks the refuser (others-regard debris) and is logged; empty-handed is not refusal. - Harvesting below the 50% commons line marks the taker per unit taken. - Soul-to-soul atmospheric pressure (SoulFieldSystem port): encased souls darken nearby atmospheres, clear souls lighten them. - Debris costs biologically: nourishment drains faster and meals restore less as the soul encases. - Instrumentation: avg_debris + refusals in daily stats; per-villager nourish/health/debris; refusals in the contact log; map dots dim with encasement. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
+24
-4
@@ -20,10 +20,12 @@ public static class StatsLogger
|
||||
"harvested,trades," +
|
||||
"avg_fatigue,avg_nourish,avg_health,carried," +
|
||||
"gather_ticks,build_ticks,trade_ticks,rest_ticks,social_ticks," +
|
||||
"shelters_done,ruins,avg_cond,upkeep_stock,burn_per_day,modules,granary_food";
|
||||
"shelters_done,ruins,avg_cond,upkeep_stock,burn_per_day,modules,granary_food," +
|
||||
"avg_debris,refusals";
|
||||
|
||||
private const string NpcHeader =
|
||||
"day,npc,name,soul,dominant,gather_ticks,build_ticks,trade_ticks,rest_ticks,social_ticks";
|
||||
"day,npc,name,soul,dominant,gather_ticks,build_ticks,trade_ticks,rest_ticks,social_ticks," +
|
||||
"nourish,health,debris";
|
||||
|
||||
private const string GiftHeader =
|
||||
"day,giver,giver_soul,receiver,receiver_soul,material,amount";
|
||||
@@ -52,6 +54,15 @@ public static class StatsLogger
|
||||
$"{material},{amount.ToString("0.0", CultureInfo.InvariantCulture)}\n");
|
||||
}
|
||||
|
||||
/// <summary>Every refusal too — the gift log is really a contact log.</summary>
|
||||
public static void LogRefusal(Npc giver, Npc asker)
|
||||
{
|
||||
if (string.IsNullOrEmpty(_giftPath)) return;
|
||||
int day = GameManager.Instance?.Day ?? -1;
|
||||
File.AppendAllText(_giftPath,
|
||||
$"{day},{giver.Name},{giver.Soul.Type},{asker.Name},{asker.Soul.Type},Refusal,0.0\n");
|
||||
}
|
||||
|
||||
public static void LogDay(GameManager gm)
|
||||
{
|
||||
var ci = CultureInfo.InvariantCulture;
|
||||
@@ -123,7 +134,12 @@ public static class StatsLogger
|
||||
row.Append(stock.ToString("0.0", ci)).Append(',');
|
||||
row.Append(burn.ToString("0.0", ci)).Append(',');
|
||||
row.Append(modules).Append(',');
|
||||
row.Append(granaryFood.ToString("0.0", ci));
|
||||
row.Append(granaryFood.ToString("0.0", ci)).Append(',');
|
||||
|
||||
float debrisSum = 0f;
|
||||
foreach (var npc in gm.Npcs) debrisSum += npc.Imprint.Total;
|
||||
row.Append((debrisSum / count).ToString("0.0000", ci)).Append(',');
|
||||
row.Append(TradeSystem.RefusalsToday);
|
||||
|
||||
File.AppendAllText(_path, row + "\n");
|
||||
|
||||
@@ -143,7 +159,10 @@ public static class StatsLogger
|
||||
.Append(t[(int)NpcState.Building]).Append(',')
|
||||
.Append(t[(int)NpcState.Trading]).Append(',')
|
||||
.Append(t[(int)NpcState.Resting]).Append(',')
|
||||
.Append(t[(int)NpcState.Socializing]).Append('\n');
|
||||
.Append(t[(int)NpcState.Socializing]).Append(',')
|
||||
.Append(npc.Nourishment.ToString("0.000", ci)).Append(',')
|
||||
.Append(npc.Health.ToString("0.0", ci)).Append(',')
|
||||
.Append(npc.Imprint.Total.ToString("0.0000", ci)).Append('\n');
|
||||
System.Array.Clear(npc.StateTicksToday, 0, npc.StateTicksToday.Length);
|
||||
}
|
||||
File.AppendAllText(_npcPath, npcRows.ToString());
|
||||
@@ -151,5 +170,6 @@ public static class StatsLogger
|
||||
// Reset per-day counters
|
||||
gm.World.HarvestedToday = 0f;
|
||||
TradeSystem.TradesToday = 0;
|
||||
TradeSystem.RefusalsToday = 0;
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user