Final Project Update
This week I continued work on my final project for Live Web. My goal was to integrate Socket.io into an existing P5.js sketch I created in The Nature of Code to enable multiple users on the same canvas.
After our earlier assignments in Live Web adding the basic Socket.io server code to the P5 sketch was simple enough. For my initial setup all users are peers on the same page. In order to reduce the workload on the server the user who has the oldest socket connection is dynamically assigned by the server as the “controller” of the planet array.
// Planet controller if(users[0].id == socket.id){ var data = true; socket.emit('planetController', data); //you are the first socket } else { var data = false; socket.emit('planetController', data); //you are not the first socket } socket.on('disconnect', function() { console.log("Client has disconnected " + socket.id); io.emit('peer_disconnect', socket.id); for (let i = 0; i < users.length; i++) { if (users[i].id == socket.id) { users.splice(i,1); } } // Update planet controller // First make sure a user is connected, otherwise server will crash if(users.length > 0){ var data = true; users[0].emit('planetController', data); //you are the first socket } });
The “controller” emits a planet array on a designated interval that is broadcast to the other users, currently every second, that is then applied by all other users.
Sorting out what data to send as the planet array took some troubleshooting. My initial attempt at emitting the array of planet objects resulted in an error in the Javascript Console:
Wrapping the array in JSON.stringify() lead to another error:
Manually looping through the necessary variables in the planet array lead to:
function emitPlanets() { if(planetControl && planets.length > 0 && fpsCounter == 1){ var planetArrayTemp = []; for (let [i, planet] of planets.entries()) { var planetTemp = []; planetTemp.push(planet.scale); planetTemp.push(planet.pos.x); planetTemp.push(planet.pos.y); planetTemp.push(planet.vel.x); planetTemp.push(planet.vel.y); planetTemp.push(planet.acc.x); planetTemp.push(planet.acc.y); planetTemp.push(planet.mass); planetTemp.push(planet.r); // Need to handle sound variables too!! planetArrayTemp.push(planetTemp); } console.log('Emitting planet array') socket.emit('planets', planetArrayTemp); //console.log(planetArrayTemp); } }
Which works!
There is still some optimizing to do, but the main functionality is there!