Fish Game - An open reference game using Nakama for multiplayer

Fish Game is an open game development project, sponsored by Heroic Labs.

We are making this game because:

  • Nakama users need better from-scratch examples of how to build multiplayer games with Nakama in the stack.

  • Nakama developers need dogfooding projects that are easy to sustain long-term.

  • Indie game developers need more in-depth tutorials and reference implementations of networked multiplayer games.

  • The open game development ecosystem needs standardized language & models for talking about network design.

A “RealWorld” example for multiplayer games

In web development there’s a hugely popular ‘glue layer’ project called RealWorld.

See how the exact same Medium.com clone (called Conduit) is built using any of our supported frontends and backends. Yes, you can mix and match them, because they all adhere to the same API spec :open_mouth::sunglasses:

While most “todo” demos provide an excellent cursory glance at a framework’s capabilities, they typically don’t convey the knowledge & perspective required to actually build real applications with it.

RealWorld solves this by allowing you to choose any frontend (React, Angular 2, & more) and any backend (Node, Django, & more) and see how they power a real world, beautifully designed fullstack app called “Conduit”.

Read the full blog post announcing RealWorld on Medium.

So this is effectively what we’re setting out to do, in our own small way. Certainly we’re gonna have to go about it a bit differently because web app architecture doesn’t map 1:1 to games, but the fundamental concepts are largely the same. Games, just like web apps, can draw a pretty clear line between backend and frontend.

Our minimal approach here is to start by making the same game in two different toolsets. There won’t be a strict API spec to follow yet; the two implementations will merely follow an identical Fish Game - Game Design Document.

Godot and Macroquad (Rust) as first examples

For our two initial game examples, one will be made in the Godot Engine and the other in Rust-lang with macroquad. Both will use Nakama for their social multiplayer infrastructure ( i.e. authentication, matchmaking & leaderboards) as well as real-time multiplayer.

Godot is the most popular game engine among indie and open source game developers. It’s also very high level (if desired), letting users make games with its own GDscript.

Rust for gamedev on the other hand is a fast-growing new trend. It’s pretty much as low-level as any gamedev gets (without the foot-guns :heart_eyes_cat: ). The language has an official Working Group dedicated to gamedev.

Both games will be full-stack implementations of loosely coupled back- and front-ends for the Fish Game concept.

:bulb: While it is entirely feasible to make a game with a Rust backend and Godot frontend, we won’t be attempting that for now. Check out godot-rust for excellent guidance and examples on that front.

The :fish: Game(s)

What we are making is an open remake of the excellent Duck Game.

Blast your friends with Shotguns, Net Guns, Mind Control Rays, Saxophones, Magnet Guns, and much, much more. This is DUCK FISH GAME. Don’t blink.

Key Features

  • 2 to 4 players in either Local Multiplayer or Online Play
  • Easy to pick up, emphasizing strategy over twitch reaction
  • Customize characters with hats, saved to your cross-platform profile (later)
  • Create & explore user-made levels (later)

Why a remake of Duck Game

Duck Game is an excellent game. It deserves the 10/10 rating it can boast on Steam. But it is also a bit stuck in an older tech stack. A combination of tech debt and lacking cross-platform infrastructure makes it very PC-centric. It’s been ported to other platforms, albeit with a more limited experience (e.g. no online map sharing on consoles).

It is also a perfectly moddable game, enabling players to make and share custom maps, weapons and, most importantly, hats! :womans_hat: This level of moddability lends itself exceptionally well to open source practices. Hence our belief that we can level up what Duck Game currently is.

There’s ample opportunity for collaboration here: Fish Game should not be perceived as a threat, but rather as a tribute to Duck Game. We are not looking to co-opt the game; we wanna help make it better.

Play & Inspect!

The games are currently at varying stages of development. None of them have yet incorporated our awesome art pack by Pixel Frog. We’ll post more updates as we near completion in the coming weeks.

Please feel free to reply here with any first impressions or questions you may have.

Godot version

Rust Version

Unity Version

6 Likes

