UNPKG

@woosh/meep-engine

Version:

Pure JavaScript game engine. Fully featured and production ready.

103 lines (72 loc) 3.24 kB
import { assert } from "../../../../../core/assert.js"; import { compileReactiveExpression } from "../../../../../core/lang/reactive/compileReactiveExpression.js"; import { ActionBehavior } from "../../../../intelligence/behavior/primitive/ActionBehavior.js"; import { Transform } from "../../../transform/Transform.js"; import { AbstractActionDescription } from "./AbstractActionDescription.js"; export class SendRequestActionDescription extends AbstractActionDescription { distance = Number.POSITIVE_INFINITY; responders = 1; context = {}; fromJSON({ distance = Number.POSITIVE_INFINITY, responders = 1, context = {} }) { assert.defined(context, 'context'); assert.notNull(context, 'context'); assert.isObject(context, 'context'); this.distance = distance; this.responders = responders; this.context = context; } execute(actor, dataset, context, system) { const raw_action_context = this.context; // decode context const action_context = {}; for (const key in raw_action_context) { const raw_value = raw_action_context[key]; if (typeof raw_value === "string" && raw_value.startsWith('!')) { // rewrite rule const code = raw_value.slice(1); const exp = compileReactiveExpression(code); const evaluated_value = exp.evaluate(context); action_context[key] = evaluated_value; } else { action_context[key] = raw_value; } } return new ActionBehavior(() => { /** * * @param {number} entity * @param {EntityComponentDataset} ecd */ function filter(entity, ecd) { const distance = this.distance; if (!Number.isFinite(distance)) { return true; } const actor_transform = ecd.getComponent(actor, Transform); if (actor_transform === undefined) { return true; } const target_transform = ecd.getComponent(entity, Transform); if (target_transform === undefined) { return false; } return target_transform.position.distanceTo(actor_transform.position) <= distance; } const bestActors = system.requestBestActors(action_context, filter, this, this.responders); bestActors.forEach((match) => { /** * * @type {DynamicRuleDescription} */ const rule = match.rule; // console.log(`Requested response from ${match.entity}, because rule matched: ${match.rule.condition.toCode()}`); // DEBUG system.attemptRuleExecution(match.entity, match.rule, match.scope); }); }); } } SendRequestActionDescription.prototype.type = 'SendRequest';