phaser/src/utils/ArraySet.js

282 lines
6.4 KiB
JavaScript
Raw Normal View History

/**
* @author Richard Davey <rich@photonstorm.com>
2015-02-25 03:36:23 +00:00
* @copyright 2015 Photon Storm Ltd.
* @license {@link https://github.com/photonstorm/phaser/blob/master/license.txt|MIT License}
*/
/**
* ArraySet is a Set data structure (items must be unique within the set) that also maintains order.
* This allows specific items to be easily added or removed from the Set.
*
* Item equality (and uniqueness) is determined by the behavior of `Array.indexOf`.
*
* This used primarily by the Input subsystem.
*
* @class Phaser.ArraySet
* @constructor
* @param {any[]} [list=(new array)] - The backing array: if specified the items in the list _must_ be unique, per `Array.indexOf`, and the ownership of the array _should_ be relinquished to the ArraySet.
*/
Phaser.ArraySet = function (list) {
/**
* Current cursor position as established by `first` and `next`.
* @property {integer} position
* @default
*/
this.position = 0;
/**
* The backing array.
* @property {any[]} list
*/
this.list = list || [];
};
Phaser.ArraySet.prototype = {
/**
* Adds a new element to the end of the list.
* If the item already exists in the list it is not moved.
*
* @method Phaser.ArraySet#add
* @param {any} item - The element to add to this list.
* @return {any} The item that was added.
*/
add: function (item) {
if (!this.exists(item))
{
this.list.push(item);
}
return item;
},
/**
* Gets the index of the item in the list, or -1 if it isn't in the list.
*
* @method Phaser.ArraySet#getIndex
* @param {any} item - The element to get the list index for.
* @return {integer} The index of the item or -1 if not found.
*/
getIndex: function (item) {
return this.list.indexOf(item);
},
/**
* Gets an item from the set based on the property strictly equaling the value given.
* Returns null if not found.
*
* @method Phaser.ArraySet#getByKey
* @param {string} property - The property to check against the value.
* @param {any} value - The value to check if the property strictly equals.
* @return {any} The item that was found, or null if nothing matched.
*/
getByKey: function (property, value) {
var i = this.list.length;
while (i--)
{
if (this.list[i][property] === value)
{
return this.list[i];
}
}
return null;
},
/**
* Checks for the item within this list.
*
* @method Phaser.ArraySet#exists
* @param {any} item - The element to get the list index for.
* @return {boolean} True if the item is found in the list, otherwise false.
*/
exists: function (item) {
return (this.list.indexOf(item) > -1);
},
/**
* Removes all the items.
*
* @method Phaser.ArraySet#reset
*/
reset: function () {
this.list.length = 0;
},
/**
* Removes the given element from this list if it exists.
*
* @method Phaser.ArraySet#remove
* @param {any} item - The item to be removed from the list.
* @return {any} item - The item that was removed.
*/
remove: function (item) {
var idx = this.list.indexOf(item);
if (idx > -1)
{
this.list.splice(idx, 1);
return item;
}
},
/**
* Sets the property `key` to the given value on all members of this list.
*
* @method Phaser.ArraySet#setAll
2015-02-11 05:19:09 +00:00
* @param {any} key - The property of the item to set.
* @param {any} value - The value to set the property to.
*/
setAll: function (key, value) {
var i = this.list.length;
while (i--)
{
if (this.list[i])
{
this.list[i][key] = value;
}
}
},
/**
* Calls a function on all members of this list, using the member as the context for the callback.
*
* If the `key` property is present it must be a function.
* The function is invoked using the item as the context.
*
* @method Phaser.ArraySet#callAll
* @param {string} key - The name of the property with the function to call.
* @param {...*} parameter - Additional parameters that will be passed to the callback.
*/
callAll: function (key) {
var args = Array.prototype.splice.call(arguments, 1);
var i = this.list.length;
while (i--)
{
if (this.list[i] && this.list[i][key])
{
this.list[i][key].apply(this.list[i], args);
}
}
},
/**
* Removes every member from this ArraySet and optionally destroys it.
*
* @method Phaser.ArraySet#removeAll
* @param {boolean} [destroy=false] - Call `destroy` on each member as it's removed from this set.
*/
removeAll: function (destroy) {
if (destroy === undefined) { destroy = false; }
var i = this.list.length;
while (i--)
{
if (this.list[i])
{
var item = this.remove(this.list[i]);
if (destroy)
{
item.destroy();
}
}
}
this.position = 0;
this.list = [];
}
};
/**
* Number of items in the ArraySet. Same as `list.length`.
*
* @name Phaser.ArraySet#total
* @property {integer} total
*/
Object.defineProperty(Phaser.ArraySet.prototype, "total", {
get: function () {
return this.list.length;
}
});
/**
* Returns the first item and resets the cursor to the start.
*
* @name Phaser.ArraySet#first
* @property {any} first
*/
Object.defineProperty(Phaser.ArraySet.prototype, "first", {
get: function () {
this.position = 0;
if (this.list.length > 0)
{
return this.list[0];
}
else
{
return null;
}
}
});
/**
* Returns the the next item (based on the cursor) and advances the cursor.
*
* @name Phaser.ArraySet#next
* @property {any} next
*/
Object.defineProperty(Phaser.ArraySet.prototype, "next", {
get: function () {
if (this.position < this.list.length)
{
this.position++;
return this.list[this.position];
}
else
{
return null;
}
}
});
Phaser.ArraySet.prototype.constructor = Phaser.ArraySet;