/** * Bounty Hunter - repeatable kill contracts handed out at the Bounty Board on the * Crossroads by Bruce. Completing one trains the Bounty Hunter skill (XP is granted * per counted kill, equal to that NPC's normal kill XP) and pays a Small Satchel. * * Tiers are gated by the player's Combat level. Bruce only ever offers the single * highest tier the player has unlocked, so lower-tier targets stop being offered as * the hunter grows (seagull / crab contracts vanish once Combat reaches 8). * * Combat 20-40 is `BOUNTY_TIERS_20_TO_40_PROVISIONAL`; its counts are placeholders for the balance pass. */ import type { NpcKind } from './constants.js'; /** Bounty targets - all reuse an existing NpcKind. */ export type BountyTargetKind = 'seagull' | 'crab' | 'rabbit' | 'fox' | 'hijacker' | 'soldier' | 'goblin' | 'amazon' | 'redcap' | 'redcaparcher' | 'blackwakedeckhand' | 'cutthroat' | 'drowneddeckhand' | 'gravehound' | 'mosswolf' | 'mammoth' | 'mammothbull' | 'polarbear' | 'ironjawogre' | 'mireleech' | 'blacktom' | 'galecrow' | 'chalkburrower' | 'chasmprowler' | 'wasteraider' | 'crook'; /** Compile-time check: every bounty target is a real NpcKind (a typo or a retired kind fails the build). */ type BountyTargetsAreNpcKinds = BountyTargetKind extends NpcKind ? true : never; export declare const BOUNTY_TARGETS_ARE_NPC_KINDS: BountyTargetsAreNpcKinds; /** * Targets that live only inside the Dreadwoods, the PvP zone with no healing in a fight (zones.ts isPvpZone). * A tier never offers one as its only choice: a player who avoids PvP always has an open-country contract too. * The guide and the board label these so nobody takes one by surprise. */ export declare const BOUNTY_PVP_TARGETS: readonly BountyTargetKind[]; /** * Targets that are a single named boss (not a herd): their contract asks for fewer kills than the 5-50 of a band's ordinary quarry, * because the boss returns only every eight to ten minutes (northWilds.ts MAMMOTH_BULL_RESPAWN_MS). */ export declare const BOUNTY_BOSS_TARGETS: readonly BountyTargetKind[]; export declare function isBossBountyTarget(target: BountyTargetKind): boolean; export declare function isPvpBountyTarget(target: BountyTargetKind): boolean; export type BountyOffer = { target: BountyTargetKind; count: number; /** * Representative creature level used only for the Small Satchel gold roll. Fixed * per offer rather than read from the NPC's rolled level so a bounty always pays * the same band. */ rewardLevel: number; }; export type BountyTier = { /** Minimum Combat level to be offered this tier. */ minCombat: number; offers: BountyOffer[]; }; /** * Combat 20-40 (slice B1 of PLAN_1_TO_40.md, 2026-10-12): every contract names a creature that already lives in the * world, at or below the unlocking Combat level and never above 40 (41+ stays behind its gates). * * PROVISIONAL (balance pass): every `count` below is a placeholder, sized only by how many of the creature spawn * (three archers, two polar bears) so a contract finishes in one sitting. `rewardLevel` is not new: it is the * creature's own level, as in the tiers above, so the Small Satchel pays by the existing formula * (`satchelGoldRange`: level x 20-60 gold). Change these numbers in the balance pass, and only here. * * Where each lives (a player reaches all of them on foot, no key and no Explorer gate): * - redcap, redcaparcher: Highwayman's Ridge (east of Calverton). * - blackwakedeckhand, cutthroat, drowneddeckhand: the Sundered Coast's Blackwake Cove and Fort Rook. * - goblin: the battlefield's goblins (the same grind as the lists above, the open-country fallback at Combat 20). * - mammoth: the Snowfields' herd (north). polarbear: the Bear Floes beaches (north). * - gravehound, mosswolf, ironjawogre, mireleech (the Blood Mire, T73): inside the Dreadwoods (PvP zone, BOUNTY_PVP_TARGETS), always a third choice. * Left out on purpose: amazons (only past the Rat Tunnel hole, itself gated), spiders (Spider Cave), and every 41+ creature. * Frost wolf and crystal skitter (the Ice Prison, end-game ground behind the Combat 40 Hallway since James's rule of 2026-10-12) stay out: each * needs a painted target icon in the frontend's bountyIcons.ts, and the prison is reached by the Hallway's teleport, which * scripts/bounty-tiers-smoke.ts's on-foot flood fill does not follow. Add them with both (PLAN_1_TO_40.md B1 follow-up). */ export declare const BOUNTY_TIERS_20_TO_40_PROVISIONAL: readonly BountyTier[]; /** Ordered low to high; the last entry whose `minCombat` a player meets is theirs. */ export declare const BOUNTY_TIERS: readonly BountyTier[]; /** The offers Bruce shows a player at this Combat level (empty below tier 1). */ export declare function bountyTierForCombat(combatLevel: number): BountyOffer[]; export declare function isBountyTargetKind(value: unknown): value is BountyTargetKind; /** Find the offer for a target at the player's tier, or null if not currently offered. */ export declare function bountyOfferFor(combatLevel: number, target: BountyTargetKind): BountyOffer | null; export type ActiveBounty = { target: BountyTargetKind; count: number; killed: number; /** Creature level for the Small Satchel gold roll when the reward is claimed. */ rewardLevel: number; /** Set when it was taken as that UTC day's daily contract (dailyHooks.ts): handed in the same day it pays a second satchel. */ dailyDay?: number; /** Set when it was taken as that UTC week's hunt of the week (weeklyHunt.ts): handed in the same week it pays a second satchel. */ weekly?: number; }; export declare function normalizeActiveBounty(raw: unknown): ActiveBounty | null; export declare function isBountyComplete(bounty: ActiveBounty | null | undefined): boolean; /** Plural creature name for chat and panel copy ("30 seagulls"). */ export declare const BOUNTY_TARGET_NAME: Record; export declare function bountyTargetDisplayName(target: BountyTargetKind): string; export declare const SATCHEL_GOLD_MIN_MULT = 20; export declare const SATCHEL_GOLD_MAX_MULT = 60; /** 0.1% chance the satchel also holds one poplar / spruce item. */ export declare const SATCHEL_RARE_CHANCE = 0.001; /** 5% chance the satchel also holds a bundle of Birch Arrows. */ export declare const SATCHEL_ARROW_CHANCE = 0.05; export declare const SATCHEL_ARROW_MIN = 10; export declare const SATCHEL_ARROW_MAX = 100; export type SatchelPoolEntry = { kind: string; minQty: number; maxQty: number; }; /** One of these is picked when the rare roll hits. */ export declare const SATCHEL_RARE_POOL: readonly SatchelPoolEntry[]; /** Gold band a satchel for this creature level can pay. */ export declare function satchelGoldRange(rewardLevel: number): { min: number; max: number; }; export {}; //# sourceMappingURL=bounty.d.ts.map