NPM Publish prep

This commit is contained in:
Jeremiah Billmann
2013-08-01 15:18:40 -04:00
parent 2eb752f71d
commit 65673598dc
9 changed files with 18 additions and 7 deletions
+36
View File
@@ -0,0 +1,36 @@
var entity = require('../entities/entity');
exports = module.exports = EntityController;
function EntityController (maxHistorySecondBuffer) {
this.entities = [];
this.maxHistorySecondBuffer = maxHistorySecondBuffer;
}
EntityController.prototype = {
add: function (id) {
var newEntity, entityFound = false;
this.entities.some(function (entity) {
if (entity.id === id) {
newEntity = entity;
entityFound = true;
return true;
}
});
if (!entityFound) {
newEntity = new entity(id, this.maxHistorySecondBuffer);
this.entities.push(newEntity);
}
return newEntity;
},
remove: function (id) {
for (var i = 0; i < this.entities.length; i ++) {
if (this.entities[i].id === id) {
this.entities.splice(i, 1)[0];
return;
}
}
}
};
+37
View File
@@ -0,0 +1,37 @@
var entityController = require('./entitycontroller'),
player = require('../entities/player');
exports = module.exports = PlayerController;
function PlayerController (maxHistorySecondBuffer) {
entityController.call(this, maxHistorySecondBuffer);
}
PlayerController.prototype = Object.create(entityController.prototype);
PlayerController.prototype.add = function (client) {
var newPlayer, playerFound = false;
this.entities.some(function (player) {
if (player.client.id === client.id) {
newPlayer = player;
playerFound = true;
return true;
}
});
if (!playerFound) {
newPlayer = new player(client, this.maxHistorySecondBuffer);
this.entities.push(newPlayer);
}
return newPlayer;
};
PlayerController.prototype.addInput = function (id, input, sequence, time) {
this.entities.some(function (player) {
if (player.client.id === id) {
player.inputs.push({ input: input, seq: sequence, time: time });
return true;
}
});
};
+35
View File
@@ -0,0 +1,35 @@
var history = require('./history');
exports = module.exports = Entity;
function Entity (id, maxHistorySecondBuffer) {
this.state = {};
this.sequence = 1;
this.id = id;
this.maxHistorySecondBuffer = maxHistorySecondBuffer;
this.stateHistory = [];
}
Entity.prototype = {
addState: function (state, executionTime) {
this.addHistory(state, executionTime);
this.state = state;
this.sequence += 1;
},
addHistory: function (state, executionTime) {
var minTime, spliceTo = 0, newHistory = new history(state, executionTime);
this.stateHistory.push(newHistory);
minTime = this.stateHistory[this.stateHistory.length - 1].executionTime - this.maxHistorySecondBuffer;
for (var i = 0; i < this.stateHistory.length; i ++) {
if (this.stateHistory[i].executionTime > minTime) {
spliceTo = i - 1;
break;
}
}
if (spliceTo > 0) {
this.stateHistory.splice(0, spliceTo);
}
}
};
+6
View File
@@ -0,0 +1,6 @@
exports = module.exports = History;
function History (state, executionTime) {
this.state = state;
this.executionTime = executionTime;
}
+17
View File
@@ -0,0 +1,17 @@
var entity = require('./entity');
exports = module.exports = Player;
function Player (client, maxHistorySecondBuffer) {
entity.call(this, client.id, maxHistorySecondBuffer);
this.client = client;
this.inputs = [];
}
Player.prototype = Object.create(entity.prototype);
Player.prototype.addState = function (state, executionTime) {
this.addHistory(state, executionTime);
this.sequence += this.inputs.length;
this.inputs = [];
};
+165
View File
@@ -0,0 +1,165 @@
var garageServerGame = require('./garageservergame');
/*
options = {
stateInterval: 45,
logging: true,
clientSidePrediction: true,
interpolation: true,
interpolationDelay: 100,
smoothingFactor: 0.3,
pingInterval: 2000,
maxUpdateBuffer: 120,
maxHistorySecondBuffer: 1000,
worldState: {},
onPlayerConnect(callback(socket)),
onPlayerInput(callback(socket, input)),
onPlayerDisconnect(callback(socket)),
onPing(callback(socket, data)),
onEvent(callback(data))
}
api methods
createGarageServer(io, options)
start()
stop()
getPlayers() : [,{ id, state, [,inputs], [,{ states, executionTimes }] }]
getEntities() :[,{ id, state, [,{ state, executionTime }] }]
updatePlayerState(id, state)
updateEntityState(id, state)
addEntity(id)
removeEntity(id)
sendPlayerEvent(id, data)
sendPlayersEvent(data)
*/
function GarageServer(socketio, options) {
var namespace = '/garageserver.io';
this.socketPath = namespace;
this.io = socketio;
this.registerSocketEvents(options);
this.game = new garageServerGame(options, function (state) {
socketio.of(namespace).emit('update' ,state);
});
}
GarageServer.prototype.registerSocketEvents = function (options) {
var self = this;
self.io.of(self.socketPath).on('connection', function (socket) {
if (options.logging) {
console.log('garageserver.io:: socket ' + socket.id + ' connection');
}
socket.emit('state', {
physicsDelta: (options.physicsInterval ? options.physicsInterval : 15) / 1000,
smoothingFactor: options.smoothingFactor ? options.smoothingFactor : 0.3,
interpolation: options.interpolation ? options.interpolation : false,
interpolationDelay: options.interpolationDelay ? options.interpolationDelay : 100,
pingInterval: options.pingInterval ? options.pingInterval : 2000,
clientSidePrediction: options.clientSidePrediction ? options.clientSidePrediction : false,
maxUpdateBuffer: options.maxUpdateBuffer ? options.maxUpdateBuffer : 120,
worldState: options.worldState ? options.worldState : {}
});
self.onPlayerConnect(socket, options);
socket.on('disconnect', function () {
if (options.logging) {
console.log('garageserver.io:: socket ' + socket.id + ' disconnect');
}
self.onPlayerDisconnect(socket, options);
});
socket.on('input', function (data) {
if (options.logging) {
console.log('garageserver.io:: socket input ' + socket.id + ' ' + data[0] + ' ' + data[1]);
}
self.onPlayerInput(socket, data, options);
});
socket.on('ping', function (data) {
if (options.logging) {
console.log('garageserver.io:: socket ping ' + data);
}
self.onPing(socket, data, options);
});
socket.on('event', function (data) {
if (options.OnEvent) {
options.OnEvent(data);
}
});
});
};
GarageServer.prototype.onPlayerConnect = function (socket, options) {
this.game.addPlayer(socket);
if (options.onPlayerConnect) {
options.onPlayerConnect(socket);
}
};
GarageServer.prototype.onPlayerDisconnect = function (socket, options) {
this.game.removePlayer(socket.id);
socket.broadcast.emit('removePlayer', socket.id);
if (options.onPlayerDisconnect) {
options.onPlayerDisconnect(socket);
}
};
GarageServer.prototype.onPlayerInput = function (socket, input, options) {
this.game.addPlayerInput(socket.id, input[0], input[1], input[2]);
if (options.onPlayerInput) {
options.onPlayerInput(socket, input);
}
};
GarageServer.prototype.onPing = function (socket, data, options) {
socket.emit('ping', data);
if (options.onPing) {
options.onPing(socket, data);
}
};
GarageServer.prototype.start = function () {
this.game.start();
};
GarageServer.prototype.stop = function () {
this.game.stop();
};
GarageServer.prototype.getPlayers = function () {
return this.game.getPlayers();
};
GarageServer.prototype.getEntities = function () {
return this.game.getEntities();
};
GarageServer.prototype.updatePlayerState = function (id, state) {
this.game.updatePlayerState(id, state);
};
GarageServer.prototype.updateEntityState = function (id, state) {
this.game.updateEntityState(id, state);
};
GarageServer.prototype.addEntity = function (id) {
this.game.addEntity(id);
};
GarageServer.prototype.removeEntity = function (id) {
this.io.of(this.socketPath).emit('removeEntity', id);
this.game.removeEntity(id);
};
GarageServer.prototype.sendPlayerEvent = function (id, data) {
this.game.sendPlayerEvent(id, data);
};
GarageServer.prototype.sendPlayersEvent = function (data) {
this.io.of(this.socketPath).emit('event', data);
};
exports.createGarageServer = function (io, options) {
return new GarageServer(io, options);
};
+119
View File
@@ -0,0 +1,119 @@
var playerController = require('./controllers/playercontroller'),
entityController = require('./controllers/entitycontroller');
exports = module.exports = GarageServerGame;
function GarageServerGame(options, broadcastCallback) {
this.options = options;
this.startTime = 0;
this.stateInterval = options.stateInterval ? options.stateInterval : 45;
this.stateIntervalId = 0;
this.playerController = new playerController(this.options.maxHistorySecondBuffer ? this.options.maxHistorySecondBuffer : 1000);
this.entityController = new entityController(this.options.maxHistorySecondBuffer ? this.options.maxHistorySecondBuffer : 1000);
this.broadcastCallback = broadcastCallback;
}
GarageServerGame.prototype.start = function () {
var self = this;
this.startTime = new Date().getTime();
this.stateIntervalId = setInterval(function () { self.broadcastState(); }, this.stateInterval);
};
GarageServerGame.prototype.stop = function () {
clearInterval(this.stateIntervalId);
};
GarageServerGame.prototype.broadcastState = function () {
var currentTime = new Date().getTime() - this.startTime,
state = { time: currentTime, playerStates: [], entityStates: [] };
state.playerStates = this.getState(this.playerController);
state.entityStates = this.getState(this.entityController);
this.broadcastCallback(state);
};
GarageServerGame.prototype.getState = function (controller) {
var states = [];
controller.entities.forEach(function (entity) {
states.push([ entity.id, entity.state, entity.sequence ]);
});
return states;
};
GarageServerGame.prototype.getPlayers = function () {
var list = [];
this.playerController.entities.forEach(function (player) {
list.push({ id: player.id, state: player.state, inputs: player.inputs, stateHistory: player.stateHistory });
});
return list;
};
GarageServerGame.prototype.getEntities = function () {
var list = [];
this.entityController.entities.forEach(function (entity) {
list.push({ id: entity.id, state: entity.state, stateHistory: entity.stateHistory });
});
return list;
};
GarageServerGame.prototype.getPlayer = function (id) {
var playerFound;
this.playerController.entities.some(function (player) {
if (player.id === id) {
playerFound = player;
return true;
}
});
return playerFound;
};
GarageServerGame.prototype.updatePlayerState = function (id, state) {
this.updateState(this.playerController, id, state);
};
GarageServerGame.prototype.updateEntityState = function (id, state) {
this.updateState(this.entityController, id, state);
};
GarageServerGame.prototype.updateState = function (controller, id, state) {
var currentTime = new Date().getTime() - this.startTime;
controller.entities.some(function (entity) {
if (entity.id === id) {
entity.addState(state, currentTime);
return true;
}
});
};
GarageServerGame.prototype.addPlayer = function (client) {
this.playerController.add(client);
};
GarageServerGame.prototype.removePlayer = function (id) {
this.playerController.remove(id);
};
GarageServerGame.prototype.addEntity = function (id) {
this.entityController.add(id);
};
GarageServerGame.prototype.removeEntity = function (id) {
this.entityController.remove(id);
};
GarageServerGame.prototype.addPlayerInput = function (id, input, sequence, time) {
this.playerController.addInput(id, input, sequence, time);
};
GarageServerGame.prototype.sendPlayerEvent = function (id, data) {
this.playerController.entities.some(function (player) {
if (player.id === id) {
player.client.emit('event', data);
return true;
}
});
};