Creating collaborative sketches with web sockets on OpenProcessing.org

It is very easy to create a P5JS sketch that allows multiple users to connect at the same time, and make a collaborative drawing or play multiple sounds using p5.sound library. Below is a quick tutorial on how to. Give it a try, and contact me (Sinan) if you have any questions!


How does it work?

Usually, a standard p5js sketch on OpenProcessing runs in your browser when you are viewing it. It doesn’t have a sense of who else is viewing the same sketch during the time you are viewing it. By using web sockets, we will use OpenProcessing web socket server to send messages to any other user that is viewing the same sketch at the same time. This way, all the users will be able to communicate with each other and send messages, such as “Hey, I am here drawing a circle on this position!!”. All the other users that receive this message will take the related action (draw a circle for the user above), therefore all the users will be able to interact and draw collaboratively on the same canvas live.

If you decide to build your own socket server instead definitely check out Daniel Shiffman’s web socket videos on Youtube.

When creating web sockets manually, the hardest part is to create a socket server that listens to any clients connecting and decide what to do with those messages. This requires relatively heavy terminal action to install a node server on your computer and write the code that defines the actions of the server. The good news is: OpenProcessing covers you on this part! Every sketch has a socket server set up already, which echoes (broadcasts) every message to all the other users who are viewing the same sketch at the same time.

Start by creating a sketch on OpenProcessing

In this example, we will build on the default sketch that draws circles when user moves the mouse. 
Our goal will be to allow multiple users connect to the same sketch and draw on the same canvas at the same time.

Default code on OpenProcessing sketches draw ellipses on our mouse position

Make sure you save your sketch before you continue any further. This way, socket server will be enabled for our sketch on the OpenProcessing Server.

Enable Socket.IO library on your sketch

On the library list on the right, you will find SocketIO. Enable it to load socket.io library when our sketch is running. In the description, you can see that there is already the first line of code you will need to connect to the socket server running on OpenProcessing. Copy/paste the line to the top of your sketch code.

Copy and paste the line “var socket = ….”

Send a message to other clients

Once enabled, our sketch will connect to the socket server on OpenProcessing. Next thing we want is to send a message to all the other users that will connect to our sketch, with the information of the each ellipse we draw on the screen. We do this by using the socket.emit method:

socket.emit(“IamDrawing”, mouseX, mouseY);

This method basically sends a message to other users. A message (‘IamDrawing’) can be anything: we will use this to define what action to take later on. What follows this message is anything you want to add to this message. In this case, we want to let other users know our mouse position, so that they can put an ellipse on that location as well.

You code should look like above at this point.

Define what to do when a message received

So far, we coded when to send a message, but we did not define what to do when our sketch receives a message. In this example, we want to draw a similar ellipse on behalf of other users on our screen. Let’s define that function first.

function drawEllipse(x,y){
ellipse(x, y, 20, 20);
}

All that is left is to make this function run every time there is a message, and we do this with socket.on method:

socket.on("IamDrawing", drawEllipse);

As self-explanatory as itself, with the code above we are telling our socket connection to run the function ‘drawEllipse’ function everytime it receives the ‘IamDrawing’ message. It is okay to define it only once, so we will write this under Setup function.

Final code will look like below:

var socket = io.connect(":30000?sketch=422944");
function setup() {
createCanvas(windowWidth, windowHeight);
background(100);

//tell socket what to do when "IamDrawing" message is received
socket.on("IamDrawing", drawEllipse);
}
function draw() {
ellipse(mouseX, mouseY, 20, 20);

//tell socket to send a message every time we draw an ellipse
//with the coordinates of our mouse
socket.emit("IamDrawing", mouseX, mouseY);
}
//this function will be run every time a message is received
function drawEllipse(x,y){
ellipse(x, y, 20, 20);
}

You can find the final sketch below:
https://www.openprocessing.org/sketch/422944

Time to test!

This is a good time to test our sketch. If you have friends around to invite, save your sketch, and share the URL of your sketch. Once they open this in their browser, you should be able to go crazy with ellipses together!

You can also simply open a new browser window, go to the URL, to easily simulate multiple users joining to your sketch. What you draw on one browser window should show up on the other one!

In this test, I draw the top part on one window, and the bottom part on another.

Get Creative!

These 4 lines of code above pretty much sums up all you need to make users/sketches speak to each other in real time. The rest is up to you: You can assign different colors, sizes, or even shapes and behaviors to other users’ ellipses.

Below is a version we have created in CCFest workshop on April 24th, 2017, in which mouse speed defines the radius of the ellipses, and other connecting users’ drawing are displayed in red color.

Check out this sketch on https://www.openprocessing.org/sketch/422562

Share what you came up with and give feedback

I hope you enjoy creating collaborative sketches as I do, and please share if you have any feedback or if you come up with any sketches of your own in the comment section below. I would love to check them out, and any more examples would help others to learn better! Happy collaborative drawings!