@woosh/meep-engine
Version:
Pure JavaScript game engine. Fully featured and production ready.
128 lines (101 loc) • 3.09 kB
JavaScript
import { AbstractBlackboard } from "./AbstractBlackboard.js";
/**
* Cascading blackboard interface. Allows composition of multiple blackboard to be used to represent a single whole
* The access is always done from top to bottom. If a value is not found at the top of the stack, a lower slot will be considered until the end. In which case value will be created in the blackboard identified by "write_slot"
*/
export class BlackboardStack extends AbstractBlackboard {
constructor() {
super();
/**
* @private
* @type {AbstractBlackboard[]}
*/
this.__items = [];
/**
*
* @type {AbstractBlackboard}
* @private
*/
this.__write_slot = null;
}
contains(name, type) {
const items = this.__items;
const n = items.length;
for (let i = 0; i < n; i++) {
const blackboard = items[i];
if (blackboard.contains(name, type)) {
return true;
}
}
return false;
}
acquire(name, type, initialValue) {
// check for value at each level of the stack starting from the top
const items = this.__items;
const stack_length = items.length;
for (let i = stack_length - 1; i >= 0; i--) {
const blackboard = items[i];
if (blackboard.contains(name, type)) {
return blackboard.acquire(name, type, initialValue);
}
}
// not found, use write slot
return this.__write_slot.acquire(name, type, initialValue);
}
/**
*
* @param {AbstractBlackboard} v
*/
setWriteSlot(v) {
this.__write_slot = v;
}
__pick_write_slot() {
const length = this.__items.length;
if (length === 0) {
this.setWriteSlot(null);
} else {
const blackboard = this.__items[length - 1];
this.setWriteSlot(blackboard);
}
}
/**
*
* @param {AbstractBlackboard} item
*/
push(item) {
this.__items.push(item);
if (this.__write_slot === null) {
// update write slot
this.__pick_write_slot();
}
}
/**
*
* @param {AbstractBlackboard} item
* @param {number} position
*/
insert(item, position) {
this.__items.splice(position, 0, item);
if (this.__write_slot === null) {
// update write slot
this.__pick_write_slot();
}
}
/**
*
* @param {AbstractBlackboard} item
* @returns {boolean}
*/
remove(item) {
const i = this.__items.indexOf(item);
if (i === -1) {
return false;
}
this.__items.splice(i, 1);
if (this.__write_slot === item) {
// update write slot
this.__pick_write_slot();
}
return true;
}
}