Files
Genarrative/src/types/scene.ts
高物 c49c64896a
Some checks failed
CI / verify (push) Has been cancelled
初始仓库迁移
2026-04-04 23:57:06 +08:00

191 lines
4.3 KiB
TypeScript

import type {
RoleActionDefinition,
RoleAttributeProfile,
RoleRelationState,
} from './attributes';
import type {Character} from './characters';
import {
AnimationState,
type CharacterGender,
type CombatActionMode,
type CombatDelivery,
type FacingDirection,
type HostileNpcRenderAnimation,
type NpcFunctionType,
} from './core';
import type {InventoryItem} from './items';
export interface NpcPersistentState {
affinity: number;
relationState?: RoleRelationState;
helpUsed: boolean;
chattedCount: number;
giftsGiven: number;
inventory: InventoryItem[];
recruited: boolean;
revealedFacts?: string[];
knownAttributeRumors?: string[];
firstMeaningfulContactResolved?: boolean;
seenBackstoryChapterIds?: string[];
}
export interface CompanionState {
npcId: string;
characterId: string;
joinedAtAffinity: number;
hp: number;
maxHp: number;
mana: number;
maxMana: number;
skillCooldowns: Record<string, number>;
animationState?: AnimationState;
actionMode?: CombatActionMode;
offsetX?: number;
offsetY?: number;
transitionMs?: number;
}
export interface CompanionRenderState {
npcId: string;
character: Character;
hp: number;
maxHp: number;
mana: number;
maxMana: number;
skillCooldowns: Record<string, number>;
animationState: AnimationState;
actionMode?: CombatActionMode;
slot: 'upper' | 'lower';
facing?: FacingDirection;
entryOffsetX?: number;
entryOffsetY?: number;
transitionMs?: number;
recruitToken?: number;
}
export interface Encounter {
id?: string;
kind?: 'npc' | 'treasure';
npcName: string;
npcDescription: string;
npcAvatar: string;
context: string;
gender?: CharacterGender;
specialBehavior?: 'initial_companion' | 'camp_companion';
xMeters?: number;
characterId?: string;
hostileNpcPresetId?: string;
monsterPresetId?: string;
initialAffinity?: number;
hostile?: boolean;
attributeProfile?: RoleAttributeProfile;
}
export interface SceneHostileNpc {
id: string;
name: string;
action: string;
description: string;
animation: HostileNpcRenderAnimation;
xMeters: number;
yOffset: number;
facing: FacingDirection;
attackRange: number;
speed: number;
hp: number;
maxHp: number;
renderKind?: 'npc';
encounter?: Encounter;
characterAnimation?: AnimationState;
combatMode?: CombatDelivery;
combatTags?: string[];
attributeProfile?: RoleAttributeProfile;
behaviorVectors?: RoleActionDefinition[];
}
export type SceneMonster = SceneHostileNpc;
export interface SceneNpc {
id: string;
name: string;
description: string;
avatar: string;
role: string;
gender?: CharacterGender;
characterId?: string;
hostileNpcPresetId?: string;
monsterPresetId?: string;
initialAffinity?: number;
hostile?: boolean;
functions?: NpcFunctionType[];
recruitable?: boolean;
attributeProfile?: RoleAttributeProfile;
}
export type SceneEncounterKind = 'npc' | 'treasure' | 'none';
export interface SceneEncounterResult {
kind: SceneEncounterKind;
npcId?: string;
treasureText?: string;
}
export interface CombatVisualEffect {
id: string;
frames: string[];
fps: number;
startX: number;
endX?: number;
startOrigin: 'player' | 'hostile_npc' | 'monster';
endOrigin?: 'player' | 'hostile_npc' | 'monster';
startMonsterId?: string;
endMonsterId?: string;
startHostileNpcId?: string;
endHostileNpcId?: string;
startAnchorOffsetY?: number;
endAnchorOffsetY?: number;
startOffsetX?: number;
endOffsetX?: number;
startYOffset: number;
endYOffset?: number;
durationMs: number;
sizePx: number;
scale?: number;
facing: FacingDirection;
zIndex?: number;
traveling?: boolean;
}
export interface SceneHostileNpcChange {
id: string;
action: string;
animation: HostileNpcRenderAnimation;
moveMeters?: number;
yOffset?: number;
}
export type SceneMonsterChange = SceneHostileNpcChange;
export interface SceneDirective {
playerAnimation: AnimationState;
playerMoveMeters: number;
playerOffsetY: number;
playerFacing: FacingDirection;
scrollWorld: boolean;
monsterChanges: SceneMonsterChange[];
hostileNpcChanges?: SceneHostileNpcChange[];
}
export interface ScenePresetInfo {
id: string;
name: string;
description: string;
imageSrc: string;
forwardSceneId?: string;
connectedSceneIds?: string[];
hostileNpcIds?: string[];
monsterIds?: string[];
npcs?: SceneNpc[];
treasureHints?: string[];
}