Ever felt like you needed something to sink a whole bunch of time into?
Some silly yet at the same time very satisfying, extremely glowy project?
Well, maybe this could be for you! This Lasertag project was created mainly out of my interest, over a long and fun process of a few years - of the last few have been documented here!
The whole project is still very fluid and active as of Oct. 2019, and I am making more and more sure that it is suitable for anyone to build and experiment with, without compromising on some of the more awesome features that any good Lasertag system should have.
Below, I'll outline a few nice key aspects of the system - if you want to see videos of its progress or similar though there are always the project logs further below ;)
This project had a history of somewhat haphazardly hardware, using a breadboard and only an ATMega328P.
This is no longer the case as of Revision 3.2, and I can proudly say that this project has evolved to have expert hardware.
Based on the powerful ESP32 this project's PCB features a set of numerous peripherals to deliver a rich game experience.
These include a 44.1kHz I2S audio amplifier for crisp game sounds, an I2C gyro/accelerometer to detect gestures and player activities, and multiple WS2812 LEDs, both on the PCB and broken out on the vest, to provide colourful visual feedback.
Aside from this the board also contains a robust 3.3V LDO, good capacitance to keep the ESP running, a USB to UART converter with an auto-programming circuit, a LiPo charge circuit with voltage measurement, and a vibration motor to provide haptic feedback.
Despite all this, the boards are designed with ease of use in mind. It features only two components that require hot air reflowing - one of which (the IMU) is optional, the other one can be replaced with a cheaply available breakout board.
All other components are hand-solderable 0805 capacitors and resistors as well as a few TSOP packages - nothing that a fine soldering iron couldn't handle.
Communication between the sets is done via a simplistic but surprisingly effective IR channel. Using 850nm VSCEL IR lasers as emitters, their range exceeds 40 meters in good conditions.
Sunlight sadly reduces this to just a few meters, but during dawn, dusk, or indoors, this will work plenty.
The receivers are made from a simple single-sided board, but even they feature a nice WS2812 LED and high-quality 40kHz VISHAY receivers that provide precise decoding of the IR signals.
Due to the nature of the IR encoding, cheaper AVR based modules like my IR-Bacon can also be used as positioning beacons, providing a cheap way to set up capture points and spawn rooms. The signals can even be expanded to include custom signals, such as grenade shots, weapon type, and other interactions.
Now, this is where it gets a bit more interesting. For Revision 3.2, a lot of the code on both server and client-side have been majorly reworked and documented, making sure they provide a simple but flexible interface for the user to work with.
Based on the ESP-IDF v3.3 the firmware for the ESP has been written in pure C++. This makes sure that it remains fast and snappy in all situations.
The ESP handles a multitude of tasks, the most important of which are:
- Providing a smooth 60FPS LED animation
- Running the I2S sound interface
- Detecting and sending shots, which includes different weapon profiles, ammo counting and reloading.
- Sending measurements back to the server
- And providing the player with haptic and visual feedback about their score and other statistics
Communication is done via MQTT, providing a solid, low-latency backend. This also makes it very easy to let other modules and programs interact with the Lasertag environment, as libraries to communicate via this protocol are available for almost all languages.
A BlueTooth configuration mode will also be available soon, making it easy to set your WiFi SSID, password and MQTT server IP on the fly.
For the backend, Ruby was chosen as programming language due to its wonderfully flexible and easy to learn nature. The lasertag library gem (lzrtag-base) provides a well documented and sturdy interface for anyone to work with while handling a lot of the heavy lifting in the back.
Once the Ruby server is started, it handles a plenitude of tasks:
- It hands out unique IDs to any connected lasertag sets. Up to 255 are supported simultaneously, so running out won't happen soon.
- It receives and processes "hit" events of the lasertag sets. This is to prevent a single physical shot to hit multiple people at once, while not letting hits to dead players or friendly-fire count - though this is highly customizable.
- After triggering a hit it computes the dealt damage to a player, letting the application modify this value based on shielding, class, weapon, etc, while also providing automatic or area-of-effect based regeneration.
- It configures all players and thusly creates the whole game. Each player can be given a unique behaviour, with distinctive flash patterns, team colours, weapon loadouts, tasks, and so forth! It's quite rich and creates the immense flexibility of the system that I wanted to strive for.
- Everything that happens inside the game triggers events. These are messages with a small payload, giving the user information on player team changes, kills, beacons, anything that you need to create your game.
- Finally, and most importantly, it allows for so-called hooks and game configurations to be loaded on the fly. Each hook can define specific actions and behaviours, like validating a shot, calculating damage, killing a player or tracking scores. This makes for an immensely powerful, yet simple way of creating games and game-styles:
- Do you want to create a Zombie-Type game mode? Sure, just change a player's team when he dies! You want to create Team Deathmatch or Capture the Flag? Just write up a little bit more Ruby code to handle the appropriate events, and you're good to go!
One last note:
In the future, there will almost certainly be a React-based web interface and a SQL server to control and track your games!
The former already has a proof of concept, while the latter will be easy to implement by simply hooking into the MQTT broker of the game - so stay tuned!