1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556 |
- /// <reference path="../AI.ts" />
- module AIRules {
- export var Wander = AI.rules.createAndAddRule({
- name : "Wander",
- firstPriority : AIRules.PRIORITY_ACTING_ON_IDLE,
- conditions : (runner : RulebookRunner<Person>) => {
- let person = runner.noun;
- return person.AI.wanderer && (Math.random() * 100) > person.AI.wanderChance;
- },
- code : (runner : RulebookRunner<Person>) => {
- let person = runner.noun;
- let room = <RoomRandom> person.getRoom();
- if (person.AI.wandersOn != undefined) {
- // stick to region while wandering
- if (person.AI.wandersOn.containsRoom(room)) {
- // Alredy in region, so just wander off inside it
- let connections = room.connections.slice();
- let realConnections = [];
- for (let i = 0; i < connections.length; i++) {
- if (connections[i] != undefined && person.AI.wandersOn.containsRoom(connections[i])) {
- realConnections.push(i);
- }
- }
- let direction = ((new Shuffler(realConnections)).getOne());
- return new ActionGo(person, direction);
- } else {
- // return to region
- let regionRooms = person.AI.wandersOn.getRooms().filter((a : Room) => {
- if (a instanceof RoomRandom && a.placed) {
- return true;
- }
- });
- // Ideally we'd actually make a path to it and check the distance, since mazes can make it be longer than it really is
- // But this is quick and dirty enough. And since regions are closely packed, even if this is not really the closest room, the NPC will end up
- // entering the region earlier by accident.
- regionRooms.sort((a : RoomRandom, b : RoomRandom) => {
- let dist = a.getDistanceTo(b);
- if (dist != undefined) {
- return -dist; // This means that the latest element will be the closest.
- } else {
- return 0; // This means that the first elements will be unreachable
- }
- });
- let targetRoom = regionRooms.pop();
- return new ActionGo(person, targetRoom);
- }
- } else {
- // just wander in random direction
- let direction = room.getConnectedDirection();
- return new ActionGo(person, direction);
- }
- }
- });
- }
|