aboutsummaryrefslogtreecommitdiff
path: root/tools/claim.js
diff options
context:
space:
mode:
Diffstat (limited to 'tools/claim.js')
-rw-r--r--tools/claim.js50
1 files changed, 50 insertions, 0 deletions
diff --git a/tools/claim.js b/tools/claim.js
new file mode 100644
index 0000000..2e568f2
--- /dev/null
+++ b/tools/claim.js
@@ -0,0 +1,50 @@
+// A tool to manage land claims (i.e. a certain Space is delegated to only call a specific `call()` if a tileUpdate occurs differing from that Space)
+
+const ms = require('../utils/measurespace');
+const ri = require('../utils/rectintersect');
+const vec = require('../utils/vec');
+const comb = require('../utils/comb');
+
+module.exports = function(catchall){
+ // socket is a Socket() object to declare the hook on.
+ // catchall is called if tileUpdate occurs w/ no relevant claim on a part.
+ let claims = {};
+ let claimId = 0;
+ this.claim = function(space, call, excl=true){
+ // `space` is Space obj; `call` is callback function
+ // `exclusive` sets whether this callback will prevent other (incl. catchall) functions from seeing the space. Cannot be used with an exclusive callback, and does not guarantee order.
+ // If exclusive claim intersects another claim, behavior undefined.
+ claimId++;
+ claims[claimId] = {'space':space, 'call':call, 'excl':excl, 'area':ms(space)}
+ return claimId;
+ }
+
+ this.unclaim = function(id){
+ delete claims[id];
+ }
+
+ this.handle = function(send, tilespaces, locs){
+ // Because usually tilespaces is small, the inefficiency of an O(nk) rect match is acceptable
+ for (let id in claims){
+ claim = claims[id];
+ diffspace = {};
+ rellocs = [];
+ for (let loc of locs){
+ let tile = tilespaces[loc];
+ if (ri(claim.area, [vec.tileToChar(loc), vec.tileToChar(vec.add(loc, [1,1]))])){
+ let diff = claim.space.copy();
+ diff.comb(tile, comb.unmask);
+ rellocs.push(loc);
+ diffspace[loc] = diff;
+ if (claim.excl){
+ let newtile = claim.space.copy();
+ newtile.comb(tile, comb.mask);
+ tilespaces[loc] = newtile;
+ }
+ }
+ }
+ claim.call(send, diffspace, rellocs, id, claim.space, claim.area); // claim.space should not be modified by the function. it is only present to make functions easier to write
+ }
+ catchall(send, tilespaces, locs);
+ }
+}