Black market in Web3 page, shelf UI, no dead drop, tech and GPU goods; rules moved to Web3 handbook
Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
This commit is contained in:
1 parent
6bc479f710
commit
e44a4439ed
12 files changed
+296
-245
No files matched your search
@@ -4,18 +4,29 @@ using System.Linq;
|
||||
|
||||
namespace Decentralized.Domain
|
||||
{
|
||||
/// <summary>黑市现货柜台上的一件货:游戏物品 id、剩余件数、含溢价的单价(信用点)。</summary>
|
||||
public sealed class BmOffer
|
||||
/// <summary>货的种类:违禁品、高科技物品、显卡。</summary>
|
||||
public enum GoodKind { Contraband, Tech, Gpu }
|
||||
|
||||
/// <summary>黑市货架上的一种货。显卡的 Item 是 "gpu:型号",Model 是标称型号,FakeOf 非空表示背后是别的芯片(买家看不到)。</summary>
|
||||
public class BmGood
|
||||
{
|
||||
public string Item;
|
||||
public int Qty;
|
||||
public int Price;
|
||||
public GoodKind Kind;
|
||||
public int Level;
|
||||
public int Price;
|
||||
public string Model, FakeOf;
|
||||
public double Health;
|
||||
}
|
||||
|
||||
/// <summary>现货柜台上的一件货:剩余件数、含溢价的单价(信用点)。</summary>
|
||||
public sealed class BmOffer : BmGood
|
||||
{
|
||||
public int Qty;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Web3 黑市:黑市派系在链上的实体。现货柜台每周刷新一批违禁品(档次随黑市声望放开),只收币,脏币也收,
|
||||
/// 付出去的币连同按比例的污点一起留在卖家那边;Ponero 兑换处把任意币兑成无法追踪的 Ponero(污点留在原地),有每日额度和手续费。
|
||||
/// Web3 黑市:黑市派系在链上的实体。货架上主要是违禁品(档次随黑市声望放开),偶尔有高科技物品和显卡(加价),
|
||||
/// 现货只收币,脏币也收,付出去的币连同按比例的污点一起留在卖家那边;Ponero 兑换处把任意币兑成无法追踪的 Ponero(这部分价值的污点被清除),有每日额度和手续费。
|
||||
/// 镇压期间整个平台下线。
|
||||
/// </summary>
|
||||
public sealed partial class BlackMarket
|
||||
@@ -26,7 +37,7 @@ namespace Decentralized.Domain
|
||||
public double DeskToday;
|
||||
public int DeskDay = -1;
|
||||
|
||||
/// <summary>现货池:游戏物品 id 与违禁等级(1 低、2 中、3 高)。全部来自游戏已有的违禁品。</summary>
|
||||
/// <summary>违禁品池:游戏物品 id 与违禁等级(1 低、2 中、3 高)。全部来自游戏已有的违禁品。</summary>
|
||||
public static readonly KeyValuePair<string, int>[] Pool =
|
||||
{
|
||||
P("small_pistol_ammo", 1), P("heavy_pistol_ammo", 1), P("handmade_pistol", 1), P("printed_gun", 1), P("stun_baton", 1),
|
||||
@@ -38,6 +49,13 @@ namespace Decentralized.Domain
|
||||
P("shotgun", 3), P("smg", 3), P("c4", 3), P("fanta_pill", 3), P("nightmare_dust", 3), P("cmd_keycard", 3), P("crypto_module_sec", 3),
|
||||
};
|
||||
|
||||
/// <summary>高科技物品池(不是违禁品,黑市上要加价)。</summary>
|
||||
public static readonly string[] TechPool =
|
||||
{
|
||||
"hand", "aug_chip", "energy_credit_hyp", "energy_credit_breeder", "makeshift_reactor", "mirage_projector", "printer",
|
||||
"system_module_overclock", "system_module_performance", "system_module_quality", "module_extractor_advanced", "powerblock",
|
||||
};
|
||||
|
||||
private static KeyValuePair<string, int> P(string id, int level) => new KeyValuePair<string, int>(id, level);
|
||||
|
||||
public static bool Open(int rep) => rep >= Tuning.BmOpenRep;
|
||||
@@ -45,26 +63,55 @@ namespace Decentralized.Domain
|
||||
public static bool DeskOpen(int rep) => rep >= Tuning.PoneroOpenRep;
|
||||
public static int StockCount(int rep) => Tuning.BmStockBase + (int)Math.Max(0, rep / Tuning.BmStockPerRep);
|
||||
|
||||
/// <summary>溢价后的单价(信用点)。</summary>
|
||||
public static int PriceOf(long baseValue) => (int)Math.Max(1, Math.Round(baseValue * (1 + Tuning.BmPremium)));
|
||||
/// <summary>货的加价:违禁品 0,高科技、显卡各有额外加价(在现货溢价 / 订单折扣之外)。</summary>
|
||||
public static double Extra(GoodKind k) => k == GoodKind.Tech ? Tuning.BmTechMarkup : k == GoodKind.Gpu ? Tuning.BmGpuMarkup : 0;
|
||||
|
||||
/// <summary>每周刷新一次(或首次开放时):按声望开放的档次抽 StockCount 种货,每种 1–3 件。value 给出物品的游戏基础价。</summary>
|
||||
/// <summary>现货单价(信用点):基础价 ×(1 + 溢价 + 货的加价)。</summary>
|
||||
public static int PriceOf(long baseValue, GoodKind k = GoodKind.Contraband) => (int)Math.Max(1, Math.Round(baseValue * (1 + Tuning.BmPremium + Extra(k))));
|
||||
|
||||
/// <summary>抽 count 种货:高科技(中档声望起)和显卡按概率换掉违禁品。value 给出游戏物品的基础价;显卡的基础价按标称型号与成色算。</summary>
|
||||
private List<BmGood> Roll(int count, int day, int rep, Rng rng, Func<string, long> value, Func<long, GoodKind, int> price)
|
||||
{
|
||||
var goods = new List<BmGood>();
|
||||
var pool = Pool.Where(x => x.Value <= MaxLevel(rep)).ToList();
|
||||
var tech = TechPool.ToList();
|
||||
var gpus = UsedDealers.Pool(day);
|
||||
for (int i = 0; i < count; i++)
|
||||
{
|
||||
double r = rng.NextDouble();
|
||||
if (r < Tuning.BmGpuChance)
|
||||
{
|
||||
var c = UsedDealers.Card(gpus, Tuning.BmGpuFake, 0, rng);
|
||||
goods.Add(new BmGood { Item = "gpu:" + c.Model, Kind = GoodKind.Gpu, Level = 2, Model = c.Model, FakeOf = c.FakeOf, Health = c.Health, Price = price(CardValue.Of(c.Model, c.Health), GoodKind.Gpu) });
|
||||
}
|
||||
else if (r < Tuning.BmGpuChance + Tuning.BmTechChance && rep >= Tuning.BmMidRep && tech.Count > 0)
|
||||
{
|
||||
int k = rng.Range(0, tech.Count - 1);
|
||||
string id = tech[k];
|
||||
tech.RemoveAt(k);
|
||||
long v = value(id);
|
||||
if (v > 0) goods.Add(new BmGood { Item = id, Kind = GoodKind.Tech, Level = 3, Price = price(v, GoodKind.Tech) });
|
||||
}
|
||||
else if (pool.Count > 0)
|
||||
{
|
||||
int k = rng.Range(0, pool.Count - 1);
|
||||
var pick = pool[k];
|
||||
pool.RemoveAt(k);
|
||||
long v = value(pick.Key);
|
||||
if (v > 0) goods.Add(new BmGood { Item = pick.Key, Kind = GoodKind.Contraband, Level = pick.Value, Price = price(v, GoodKind.Contraband) });
|
||||
}
|
||||
}
|
||||
return goods;
|
||||
}
|
||||
|
||||
/// <summary>每周刷新一次(或首次开放时):按声望开放的档次抽 StockCount 种货,每种 1–3 件(高档与显卡、高科技 1 件)。</summary>
|
||||
public bool Refresh(int day, int rep, Rng rng, Func<string, long> value)
|
||||
{
|
||||
if (!Open(rep) || day - RefreshedDay < Tuning.BmRefreshDays) return false;
|
||||
RefreshedDay = day;
|
||||
Offers.Clear();
|
||||
var pool = Pool.Where(x => x.Value <= MaxLevel(rep)).ToList();
|
||||
int n = Math.Min(StockCount(rep), pool.Count);
|
||||
for (int i = 0; i < n; i++)
|
||||
{
|
||||
int k = rng.Range(0, pool.Count - 1);
|
||||
var pick = pool[k];
|
||||
pool.RemoveAt(k);
|
||||
long v = value(pick.Key);
|
||||
if (v <= 0) continue;
|
||||
Offers.Add(new BmOffer { Item = pick.Key, Level = pick.Value, Qty = pick.Value == 3 ? 1 : rng.Range(1, 3), Price = PriceOf(v) });
|
||||
}
|
||||
foreach (var g in Roll(StockCount(rep), day, rep, rng, value, PriceOf))
|
||||
Offers.Add(new BmOffer { Item = g.Item, Kind = g.Kind, Level = g.Level, Price = g.Price, Model = g.Model, FakeOf = g.FakeOf, Health = g.Health, Qty = g.Kind != GoodKind.Contraband || g.Level == 3 ? 1 : rng.Range(1, 3) });
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -91,7 +138,7 @@ namespace Decentralized.Domain
|
||||
|
||||
public double DeskLeft(int day) => Math.Max(0, Tuning.PoneroDailyCap - (DeskDay == day ? DeskToday : 0));
|
||||
|
||||
/// <summary>兑入 Ponero:from 币 amount 个,扣手续费后按 Ponero 价到账;这部分价值带的污点留在原地(不跟着 Ponero)。返回到账数量,额度或余额不足返回 -1。</summary>
|
||||
/// <summary>兑入 Ponero:from 币 amount 个,扣手续费后按 Ponero 价到账;这部分价值带的污点被清除(不跟着 Ponero)。返回到账数量,额度或余额不足返回 -1。</summary>
|
||||
public double ToPonero(Wallet w, string from, double amount, int day, Func<string, double> price)
|
||||
{
|
||||
double value = amount * price(from);
|
||||
|
||||
Reference in new issue
Block a user