/// <reference types="node" />
import type { DemonData, PersonaData } from './dataTypes.js';
import { AnySkill } from './skill.js';
import type { AnyGame, Arcana, DemonAffinities, DemonAlignment, DemonOrigin, DemonResistances, DemonSkill, DemonStats, If, PersonaGame, PersonaRace, SMTRace, Stage } from './types.js';
export type AnyDemon = Demon<true> | Demon<false>;
export declare class Demon<PersonaBased extends boolean = boolean> implements DemonData<PersonaBased> {
    /** The demon's name */
    name: string;
    /** The demon's alternative names */
    aliases: string[];
    /** The demon's normalized name used for matching queries */
    devName: string;
    /** The demon's skill potential and inherit affinity */
    affinities: DemonAffinities<PersonaBased>;
    /** The demon's Arcana in Persona titles, or null if unknown */
    arcana: If<PersonaBased, Arcana, Arcana | null>;
    /** The demon's race in mainline Shin Megami Tensei titles, or null if unknown */
    race: If<PersonaBased, PersonaRace, SMTRace | null>;
    /** The demon's initial level */
    level: number;
    /** The demon's initial HP */
    hp: If<PersonaBased, null, number | null>;
    /** The demon's initial MP/SP */
    mp: If<PersonaBased, null, number | null>;
    /** The demon's initial stats */
    stats: DemonStats;
    /** The skills that the demon learns via leveling up */
    learnset: DemonSkill[];
    /** The demon's ailment and affinity resistances */
    resistances: DemonResistances<PersonaBased>;
    /** The game that the demon's data originates from */
    game: If<PersonaBased, PersonaGame, AnyGame>;
    /** The demon's moral and ethical alignment */
    alignment: If<PersonaBased, null, DemonAlignment>;
    /** The demon's backstory, or null for older Personas */
    lore: If<PersonaBased, string | null, string>;
    /** The demon's mythological origin */
    origin: DemonOrigin;
    constructor(data: DemonData<PersonaBased>);
    /** Asynchronously gets an image of the demon */
    getImage(): Promise<Buffer>;
    /** Whether the demon is a Persona instance */
    isPersona(): this is Persona;
    /** Whether the demon is exclusive to Persona games */
    isPersonaBased(): this is Demon<true>;
    /** Returns a string in "(Race) (Name)" format, or the name if the race is unknown */
    toString(): string;
    /** An image of the demon */
    get image(): Buffer;
    /** An array of every Demon and Persona instance */
    static array: readonly AnyDemon[];
    /** A map of every Demon and Persona instance, keyed by their devName properties */
    static map: Map<string, AnyDemon>;
    /**
     *
     * Gets a Demon instance by its name.
     * @example
     * ```ts
     * const demon1 = Demon.get('Jack Frost', true); // Type: Demon
     * console.log(demon1); // Demon { ... }
     *
     * const demon2 = Demon.get('Kazuma Kaneko'); // Type: Demon | null
     * console.log(demon2); // null
     *
     * const demon3 = Demon.get('Masayuki Doi', true); // Type: Demon; Throws a MegatenError
     * ```
     *
     * @param name - The demon's name
     * @param error - Whether to throw an exception instead of returning null if no demon is found; defaults to false
     */
    static get(name: string, error: true): AnyDemon;
    static get(name: string, error?: boolean): AnyDemon | null;
}
export declare class Persona extends Demon<true> implements PersonaData {
    affinities: DemonAffinities<true>;
    arcana: Arcana;
    race: 'Persona';
    hp: null;
    mp: null;
    resistances: DemonResistances<true>;
    game: PersonaGame;
    moral: null;
    ethical: null;
    /** The Persona's user */
    user: string;
    /** The Persona's stage of evolution */
    stage: Stage;
    /** The name of the skill that the Persona will learn upon reaching this stage, or null if none */
    evoSkillName: string | null;
    /** The Skill instance that the Persona will learn upon reaching this stage, or null if none */
    evoSkill: AnySkill | null;
    constructor(data: PersonaData);
    /** The Persona that this Persona can evolve into, or null if none */
    get evolution(): Persona | null;
    /**
     * Returns a string in "(User)'s (Name)" format
     */
    toString(): string;
    /** An array of every Persona instance */
    static array: readonly Persona[];
    /** A map of every Persona instance, keyed by their devName properties */
    static map: Map<string, Persona>;
    /**
     *
     * Gets a Persona instance by its name.
     * @example
     * ```ts
     * const persona1 = Persona.get('Arsene', true); // Type: Persona
     * console.log(persona1); // Persona { ... }
     *
     * const persona2 = Persona.get('Jack Frost'); // Type: Persona | null
     * console.log(persona2); // null
     *
     * const persona3 = Persona.get('Shigenori Soejima', true); // Type: Persona; Throws a MegatenError
     * ```
     *
     * @param name - The Persona's name
     * @param error - Whether to throw an exception instead of returning null if no Persona is found; defaults to false
     */
    static get(name: string, error: true): Persona;
    static get(name: string, error?: boolean): Persona | null;
}
