From 82385faf56946a432dcc2221aef8155b9d61fd44 Mon Sep 17 00:00:00 2001 From: "Clarence \"Sparr\" Risher" Date: Tue, 17 Oct 2017 15:49:00 -0700 Subject: [PATCH 1/4] implement StructureSpawn.setSpawnDirections --- src/game/structures.js | 19 ++++++++++++++++++- src/processor/intents/spawns/intents.js | 3 +++ .../intents/spawns/set-spawn-directions.js | 18 ++++++++++++++++++ src/utils.js | 5 +++++ 4 files changed, 44 insertions(+), 1 deletion(-) create mode 100644 src/processor/intents/spawns/set-spawn-directions.js diff --git a/src/game/structures.js b/src/game/structures.js index 1ab24513..7c02b13d 100644 --- a/src/game/structures.js +++ b/src/game/structures.js @@ -910,7 +910,8 @@ exports.make = function(_runtimeData, _intents, _register, _globals) { name: (o) => o.user == runtimeData.user._id ? o.name : undefined, energy: (o) => o.energy, energyCapacity: (o) => o.energyCapacity, - spawning: (o) => o.spawning || null + spawning: (o) => o.spawning || null, + spawnDirections: (o) => o.user == runtimeData.user._id ? o.spawnDirections : undefined }); Object.defineProperty(StructureSpawn.prototype, 'memory', { @@ -1352,6 +1353,22 @@ exports.make = function(_runtimeData, _intents, _register, _globals) { return C.OK; }); + StructureSpawn.prototype.setSpawnDirections = register.wrapFn(function(spawnDirections) { + if(!this.my) { + return C.ERR_NOT_OWNER; + } + if(_.isArray(spawnDirections) && spawnDirections.length > 0) { + // convert directions to numbers, eliminate duplicates + spawnDirections = _.uniq(_.map(spawnDirections, e => +e)); + // bail if any numbers are out of bounds or non-integers + if(!_.any(spawnDirections, (direction)=>direction < 1 || direction > 8 || direction !== (direction | 0))) { + intents.set(this.id, 'setSpawnDirections', {spawnDirections}); + return C.OK; + } + } + return C.ERR_INVALID_ARGS; + }); + globals.StructureSpawn = StructureSpawn; globals.Spawn = StructureSpawn; diff --git a/src/processor/intents/spawns/intents.js b/src/processor/intents/spawns/intents.js index f2f70071..faf3efdf 100644 --- a/src/processor/intents/spawns/intents.js +++ b/src/processor/intents/spawns/intents.js @@ -12,4 +12,7 @@ module.exports = function(object, objectIntents, roomObjects, roomTerrain, bulk, if(objectIntents.recycleCreep) require('./recycle-creep')(object, objectIntents.recycleCreep, roomObjects, roomTerrain, bulk, bulkUsers, roomController, stats, gameTime); + if(objectIntents.setSpawnDirections) + require('./set-spawn-directions')(object, objectIntents.setSpawnDirections, roomObjects, roomTerrain, bulk); + }; \ No newline at end of file diff --git a/src/processor/intents/spawns/set-spawn-directions.js b/src/processor/intents/spawns/set-spawn-directions.js new file mode 100644 index 00000000..28c28e55 --- /dev/null +++ b/src/processor/intents/spawns/set-spawn-directions.js @@ -0,0 +1,18 @@ +var _ = require('lodash'), + utils = require('../../../utils'), + driver = utils.getDriver(), + C = driver.constants; + +module.exports = function(spawn, intent, roomObjects, roomTerrain, bulk) { + if(spawn.type != 'spawn') + return; + const spawnDirections = intent.spawnDirections; + if(_.isArray(spawnDirections) && spawnDirections.length > 0) { + // convert directions to numbers, eliminate duplicates + spawnDirections = _.uniq(_.map(spawnDirections, e => +e)); + // bail if any numbers are out of bounds or non-integers + if(!_.any(spawnDirections, (direction)=>direction < 1 || direction > 8 || direction !== (direction | 0))) { + bulk.update(spawn, {spawnDirections}); + } + } +}; \ No newline at end of file diff --git a/src/utils.js b/src/utils.js index 27390984..0c913b0f 100644 --- a/src/utils.js +++ b/src/utils.js @@ -805,6 +805,11 @@ exports.storeIntents = function(userId, userIntents, userRuntimeData) { sign: (""+objectIntentsResult.signController.sign).substring(0,100) }; } + if(objectIntentsResult.setSpawnDirections) { + objectIntents.setSpawnDirections = { + spawnDirections: objectIntentsResult.setSpawnDirections.spawnDirections + }; + } for(var iCustomType in driver.config.customIntentTypes) { From 38b551d3559499f710394093ac666a9b4aac4bf1 Mon Sep 17 00:00:00 2001 From: "Clarence \"Sparr\" Risher" Date: Tue, 17 Oct 2017 19:17:47 -0700 Subject: [PATCH 2/4] implement Spawn.spawnCreep(...,{spawnDirections:[]}) --- src/game/structures.js | 19 +++++++++++++++++-- src/processor/intents/spawns/create-creep.js | 18 +++++++++++++++++- src/utils.js | 3 ++- 3 files changed, 36 insertions(+), 4 deletions(-) diff --git a/src/game/structures.js b/src/game/structures.js index 7c02b13d..78098463 100644 --- a/src/game/structures.js +++ b/src/game/structures.js @@ -910,7 +910,7 @@ exports.make = function(_runtimeData, _intents, _register, _globals) { name: (o) => o.user == runtimeData.user._id ? o.name : undefined, energy: (o) => o.energy, energyCapacity: (o) => o.energyCapacity, - spawning: (o) => o.spawning || null, + spawning: (o) => (o.user == runtimeData.user._id ? o.spawning : _.omit(o.spawning, 'spawnDirections')) || null, spawnDirections: (o) => o.user == runtimeData.user._id ? o.spawnDirections : undefined }); @@ -1112,6 +1112,21 @@ exports.make = function(_runtimeData, _intents, _register, _globals) { let energyStructures = options.energyStructures && _.uniq(_.map(options.energyStructures, 'id')); + let spawnDirections = options.spawnDirections; + if(spawnDirections !== undefined) { + if(!_.isArray(spawnDirections)) { + return C.ERR_INVALID_ARGS; + } + // convert directions to numbers, eliminate duplicates + spawnDirections = _.uniq(_.map(spawnDirections, d => +d)); + if(spawnDirections.length > 0) { + // bail if any numbers are out of bounds or non-integers + if(!_.all(spawnDirections, direction => direction >= 1 && direction <= 8 && direction === (direction | 0))) { + return C.ERR_INVALID_ARGS; + } + } + } + if(!this.my) { return C.ERR_NOT_OWNER; } @@ -1229,7 +1244,7 @@ exports.make = function(_runtimeData, _intents, _register, _globals) { } }); - intents.set(this.id, 'createCreep', {name, body, energyStructures}); + intents.set(this.id, 'createCreep', {name, body, energyStructures, spawnDirections}); return C.OK; }); diff --git a/src/processor/intents/spawns/create-creep.js b/src/processor/intents/spawns/create-creep.js index 8904e11d..0b8ef431 100644 --- a/src/processor/intents/spawns/create-creep.js +++ b/src/processor/intents/spawns/create-creep.js @@ -16,6 +16,21 @@ module.exports = function(spawn, intent, roomObjects, roomTerrain, bulk, bulkUse return; } + let spawnDirections = intent.spawnDirections; + if(spawnDirections !== undefined) { + if(!_.isArray(spawnDirections)) { + return; + } + // convert directions to numbers, eliminate duplicates + spawnDirections = _.uniq(_.map(spawnDirections, e => +e)); + if(spawnDirections.length > 0) { + // bail if any numbers are out of bounds or non-integers + if(!_.all(spawnDirections, direction => direction >= 1 && direction <= 8 && direction === (direction | 0))) { + return; + } + } + } + intent.body = intent.body.slice(0, C.MAX_CREEP_SIZE); var cost = utils.calcCreepCost(intent.body); @@ -33,7 +48,8 @@ module.exports = function(spawn, intent, roomObjects, roomTerrain, bulk, bulkUse spawning: { name: intent.name, needTime: C.CREEP_SPAWN_TIME * intent.body.length, - remainingTime: C.CREEP_SPAWN_TIME * intent.body.length + remainingTime: C.CREEP_SPAWN_TIME * intent.body.length, + spawnDirections } }); diff --git a/src/utils.js b/src/utils.js index 0c913b0f..5f022ada 100644 --- a/src/utils.js +++ b/src/utils.js @@ -665,7 +665,8 @@ exports.storeIntents = function(userId, userIntents, userRuntimeData) { objectIntents.createCreep = { name: ""+objectIntentsResult.createCreep.name, body: _.filter(objectIntentsResult.createCreep.body, (i) => _.contains(C.BODYPARTS_ALL, i)), - energyStructures: objectIntentsResult.createCreep.energyStructures + energyStructures: objectIntentsResult.createCreep.energyStructures, + spawnDirections: objectIntentsResult.createCreep.spawnDirections }; } if(objectIntentsResult.renewCreep) { From d4e02ac5e4947edf107f4dabfcbeed4b5b8f4718 Mon Sep 17 00:00:00 2001 From: "Clarence \"Sparr\" Risher" Date: Tue, 17 Oct 2017 19:18:34 -0700 Subject: [PATCH 3/4] honor spawnDirections when spawning creep --- src/processor/intents/spawns/_born-creep.js | 26 +++++++++++++++++++-- 1 file changed, 24 insertions(+), 2 deletions(-) diff --git a/src/processor/intents/spawns/_born-creep.js b/src/processor/intents/spawns/_born-creep.js index 7dc3caab..a4a5cf4b 100644 --- a/src/processor/intents/spawns/_born-creep.js +++ b/src/processor/intents/spawns/_born-creep.js @@ -9,7 +9,10 @@ module.exports = function(spawn, creep, roomObjects, roomTerrain, bulk, stats) { var newX, newY, isOccupied, hostileOccupied; var checkObstacleFn = (i) => _.contains(C.OBSTACLE_OBJECT_TYPES, i.type) && i.x == newX && i.y == newY; - for (var direction = 1; direction <= 8; direction++) { + const spawnDirections = spawn.spawning.spawnDirections || spawn.spawnDirections || [1,2,3,4,5,6,7,8]; + const otherDirections = _.difference([1,2,3,4,5,6,7,8], spawnDirections); + // find the first direction where the creep can spawn + for (var direction of spawnDirections) { var [dx,dy] = utils.getOffsetsByDirection(direction); newX = spawn.x + dx; @@ -22,11 +25,13 @@ module.exports = function(spawn, creep, roomObjects, roomTerrain, bulk, stats) { break; } + // remember the first direction where we found a hostile creep if(!hostileOccupied) { hostileOccupied = _.find(roomObjects, i => i.x == newX && i.y == newY && i.type == 'creep' && i.user != spawn.user); } } + // if we found a place to spawn, do so if(!isOccupied) { bulk.update(creep, { x: newX, @@ -35,7 +40,24 @@ module.exports = function(spawn, creep, roomObjects, roomTerrain, bulk, stats) { }); return true; } - else if(hostileOccupied) { + + // bail if there's an opening we could spawn to but chose not to + for (var direction of otherDirections) { + var [dx,dy] = utils.getOffsetsByDirection(direction); + + newX = spawn.x + dx; + newY = spawn.y + dy; + isOccupied = _.any(roomObjects, checkObstacleFn) || + utils.checkTerrain(roomTerrain, newX, newY, C.TERRAIN_MASK_WALL) || + movement.isTileBusy(newX, newY); + + if (!isOccupied) { + return false; + } + } + + // spawn is surrounded, spawnstomp the first hostile we found above + if(hostileOccupied) { require('../creeps/_die')(hostileOccupied, roomObjects, bulk, stats); bulk.update(creep, { x: hostileOccupied.x, From 73f906f089d4d1da11f1044be576af8faf936c07 Mon Sep 17 00:00:00 2001 From: "Clarence \"Sparr\" Risher" Date: Mon, 23 Oct 2017 22:13:24 -0700 Subject: [PATCH 4/4] move StructureSpawn.setSpawnDirections to StructureSpawn.Spawning.setDirections --- src/game/structures.js | 49 ++++++++++++------- src/processor/intents/spawns/_born-creep.js | 32 ++++++------ src/processor/intents/spawns/create-creep.js | 15 +++--- .../intents/spawns/set-spawn-directions.js | 10 ++-- src/utils.js | 4 +- 5 files changed, 62 insertions(+), 48 deletions(-) diff --git a/src/game/structures.js b/src/game/structures.js index 78098463..85d27de1 100644 --- a/src/game/structures.js +++ b/src/game/structures.js @@ -910,8 +910,7 @@ exports.make = function(_runtimeData, _intents, _register, _globals) { name: (o) => o.user == runtimeData.user._id ? o.name : undefined, energy: (o) => o.energy, energyCapacity: (o) => o.energyCapacity, - spawning: (o) => (o.user == runtimeData.user._id ? o.spawning : _.omit(o.spawning, 'spawnDirections')) || null, - spawnDirections: (o) => o.user == runtimeData.user._id ? o.spawnDirections : undefined + spawning: (o) => o.spawning ? new StructureSpawn.Spawning(o.spawning, o.user == runtimeData.user._id) : null, }); Object.defineProperty(StructureSpawn.prototype, 'memory', { @@ -1112,16 +1111,16 @@ exports.make = function(_runtimeData, _intents, _register, _globals) { let energyStructures = options.energyStructures && _.uniq(_.map(options.energyStructures, 'id')); - let spawnDirections = options.spawnDirections; - if(spawnDirections !== undefined) { - if(!_.isArray(spawnDirections)) { + let directions = options.directions; + if(directions !== undefined) { + if(!_.isArray(directions)) { return C.ERR_INVALID_ARGS; } // convert directions to numbers, eliminate duplicates - spawnDirections = _.uniq(_.map(spawnDirections, d => +d)); - if(spawnDirections.length > 0) { + directions = _.uniq(_.map(directions, d => +d)); + if(directions.length > 0) { // bail if any numbers are out of bounds or non-integers - if(!_.all(spawnDirections, direction => direction >= 1 && direction <= 8 && direction === (direction | 0))) { + if(!_.all(directions, (direction) => direction >= 1 && direction <= 8 && direction === (direction | 0))) { return C.ERR_INVALID_ARGS; } } @@ -1244,7 +1243,7 @@ exports.make = function(_runtimeData, _intents, _register, _globals) { } }); - intents.set(this.id, 'createCreep', {name, body, energyStructures, spawnDirections}); + intents.set(this.id, 'createCreep', {name, body, energyStructures, directions}); return C.OK; }); @@ -1368,25 +1367,39 @@ exports.make = function(_runtimeData, _intents, _register, _globals) { return C.OK; }); - StructureSpawn.prototype.setSpawnDirections = register.wrapFn(function(spawnDirections) { - if(!this.my) { + globals.StructureSpawn = StructureSpawn; + globals.Spawn = StructureSpawn; + + /** + * SpawnSpawning + * @param {Number} spawnId + * @param {Object} properties + * @constructor + */ + StructureSpawn.Spawning = register.wrapFn(function(spawningObject, exposePrivate = false) { + this.spawnId = spawningObject.spawnId; + this.name = exposePrivate ? spawningObject.name : null; + this.needTime = spawningObject.needtime; + this.remainingTime = spawningObject.remainingTime; + this.directions = exposePrivate ? spawningObject.directions : null; + }); + + StructureSpawn.Spawning.prototype.setDirections = register.wrapFn(function(directions) { + if(!(new StructureSpawn(this.spawnId).my)) { return C.ERR_NOT_OWNER; } - if(_.isArray(spawnDirections) && spawnDirections.length > 0) { + if(_.isArray(directions) && directions.length > 0) { // convert directions to numbers, eliminate duplicates - spawnDirections = _.uniq(_.map(spawnDirections, e => +e)); + directions = _.uniq(_.map(directions, e => +e)); // bail if any numbers are out of bounds or non-integers - if(!_.any(spawnDirections, (direction)=>direction < 1 || direction > 8 || direction !== (direction | 0))) { - intents.set(this.id, 'setSpawnDirections', {spawnDirections}); + if(!_.any(directions, (direction)=>direction < 1 || direction > 8 || direction !== (direction | 0))) { + intents.set(this.spawnId, 'setSpawnDirections', {directions}); return C.OK; } } return C.ERR_INVALID_ARGS; }); - globals.StructureSpawn = StructureSpawn; - globals.Spawn = StructureSpawn; - /** * StructureNuker * @param id diff --git a/src/processor/intents/spawns/_born-creep.js b/src/processor/intents/spawns/_born-creep.js index a4a5cf4b..25bdb356 100644 --- a/src/processor/intents/spawns/_born-creep.js +++ b/src/processor/intents/spawns/_born-creep.js @@ -9,10 +9,10 @@ module.exports = function(spawn, creep, roomObjects, roomTerrain, bulk, stats) { var newX, newY, isOccupied, hostileOccupied; var checkObstacleFn = (i) => _.contains(C.OBSTACLE_OBJECT_TYPES, i.type) && i.x == newX && i.y == newY; - const spawnDirections = spawn.spawning.spawnDirections || spawn.spawnDirections || [1,2,3,4,5,6,7,8]; - const otherDirections = _.difference([1,2,3,4,5,6,7,8], spawnDirections); + const directions = spawn.spawning.directions || [1,2,3,4,5,6,7,8]; + const otherDirections = _.difference([1,2,3,4,5,6,7,8], directions); // find the first direction where the creep can spawn - for (var direction of spawnDirections) { + for (var direction of directions) { var [dx,dy] = utils.getOffsetsByDirection(direction); newX = spawn.x + dx; @@ -41,23 +41,23 @@ module.exports = function(spawn, creep, roomObjects, roomTerrain, bulk, stats) { return true; } - // bail if there's an opening we could spawn to but chose not to - for (var direction of otherDirections) { - var [dx,dy] = utils.getOffsetsByDirection(direction); + // spawn is surrounded, spawnstomp the first hostile we found above, unless... + if(hostileOccupied) { + // bail if there's an opening we could spawn to but chose not to + for (var direction of otherDirections) { + var [dx,dy] = utils.getOffsetsByDirection(direction); - newX = spawn.x + dx; - newY = spawn.y + dy; - isOccupied = _.any(roomObjects, checkObstacleFn) || - utils.checkTerrain(roomTerrain, newX, newY, C.TERRAIN_MASK_WALL) || - movement.isTileBusy(newX, newY); + newX = spawn.x + dx; + newY = spawn.y + dy; + isOccupied = _.any(roomObjects, checkObstacleFn) || + utils.checkTerrain(roomTerrain, newX, newY, C.TERRAIN_MASK_WALL) || + movement.isTileBusy(newX, newY); - if (!isOccupied) { - return false; + if (!isOccupied) { + return false; + } } - } - // spawn is surrounded, spawnstomp the first hostile we found above - if(hostileOccupied) { require('../creeps/_die')(hostileOccupied, roomObjects, bulk, stats); bulk.update(creep, { x: hostileOccupied.x, diff --git a/src/processor/intents/spawns/create-creep.js b/src/processor/intents/spawns/create-creep.js index 0b8ef431..f9a35dec 100644 --- a/src/processor/intents/spawns/create-creep.js +++ b/src/processor/intents/spawns/create-creep.js @@ -16,16 +16,16 @@ module.exports = function(spawn, intent, roomObjects, roomTerrain, bulk, bulkUse return; } - let spawnDirections = intent.spawnDirections; - if(spawnDirections !== undefined) { - if(!_.isArray(spawnDirections)) { + let directions = intent.directions; + if(directions !== undefined) { + if(!_.isArray(directions)) { return; } // convert directions to numbers, eliminate duplicates - spawnDirections = _.uniq(_.map(spawnDirections, e => +e)); - if(spawnDirections.length > 0) { + directions = _.uniq(_.map(directions, e => +e)); + if(directions.length > 0) { // bail if any numbers are out of bounds or non-integers - if(!_.all(spawnDirections, direction => direction >= 1 && direction <= 8 && direction === (direction | 0))) { + if(!_.all(directions, direction => direction >= 1 && direction <= 8 && direction === (direction | 0))) { return; } } @@ -46,10 +46,11 @@ module.exports = function(spawn, intent, roomObjects, roomTerrain, bulk, bulkUse bulk.update(spawn, { spawning: { + spawnId: spawn._id, name: intent.name, needTime: C.CREEP_SPAWN_TIME * intent.body.length, remainingTime: C.CREEP_SPAWN_TIME * intent.body.length, - spawnDirections + directions } }); diff --git a/src/processor/intents/spawns/set-spawn-directions.js b/src/processor/intents/spawns/set-spawn-directions.js index 28c28e55..ec50e16c 100644 --- a/src/processor/intents/spawns/set-spawn-directions.js +++ b/src/processor/intents/spawns/set-spawn-directions.js @@ -6,13 +6,13 @@ var _ = require('lodash'), module.exports = function(spawn, intent, roomObjects, roomTerrain, bulk) { if(spawn.type != 'spawn') return; - const spawnDirections = intent.spawnDirections; - if(_.isArray(spawnDirections) && spawnDirections.length > 0) { + var directions = intent.directions; + if(_.isArray(directions) && directions.length > 0) { // convert directions to numbers, eliminate duplicates - spawnDirections = _.uniq(_.map(spawnDirections, e => +e)); + directions = _.uniq(_.map(directions, e => +e)); // bail if any numbers are out of bounds or non-integers - if(!_.any(spawnDirections, (direction)=>direction < 1 || direction > 8 || direction !== (direction | 0))) { - bulk.update(spawn, {spawnDirections}); + if(!_.any(directions, (direction)=>direction < 1 || direction > 8 || direction !== (direction | 0))) { + bulk.update(spawn, {spawning:{directions}}); } } }; \ No newline at end of file diff --git a/src/utils.js b/src/utils.js index 5f022ada..7026b950 100644 --- a/src/utils.js +++ b/src/utils.js @@ -666,7 +666,7 @@ exports.storeIntents = function(userId, userIntents, userRuntimeData) { name: ""+objectIntentsResult.createCreep.name, body: _.filter(objectIntentsResult.createCreep.body, (i) => _.contains(C.BODYPARTS_ALL, i)), energyStructures: objectIntentsResult.createCreep.energyStructures, - spawnDirections: objectIntentsResult.createCreep.spawnDirections + directions: objectIntentsResult.createCreep.directions }; } if(objectIntentsResult.renewCreep) { @@ -808,7 +808,7 @@ exports.storeIntents = function(userId, userIntents, userRuntimeData) { } if(objectIntentsResult.setSpawnDirections) { objectIntents.setSpawnDirections = { - spawnDirections: objectIntentsResult.setSpawnDirections.spawnDirections + directions: objectIntentsResult.setSpawnDirections.directions }; }