mirror of
https://github.com/blitzkit/blitzkit.git
synced 2026-10-21 02:37:05 +02:00
feat: added all buttons to dynamic commands
This commit is contained in:
1 parent
dd39563d6d
commit
d1d8aad6c7
9 files changed
+157
-57
No files matched your search
+50
-15
@@ -1,17 +1,26 @@
|
||||
import { SlashCommandBuilder } from 'discord.js';
|
||||
import { CYCLIC_API } from '../constants/cyclic.js';
|
||||
import getWargamingResponse from '../core/blitz/getWargamingResponse.js';
|
||||
import resolveTankId from '../core/blitz/resolveTankId.js';
|
||||
import addStatTypeSubCommandGroups from '../core/discord/addStatTypeSubCommandGroups.js';
|
||||
import autocompleteTanks from '../core/discord/autocompleteTanks.js';
|
||||
import autocompleteUsername from '../core/discord/autocompleteUsername.js';
|
||||
import interactionToURL from '../core/discord/interactionToURL.js';
|
||||
import linkButton from '../core/discord/linkButton.js';
|
||||
import primaryButton from '../core/discord/primaryButton.js';
|
||||
import resolvePeriodFromButton from '../core/discord/resolvePeriodFromButton.js';
|
||||
import resolvePeriodFromCommand from '../core/discord/resolvePeriodFromCommand.js';
|
||||
import resolvePlayerFromButton from '../core/discord/resolvePlayerFromButton.js';
|
||||
import resolvePlayerFromCommand from '../core/discord/resolvePlayerFromCommand.js';
|
||||
import { WARGAMING_APPLICATION_ID } from '../core/node/arguments.js';
|
||||
import { CommandRegistry } from '../events/interactionCreate/index.js';
|
||||
import evolution from '../renderers/evolution.js';
|
||||
import { StatType } from '../renderers/statsfull.js';
|
||||
import { AccountInfo } from '../types/accountInfo.js';
|
||||
|
||||
export default {
|
||||
inProduction: true,
|
||||
inDevelopment: false,
|
||||
inDevelopment: true,
|
||||
inPublic: true,
|
||||
|
||||
command: addStatTypeSubCommandGroups(
|
||||
@@ -27,25 +36,51 @@ export default {
|
||||
const player = await resolvePlayerFromCommand(interaction);
|
||||
const period = resolvePeriodFromCommand(interaction);
|
||||
const tankIdRaw = interaction.options.getString('tank')!;
|
||||
const tankId = commandGroup === 'tank' ? resolveTankId(tankIdRaw) : 0;
|
||||
const tankId = commandGroup === 'tank' ? resolveTankId(tankIdRaw) : null;
|
||||
const start = interaction.options.getInteger('start');
|
||||
const end = interaction.options.getInteger('end');
|
||||
const { nickname } = (
|
||||
await getWargamingResponse<AccountInfo>(
|
||||
`https://api.wotblitz.${player.server}/wotb/account/info/?application_id=${WARGAMING_APPLICATION_ID}&account_id=${player.id}`,
|
||||
)
|
||||
)[player.id];
|
||||
const path = interactionToURL(interaction, {
|
||||
...player,
|
||||
tankId,
|
||||
start,
|
||||
end,
|
||||
});
|
||||
|
||||
return await evolution(commandGroup, period, player, tankId);
|
||||
|
||||
// TODO: implement this
|
||||
// new ButtonBuilder()
|
||||
// .setStyle(ButtonStyle.Link)
|
||||
// .setLabel('View on BlitzStars')
|
||||
// .setURL(
|
||||
// commandGroup === 'tank'
|
||||
// ? `https://www.blitzstars.com/player/com/${
|
||||
// accountInfo[id].nickname
|
||||
// }/tank/${tankId!}`
|
||||
// : `https://www.blitzstars.com/player/com/${accountInfo[id].nickname}`,
|
||||
// );
|
||||
return [
|
||||
await evolution(commandGroup, period, player, tankId),
|
||||
primaryButton(path, 'Refresh'),
|
||||
linkButton(`${CYCLIC_API}/${path}`, 'Embed'),
|
||||
linkButton(
|
||||
`https://www.blitzstars.com/player/${player.server}/${nickname}${
|
||||
commandGroup === 'tank' ? `/tank/${tankId!}` : ''
|
||||
}`,
|
||||
'BlitzStars',
|
||||
),
|
||||
];
|
||||
},
|
||||
|
||||
autocomplete: (interaction) => {
|
||||
autocompleteUsername(interaction);
|
||||
autocompleteTanks(interaction);
|
||||
},
|
||||
|
||||
async button(interaction) {
|
||||
const url = new URL(`${CYCLIC_API}/${interaction.customId}`);
|
||||
const path = url.pathname.split('/').filter(Boolean);
|
||||
const commandGroup = path[1] as StatType;
|
||||
const period = resolvePeriodFromButton(interaction);
|
||||
const player = await resolvePlayerFromButton(interaction);
|
||||
|
||||
return await evolution(
|
||||
commandGroup,
|
||||
period,
|
||||
player,
|
||||
parseInt(url.searchParams.get('tankId')!),
|
||||
);
|
||||
},
|
||||
} satisfies CommandRegistry;
|
||||
+21
-9
@@ -1,19 +1,22 @@
|
||||
import { SlashCommandBuilder } from 'discord.js';
|
||||
import { CYCLIC_API } from '../constants/cyclic.js';
|
||||
import getWargamingResponse from '../core/blitz/getWargamingResponse.js';
|
||||
import resolveTankId from '../core/blitz/resolveTankId.js';
|
||||
import { Period } from '../core/discord/addPeriodSubCommands.js';
|
||||
import addStatTypeSubCommandGroups from '../core/discord/addStatTypeSubCommandGroups.js';
|
||||
import autocompleteTanks from '../core/discord/autocompleteTanks.js';
|
||||
import autocompleteUsername from '../core/discord/autocompleteUsername.js';
|
||||
import interactionToURL from '../core/discord/interactionToURL.js';
|
||||
import linkButton from '../core/discord/linkButton.js';
|
||||
import primaryButton from '../core/discord/primaryButton.js';
|
||||
import resolvePeriodFromButton from '../core/discord/resolvePeriodFromButton.js';
|
||||
import resolvePeriodFromCommand from '../core/discord/resolvePeriodFromCommand.js';
|
||||
import resolvePlayerFromButton from '../core/discord/resolvePlayerFromButton.js';
|
||||
import resolvePlayerFromCommand from '../core/discord/resolvePlayerFromCommand.js';
|
||||
import { WARGAMING_APPLICATION_ID } from '../core/node/arguments.js';
|
||||
import { CommandRegistry } from '../events/interactionCreate/index.js';
|
||||
import stats from '../renderers/stats.js';
|
||||
import { StatType } from '../renderers/statsfull.js';
|
||||
import { AccountInfo } from '../types/accountInfo.js';
|
||||
|
||||
export default {
|
||||
inProduction: true,
|
||||
@@ -30,23 +33,32 @@ export default {
|
||||
const commandGroup = interaction.options.getSubcommandGroup(
|
||||
true,
|
||||
) as StatType;
|
||||
const subcommand = interaction.options.getSubcommand() as Period;
|
||||
const player = await resolvePlayerFromCommand(interaction);
|
||||
const period = resolvePeriodFromCommand(interaction);
|
||||
const tankIdRaw = interaction.options.getString('tank')!;
|
||||
const tankId = commandGroup === 'tank' ? resolveTankId(tankIdRaw) : 0;
|
||||
const tankId = commandGroup === 'tank' ? resolveTankId(tankIdRaw) : null;
|
||||
const start = interaction.options.getInteger('start');
|
||||
const end = interaction.options.getInteger('end');
|
||||
const path = `stats/${commandGroup}/${subcommand}?server=${
|
||||
player.server
|
||||
}&id=${player.id}&tankId=${tankId}&start=${start ?? 0}&end=${end ?? 0}`;
|
||||
|
||||
// interactionToURL(interaction);
|
||||
const path = interactionToURL(interaction, {
|
||||
...player,
|
||||
tankId,
|
||||
start,
|
||||
end,
|
||||
});
|
||||
const { nickname } = (
|
||||
await getWargamingResponse<AccountInfo>(
|
||||
`https://api.wotblitz.${player.server}/wotb/account/info/?application_id=${WARGAMING_APPLICATION_ID}&account_id=${player.id}`,
|
||||
)
|
||||
)[player.id];
|
||||
|
||||
return [
|
||||
await stats(commandGroup, period, player, tankId),
|
||||
primaryButton(path, 'Refresh'),
|
||||
linkButton(path, 'Embed'),
|
||||
linkButton(`${CYCLIC_API}/${path}`, 'Embed'),
|
||||
linkButton(
|
||||
`https://www.blitzstars.com/player/${player.server}/${nickname}`,
|
||||
'BlitzStars',
|
||||
),
|
||||
];
|
||||
},
|
||||
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
import { SlashCommandBuilder } from 'discord.js';
|
||||
import { CYCLIC_API } from '../constants/cyclic.js';
|
||||
import getWargamingResponse from '../core/blitz/getWargamingResponse.js';
|
||||
import resolveTankId from '../core/blitz/resolveTankId.js';
|
||||
import { Period } from '../core/discord/addPeriodSubCommands.js';
|
||||
import addStatTypeSubCommandGroups from '../core/discord/addStatTypeSubCommandGroups.js';
|
||||
import autocompleteTanks from '../core/discord/autocompleteTanks.js';
|
||||
import autocompleteUsername from '../core/discord/autocompleteUsername.js';
|
||||
@@ -12,8 +12,10 @@ import resolvePeriodFromButton from '../core/discord/resolvePeriodFromButton.js'
|
||||
import resolvePeriodFromCommand from '../core/discord/resolvePeriodFromCommand.js';
|
||||
import resolvePlayerFromButton from '../core/discord/resolvePlayerFromButton.js';
|
||||
import resolvePlayerFromCommand from '../core/discord/resolvePlayerFromCommand.js';
|
||||
import { WARGAMING_APPLICATION_ID } from '../core/node/arguments.js';
|
||||
import { CommandRegistry } from '../events/interactionCreate/index.js';
|
||||
import statsfull, { StatType } from '../renderers/statsfull.js';
|
||||
import { AccountInfo } from '../types/accountInfo.js';
|
||||
|
||||
export default {
|
||||
inProduction: true,
|
||||
@@ -30,23 +32,32 @@ export default {
|
||||
const commandGroup = interaction.options.getSubcommandGroup(
|
||||
true,
|
||||
) as StatType;
|
||||
const subcommand = interaction.options.getSubcommand() as Period;
|
||||
const player = await resolvePlayerFromCommand(interaction);
|
||||
const period = resolvePeriodFromCommand(interaction);
|
||||
const tankIdRaw = interaction.options.getString('tank')!;
|
||||
const tankId = commandGroup === 'tank' ? resolveTankId(tankIdRaw) : 0;
|
||||
const start = interaction.options.getInteger('start');
|
||||
const end = interaction.options.getInteger('end');
|
||||
const path = `statsfull/${commandGroup}/${subcommand}?server=${
|
||||
player.server
|
||||
}&id=${player.id}&tankId=${tankId}&start=${start ?? 0}&end=${end ?? 0}`;
|
||||
|
||||
interactionToURL(interaction);
|
||||
const path = interactionToURL(interaction, {
|
||||
...player,
|
||||
tankId,
|
||||
start,
|
||||
end,
|
||||
});
|
||||
const { nickname } = (
|
||||
await getWargamingResponse<AccountInfo>(
|
||||
`https://api.wotblitz.${player.server}/wotb/account/info/?application_id=${WARGAMING_APPLICATION_ID}&account_id=${player.id}`,
|
||||
)
|
||||
)[player.id];
|
||||
|
||||
return [
|
||||
await statsfull(commandGroup, period, player, tankId),
|
||||
primaryButton(path, 'Refresh'),
|
||||
linkButton(path, 'Embed'),
|
||||
linkButton(`${CYCLIC_API}/${path}`, 'Embed'),
|
||||
linkButton(
|
||||
`https://www.blitzstars.com/player/${player.server}/${nickname}`,
|
||||
'BlitzStars',
|
||||
),
|
||||
];
|
||||
},
|
||||
|
||||
|
||||
+30
-2
@@ -1,13 +1,21 @@
|
||||
import { SlashCommandBuilder } from 'discord.js';
|
||||
import { CYCLIC_API } from '../constants/cyclic.js';
|
||||
import getWargamingResponse from '../core/blitz/getWargamingResponse.js';
|
||||
import addUsernameChoices from '../core/discord/addUsernameChoices.js';
|
||||
import autocompleteUsername from '../core/discord/autocompleteUsername.js';
|
||||
import interactionToURL from '../core/discord/interactionToURL.js';
|
||||
import linkButton from '../core/discord/linkButton.js';
|
||||
import primaryButton from '../core/discord/primaryButton.js';
|
||||
import resolvePlayerFromButton from '../core/discord/resolvePlayerFromButton.js';
|
||||
import resolvePlayerFromCommand from '../core/discord/resolvePlayerFromCommand.js';
|
||||
import { WARGAMING_APPLICATION_ID } from '../core/node/arguments.js';
|
||||
import { CommandRegistry } from '../events/interactionCreate/index.js';
|
||||
import today from '../renderers/today.js';
|
||||
import { AccountInfo } from '../types/accountInfo.js';
|
||||
|
||||
export default {
|
||||
inProduction: true,
|
||||
inDevelopment: false,
|
||||
inDevelopment: true,
|
||||
inPublic: true,
|
||||
|
||||
command: new SlashCommandBuilder()
|
||||
@@ -17,9 +25,29 @@ export default {
|
||||
|
||||
async handler(interaction) {
|
||||
const player = await resolvePlayerFromCommand(interaction);
|
||||
const { nickname } = (
|
||||
await getWargamingResponse<AccountInfo>(
|
||||
`https://api.wotblitz.${player.server}/wotb/account/info/?application_id=${WARGAMING_APPLICATION_ID}&account_id=${player.id}`,
|
||||
)
|
||||
)[player.id];
|
||||
const path = interactionToURL(interaction, player);
|
||||
|
||||
return await today(player);
|
||||
return [
|
||||
await today(player),
|
||||
primaryButton(path, 'Refresh'),
|
||||
linkButton(`${CYCLIC_API}/${path}`, 'Embed'),
|
||||
linkButton(
|
||||
`https://www.blitzstars.com/player/${player.server}/${nickname}`,
|
||||
'BlitzStars',
|
||||
),
|
||||
];
|
||||
},
|
||||
|
||||
autocomplete: autocompleteUsername,
|
||||
|
||||
async button(interaction) {
|
||||
const player = await resolvePlayerFromButton(interaction);
|
||||
|
||||
return await today(player);
|
||||
},
|
||||
} satisfies CommandRegistry;
|
||||
@@ -1,20 +1,33 @@
|
||||
import { CacheType, ChatInputCommandInteraction } from 'discord.js';
|
||||
import {
|
||||
CacheType,
|
||||
ChatInputCommandInteraction,
|
||||
CommandInteractionOption,
|
||||
} from 'discord.js';
|
||||
|
||||
export interface Parameters {
|
||||
[key: string]: CommandInteractionOption['value'] | undefined | null;
|
||||
}
|
||||
|
||||
export default function interactionToURL(
|
||||
interaction: ChatInputCommandInteraction<CacheType>,
|
||||
parameters?: Parameters,
|
||||
) {
|
||||
const pathname = [
|
||||
interaction.commandName,
|
||||
interaction.options.getSubcommandGroup(),
|
||||
interaction.options.getSubcommand(),
|
||||
interaction.options.getSubcommandGroup(false),
|
||||
interaction.options.getSubcommand(false),
|
||||
]
|
||||
.filter(Boolean)
|
||||
.join('/');
|
||||
const urlSearchParams = new URLSearchParams();
|
||||
const params = [
|
||||
...interaction.options.data.map(
|
||||
(option) => [option.name, option.value] as const,
|
||||
),
|
||||
...Object.entries(parameters ?? {}),
|
||||
]
|
||||
.filter(([, value]) => value !== undefined && value !== null)
|
||||
.map(([key, value]) => `${key}=${value}`)
|
||||
.join('&');
|
||||
|
||||
interaction.options.data.forEach((option) => {
|
||||
if (option.value) urlSearchParams.set(option.name, `${option.value}`);
|
||||
});
|
||||
|
||||
console.log(`${urlSearchParams}`);
|
||||
return `${pathname}${params.length > 0 ? `?${params}` : ''}`;
|
||||
}
|
||||
@@ -3,16 +3,15 @@ import {
|
||||
ButtonStyle,
|
||||
ComponentEmojiResolvable,
|
||||
} from 'discord.js';
|
||||
import { CYCLIC_API } from '../../constants/cyclic.js';
|
||||
|
||||
export default function linkButton(
|
||||
id: string,
|
||||
url: string,
|
||||
label: string,
|
||||
emoji?: ComponentEmojiResolvable,
|
||||
) {
|
||||
const button = new ButtonBuilder()
|
||||
.setStyle(ButtonStyle.Link)
|
||||
.setURL(`${CYCLIC_API}/${id}`)
|
||||
.setURL(url)
|
||||
.setLabel(label);
|
||||
|
||||
if (emoji) button.setEmoji(emoji);
|
||||
|
||||
@@ -1,11 +1,13 @@
|
||||
import { ButtonInteraction, CacheType } from 'discord.js';
|
||||
import { CYCLIC_API } from '../../../constants/cyclic.js';
|
||||
import normalizeInteractionReturnable from '../../../core/discord/normalizeInteractionReturnable.js';
|
||||
import { commands } from '../index.js';
|
||||
|
||||
export default async function handleButton(
|
||||
interaction: ButtonInteraction<CacheType>,
|
||||
) {
|
||||
const commandName = interaction.customId.split('/')[0];
|
||||
const url = new URL(`${CYCLIC_API}/${interaction.customId}`);
|
||||
const commandName = url.pathname.split('/')[1];
|
||||
const button = commands[commandName]?.button;
|
||||
|
||||
if (!button) {
|
||||
|
||||
@@ -21,7 +21,7 @@ export default async function evolution<Type extends StatType>(
|
||||
type: Type,
|
||||
{ start, end, evolutionName }: ResolvedPeriod,
|
||||
{ server, id }: ResolvedPlayer,
|
||||
tankId: Type extends 'tank' ? number : never,
|
||||
tankId: Type extends 'tank' ? number : null,
|
||||
) {
|
||||
let nameDiscriminator: string | undefined;
|
||||
let image: string | undefined;
|
||||
@@ -38,8 +38,8 @@ export default async function evolution<Type extends StatType>(
|
||||
? `https://wotblitz-gc.gcdn.co/icons/clanEmblems1x/clan-icon-v2-${clan.emblem_set_id}.png`
|
||||
: undefined;
|
||||
} else {
|
||||
nameDiscriminator = `(${resolveTankName(tankId)})`;
|
||||
image = tankopedia[tankId].images.normal;
|
||||
nameDiscriminator = `(${resolveTankName(tankId!)})`;
|
||||
image = tankopedia[tankId!].images.normal;
|
||||
}
|
||||
|
||||
let histories: Histories;
|
||||
@@ -53,7 +53,7 @@ export default async function evolution<Type extends StatType>(
|
||||
});
|
||||
} else {
|
||||
histories = await getTankHistories(server, id, {
|
||||
tankId,
|
||||
tankId: tankId!,
|
||||
start,
|
||||
end,
|
||||
includeLatestHistories: true,
|
||||
|
||||
@@ -28,7 +28,7 @@ export default async function stats<Type extends StatType>(
|
||||
type: Type,
|
||||
{ start, end, statsName }: ResolvedPeriod,
|
||||
{ server, id }: ResolvedPlayer,
|
||||
tankId: Type extends 'tank' ? number : never,
|
||||
tankId: Type extends 'tank' ? number : null,
|
||||
) {
|
||||
let nameDiscriminator: string | undefined;
|
||||
let image: string | undefined;
|
||||
@@ -45,8 +45,8 @@ export default async function stats<Type extends StatType>(
|
||||
? `https://wotblitz-gc.gcdn.co/icons/clanEmblems1x/clan-icon-v2-${clan.emblem_set_id}.png`
|
||||
: undefined;
|
||||
} else if (type === 'tank') {
|
||||
nameDiscriminator = `(${resolveTankName(tankId)})`;
|
||||
image = tankopedia[tankId].images.normal;
|
||||
nameDiscriminator = `(${resolveTankName(tankId!)})`;
|
||||
image = tankopedia[tankId!].images.normal;
|
||||
}
|
||||
|
||||
const tankStats = await getTankStatsDiffed(server, id, start, end);
|
||||
@@ -112,11 +112,11 @@ export default async function stats<Type extends StatType>(
|
||||
{},
|
||||
);
|
||||
} else {
|
||||
stats = tankStats[tankId];
|
||||
stats = tankStats[tankId!];
|
||||
|
||||
supplementaryStats = {
|
||||
WN8: calculateWN8(tankAverages[tankId].all, tankStats[tankId]),
|
||||
tier: tankopedia[tankId].tier,
|
||||
WN8: calculateWN8(tankAverages[tankId!].all, tankStats[tankId!]),
|
||||
tier: tankopedia[tankId!].tier,
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
Reference in new issue
Block a user