Basecamp recently announced Hotwire and it seemed like a perfect replacement to complicated React code I was using to build a browser-based, role-playing game. While still a little rough around the edges, it’s impressive how a few HTML elements can change how interactive a website is.
Subscribing to Streams
The game is based around the concept of individual rooms which isolate communication, items, enemies, etc. Characters stream from the room they’re in to receive messages.
Behind the seasons it creates a custom
<turbo-cable-stream-source> element, which triggers a channel subscription via Action Cable. Now we can trigger the standard stream events to append, prepend, replace, and remove elements from the target.
Unsubscribing from Streams
When a character in the game leaves a room, they need to unsubscribe from the room their leaving and subscribe to the room their joining. The new subscription is done the same as before, but unsubscribing from a stream wasn’t clear to me from the documentation.
After digging into the
turbo-rails code, I noticed that when a stream element is disconnected it’ll automatically unsubscribe.
So now that we know if we remove the element the subscription is unsubscribed, how do we remove the stream element?
As mentioned before, the Turbo stream has a remove event that can remove any DOM identifier, not necessarily specific to Turbo connected elements. Unfortunately, the
turbo_stream_from helper doesn’t currently include an ID or parameter to specify one. Luckily it’s pretty easy to modify ourselves by adding our own version to a helper.
With the stream identified we can remove and add streams as needed, which works perfectly for us when a character is moving between two rooms.
While we can append the streams to any element, we’re appending to an element identified by
streams. This is simply to allow a central location to see what streams the character is connected to.
While Turbo requires thinking about implementation a bit differently, it’s incredibly easy to use and should be much easier to maintain than a full React application. I’m excited to see how Turbo is implemented over the next year.