Mod: mining rig, graphics cards, trading terminal, nightly settlement

First playable slice, tested in game on the test save:
- Network upgrade "Mining Access" (300) delivers a trading terminal, a
  mining rig and an RZX 50.
- The rig is a machine with a battery slot and four card slots; each night
  it draws its total power from the battery and its cards mine PSCoin.
  Cards show hashrate, power draw and condition, wear every night and can
  burn out. All state lives on item tags or in the mod save data.
- Trading terminal with wallet, trade (four pairs, deposit credits as CRC,
  withdraw CRC through the compliance desk) and report pages.
- Nightly log lines; exchange opening and halving news on the paper.
- English and Chinese text; sprites generated by art/sprites.py.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
ZHU MINCHAOandClaude Opus 5.5 committed 2026-11-03 09:11:46 +08:00
1 parent efc58888f3
commit 750b26e4b3
21 files changed
+1040

No files matched your search

@@ -276,7 +276,43 @@ internal static class Program
Check(Near(dr.Received, 900 * (1 - Tuning.ExchangeFee), 1e-6), "CRC 脱锚时按市价兑出");
});
Test("存档:市场、稳定币、全网、钱包、交易所、随机数序列化后读回,之后的结果一致", () =>
{
var m = Market.CreateDefault(3);
var st = new Stablecoins();
var net = new Network();
var w = new Wallet { Address = "hot", Taint = 12, Basis = 34 };
w.Add(Assets.PSC, 5);
var ex = new Exchange();
ex.History.Add(new KeyValuePair<int, double>(2, 100));
var rng = new Rng(77);
for (int d = 1; d <= 5; d++) { m.Night(new MarketEvent[0], rng, d, a => 1); st.Night(d, rng, 0); net.Night(d, m.Price, 10); }
var bundle = new SaveBundle { Market = m, Stable = st, Network = net, Hot = w, Exchange = ex, Rng = rng };
string json = Newtonsoft.Json.JsonConvert.SerializeObject(bundle);
var back = Newtonsoft.Json.JsonConvert.DeserializeObject<SaveBundle>(json);
Check(Near(back.Market.Price, m.Price, 1e-9) && back.Market.Pools.Count == m.Pools.Count && back.Market.Pools[1].Id == m.Pools[1].Id, "交易对与价格");
Check(back.Hot.Get(Assets.PSC) == 5 && back.Hot.Taint == 12 && back.Hot.Basis == 34, "钱包余额、污点、成本");
Check(back.Exchange.History.Count == 1 && back.Exchange.History[0].Value == 100, "出金记录");
Check(Near(back.Network.NpcHash, net.NpcHash, 1e-9) && Near(back.Stable.CraSubsidy, st.CraSubsidy, 1e-9), "全网算力、CRA 补贴池");
for (int d = 6; d <= 10; d++)
{
m.Night(new MarketEvent[0], rng, d, a => 1);
back.Market.Night(new MarketEvent[0], back.Rng, d, a => 1);
}
Check(Near(back.Market.Price, m.Price, 1e-9), "读回后继续推进,行情与原来完全相同");
});
Console.WriteLine($"\n{_passed} 通过,{_failed} 失败");
return _failed == 0 ? 0 : 1;
}
}
internal sealed class SaveBundle
{
public Market Market;
public Stablecoins Stable;
public Network Network;
public Wallet Hot;
public Exchange Exchange;
public Rng Rng;
}