Thanks! Adding multiplayer and social functions to my Godot game is one of my top priorities for the couple of month. But I’m hesitating to start with Nakama lacking tutorials and examples.
This project is also not easy to pick up because the game is already rather complex and there are no comments in code or help for usage of Nakama functions. Created an issue for these questions.
Hope this project will help a lot of Godot users to start making MP games.

1 Like

Thanks for checking it out! I’ve replied on GitHub :slight_smile:

Chatted with you about this a bit on Discord, but following up here so maybe others can benefit. Here’s something I don’t get and would like clarity on.

Say I build my game in something like Bevy. I create my components, code up a number of systems to capture my game logic, etc.

I then want to make it networked. Obviously there’s more to making a network game than flipping a switch and deciding it’s networked, but never mind. :slight_smile: How do I achieve that with Nakama?

Unless I’m missing something, the way forward is to implement custom server code in Go/Lua. But does that mean I’m deconstructing my nice C#, Rust, etc. code into a series of Lua command handlers, and re-implementing my game logic in Lua or Go? Not that either are bad languages, I’m just not getting what the networking systems provide me. The authentication/matchmaking/leaderboard systems make sense, and maybe there’s some way to bridge these to existing server processes via GRPC calls so an existing server process in Rust might be told that connection ID X from IP Y is guaranteed to belong to account Z. But I don’t understand how a game like this is meant to work without essentially implementing significant game logic in more than one language.

Put more simply, I see what I assume is the Nakama client API in this example. Where is the server-side functionality? Is there a pile of missing Lua functions, or did I miss a page in the docs?

In fishgame we are trying to avoid any server side logic and use relayed multiplayer instead.

Check fishgame-macroquad as a reference, especially this: fishgame-macroquad/net_syncronizer.rs at master · heroiclabs/fishgame-macroquad · GitHub, its pretty much all the networking code involved in rust’s fishgame now.

1 Like

Hmm, there seems to be a lower-level networking API in wasm.rs for
sending/receiving data. Is this what’s being used on Nakama’s end, and
if so, is it documented anywhere? The readme mentions a networking API
that isn’t supported on PC yet, but I’m not clear where this API is
documented or which specific one it is, given that there isn’t mention
of any platform restrictions in the docs I’ve read so far.

But assuming you did want an authoritative server, how would you bridge
your game logic to Nakama without reimplementing significant portions in
Lua/Go? I.e. say instead of a pingpong game as featured on
Authoritative Multiplayer - Nakama server, I
wanted to take client messages and process them with existing Rust logic
and return something to be processed by the clients. What would be the
recommended pattern for handing that data into my non Go/Lua server, if
in fact there is a way? Or should I be looking at a different subsystem?
Maybe the Rust game server implements some sort of GRPC handler for
consuming messages from the server, and the client Lua command handlers
call those custom APIs in my server?

Sorry, I know that isn’t in scope for this specific project. But I’ve
been wondering that for a while, and expected to find an answer in this
project. I think that at least saying something like “Look into X and Y,
documented at Z” would put folks on the right track.

Thanks!

The nakama crate is heavily work in progress and is only (very)partially implemented for wasm at the moment.
We do not use any authoritative multiplayer - fishgame use relayed multiplayer instead.

I do not have any advices for rust authoritative server. Right now server modules may be implemented only in Go, Lua or (as of 3.0) TypeScript, and I do not know about any plans on general C API for server modules or rust modules support.

2 Likes

@nolan You might be interested in this fork where I’m adding C-language module support.

My plans are to enable C/C++/Rust server-side logic, using this crate to provide a “Rusty” API. This should get to the merge-review stage soon.

1 Like

Interesting. I’m mildly concerned about your nakama crate. Is it only
for server-side logic, as indicated in its description? What about
client-side code wanting to update a leaderboard? Hoping it’s just a
matter of a quickly-written description.

Thanks for the pointers, I’ll be watching both repos.

Hmm… Good point! That description needs to be tweaked. The stuff I mentioned will help writing a server, and the other stuff in this thread helps write a client.

Joining these two separate efforts is on-going work.

The Unity version of Fish Game and its accompanying tutorial is now out! :point_down:

1 Like