83 lines
2.4 KiB
TypeScript
83 lines
2.4 KiB
TypeScript
import { InitHealth, InvincibleUser, ItemInventory, db } from '../db';
|
|
import { DefaultItems, getDefaultItem, giveItem, getItemQuantity, formatItems } from './items';
|
|
import { Client } from 'discord.js';
|
|
|
|
export const BLOOD_ID = -DefaultItems.BLOOD;
|
|
export const BLOOD_ITEM = getDefaultItem(BLOOD_ID);
|
|
export const MAX_HEALTH = BLOOD_ITEM.maxStack;
|
|
const BLOOD_GAIN_PER_HOUR = 2;
|
|
export const INVINCIBLE_TIMER = 1_000 * 60 * 30;
|
|
|
|
export async function initHealth(user: string) {
|
|
const isInitialized = await db<InitHealth>('initHealth')
|
|
.where('user', user)
|
|
.first();
|
|
|
|
if (!isInitialized) {
|
|
giveItem(user, BLOOD_ITEM, MAX_HEALTH);
|
|
await db<InitHealth>('initHealth').insert({ user });
|
|
}
|
|
}
|
|
|
|
export async function getInvincibleMs(user: string) {
|
|
const invincible = await db<InvincibleUser>('invincibleUsers')
|
|
.where('user', user)
|
|
.first();
|
|
|
|
if (!invincible) return 0;
|
|
return Math.max((invincible.since + INVINCIBLE_TIMER) - Date.now(), 0);
|
|
}
|
|
|
|
export async function resetInvincible(user: string) {
|
|
await db<InvincibleUser>('invincibleUsers')
|
|
.where('user', user)
|
|
.delete();
|
|
}
|
|
|
|
export async function applyInvincible(user: string) {
|
|
const exists = await db<InvincibleUser>('invincibleUsers')
|
|
.where('user', user)
|
|
.first();
|
|
|
|
if (exists) {
|
|
await db<InvincibleUser>('invincibleUsers')
|
|
.update({ since: Date.now() });
|
|
} else {
|
|
await db<InvincibleUser>('invincibleUsers')
|
|
.insert({ since: Date.now(), user });
|
|
}
|
|
}
|
|
|
|
export async function getHealth(user: string) {
|
|
await initHealth(user);
|
|
return await getItemQuantity(user, BLOOD_ID);
|
|
}
|
|
|
|
export async function dealDamage(user: string, dmg: number) {
|
|
await initHealth(user);
|
|
await applyInvincible(user);
|
|
return await giveItem(user, BLOOD_ITEM, -dmg);
|
|
}
|
|
|
|
async function healthCron(bot: Client) {
|
|
await db<ItemInventory>('itemInventories')
|
|
.where('item', BLOOD_ID)
|
|
.update({
|
|
quantity: db.raw('MIN(quantity + ?, ?)', [BLOOD_GAIN_PER_HOUR, MAX_HEALTH])
|
|
});
|
|
|
|
const debtedUsers = await db<ItemInventory>('itemInventories')
|
|
.select('user', 'quantity')
|
|
.where('quantity', '<', '0');
|
|
|
|
for (const debted of debtedUsers) {
|
|
const user = await bot.users.fetch(debted.user);
|
|
if (!user) continue;
|
|
await user.send(`${formatItems(BLOOD_ITEM, debted.quantity)} You are bleeding out to death`);
|
|
}
|
|
}
|
|
|
|
export function init(bot: Client) {
|
|
healthCron(bot);
|
|
setInterval(() => healthCron(bot), 1_000 * 60 * 60);
|
|
} |