From f2f20a5ea41e0299b657d869e7b628b5233fb00d Mon Sep 17 00:00:00 2001 From: "Jill \"oatmealine\" Monoids" Date: Sun, 26 Nov 2023 14:37:33 +0300 Subject: [PATCH] make assigning one behavior to multiple types possible --- src/commands/item.ts | 13 ++++++++----- src/lib/rpg/behaviors.ts | 17 +++++++++++------ 2 files changed, 19 insertions(+), 11 deletions(-) diff --git a/src/commands/item.ts b/src/commands/item.ts index 9f97aac..b64219e 100644 --- a/src/commands/item.ts +++ b/src/commands/item.ts @@ -1,6 +1,6 @@ import { AutocompleteInteraction, CommandInteraction, SlashCommandBuilder } from 'discord.js'; import { Counter, CustomCraftingRecipeItem, CustomItem, ItemBehavior, db } from '../lib/db'; -import { customItemAutocomplete, formatItem, formatItems, getCustomItem, getItem, giveItem, isDefaultItem, itemAutocomplete } from '../lib/rpg/items'; +import { Item, customItemAutocomplete, formatItem, formatItems, getCustomItem, getItem, giveItem, isDefaultItem, itemAutocomplete } from '../lib/rpg/items'; import { Command } from '../types/index'; import { formatRecipe, getCustomRecipe } from '../lib/rpg/recipes'; import { behaviors, formatBehavior, getBehavior } from '../lib/rpg/behaviors'; @@ -329,19 +329,22 @@ export default { const focused = interaction.options.getFocused(); let foundBehaviors = behaviors.filter(b => b.name.toLowerCase().includes(focused.toLowerCase())); const itemID = interaction.options.getString('customitem'); + let item: Item | undefined; if (itemID) { - const item = await getItem(parseInt(itemID)); + item = await getItem(parseInt(itemID)); if (item) { - foundBehaviors = foundBehaviors.filter(b => b.type === item.type); + foundBehaviors = foundBehaviors.filter(b => b.types.includes(item!.type)); } } - return foundBehaviors.map(b => ({name: `${b.type}:${b.name} - ${b.description}`, value: b.name})); + return foundBehaviors.map(b => ({name: `${item ? item.type : b.types[0]}:${b.name} - ${b.description}`, value: b.name})); }, removebehavior: async (interaction: AutocompleteInteraction) => { const focused = interaction.options.getFocused(); const itemID = interaction.options.getString('customitem'); if (!itemID) return []; + const item = await getItem(parseInt(itemID)); + if (!item) return []; const behaviors = await db('itemBehaviors') .where('item', itemID); @@ -351,7 +354,7 @@ export default { .filter(b => b.behavior.name.toLowerCase().includes(focused.toLowerCase())); return foundBehaviors.map(b => ({ - name: `${b.behavior.type}:${formatBehavior(b.behavior, b.value)} - ${b.behavior.description}`, + name: `${item.type}:${formatBehavior(b.behavior, b.value)} - ${b.behavior.description}`, value: b.behavior.name })); }, diff --git a/src/lib/rpg/behaviors.ts b/src/lib/rpg/behaviors.ts index fd6dc7b..6c375d8 100644 --- a/src/lib/rpg/behaviors.ts +++ b/src/lib/rpg/behaviors.ts @@ -18,7 +18,7 @@ type AttackContext = ItemContext & { export interface Behavior { name: string, description: string, - type: 'plain' | 'weapon' | 'consumable', + types: ('plain' | 'weapon' | 'consumable')[], // make it look fancy format?: (value?: number) => string, // triggers upon use @@ -37,7 +37,7 @@ export const behaviors: Behavior[] = [ { name: 'heal', description: 'Heals the user by `value`', - type: 'consumable', + types: ['plain', 'consumable'], async onUse(ctx) { if (!ctx.value) return new Right('A value is required for this behavior'); await dealDamage(ctx.user, -Math.floor(ctx.value)); @@ -47,17 +47,22 @@ export const behaviors: Behavior[] = [ { name: 'damage', description: 'Damages the user by `value', - type: 'consumable', + types: ['plain', 'consumable'], async onUse(ctx) { if (!ctx.value) return new Right('A value is required for this behavior'); await dealDamage(ctx.user, Math.floor(ctx.value)); return new Left(`You were damaged by ${formatItems(BLOOD_ITEM, ctx.value)}!`); }, }, + { + name: 'give', + description: 'Give an item of ID `value` to the user', + types: ['plain', 'consumable'], + }, { name: 'random_up', description: 'Randomizes the attack value up by a maximum of `value`', - type: 'weapon', + types: ['weapon'], format: (value) => `random +${value}`, async onAttack(ctx) { if (!ctx.value) return new Right('A value is required for this behavior'); @@ -67,7 +72,7 @@ export const behaviors: Behavior[] = [ { name: 'random_down', description: 'Randomizes the attack value down by a maximum of `value`', - type: 'weapon', + types: ['weapon'], format: (value) => `random -${value}`, async onAttack(ctx) { if (!ctx.value) return new Right('A value is required for this behavior'); @@ -77,7 +82,7 @@ export const behaviors: Behavior[] = [ { name: 'lifesteal', description: 'Gain blood by stabbing your foes, scaled by `value`x', - type: 'weapon', + types: ['weapon'], format: (value) => `lifesteal ${value}x`, async onAttack(ctx) { if (!ctx.value) return new Right('A value is required for this behavior');