koishi-plugin-xxck-1 0.3.5 → 0.3.7

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/lib/index.d.ts CHANGED
@@ -11,6 +11,7 @@ export interface PluginConfig {
11
11
  eventExchangePrice7: number;
12
12
  collectionPart1Pattern: string;
13
13
  collectionPart2Pattern: string;
14
+ disturbExchangePrice: number;
14
15
  normalStar7Threshold: number;
15
16
  normalStar6Threshold: number;
16
17
  normalStar6Prob: number;
@@ -27,6 +28,7 @@ export declare const Config: Schema<Schemastery.ObjectS<{
27
28
  eventExchangePrice7: Schema<number, number>;
28
29
  collectionPart1Pattern: Schema<string, string>;
29
30
  collectionPart2Pattern: Schema<string, string>;
31
+ disturbExchangePrice: Schema<number, number>;
30
32
  normalStar7Threshold: Schema<number, number>;
31
33
  normalStar6Threshold: Schema<number, number>;
32
34
  normalStar6Prob: Schema<number, number>;
@@ -42,6 +44,7 @@ export declare const Config: Schema<Schemastery.ObjectS<{
42
44
  eventExchangePrice7: Schema<number, number>;
43
45
  collectionPart1Pattern: Schema<string, string>;
44
46
  collectionPart2Pattern: Schema<string, string>;
47
+ disturbExchangePrice: Schema<number, number>;
45
48
  normalStar7Threshold: Schema<number, number>;
46
49
  normalStar6Threshold: Schema<number, number>;
47
50
  normalStar6Prob: Schema<number, number>;
@@ -144,6 +147,10 @@ declare module 'koishi' {
144
147
  got6: boolean;
145
148
  got7: boolean;
146
149
  };
150
+ gacha_user_disturb_draw: {
151
+ qq: string;
152
+ draw_count: number;
153
+ };
147
154
  gacha_battle_user: {
148
155
  qq: string;
149
156
  win: number;
package/lib/index.js CHANGED
@@ -40,7 +40,7 @@ var zh_CN_default = {
40
40
  "command.wwc.help.sign": "签到:每日领取抽数 | 指令:WWC签到 | 说明:每日1次,获得40抽",
41
41
  "command.wwc.help.draw": "抽卡:普通抽卡 | 指令:WWC抽卡 [次数] | 说明:1-20连,消耗普通抽数,默认1连",
42
42
  "command.wwc.help.warehouse": "仓库:查看已拥有卡片 | 指令:WWC仓库 | 说明:显示等级/星级/限定标记,按星级排序",
43
- "command.wwc.help.shop": "店铺:查看今日可升格卡片 | 指令:WWC店铺 | 说明:每日随机刷新3个7星卡,全服限购",
43
+ "command.wwc.help.shop": "店铺:查看今日可升格卡片 | 指令:WWC店铺 | 说明:每日随机刷新4个7星、6个6星、10个5星(均来自普通卡池),全服限购5次",
44
44
  "command.wwc.help.upgrade": "升格:兑换店铺卡片 | 指令:WWC升格 [卡片编号...] | 说明:消耗热带扰动,重复卡片自动升级",
45
45
  "command.wwc.help.exchange": "兑换:水汽换普通抽数 | 指令:WWC兑换 [次数] | 说明:100水汽=1抽,每日上限80抽,单次1-40",
46
46
  "command.wwc.help.collection": "收藏:查看卡片收藏进度 | 指令:WWC收藏(全部分类);WWC收藏1 / WWC收藏2 / WWC收藏3 为拆分版(分类正则可在插件配置项 collectionPart1Pattern / collectionPart2Pattern 中定义,收藏3 = 两者都不匹配的类别)| 说明:含普通+限定卡",
@@ -48,6 +48,8 @@ var zh_CN_default = {
48
48
  "command.wwc.help.eventStatus": "限时状态:查看开放的限时卡池 | 指令:WWC限时状态 | 说明:显示期数/名称/星级/开放时间",
49
49
  "command.wwc.help.eventDraw": "限时抽卡:参与限时卡池 | 指令:WWC限时抽卡 [期数] [次数] | 说明:1-20连,消耗限时抽数,无期限数匹配唯一开放池",
50
50
  "command.wwc.help.eventExchange": "限时兑换:水汽换限时抽数 | 指令:WWC限时兑换 [期数] [次数] | 说明:6星300水汽/抽,7星450水汽/抽,单次1-40",
51
+ "command.wwc.help.disturbDraw": "扰动抽卡:使用扰动抽数抽卡 | 指令:WWC扰动抽卡 [次数] | 说明:普通卡池5/6/7星,7星10%、6星36%、5星54%,单次1-20连",
52
+ "command.wwc.help.disturbExchange": "扰动兑换:热带扰动换扰动抽数 | 指令:WWC扰动兑换 [次数] | 说明:每抽消耗扰动由配置项决定(默认100),单次1-40",
51
53
  "command.wwc.help.tip": "💡 提示:所有指令前缀为「WWC」,区分大小写;抽卡/兑换次数超出限制会自动兜底为1次",
52
54
  // ==============================================
53
55
  // 2. 功能操作成功提示
@@ -64,6 +66,8 @@ var zh_CN_default = {
64
66
  "tip.switch.groupClose": "❌ 本群WWC抽卡功能已关闭!群成员无法使用任何指令",
65
67
  "tip.eventAdd.success": "✅ 限时卡池创建成功:{code} | 请检查时间戳是否正确",
66
68
  "tip.eventExchange.success": "✅ 限时兑换成功\n卡池:{code} | 数量:{count}抽 | 消耗:{cost}水汽",
69
+ "tip.disturbExchange.success": "✅ 扰动兑换成功\n数量:{count}抽 | 消耗:{cost}热带扰动 | 当前扰动抽数:{left}抽",
70
+ "tip.disturbDraw.title": "🎲 [{name}] 扰动抽卡完成(剩余扰动抽数:{left}抽)!获得以下卡片:",
67
71
  "tip.eventStatus.info": "📅 限时卡池【{code}】\n卡片:{cardName}({star}星)\n类型:{type}\n开放时间:{start} ~ {end}",
68
72
  "tip.upgrade.success": "✅ 升格成功!恭喜您获得了以下卡片:\n",
69
73
  "tip.upgrade.cost": "💸 消耗扰动:-{total_cost}",
@@ -76,6 +80,8 @@ var zh_CN_default = {
76
80
  "tip.draw.upgrade": "✅ 原有卡片升级成功\n",
77
81
  "tip.draw.vapor": "💧 水汽 +{vapor}\n",
78
82
  "tip.draw.disturb": "🌪️ 热带扰动 +{disturbanceTotal}",
83
+ "tip.draw.left": "🔢 剩余普通抽数:{left}抽",
84
+ "tip.eventDraw.left": "🔢 剩余{star}星限时抽数:{left}抽",
79
85
  "tip.eventDraw.pityReset": "✨ 已获得当期限时{star}星卡,保底进度重置;",
80
86
  "tip.eventDraw.pityProgress": "📊 限时{star}星保底进度:{current}/{threshold}抽(再抽{left}抽必出);",
81
87
  // ==============================================
@@ -111,6 +117,8 @@ var zh_CN_default = {
111
117
  "error.eventDraw.count.notEnough": "❌ {star}星限时抽数不足:\n当前{have}抽/需要{need}抽\n可使用WWC限时兑换获取",
112
118
  "error.eventDraw.param.invalid": "❌ 抽卡参数无效,请传入期数和次数",
113
119
  "error.eventExchange.pool.none": "❌ 该期数限时卡池未开放或不存在!\n请使用WWC限时状态查看",
120
+ "error.disturbExchange.disturb.notEnough": "❌ 热带扰动不足!\n本次兑换需要:{need}扰动 | 当前拥有:{have}扰动",
121
+ "error.disturbDraw.count.notEnough": "❌ 扰动抽数不足!\n当前剩余:{have} 次 | 需要:{need} 次(可使用 WWC扰动兑换 兑换)",
114
122
  "error.switch.private": "❌ 私信场景无需设置群开关!该指令仅可在群聊中使用",
115
123
  "error.switch.fail": "❌ 开关操作失败!{msg}",
116
124
  "error.shop.no7starCard": "❌ 店铺生成失败!普通卡池中无7星卡片,请联系主人录入",
@@ -134,7 +142,7 @@ var zh_CN_default = {
134
142
  "image.warehouse.empty": "你的仓库暂无任何卡片,快去抽卡吧!",
135
143
  "image.shop.title": "WWC每日商店({date})",
136
144
  "image.shop.userInfo": "玩家:{name}",
137
- "image.shop.asset": "热带扰动: {disturb} | 水汽:{vapor}",
145
+ "image.shop.asset": "热带扰动: {disturb} | 水汽:{vapor} | 剩余抽数:{draw}",
138
146
  "image.shop.exchangeCount": "今日普通兑换:{used}/{limit}抽(单次最多40)",
139
147
  "image.shop.header.card": "卡片信息",
140
148
  "image.shop.header.price": "升格价格",
@@ -180,6 +188,7 @@ var Config = import_koishi.Schema.object({
180
188
  eventExchangePrice7: import_koishi.Schema.number().description("限时卡池7星兑换每抽消耗的水汽量(默认450)").default(450).min(1).max(1e4),
181
189
  collectionPart1Pattern: import_koishi.Schema.string().description('WWC收藏1的分类正则:类别名匹配此正则的归入收藏图1(默认匹配"纯数字且≥2000")').default("^([2-9]\\d{3}|\\d{5,})$").role("textarea"),
182
190
  collectionPart2Pattern: import_koishi.Schema.string().description('WWC收藏2的分类正则:类别名匹配此正则的归入收藏图2(默认匹配"纯数字且<2000");两个正则都不匹配的类别归入WWC收藏3').default("^(\\d{1,3}|1\\d{3})$").role("textarea"),
191
+ disturbExchangePrice: import_koishi.Schema.number().description("扰动兑换:每抽扰动抽数消耗的热带扰动量(默认100)").default(100).min(1).max(1e5),
183
192
  normalStar7Threshold: import_koishi.Schema.number().description("普通卡池7星保底抽数(默认1500)").default(1500).min(1).max(1e4),
184
193
  normalStar6Threshold: import_koishi.Schema.number().description("普通卡池6星保底抽数(默认300)").default(300).min(1).max(1e4),
185
194
  normalStar6Prob: import_koishi.Schema.number().description("普通卡池6星保底抽出6星概率百分比(减去为抽出7星概率)").default(90).min(0).max(100),
@@ -335,15 +344,19 @@ async function _warehouse_draw_image(ctx, user_cards, show_name, titleText, empt
335
344
  }
336
345
  }
337
346
  __name(_warehouse_draw_image, "_warehouse_draw_image");
338
- async function _shop_draw_image(ctx, session, userName, date, disturbance, vapor, usedExchange, limitExchange, shopCards) {
347
+ async function _shop_draw_image(ctx, session, userName, date, disturbance, vapor, drawLeft, usedExchange, limitExchange, shopCards) {
339
348
  ctx.logger.info("开始绘制店铺图片(最终稳定版)");
340
349
  try {
341
350
  if (!ctx.canvas) return null;
342
351
  const BASE_X = 40;
343
352
  const BASE_Y = 30;
344
353
  const CANVAS_WIDTH = 900;
345
- const CANVAS_HEIGHT = 1100;
346
354
  const CARD_ITEM_HEIGHT = 85;
355
+ const FIRST_CARD_Y = BASE_Y + 235;
356
+ const CANVAS_HEIGHT = Math.max(
357
+ 1100,
358
+ FIRST_CARD_Y + Math.max(0, (shopCards?.length ?? 0) - 1) * CARD_ITEM_HEIGHT + 70
359
+ );
347
360
  const FONT_FAMILY = "Microsoft YaHei, SimHei, 黑体, 宋体, sans-serif";
348
361
  const canvas = ctx.canvas.createCanvas(CANVAS_WIDTH, CANVAS_HEIGHT);
349
362
  const ctx2d = canvas.getContext("2d");
@@ -354,6 +367,7 @@ async function _shop_draw_image(ctx, session, userName, date, disturbance, vapor
354
367
  ctx2d.textAlign = "left";
355
368
  const distStr = String(disturbance ?? 0);
356
369
  const vaporStr = String(vapor ?? 0);
370
+ const drawStr = String(drawLeft ?? 0);
357
371
  ctx2d.save();
358
372
  ctx2d.textAlign = "center";
359
373
  ctx2d.fillStyle = "#E53E3E";
@@ -363,7 +377,7 @@ async function _shop_draw_image(ctx, session, userName, date, disturbance, vapor
363
377
  ctx2d.fillStyle = "#222";
364
378
  ctx2d.font = `20px ${FONT_FAMILY}`;
365
379
  ctx2d.fillText(`玩家:${userName}`, BASE_X, BASE_Y + 80);
366
- ctx2d.fillText(`热带扰动:${distStr}|水汽:${vaporStr}`, BASE_X, BASE_Y + 120);
380
+ ctx2d.fillText(`热带扰动:${distStr}|水汽:${vaporStr}|剩余抽数:${drawStr}`, BASE_X, BASE_Y + 120);
367
381
  const headerY = BASE_Y + 200;
368
382
  ctx2d.save();
369
383
  ctx2d.fillStyle = "#000";
@@ -955,6 +969,7 @@ async function _do_draw(ctx, session, draw_times, star7Threshold, star6Threshold
955
969
  if (isUpgrade) info += session.text("tip.draw.upgrade");
956
970
  info += session.text("tip.draw.vapor", { vapor: waterVaporTotal });
957
971
  info += session.text("tip.draw.disturb", { disturbanceTotal });
972
+ info += "\n" + session.text("tip.draw.left", { left: haveDraw - draw_times });
958
973
  if (info) msg += "\n" + info.replace(/;$/, "");
959
974
  await session.send(build_msg(session, msg));
960
975
  }
@@ -1287,20 +1302,24 @@ async function _do_shop(ctx, session, signResetHour, signResetMinute) {
1287
1302
  const today = `${todayDate.getFullYear()}${String(todayDate.getMonth() + 1).padStart(2, "0")}${String(todayDate.getDate()).padStart(2, "0")}`;
1288
1303
  let todayShop = await ctx.database.get("gacha_shop_daily", { shop_date: today });
1289
1304
  if (todayShop.length === 0) {
1290
- const [sevenStarCards, sixStarCards] = await Promise.all([
1305
+ const [sevenStarCards, sixStarCards, fiveStarCards] = await Promise.all([
1291
1306
  ctx.database.get("gacha_card_pool", { card_star: 7 }),
1292
- ctx.database.get("gacha_card_pool", { card_star: 6 })
1307
+ ctx.database.get("gacha_card_pool", { card_star: 6 }),
1308
+ ctx.database.get("gacha_card_pool", { card_star: 5 })
1293
1309
  ]);
1294
- if (sevenStarCards.length < 4 || sixStarCards.length < 6) {
1310
+ if (sevenStarCards.length < 4 || sixStarCards.length < 6 || fiveStarCards.length < 10) {
1295
1311
  return await session.send(import_koishi.h.text(session.text("error.shop.cardNotEnough")));
1296
1312
  }
1297
1313
  const selected7 = sevenStarCards.sort(() => Math.random() - 0.5).slice(0, 4);
1298
1314
  const selected6 = sixStarCards.sort(() => Math.random() - 0.5).slice(0, 6);
1299
- const allCards = [...selected7, ...selected6];
1315
+ const selected5 = fiveStarCards.sort(() => Math.random() - 0.5).slice(0, 10);
1316
+ const allCards = [...selected7, ...selected6, ...selected5];
1317
+ const SHOP_PRICE_BASE = { 7: 800, 6: 200, 5: 20 };
1318
+ const SHOP_PRICE_RANGE = { 7: 80, 6: 30, 5: 0 };
1300
1319
  for (const card of allCards) {
1301
- const basePrice = card.card_star === 7 ? 800 : 200;
1302
- const range = card.card_star === 7 ? 80 : 30;
1303
- const randomPrice = basePrice + Math.floor(Math.random() * (range * 2 + 1)) - range;
1320
+ const basePrice = SHOP_PRICE_BASE[card.card_star] ?? 10;
1321
+ const range = SHOP_PRICE_RANGE[card.card_star] ?? 0;
1322
+ const randomPrice = range > 0 ? basePrice + Math.floor(Math.random() * (range * 2 + 1)) - range : basePrice;
1304
1323
  const nextId = await getNextId(ctx, "gacha_shop_daily");
1305
1324
  await ctx.database.create("gacha_shop_daily", {
1306
1325
  id: nextId,
@@ -1342,9 +1361,11 @@ async function _do_shop(ctx, session, signResetHour, signResetMinute) {
1342
1361
  leftLimit: limitMap.get(item.card_id)
1343
1362
  };
1344
1363
  });
1364
+ shopCardList.sort((a, b) => b.star - a.star || String(a.id).localeCompare(String(b.id)));
1345
1365
  const userAsset = await ctx.database.get("gacha_user_draw_count", { qq });
1346
1366
  const dist = userAsset[0]?.tropical_disturbance ?? 0;
1347
1367
  const vapor = userAsset[0]?.water_vapor ?? 0;
1368
+ const drawLeft = userAsset[0]?.draw_count ?? 0;
1348
1369
  const img = await _shop_draw_image(
1349
1370
  ctx,
1350
1371
  session,
@@ -1352,6 +1373,7 @@ async function _do_shop(ctx, session, signResetHour, signResetMinute) {
1352
1373
  today,
1353
1374
  dist,
1354
1375
  vapor,
1376
+ drawLeft,
1355
1377
  0,
1356
1378
  0,
1357
1379
  shopCardList
@@ -1878,6 +1900,7 @@ async function _do_event_draw(ctx, session, data, event6Threshold, event7Thresho
1878
1900
  } else {
1879
1901
  info += session.text("tip.eventDraw.pityReset", { star: limitStar });
1880
1902
  }
1903
+ info += "\n" + session.text("tip.eventDraw.left", { star: limitStar, left: have - count });
1881
1904
  if (info) msg += "\n" + info.replace(/;$/, "");
1882
1905
  await session.send(build_msg(session, msg));
1883
1906
  if (true) {
@@ -1894,6 +1917,128 @@ async function _do_event_draw(ctx, session, data, event6Threshold, event7Thresho
1894
1917
  }
1895
1918
  }
1896
1919
  __name(_do_event_draw, "_do_event_draw");
1920
+ async function _do_disturb_exchange(ctx, session, cnt, price) {
1921
+ const qq = await getUnifiedQQ(ctx, session);
1922
+ const realCnt = Math.min(Math.max(cnt | 0, 1), 40);
1923
+ const user = await ctx.database.get("gacha_user", { qq });
1924
+ if (!user.length) return await session.send(build_msg(session, session.text("error.common.notRegister")));
1925
+ const total = price * realCnt;
1926
+ const asset = await ctx.database.get("gacha_user_draw_count", { qq });
1927
+ const disturb = asset[0]?.tropical_disturbance ?? 0;
1928
+ if (disturb < total) {
1929
+ ctx.logger.warn(`[扰动兑换] 玩家${qq}兑换失败:热带扰动不足(拥有${disturb},需${total})`);
1930
+ return await session.send(build_msg(session, session.text("error.disturbExchange.disturb.notEnough", { need: total, have: disturb })));
1931
+ }
1932
+ await ctx.database.upsert("gacha_user_draw_count", [{ qq, tropical_disturbance: disturb - total }]);
1933
+ const ud = await ctx.database.get("gacha_user_disturb_draw", { qq });
1934
+ const have = ud[0]?.draw_count ?? 0;
1935
+ await ctx.database.upsert("gacha_user_disturb_draw", [{ qq, draw_count: have + realCnt }]);
1936
+ ctx.logger.info(`[扰动兑换] 玩家${qq}兑换成功:获得${realCnt}抽,消耗扰动${total},扰动抽数${have}→${have + realCnt}`);
1937
+ await session.send(build_msg(
1938
+ session,
1939
+ session.text("tip.disturbExchange.success", { count: realCnt, cost: total, left: have + realCnt })
1940
+ ));
1941
+ }
1942
+ __name(_do_disturb_exchange, "_do_disturb_exchange");
1943
+ async function _do_disturb_draw(ctx, session, count) {
1944
+ ctx.logger.info("执行扰动抽卡,次数:", count);
1945
+ const qq = await getUnifiedQQ(ctx, session);
1946
+ const user = await ctx.database.get("gacha_user", { qq });
1947
+ if (!user.length) return await session.send(build_msg(session, session.text("error.common.notRegister")));
1948
+ const showName = user[0].status === 1 ? user[0].nickname : qq;
1949
+ if (!Number.isInteger(count) || count < 1 || count > 20) {
1950
+ return await session.send(build_msg(session, session.text("error.draw.count.invalid")));
1951
+ }
1952
+ const ud = await ctx.database.get("gacha_user_disturb_draw", { qq });
1953
+ const have = ud[0]?.draw_count ?? 0;
1954
+ if (have < count) {
1955
+ return await session.send(build_msg(session, session.text("error.disturbDraw.count.notEnough", {
1956
+ need: count,
1957
+ have
1958
+ })));
1959
+ }
1960
+ const allCards = await ctx.database.get("gacha_card_pool", {});
1961
+ const starCardMap = { 5: [], 6: [], 7: [] };
1962
+ allCards.forEach((card) => {
1963
+ if (starCardMap[card.card_star]) starCardMap[card.card_star].push(card);
1964
+ });
1965
+ const DISTURB_STAR_PROB = { 7: 10, 6: 36, 5: 54 };
1966
+ const weightedPool = [];
1967
+ for (const [star, prob] of Object.entries(DISTURB_STAR_PROB)) {
1968
+ if (!starCardMap[+star]?.length) continue;
1969
+ for (let i = 0; i < prob; i++) weightedPool.push(+star);
1970
+ }
1971
+ if (!weightedPool.length) {
1972
+ return await session.send(build_msg(session, session.text("error.draw.poolEmpty")));
1973
+ }
1974
+ const STAR_TO_DISTURBANCE = { 0: 0, 1: 0, 2: 0, 3: 1, 4: 5, 5: 20, 6: 100, 7: 500 };
1975
+ const INIT_WATER_VAPOR = { 0: 50, 1: 100, 2: 150, 3: 200, 4: 500, 5: 1e3, 6: 2e3, 7: 5e3 };
1976
+ const UPGRADE_WATER_VAPOR = { 0: 25, 1: 50, 2: 75, 3: 100, 4: 200, 5: 500, 6: 1e3, 7: 2e3 };
1977
+ const drawResult = [];
1978
+ let disturbanceTotal = 0;
1979
+ let waterVaporTotal = 0;
1980
+ let isUpgrade = false;
1981
+ for (let i = 0; i < count; i++) {
1982
+ const selectedStar = weightedPool[Math.floor(Math.random() * weightedPool.length)];
1983
+ const cardList = starCardMap[selectedStar];
1984
+ const card = cardList[Math.floor(Math.random() * cardList.length)];
1985
+ drawResult.push({ star: selectedStar, cid: card.card_id, name: card.card_name });
1986
+ const userCard = await ctx.database.get("gacha_user_card", { qq, card_id: card.card_id });
1987
+ if (!userCard.length) {
1988
+ await ctx.database.upsert("gacha_user_card", [{
1989
+ qq,
1990
+ card_id: card.card_id,
1991
+ card_level: 0,
1992
+ obtain_at: Date.now()
1993
+ }]);
1994
+ waterVaporTotal += INIT_WATER_VAPOR[selectedStar];
1995
+ ctx.logger.info(`[扰动抽卡] 新增卡片:${card.card_id} ${card.card_name},等级0`);
1996
+ } else {
1997
+ const currentLevel = userCard[0].card_level;
1998
+ if (currentLevel < CARD_LEVEL_MAX) {
1999
+ await ctx.database.upsert("gacha_user_card", [{
2000
+ id: userCard[0].id,
2001
+ qq,
2002
+ card_id: card.card_id,
2003
+ card_level: currentLevel + 1,
2004
+ obtain_at: Date.now()
2005
+ }]);
2006
+ isUpgrade = true;
2007
+ waterVaporTotal += UPGRADE_WATER_VAPOR[selectedStar];
2008
+ ctx.logger.info(`[扰动抽卡] 卡片升级:${card.card_id},等级${currentLevel}→${currentLevel + 1}`);
2009
+ } else {
2010
+ const d = STAR_TO_DISTURBANCE[selectedStar];
2011
+ if (d > 0) {
2012
+ disturbanceTotal += d;
2013
+ ctx.logger.info(`[扰动抽卡] 卡片满级:${card.card_id},转化为${d}热带扰动`);
2014
+ }
2015
+ }
2016
+ }
2017
+ }
2018
+ await ctx.database.upsert("gacha_user_disturb_draw", [{ qq, draw_count: have - count }]);
2019
+ const asset = await ctx.database.get("gacha_user_draw_count", { qq });
2020
+ await ctx.database.upsert("gacha_user_draw_count", [{
2021
+ qq,
2022
+ draw_count: asset[0]?.draw_count ?? 0,
2023
+ tropical_disturbance: (asset[0]?.tropical_disturbance ?? 0) + disturbanceTotal,
2024
+ water_vapor: (asset[0]?.water_vapor ?? 0) + waterVaporTotal,
2025
+ no_6star_draws: asset[0]?.no_6star_draws ?? 0,
2026
+ no_7star_draws: asset[0]?.no_7star_draws ?? 0
2027
+ }]);
2028
+ ctx.logger.info(`[扰动抽卡] ${showName}(${qq}) 消耗${count}抽,剩余${have - count},水汽+${waterVaporTotal},热带扰动+${disturbanceTotal}`);
2029
+ let msg = session.text("tip.disturbDraw.title", { name: showName, left: have - count }) + "\n";
2030
+ drawResult.forEach((item) => {
2031
+ msg += `${get_star_symbol(item.star)} ${item.cid} ${item.name}
2032
+ `;
2033
+ });
2034
+ let info = "";
2035
+ if (isUpgrade) info += session.text("tip.draw.upgrade");
2036
+ info += session.text("tip.draw.vapor", { vapor: waterVaporTotal });
2037
+ info += session.text("tip.draw.disturb", { disturbanceTotal });
2038
+ if (info) msg += "\n" + info.replace(/;$/, "");
2039
+ await session.send(build_msg(session, msg));
2040
+ }
2041
+ __name(_do_disturb_draw, "_do_disturb_draw");
1897
2042
  async function _do_broadcast(ctx, session, msg, masterQQ) {
1898
2043
  const userQQ = await getUnifiedQQ(ctx, session);
1899
2044
  if (userQQ !== masterQQ) return;
@@ -1945,7 +2090,7 @@ async function _do_reject(ctx, session, rejectQQ, masterQQ) {
1945
2090
  }
1946
2091
  __name(_do_reject, "_do_reject");
1947
2092
  async function _do_help(ctx, session) {
1948
- const helpMsg = session.text("command.wwc.help.title") + "\n" + session.text("command.wwc.help.register") + "\n" + session.text("command.wwc.help.sign") + "\n" + session.text("command.wwc.help.draw") + "\n" + session.text("command.wwc.help.warehouse") + "\n" + session.text("command.wwc.help.shop") + "\n" + session.text("command.wwc.help.upgrade") + "\n" + session.text("command.wwc.help.exchange") + "\n" + session.text("command.wwc.help.collection") + "\n" + session.text("command.wwc.help.ranking") + "\n" + session.text("command.wwc.help.eventStatus") + "\n" + session.text("command.wwc.help.eventDraw") + "\n" + session.text("command.wwc.help.eventExchange") + "\n" + session.text("command.wwc.help.tip");
2093
+ const helpMsg = session.text("command.wwc.help.title") + "\n" + session.text("command.wwc.help.register") + "\n" + session.text("command.wwc.help.sign") + "\n" + session.text("command.wwc.help.draw") + "\n" + session.text("command.wwc.help.warehouse") + "\n" + session.text("command.wwc.help.shop") + "\n" + session.text("command.wwc.help.upgrade") + "\n" + session.text("command.wwc.help.exchange") + "\n" + session.text("command.wwc.help.collection") + "\n" + session.text("command.wwc.help.ranking") + "\n" + session.text("command.wwc.help.eventStatus") + "\n" + session.text("command.wwc.help.eventDraw") + "\n" + session.text("command.wwc.help.eventExchange") + "\n" + session.text("command.wwc.help.disturbDraw") + "\n" + session.text("command.wwc.help.disturbExchange") + "\n" + session.text("command.wwc.help.tip");
1949
2094
  await session.send(build_msg(session, helpMsg));
1950
2095
  }
1951
2096
  __name(_do_help, "_do_help");
@@ -2045,6 +2190,10 @@ async function apply(ctx, config) {
2045
2190
  got6: { type: "boolean" },
2046
2191
  got7: { type: "boolean" }
2047
2192
  }, { primary: ["qq", "event_code"] });
2193
+ ctx.model.extend("gacha_user_disturb_draw", {
2194
+ qq: { type: "string" },
2195
+ draw_count: { type: "integer" }
2196
+ }, { primary: ["qq"] });
2048
2197
  ctx.model.extend("gacha_group_member", {
2049
2198
  group_id: { type: "string" },
2050
2199
  qq: { type: "string" },
@@ -2230,6 +2379,20 @@ async function apply(ctx, config) {
2230
2379
  const cnt = Number.isInteger(num) && num >= 1 && num <= 40 ? num : 1;
2231
2380
  await _do_event_exchange(ctx, session, { code, cnt }, config.eventExchangePrice6, config.eventExchangePrice7);
2232
2381
  });
2382
+ ctx.command("WWC扰动抽卡 [次数]", "使用扰动抽数抽卡(普通卡池:7星10%、6星36%、5星54%),支持1-20连").alias("wwc扰动抽卡").alias("WWC扰动抽").action(async (argv, count) => {
2383
+ if (!argv.session) return;
2384
+ const session = argv.session;
2385
+ const num = Number(count);
2386
+ const times = Number.isInteger(num) && num >= 1 && num <= 20 ? num : 1;
2387
+ await _do_disturb_draw(ctx, session, times);
2388
+ });
2389
+ ctx.command("WWC扰动兑换 <次数>", "热带扰动兑换扰动抽数,每抽消耗由配置项决定(默认100),单次1-40").alias("wwc扰动兑换").alias("WWC扰动换抽").action(async (argv, count) => {
2390
+ if (!argv.session) return;
2391
+ const session = argv.session;
2392
+ const num = Number(count);
2393
+ const cnt = Number.isInteger(num) && num >= 1 && num <= 40 ? num : 1;
2394
+ await _do_disturb_exchange(ctx, session, cnt, config.disturbExchangePrice);
2395
+ });
2233
2396
  ctx.command("WWC限时录入 <参数...>", "录入限时卡池信息,仅主人可用(格式:期数 ID 名称 星级 类别 开始戳 结束戳)").alias("wwc限时录入").action(async (argv, ...params) => {
2234
2397
  if (!argv.session) return;
2235
2398
  const session = argv.session;
@@ -12,6 +12,8 @@ declare const _default: {
12
12
  "command.wwc.help.eventStatus": string;
13
13
  "command.wwc.help.eventDraw": string;
14
14
  "command.wwc.help.eventExchange": string;
15
+ "command.wwc.help.disturbDraw": string;
16
+ "command.wwc.help.disturbExchange": string;
15
17
  "command.wwc.help.tip": string;
16
18
  "tip.register.success": string;
17
19
  "tip.register.modify": string;
@@ -25,6 +27,8 @@ declare const _default: {
25
27
  "tip.switch.groupClose": string;
26
28
  "tip.eventAdd.success": string;
27
29
  "tip.eventExchange.success": string;
30
+ "tip.disturbExchange.success": string;
31
+ "tip.disturbDraw.title": string;
28
32
  "tip.eventStatus.info": string;
29
33
  "tip.upgrade.success": string;
30
34
  "tip.upgrade.cost": string;
@@ -37,6 +41,8 @@ declare const _default: {
37
41
  "tip.draw.upgrade": string;
38
42
  "tip.draw.vapor": string;
39
43
  "tip.draw.disturb": string;
44
+ "tip.draw.left": string;
45
+ "tip.eventDraw.left": string;
40
46
  "tip.eventDraw.pityReset": string;
41
47
  "tip.eventDraw.pityProgress": string;
42
48
  "error.common.noPermission": string;
@@ -69,6 +75,8 @@ declare const _default: {
69
75
  "error.eventDraw.count.notEnough": string;
70
76
  "error.eventDraw.param.invalid": string;
71
77
  "error.eventExchange.pool.none": string;
78
+ "error.disturbExchange.disturb.notEnough": string;
79
+ "error.disturbDraw.count.notEnough": string;
72
80
  "error.switch.private": string;
73
81
  "error.switch.fail": string;
74
82
  "error.shop.no7starCard": string;
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "koishi-plugin-xxck-1",
3
3
  "description": "抽卡系统|完整指令说明见readme|建议使用skia-canvas",
4
- "version": "0.3.5",
4
+ "version": "0.3.7",
5
5
  "main": "lib/index.js",
6
6
  "typings": "lib/index.d.ts",
7
7
  "files": [