101 lines
2.7 KiB
TypeScript
101 lines
2.7 KiB
TypeScript
import { createGridInventory, placeItem } from "../grid-inventory";
|
|
import { GameItemMeta } from "../grid-inventory/types";
|
|
import { IDENTITY_TRANSFORM } from "../utils/shape-collision";
|
|
import { parseShapeString } from "../utils/parse-shape";
|
|
import { EncounterData, EncounterType, ItemData } from "../types";
|
|
import type { RNG } from "@/utils/rng";
|
|
import type {
|
|
CampEncounterState,
|
|
CombatEncounterState,
|
|
CurioEncounterState,
|
|
DialogueEncounterState,
|
|
EncounterState,
|
|
ShopEncounterState,
|
|
} from "./types";
|
|
import { buildCombatEncounterState } from "./combat";
|
|
import { buildShopEncounterState } from "./shop";
|
|
|
|
function createCurioItems(allItems: ItemData[], rng: RNG): GameItemMeta[] {
|
|
const curioItems: GameItemMeta[] = [];
|
|
const rolledIndices = new Set<number>();
|
|
|
|
for (let i = 0; i < 3 && rolledIndices.size < allItems.length; i++) {
|
|
let index: number;
|
|
do {
|
|
index = rng.nextInt(allItems.length);
|
|
} while (rolledIndices.has(index));
|
|
rolledIndices.add(index);
|
|
|
|
const itemData = allItems[index];
|
|
const shape = parseShapeString(itemData.shape);
|
|
curioItems.push({ itemData, shape });
|
|
}
|
|
|
|
return curioItems;
|
|
}
|
|
|
|
export function buildCurioEncounterState(
|
|
data: EncounterData<"curio">,
|
|
allItems: ItemData[],
|
|
rng: RNG,
|
|
): CurioEncounterState {
|
|
const items = createCurioItems(allItems, rng);
|
|
const inventory = createGridInventory<GameItemMeta>(6, 4);
|
|
|
|
for (let i = 0; i < items.length; i++) {
|
|
const meta = items[i];
|
|
placeItem(inventory, {
|
|
id: `curio-item-${i}`,
|
|
shape: meta.shape,
|
|
transform: { ...IDENTITY_TRANSFORM, offset: { x: i, y: 0 } },
|
|
meta,
|
|
});
|
|
}
|
|
|
|
return { data, items: inventory };
|
|
}
|
|
|
|
export function buildCampEncounterState(
|
|
data: EncounterData<"camp">,
|
|
): CampEncounterState {
|
|
return { data };
|
|
}
|
|
|
|
export function buildDialogueEncounterState(
|
|
data: EncounterData<"event">,
|
|
): DialogueEncounterState {
|
|
return { data, blocked: false };
|
|
}
|
|
|
|
export function buildEncounterState(
|
|
data: EncounterData<EncounterType>,
|
|
allItems: ItemData[],
|
|
rng: RNG,
|
|
idCounter: { value: number },
|
|
): EncounterState {
|
|
switch (data.type) {
|
|
case "minion":
|
|
case "elite":
|
|
return buildCombatEncounterState(
|
|
data as EncounterData<"minion" | "elite">,
|
|
);
|
|
case "shop":
|
|
return buildShopEncounterState(
|
|
data as EncounterData<"shop">,
|
|
allItems,
|
|
rng,
|
|
idCounter,
|
|
);
|
|
case "curio":
|
|
return buildCurioEncounterState(
|
|
data as EncounterData<"curio">,
|
|
allItems,
|
|
rng,
|
|
);
|
|
case "camp":
|
|
return buildCampEncounterState(data as EncounterData<"camp">);
|
|
case "event":
|
|
return buildDialogueEncounterState(data as EncounterData<"event">);
|
|
}
|
|
}
|