koishi-plugin-ggcevo-game 2.0.7 → 2.0.9
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/database.d.ts +11 -0
- package/lib/index.d.ts +1 -0
- package/lib/index.js +312 -19
- package/package.json +1 -1
package/lib/database.d.ts
CHANGED
|
@@ -28,6 +28,8 @@ declare module 'koishi' {
|
|
|
28
28
|
ggcevo_explore: explore;
|
|
29
29
|
ggcevo_global_stats: GlobalStats;
|
|
30
30
|
ggcevo_guess: guess;
|
|
31
|
+
roulettes: Roulette;
|
|
32
|
+
roulette_groups: RouletteGroup;
|
|
31
33
|
}
|
|
32
34
|
}
|
|
33
35
|
export interface Backpack {
|
|
@@ -248,3 +250,12 @@ export interface bossweights {
|
|
|
248
250
|
weight: number;
|
|
249
251
|
lastSpawn: Date;
|
|
250
252
|
}
|
|
253
|
+
export interface Roulette {
|
|
254
|
+
id: number;
|
|
255
|
+
items: string[];
|
|
256
|
+
}
|
|
257
|
+
export interface RouletteGroup {
|
|
258
|
+
id: number;
|
|
259
|
+
name: string;
|
|
260
|
+
items: number[];
|
|
261
|
+
}
|
package/lib/index.d.ts
CHANGED
|
@@ -21,6 +21,7 @@ export interface Config {
|
|
|
21
21
|
enablePlayRequirement: boolean;
|
|
22
22
|
enableGuguBattle: boolean;
|
|
23
23
|
enableMatchesRequirement: boolean;
|
|
24
|
+
signInGroupId: string[];
|
|
24
25
|
}
|
|
25
26
|
export declare const Config: Schema<Config>;
|
|
26
27
|
export declare function apply(ctx: Context, config: Config): void;
|
package/lib/index.js
CHANGED
|
@@ -7474,7 +7474,7 @@ var Config = import_koishi.Schema.intersect([
|
|
|
7474
7474
|
proxyAgent: import_koishi.Schema.string().description("代理服务器地址"),
|
|
7475
7475
|
enablePlayRequirement: import_koishi.Schema.boolean().description("开启签到需3天游戏记录(关闭时无限制)").default(false),
|
|
7476
7476
|
enableCurfew: import_koishi.Schema.boolean().description("是否开启宵禁模式(18:00-24:00禁止群聊指令)").default(false),
|
|
7477
|
-
enableGuguBattle: import_koishi.Schema.boolean().description("
|
|
7477
|
+
enableGuguBattle: import_koishi.Schema.boolean().description("是否开启咕咕之战游戏功能").default(true)
|
|
7478
7478
|
}).description("基础设置"),
|
|
7479
7479
|
// 赛季与兑换配置组
|
|
7480
7480
|
import_koishi.Schema.object({
|
|
@@ -7494,11 +7494,15 @@ var Config = import_koishi.Schema.intersect([
|
|
|
7494
7494
|
}).description("对战限制"),
|
|
7495
7495
|
// 通知系统配置组 - 新增违规提醒开关
|
|
7496
7496
|
import_koishi.Schema.object({
|
|
7497
|
-
groupId: import_koishi.Schema.array(import_koishi.Schema.string()).description("
|
|
7497
|
+
groupId: import_koishi.Schema.array(import_koishi.Schema.string()).description("咕咕之战广播通知群组").default([]),
|
|
7498
7498
|
checkInterval: import_koishi.Schema.number().description("大厅监控检查间隔(秒)").default(60),
|
|
7499
7499
|
enableViolationAlert: import_koishi.Schema.boolean().description("启用违规玩家房间提醒").default(false)
|
|
7500
7500
|
// 新增配置项
|
|
7501
|
-
}).description("通知设置").collapse()
|
|
7501
|
+
}).description("通知设置").collapse(),
|
|
7502
|
+
// 新增:签到配置组
|
|
7503
|
+
import_koishi.Schema.object({
|
|
7504
|
+
signInGroupId: import_koishi.Schema.array(import_koishi.Schema.string()).description("允许签到的群组ID列表(为空则不限制)").default([])
|
|
7505
|
+
}).description("签到设置")
|
|
7502
7506
|
]);
|
|
7503
7507
|
function apply(ctx, config) {
|
|
7504
7508
|
ctx.model.extend("ggcevo_backpack", {
|
|
@@ -7804,6 +7808,21 @@ function apply(ctx, config) {
|
|
|
7804
7808
|
}, {
|
|
7805
7809
|
primary: ["handle", "itemId"]
|
|
7806
7810
|
});
|
|
7811
|
+
ctx.model.extend("roulettes", {
|
|
7812
|
+
id: "unsigned",
|
|
7813
|
+
items: "list"
|
|
7814
|
+
}, {
|
|
7815
|
+
primary: "id",
|
|
7816
|
+
autoInc: true
|
|
7817
|
+
});
|
|
7818
|
+
ctx.model.extend("roulette_groups", {
|
|
7819
|
+
id: "unsigned",
|
|
7820
|
+
name: "string",
|
|
7821
|
+
items: "json"
|
|
7822
|
+
}, {
|
|
7823
|
+
primary: "id",
|
|
7824
|
+
autoInc: true
|
|
7825
|
+
});
|
|
7807
7826
|
ctx.setInterval(async () => {
|
|
7808
7827
|
const now = /* @__PURE__ */ new Date();
|
|
7809
7828
|
await ctx.database.set(
|
|
@@ -8048,8 +8067,20 @@ function apply(ctx, config) {
|
|
|
8048
8067
|
});
|
|
8049
8068
|
}, 24 * 60 * 60 * 1e3);
|
|
8050
8069
|
}
|
|
8070
|
+
const checkGroupAccess = /* @__PURE__ */ __name((session, featureName = "该功能") => {
|
|
8071
|
+
if (!config.signInGroupId?.length) return null;
|
|
8072
|
+
if (session.isDirect) {
|
|
8073
|
+
return `⛔ ${featureName}仅限在指定群组中使用,请前往指定的QQ群进行操作。`;
|
|
8074
|
+
}
|
|
8075
|
+
if (!config.signInGroupId.includes(session.guildId)) {
|
|
8076
|
+
return `⛔ 当前群组不允许使用${featureName},请前往指定的QQ群进行操作。`;
|
|
8077
|
+
}
|
|
8078
|
+
return null;
|
|
8079
|
+
}, "checkGroupAccess");
|
|
8051
8080
|
ctx.command("ggcevo/抽奖").action(async (argv) => {
|
|
8052
8081
|
const session = argv.session;
|
|
8082
|
+
const accessError = checkGroupAccess(session, "抽奖");
|
|
8083
|
+
if (accessError) return accessError;
|
|
8053
8084
|
let winCount = 0;
|
|
8054
8085
|
const [profile] = await ctx.database.get("sc2arcade_player", { userId: session.userId, isActive: true });
|
|
8055
8086
|
if (!profile) {
|
|
@@ -8079,14 +8110,17 @@ function apply(ctx, config) {
|
|
|
8079
8110
|
const result = await gachaWithPity(ctx, handle);
|
|
8080
8111
|
if (result) winCount++;
|
|
8081
8112
|
}
|
|
8113
|
+
const [updatedRecord] = await ctx.database.get("ggcevo_sign", { handle });
|
|
8082
8114
|
return [
|
|
8083
8115
|
`🎰 您使用了${quantity}枚咕咕币`,
|
|
8084
8116
|
winCount > 0 ? `🎉 其中获得${winCount}张兑换券!` : "💔 本次未获得任何兑换券",
|
|
8085
|
-
`📊 当前保底进度:${
|
|
8117
|
+
`📊 当前保底进度:${updatedRecord?.pityCounter || 0}/90`
|
|
8086
8118
|
].join("\n");
|
|
8087
8119
|
});
|
|
8088
8120
|
ctx.command("ggcevo/单抽").action(async (argv) => {
|
|
8089
8121
|
const session = argv.session;
|
|
8122
|
+
const accessError = checkGroupAccess(session, "单抽");
|
|
8123
|
+
if (accessError) return accessError;
|
|
8090
8124
|
const [profile] = await ctx.database.get("sc2arcade_player", { userId: session.userId, isActive: true });
|
|
8091
8125
|
if (!profile) {
|
|
8092
8126
|
return "🔒 需要先绑定游戏句柄。";
|
|
@@ -8114,6 +8148,8 @@ function apply(ctx, config) {
|
|
|
8114
8148
|
});
|
|
8115
8149
|
ctx.command("ggcevo/十连抽").action(async (argv) => {
|
|
8116
8150
|
const session = argv.session;
|
|
8151
|
+
const accessError = checkGroupAccess(session, "十连抽");
|
|
8152
|
+
if (accessError) return accessError;
|
|
8117
8153
|
const [profile] = await ctx.database.get("sc2arcade_player", { userId: session.userId, isActive: true });
|
|
8118
8154
|
if (!profile) {
|
|
8119
8155
|
return "🔒 需要先绑定游戏句柄。";
|
|
@@ -8146,6 +8182,8 @@ function apply(ctx, config) {
|
|
|
8146
8182
|
});
|
|
8147
8183
|
ctx.command("ggcevo/背包").action(async (argv) => {
|
|
8148
8184
|
const session = argv.session;
|
|
8185
|
+
const accessError = checkGroupAccess(session, "背包");
|
|
8186
|
+
if (accessError) return accessError;
|
|
8149
8187
|
const [profile] = await ctx.database.get("sc2arcade_player", { userId: session.userId, isActive: true });
|
|
8150
8188
|
if (!profile) return "🔒 需要先绑定游戏句柄。";
|
|
8151
8189
|
const handle = `${profile.regionId}-S2-${profile.realmId}-${profile.profileId}`;
|
|
@@ -8166,6 +8204,8 @@ ${itemDetails.join("\n")}`;
|
|
|
8166
8204
|
ctx.command("ggcevo/签到").action(async (argv) => {
|
|
8167
8205
|
try {
|
|
8168
8206
|
const session = argv.session;
|
|
8207
|
+
const accessError = checkGroupAccess(session, "签到");
|
|
8208
|
+
if (accessError) return accessError;
|
|
8169
8209
|
const [profile] = await ctx.database.get("sc2arcade_player", { userId: session.userId, isActive: true });
|
|
8170
8210
|
if (!profile) return "🔒 需要先绑定游戏句柄。";
|
|
8171
8211
|
const { regionId, realmId, profileId } = profile;
|
|
@@ -8324,6 +8364,8 @@ ${ticketMessage}${effectMessage}`;
|
|
|
8324
8364
|
ctx.command("ggcevo/补签").action(async (argv) => {
|
|
8325
8365
|
try {
|
|
8326
8366
|
const session = argv.session;
|
|
8367
|
+
const accessError = checkGroupAccess(session, "补签");
|
|
8368
|
+
if (accessError) return accessError;
|
|
8327
8369
|
const [profile] = await ctx.database.get("sc2arcade_player", { userId: session.userId, isActive: true });
|
|
8328
8370
|
if (!profile) return "🔒 需要先绑定游戏句柄。";
|
|
8329
8371
|
const { regionId, realmId, profileId } = profile;
|
|
@@ -8379,6 +8421,8 @@ ${ticketMessage}${effectMessage}`;
|
|
|
8379
8421
|
});
|
|
8380
8422
|
ctx.guild().command("ggcevo/每月津贴").action(async (argv) => {
|
|
8381
8423
|
const session = argv.session;
|
|
8424
|
+
const accessError = checkGroupAccess(session, "每月津贴");
|
|
8425
|
+
if (accessError) return accessError;
|
|
8382
8426
|
const [profile] = await ctx.database.get("sc2arcade_player", { userId: session.userId, isActive: true });
|
|
8383
8427
|
if (!profile) return "🔒 需要先绑定游戏句柄。";
|
|
8384
8428
|
const { regionId, realmId, profileId } = profile;
|
|
@@ -8419,6 +8463,8 @@ ${ticketMessage}${effectMessage}`;
|
|
|
8419
8463
|
});
|
|
8420
8464
|
ctx.command("ggcevo/领取 [name]").action(async (argv, name2) => {
|
|
8421
8465
|
const session = argv.session;
|
|
8466
|
+
const accessError = checkGroupAccess(session, "领取");
|
|
8467
|
+
if (accessError) return accessError;
|
|
8422
8468
|
const [profile] = await ctx.database.get("sc2arcade_player", { userId: session.userId });
|
|
8423
8469
|
if (!profile) return "🔒 需要先绑定游戏句柄。";
|
|
8424
8470
|
const handle = `${profile.regionId}-S2-${profile.realmId}-${profile.profileId}`;
|
|
@@ -8503,6 +8549,8 @@ ${ticketMessage}${effectMessage}`;
|
|
|
8503
8549
|
return `活动【${activityName}】创建成功!奖励内容:${itemName} x${quantity}。`;
|
|
8504
8550
|
});
|
|
8505
8551
|
ctx.command("ggcevo/活动列表").action(async ({ session }) => {
|
|
8552
|
+
const accessError = checkGroupAccess(session, "活动列表");
|
|
8553
|
+
if (accessError) return accessError;
|
|
8506
8554
|
const [profile] = await ctx.database.get("sc2arcade_player", { userId: session.userId });
|
|
8507
8555
|
if (!profile) return "🔒 需要先绑定游戏句柄。";
|
|
8508
8556
|
const activities = await ctx.database.get(
|
|
@@ -8587,6 +8635,8 @@ ${ticketMessage}${effectMessage}`;
|
|
|
8587
8635
|
}
|
|
8588
8636
|
});
|
|
8589
8637
|
ctx.command("ggcevo/胜点榜 [page]").alias("排行榜").usage("输入 胜点榜 [页码] 查看对应页的排行榜,每页10条").action(async ({ session }, page) => {
|
|
8638
|
+
const accessError = checkGroupAccess(session, "胜点榜");
|
|
8639
|
+
if (accessError) return accessError;
|
|
8590
8640
|
const [profile] = await ctx.database.get("sc2arcade_player", { userId: session.userId });
|
|
8591
8641
|
if (!profile) return "🔒 需要先绑定游戏句柄。";
|
|
8592
8642
|
const pageNum = parseInt(page) || 1;
|
|
@@ -8730,6 +8780,8 @@ ${ticketMessage}${effectMessage}`;
|
|
|
8730
8780
|
});
|
|
8731
8781
|
ctx.command("ggcevo/排名 [player]", "查询个人排名").alias("rank").usage("输入“排名”查看自己的排名信息").action(async (argv, player) => {
|
|
8732
8782
|
const session = argv.session;
|
|
8783
|
+
const accessError = checkGroupAccess(session, "排名");
|
|
8784
|
+
if (accessError) return accessError;
|
|
8733
8785
|
const ctx2 = session.bot.ctx;
|
|
8734
8786
|
let handle;
|
|
8735
8787
|
if (!player) {
|
|
@@ -8798,6 +8850,8 @@ ${ticketMessage}${effectMessage}`;
|
|
|
8798
8850
|
});
|
|
8799
8851
|
ctx.command("ggcevo/违规记录 [user]", "违规记录查询").usage("输入 违规记录 [@玩家] -p 页码 查看处罚记录,每页1条").option("p", "-p <page:number> 指定页码").action(async (argv) => {
|
|
8800
8852
|
const session = argv.session;
|
|
8853
|
+
const accessError = checkGroupAccess(session, "违规记录");
|
|
8854
|
+
if (accessError) return accessError;
|
|
8801
8855
|
const pageNum = argv.options.p ? argv.options.p : 1;
|
|
8802
8856
|
const user = argv.args[0];
|
|
8803
8857
|
let handle;
|
|
@@ -8850,6 +8904,8 @@ ${ticketMessage}${effectMessage}`;
|
|
|
8850
8904
|
].join("\n");
|
|
8851
8905
|
});
|
|
8852
8906
|
ctx.command("ggcevo/兑换赞助物品", "兑换赞助物品").action(async ({ session }) => {
|
|
8907
|
+
const accessError = checkGroupAccess(session, "兑换赞助物品");
|
|
8908
|
+
if (accessError) return accessError;
|
|
8853
8909
|
try {
|
|
8854
8910
|
const [profile] = await ctx.database.get("sc2arcade_player", { userId: session.userId, isActive: true });
|
|
8855
8911
|
if (!profile) return "🔒 需要先绑定游戏句柄。";
|
|
@@ -9017,6 +9073,8 @@ ${items.join("、")}
|
|
|
9017
9073
|
}
|
|
9018
9074
|
});
|
|
9019
9075
|
ctx.command("ggcevo/兑换扭蛋币").action(async ({ session }) => {
|
|
9076
|
+
const accessError = checkGroupAccess(session, "兑换扭蛋币");
|
|
9077
|
+
if (accessError) return accessError;
|
|
9020
9078
|
const [profile] = await ctx.database.get("sc2arcade_player", { userId: session.userId });
|
|
9021
9079
|
if (!profile) return "🔒 需要先绑定游戏句柄。";
|
|
9022
9080
|
const handle = `${profile.regionId}-S2-${profile.realmId}-${profile.profileId}`;
|
|
@@ -9046,6 +9104,8 @@ ${items.join("、")}
|
|
|
9046
9104
|
});
|
|
9047
9105
|
ctx.command("ggcevo/扭蛋").action(async (argv) => {
|
|
9048
9106
|
const session = argv.session;
|
|
9107
|
+
const accessError = checkGroupAccess(session, "兑换扭蛋币");
|
|
9108
|
+
if (accessError) return accessError;
|
|
9049
9109
|
const [profile] = await ctx.database.get("sc2arcade_player", { userId: session.userId, isActive: true });
|
|
9050
9110
|
if (!profile) {
|
|
9051
9111
|
return "🔒 需要先绑定游戏句柄。";
|
|
@@ -9161,6 +9221,8 @@ ${items.join("、")}
|
|
|
9161
9221
|
});
|
|
9162
9222
|
ctx.command("ggcevo/个人信息").action(async (argv) => {
|
|
9163
9223
|
const session = argv.session;
|
|
9224
|
+
const accessError = checkGroupAccess(session, "个人信息");
|
|
9225
|
+
if (accessError) return accessError;
|
|
9164
9226
|
const output = [];
|
|
9165
9227
|
const [profile] = await ctx.database.get("sc2arcade_player", { userId: session.userId, isActive: true });
|
|
9166
9228
|
if (!profile) return "🔒 需要先绑定游戏句柄。";
|
|
@@ -13081,18 +13143,17 @@ ${validBossNames.join("、")}`;
|
|
|
13081
13143
|
return "查询BOSS权重时发生错误,请检查服务器日志";
|
|
13082
13144
|
}
|
|
13083
13145
|
});
|
|
13084
|
-
|
|
13085
|
-
|
|
13086
|
-
return `
|
|
13146
|
+
ctx.command("ggcevo/签到奖励").action(({}) => {
|
|
13147
|
+
return `
|
|
13087
13148
|
签到金币奖励:
|
|
13088
13149
|
每天获得50-100金币
|
|
13089
13150
|
--------------
|
|
13090
13151
|
签到红晶奖励(辛迪加财务经理职业加成):
|
|
13091
13152
|
每天签到获得5枚红晶
|
|
13092
13153
|
`.trim();
|
|
13093
|
-
|
|
13094
|
-
|
|
13095
|
-
|
|
13154
|
+
});
|
|
13155
|
+
ctx.command("ggcevo/pk规则").action(({}) => {
|
|
13156
|
+
return `
|
|
13096
13157
|
⚔️【全新PK规则】⚔️
|
|
13097
13158
|
1️⃣ 阵营限制
|
|
13098
13159
|
仅限「人类联盟」与「辛迪加海盗」成员参与PK
|
|
@@ -13138,9 +13199,9 @@ PK同玩家限战:1次/日
|
|
|
13138
13199
|
清洁工,辛迪加财务经理,计算机专家,指挥官,装甲兵,破坏者,征募官:+3000
|
|
13139
13200
|
能量武器专家,枪手,猩红杀手,纵火狂:+4000
|
|
13140
13201
|
`.trim();
|
|
13141
|
-
|
|
13142
|
-
|
|
13143
|
-
|
|
13202
|
+
});
|
|
13203
|
+
ctx.command("ggcevo/击败奖励").alias("击杀奖励").action(({}) => {
|
|
13204
|
+
return `
|
|
13144
13205
|
🌟 异形主宰击败奖励规则 🌟
|
|
13145
13206
|
🏆 伤害榜奖励(按伤害排名):
|
|
13146
13207
|
1️⃣ 第1名:
|
|
@@ -13165,9 +13226,9 @@ PK同玩家限战:1次/日
|
|
|
13165
13226
|
2. 精灵双倍祈愿可通过“祈愿”指令概率获得
|
|
13166
13227
|
3. 排名根据实际造成伤害计算
|
|
13167
13228
|
`.trim();
|
|
13168
|
-
|
|
13169
|
-
|
|
13170
|
-
|
|
13229
|
+
});
|
|
13230
|
+
ctx.command("ggcevo/祈愿系统").action(({}) => {
|
|
13231
|
+
return `
|
|
13171
13232
|
🎋 祈愿系统
|
|
13172
13233
|
祈愿是连接星界的神秘仪式,消耗50金币可换取随机祈愿效果!通过智慧与运气的交织,助你在咕咕之战路上突破瓶颈。效果持续7天 ,冷却期间无法再次祈愿。
|
|
13173
13234
|
|
|
@@ -13185,9 +13246,9 @@ PK同玩家限战:1次/日
|
|
|
13185
13246
|
🎵 暴击韵律:攻击暴击率提高20%
|
|
13186
13247
|
⚠️ 酥手空空:立即失去50枚金币(可触发彩蛋)
|
|
13187
13248
|
`.trim();
|
|
13188
|
-
|
|
13189
|
-
|
|
13190
|
-
|
|
13249
|
+
});
|
|
13250
|
+
ctx.command("ggcevo/赛季奖励").alias("排名奖励").action(({}) => {
|
|
13251
|
+
return `
|
|
13191
13252
|
🏆 赛季排名奖励规则:
|
|
13192
13253
|
🥇 第1名:
|
|
13193
13254
|
100 咕咕币 + 🥇 赛季冠军勋章
|
|
@@ -13213,6 +13274,238 @@ PK同玩家限战:1次/日
|
|
|
13213
13274
|
2. 勋章可通过背包查看
|
|
13214
13275
|
3. 每个赛季持续2个月,可通过“胜点榜”指令查看
|
|
13215
13276
|
`.trim();
|
|
13277
|
+
});
|
|
13278
|
+
}
|
|
13279
|
+
ctx.command("roulette/创建轮盘 <items:text>", "创建轮盘(用逗号分隔选项)", { authority: 3 }).action(async ({ session }, items) => {
|
|
13280
|
+
if (!items) return "请输入轮盘选项,用逗号分隔。\n示例:roulette/创建轮盘 选项1,选项2,选项3";
|
|
13281
|
+
const itemsArray = items.split(",").map((item) => item.trim()).filter((item) => item);
|
|
13282
|
+
if (itemsArray.length === 0) return "至少需要一个有效的选项";
|
|
13283
|
+
try {
|
|
13284
|
+
const roulette = await ctx.model.create("roulettes", {
|
|
13285
|
+
items: itemsArray
|
|
13286
|
+
});
|
|
13287
|
+
return `轮盘创建成功!ID: ${roulette.id}
|
|
13288
|
+
包含选项:${itemsArray.join("、")}`;
|
|
13289
|
+
} catch (error) {
|
|
13290
|
+
return "创建轮盘失败:" + error.message;
|
|
13291
|
+
}
|
|
13292
|
+
});
|
|
13293
|
+
ctx.command("roulette/轮盘列表 [page:number]", "查看轮盘列表").option("group", "-g 查看轮盘组列表").action(async ({ session, options }, page = 1) => {
|
|
13294
|
+
const pageSize = 10;
|
|
13295
|
+
if (options.group) {
|
|
13296
|
+
const groups = await ctx.model.get("roulette_groups", {});
|
|
13297
|
+
const total = groups.length;
|
|
13298
|
+
const start = (page - 1) * pageSize;
|
|
13299
|
+
const end = start + pageSize;
|
|
13300
|
+
const pagedGroups = groups.slice(start, end);
|
|
13301
|
+
if (pagedGroups.length === 0) {
|
|
13302
|
+
return "暂无轮盘组";
|
|
13303
|
+
}
|
|
13304
|
+
let message = "轮盘组列表:\n";
|
|
13305
|
+
pagedGroups.forEach((group) => {
|
|
13306
|
+
message += `ID: ${group.id} | 名称: ${group.name} | 包含轮盘数: ${group.items.length}
|
|
13307
|
+
`;
|
|
13308
|
+
});
|
|
13309
|
+
message += `
|
|
13310
|
+
第${page}页,共${Math.ceil(total / pageSize)}页`;
|
|
13311
|
+
return message;
|
|
13312
|
+
} else {
|
|
13313
|
+
const roulettes = await ctx.model.get("roulettes", {});
|
|
13314
|
+
const total = roulettes.length;
|
|
13315
|
+
const start = (page - 1) * pageSize;
|
|
13316
|
+
const end = start + pageSize;
|
|
13317
|
+
const pagedRoulettes = roulettes.slice(start, end);
|
|
13318
|
+
if (pagedRoulettes.length === 0) {
|
|
13319
|
+
return "暂无轮盘";
|
|
13320
|
+
}
|
|
13321
|
+
let message = "轮盘列表:\n";
|
|
13322
|
+
pagedRoulettes.forEach((roulette) => {
|
|
13323
|
+
message += `ID: ${roulette.id} | 选项数: ${roulette.items.length}
|
|
13324
|
+
`;
|
|
13325
|
+
message += `选项: ${roulette.items.join("、")}
|
|
13326
|
+
|
|
13327
|
+
`;
|
|
13328
|
+
});
|
|
13329
|
+
message += `第${page}页,共${Math.ceil(total / pageSize)}页`;
|
|
13330
|
+
return message;
|
|
13331
|
+
}
|
|
13332
|
+
});
|
|
13333
|
+
ctx.command("roulette/创建轮盘组 <name> <rouletteIds:text>", "创建轮盘组(轮盘ID用逗号分隔)", { authority: 3 }).action(async ({ session }, name2, rouletteIds) => {
|
|
13334
|
+
if (!name2) return "请输入轮盘组名称";
|
|
13335
|
+
if (!rouletteIds) return "请输入轮盘ID,用逗号分隔";
|
|
13336
|
+
const ids = rouletteIds.split(",").map((id) => parseInt(id.trim())).filter((id) => !isNaN(id));
|
|
13337
|
+
if (ids.length === 0) return "至少需要一个有效的轮盘ID";
|
|
13338
|
+
for (const id of ids) {
|
|
13339
|
+
const roulette = await ctx.model.get("roulettes", { id });
|
|
13340
|
+
if (!roulette || roulette.length === 0) {
|
|
13341
|
+
return `轮盘 ID ${id} 不存在`;
|
|
13342
|
+
}
|
|
13343
|
+
}
|
|
13344
|
+
try {
|
|
13345
|
+
const existingGroup = await ctx.model.get("roulette_groups", { name: name2 });
|
|
13346
|
+
if (existingGroup && existingGroup.length > 0) {
|
|
13347
|
+
return "轮盘组名称已存在";
|
|
13348
|
+
}
|
|
13349
|
+
const group = await ctx.model.create("roulette_groups", {
|
|
13350
|
+
name: name2,
|
|
13351
|
+
items: ids
|
|
13352
|
+
});
|
|
13353
|
+
return `轮盘组创建成功!
|
|
13354
|
+
名称: ${group.name}
|
|
13355
|
+
ID: ${group.id}
|
|
13356
|
+
包含轮盘: ${ids.join("、")}`;
|
|
13357
|
+
} catch (error) {
|
|
13358
|
+
return "创建轮盘组失败:" + error.message;
|
|
13359
|
+
}
|
|
13360
|
+
});
|
|
13361
|
+
ctx.command("roulette/轮盘抽奖 <target>", "抽奖(输入轮盘ID或轮盘组名称)").option("count", "-c <count:number> 抽奖次数,默认1次", { fallback: 1 }).action(async ({ session, options }, target) => {
|
|
13362
|
+
if (!target) return "请输入轮盘ID(数字)或轮盘组名称(中文)";
|
|
13363
|
+
const count = Math.min(Math.max(1, options.count || 1), 10);
|
|
13364
|
+
const isNumeric = /^\d+$/.test(target);
|
|
13365
|
+
if (isNumeric) {
|
|
13366
|
+
const roulette = await ctx.model.get("roulettes", { id: parseInt(target) });
|
|
13367
|
+
if (!roulette || roulette.length === 0) {
|
|
13368
|
+
return `轮盘 ID ${target} 不存在`;
|
|
13369
|
+
}
|
|
13370
|
+
const items = roulette[0].items;
|
|
13371
|
+
if (items.length === 0) {
|
|
13372
|
+
return "该轮盘没有可抽奖的选项";
|
|
13373
|
+
}
|
|
13374
|
+
const results = [];
|
|
13375
|
+
for (let i = 0; i < count; i++) {
|
|
13376
|
+
const randomIndex = Math.floor(Math.random() * items.length);
|
|
13377
|
+
results.push(items[randomIndex]);
|
|
13378
|
+
}
|
|
13379
|
+
let message = `轮盘 ID: ${target}
|
|
13380
|
+
抽奖结果:
|
|
13381
|
+
`;
|
|
13382
|
+
if (count === 1) {
|
|
13383
|
+
message += `🎉 ${results[0]} 🎉`;
|
|
13384
|
+
} else {
|
|
13385
|
+
results.forEach((result, index) => {
|
|
13386
|
+
message += `${index + 1}. ${result}
|
|
13387
|
+
`;
|
|
13388
|
+
});
|
|
13389
|
+
}
|
|
13390
|
+
return message;
|
|
13391
|
+
} else {
|
|
13392
|
+
const group = await ctx.model.get("roulette_groups", { name: target });
|
|
13393
|
+
if (!group || group.length === 0) {
|
|
13394
|
+
return `轮盘组 "${target}" 不存在`;
|
|
13395
|
+
}
|
|
13396
|
+
const rouletteIds = group[0].items;
|
|
13397
|
+
if (rouletteIds.length === 0) {
|
|
13398
|
+
return "该轮盘组没有可抽奖的轮盘";
|
|
13399
|
+
}
|
|
13400
|
+
const randomRouletteId = rouletteIds[Math.floor(Math.random() * rouletteIds.length)];
|
|
13401
|
+
const roulette = await ctx.model.get("roulettes", { id: randomRouletteId });
|
|
13402
|
+
if (!roulette || roulette.length === 0) {
|
|
13403
|
+
return "轮盘组中的某个轮盘已不存在";
|
|
13404
|
+
}
|
|
13405
|
+
const items = roulette[0].items;
|
|
13406
|
+
if (items.length === 0) {
|
|
13407
|
+
return "选中的轮盘没有可抽奖的选项";
|
|
13408
|
+
}
|
|
13409
|
+
const results = [];
|
|
13410
|
+
for (let i = 0; i < count; i++) {
|
|
13411
|
+
const randomIndex = Math.floor(Math.random() * items.length);
|
|
13412
|
+
results.push(items[randomIndex]);
|
|
13413
|
+
}
|
|
13414
|
+
let message = `轮盘组: ${target}
|
|
13415
|
+
(从轮盘 ID: ${randomRouletteId} 中抽取)
|
|
13416
|
+
抽奖结果:
|
|
13417
|
+
`;
|
|
13418
|
+
if (count === 1) {
|
|
13419
|
+
message += `🎉 ${results[0]} 🎉`;
|
|
13420
|
+
} else {
|
|
13421
|
+
results.forEach((result, index) => {
|
|
13422
|
+
message += `${index + 1}. ${result}
|
|
13423
|
+
`;
|
|
13424
|
+
});
|
|
13425
|
+
}
|
|
13426
|
+
return message;
|
|
13427
|
+
}
|
|
13428
|
+
});
|
|
13429
|
+
ctx.command("roulette/删除轮盘 <id:number>", "删除轮盘", { authority: 3 }).option("group", "-g 删除轮盘组").action(async ({ session, options }, id) => {
|
|
13430
|
+
if (!id) return "请输入要删除的ID";
|
|
13431
|
+
if (options.group) {
|
|
13432
|
+
const deleted = await ctx.model.remove("roulette_groups", { id });
|
|
13433
|
+
if (deleted) {
|
|
13434
|
+
return "轮盘组删除成功";
|
|
13435
|
+
} else {
|
|
13436
|
+
return "轮盘组不存在";
|
|
13437
|
+
}
|
|
13438
|
+
} else {
|
|
13439
|
+
const deleted = await ctx.model.remove("roulettes", { id });
|
|
13440
|
+
if (deleted) {
|
|
13441
|
+
return "轮盘删除成功";
|
|
13442
|
+
} else {
|
|
13443
|
+
return "轮盘不存在";
|
|
13444
|
+
}
|
|
13445
|
+
}
|
|
13446
|
+
});
|
|
13447
|
+
ctx.command("roulette/轮盘详情 <target>", "查看轮盘或轮盘组详情").action(async ({ session }, target) => {
|
|
13448
|
+
if (!target) return "请输入轮盘ID(数字)或轮盘组名称(中文)";
|
|
13449
|
+
const isNumeric = /^\d+$/.test(target);
|
|
13450
|
+
if (isNumeric) {
|
|
13451
|
+
const roulette = await ctx.model.get("roulettes", { id: parseInt(target) });
|
|
13452
|
+
if (!roulette || roulette.length === 0) {
|
|
13453
|
+
return `轮盘 ID ${target} 不存在`;
|
|
13454
|
+
}
|
|
13455
|
+
const data = roulette[0];
|
|
13456
|
+
return `轮盘 ID: ${data.id}
|
|
13457
|
+
选项数: ${data.items.length}
|
|
13458
|
+
选项列表:
|
|
13459
|
+
${data.items.map((item, index) => `${index + 1}. ${item}`).join("\n")}`;
|
|
13460
|
+
} else {
|
|
13461
|
+
const group = await ctx.model.get("roulette_groups", { name: target });
|
|
13462
|
+
if (!group || group.length === 0) {
|
|
13463
|
+
return `轮盘组 "${target}" 不存在`;
|
|
13464
|
+
}
|
|
13465
|
+
const data = group[0];
|
|
13466
|
+
let roulettesInfo = "";
|
|
13467
|
+
for (const rouletteId of data.items) {
|
|
13468
|
+
const roulette = await ctx.model.get("roulettes", { id: rouletteId });
|
|
13469
|
+
if (roulette && roulette.length > 0) {
|
|
13470
|
+
roulettesInfo += `
|
|
13471
|
+
- 轮盘 ID ${rouletteId}: ${roulette[0].items.length} 个选项`;
|
|
13472
|
+
} else {
|
|
13473
|
+
roulettesInfo += `
|
|
13474
|
+
- 轮盘 ID ${rouletteId}: 已删除`;
|
|
13475
|
+
}
|
|
13476
|
+
}
|
|
13477
|
+
return `轮盘组: ${data.name}
|
|
13478
|
+
ID: ${data.id}
|
|
13479
|
+
包含轮盘数: ${data.items.length}
|
|
13480
|
+
轮盘列表:${roulettesInfo}`;
|
|
13481
|
+
}
|
|
13482
|
+
});
|
|
13483
|
+
ctx.command("roulette/批量轮盘抽奖 <ids:text>", "从多个轮盘中各抽一次奖(ID用逗号分隔)").action(async ({ session }, idsText) => {
|
|
13484
|
+
if (!idsText) return "请输入轮盘ID,用逗号分隔\n示例:roulette/multi 1,3,5";
|
|
13485
|
+
const ids = idsText.split(",").map((id) => parseInt(id.trim())).filter((id) => !isNaN(id));
|
|
13486
|
+
if (ids.length === 0) return "请输入有效的轮盘ID";
|
|
13487
|
+
let message = "批量抽奖结果:\n\n";
|
|
13488
|
+
for (const id of ids) {
|
|
13489
|
+
const roulette = await ctx.model.get("roulettes", { id });
|
|
13490
|
+
if (!roulette || roulette.length === 0) {
|
|
13491
|
+
message += `轮盘 ID ${id}: 不存在
|
|
13492
|
+
|
|
13493
|
+
`;
|
|
13494
|
+
continue;
|
|
13495
|
+
}
|
|
13496
|
+
const items = roulette[0].items;
|
|
13497
|
+
if (items.length === 0) {
|
|
13498
|
+
message += `轮盘 ID ${id}: 无选项
|
|
13499
|
+
|
|
13500
|
+
`;
|
|
13501
|
+
continue;
|
|
13502
|
+
}
|
|
13503
|
+
const randomIndex = Math.floor(Math.random() * items.length);
|
|
13504
|
+
message += `轮盘 ID ${id}: ${items[randomIndex]}
|
|
13505
|
+
|
|
13506
|
+
`;
|
|
13507
|
+
}
|
|
13508
|
+
return message;
|
|
13216
13509
|
});
|
|
13217
13510
|
}
|
|
13218
13511
|
__name(apply, "apply");
|