Introducing playm64.net - Multiplayer N64 Emulation in the Browser

· 783 words · 2 minute read

Over the course of the pandemic, I – like many others – found myself spending a lot more time indoors. Around this time I had developed an interest in WebRTC, and I started to play around with creating a simple 2d multiplayer game that could be played in the browser. I was aiming for a top-down medieval arena game, with different objective-based game modes. Not the strongest vision for a game, sure, but it gave me enough to get started, and like a wise person once said: “Weeks of programming can save hours of planning”. I dubbed the project “Battle Arena Online” (lame, I know), and set myself to work.

An unreleased version (there are no actual releases) of “Battle Arena Online”, circa early 2020. Complete with the best graphics I could muster, and arrows that shoot from swords. A portion of the matchmaking, room management, and WebRTC signaling functionality was adopted for playm64.net

As time passed, I got to a point where I had many of the boring parts of a networked game working. Things like matchmaking, game queueing, and player interpolation and input prediction. Each of these had their own challenges, and I learned a lot trying out different strategies for overcoming them. As it turns out though, making something that works and making something that’s fun and interesting to play are two different things. I had spent a lot of time focused on (and rather enjoying) the former, to the point where I found I had a lack of direction for the latter.

I kept trying to imagine a game that my friends would enjoy playing. COVID-19 had us all stuck inside, and we found ourselves having online game nights much more often. It made me nostalgic of the nights spent playing splitscreen huddled in front of a glowing box CRT screen early in my childhood, which eventually manifested and inspired me to abandon “Battle Arena Online”, and instead create playm64.net.

A netplay session in playm64.net with my favorite non-Nintendo-licensed N64 game, Telocation, where two different players are being controlled independently from separate browser sessions for some co-op play

The idea was simple: try to recreate that splitscreen experience for the Nintendo 64 in the browser. In the middle of each user’s screen would sit the old CRT TV, and below it there would be controller slots that could be reassigned to different players in the session. Every user in the session would see the same game image and audio being played on their virtual TV, and the users that were assigned controllers could play the game. It would be just as if all the players were in the same room together playing an actual N64.

This isn’t a new concept or idea of course. Netplay for n64 emulation has been around for 10+ years, and there are now even cloud-gaming services like parsec or jam.gg, which can share the video feed of a single running emulator with each participant. The challenge here is getting this all to work in the browser in a manner that is at least somewhat playable. Short of starting a video streaming service, this means trying to get an emulator working in the browser with netplay support.

playm64.net (the “m” being a reference to the Mupen64plus emulator) is my attempt at accomplishing this. It allows users to form netplay sessions, where each player has their own emulator running their own copy of a particular ROM, with “playback” synchronized with everyone else in the session. There were a number of pieces that needed to be in place in order for this to work:

  1. mupen64plus-web, which is an attempt at compiling the Mupen64Plus emulator into a somewhat web-friendly module with Emscripten
  2. A netplay server implementation written in Typescript based on loganmc’s original netplay server implementation, with some additional added functionality to allow for synchronized pausing, controller swapping, and join-in-progress
  3. A “matchmaking” + WebRTC signaling service, which I may release the source for one day ¯\_(ツ)_/¯
  4. A crappy React frontend to bring it all together

I hope to write more about each of these in future blog posts. As for now, the result seems to be somewhat playable for a good portion of games running on chrome with modern hardware. There’s certainly plenty of improvements that can be made, especially as browser technology continues to evolve and open doors for projects like this to take better advantage of client hardware. I expect most future efforts will likely be to work towards improving the accuracy and performance of mupen64plus-web, but as of late I’ve been trying to spend more of my free-time on non-computery things, so I guess we’ll see :)