top of page

Dicey: An RPG Dice Rolling
Bot for Discord

A JavaScript-based Discord bot application designed to roll psuedo-random RPG dice notation for the purposes of playing various tabletop roleplay games.

THE PROBLEM

"Roll20 now utilizes a "true random" source of entropy, based on the quantum fluctuations in the power of a beam of light. All rolling is done via our server. This ensures that dice rolls on Roll20 are as random as possible."
- Roll20.net

Popular Virtual Table Top (VTT) website Roll20, claims to use "true random" entropy in their dice rolling calculations. However, the benefits of this randomiser - that spans all games across the web service at once - are not necessarily seen at the level of a single group of players.

 

There are many that doubt the efficacy and even relevance of Roll20's claims, given that they do not match up with the reported experience that the players are having. Many players report rolling the same result seven or eight times in a row on their turns - this becomes a problem when that result is too low to meet skill checks or DC values, resulting in the player's character repeatedly 'failing' a task (or multiple tasks) they are meant to be relatively competent at.

 

Unfortunately, Roll20 and many of its diehard fans have taken a staunch unwillingness to listen to this feedback, insisting that their randomiser is working as intended to absolve themselves of any responsibility to provide a good user experience.

 

The promise of "true random" leaves much to be desired in terms of user experience, and in many cases has actively been a detriment to many players' experiences of what is meant to be a fun game played with friends.

 

However, it begs the question: Are these 'true random' dice rolls really worth it if the end result is a miserable user experience for players? Or is it simply overkill for the sake of sounding impressive to purists?

HIGH LEVEL TIMELINE

Ongoing project of 3+ years that I am completing as a hobby project.

MAKE OF THE TEAM

I am the sole designer on this program.

PRIMARY GOAL

To create an alternative to Roll20's 'true random' roll calculation using their command notation that provides a better experience for players.

MY ROLE

This project was started as a hobby to expand my programming skills and create a better user experience for my fellow players.

This project utilises the RPG Dice Roller code library, as developing my own  psuedo-random number generation code library is currently above my skill level, and there is also no point in re-inventing the wheel when that is not the primary goal of the project.

ETHNOGRAPHIC STUDY

Below is a sample of the many posts made by users reporting a poor user experience with the Quantum Dice Engine. While many of these posts were made a few years ago, the complaints are still commonly heard in tabletop gaming circles today.

RESPONSES TO FEEDBACK

The responses to the above concerns have been, to put it charitably, dismissive. The repeated insistence on the quality of the Dice Engine based on its overall performance in all games across the userbase, and references to the psychology of randomness and Gambler's Fallacy, effectively dismiss the user's valid concerns about a poor user experience as user error, and prevents any further constructive discussion on improving the user experience in any capacity.

THE ISSUE WITH "TRUE RANDOM"

The issue with the Quantum Dice Engine is not a matter of its quality or efficacy. The arguments for the use of the dice engine are true and their comments about the psychology and perception of randomness are valid points to make. It IS true that a streak of the same number occurring multiple times in a row is a normal part of randomisation and entropy.

The issue, is that the purpose this dice engine is meant to serve to the user, is that of facilitating the enjoyment of and participation in, a tabletop game. This dice engine is meant to facilitate enjoyment and a pleasurable experience.

 

Currently, the dice engine is failing to do that for many of its users, and the steps that could be taken to explore solutions to this poor user experience are not being considered.

THE PSYCHOLOGY OF RANDOMNESS VS. THE PSYCHOLOGY OF PLAY

It only takes one brief look into the development of video games to understand that there are many things that game developers do, to facilitate an enjoyable user experience, that do not reflect reality or accuracy in situations.

 

The Polygon Article 'Video Game Developers Confess Their Hidden Tricks At Last' details many of the subtle ways in which game developers would tweak the percieved reality of their games to deliver a better, more satisfying game experience.

 

Invincibility frames, hitpoints with different weightings, characters not needing to eat or drink (in non survival games), hit/miss probability of enemies, first shots of enemies always missing, giving a few additional milliseconds of leeway in performing actions... the list goes on and on.

 

Every video game embodies this ethos in some way, because unless the game's express purpose is to be a 'Simulator' game, a simulationist experience is not actually that enjoyable to play - Indeed many 'simulator' games, such as Surgeon Simulator or Goat Simulator are fun because they do not adhere to the seriousness and granularity of real life. Psychology of play is a core unit in game development courses for this exact reason.

This is where the true crux of the issue lies. A truly random dice engine - however technically impressive it may be - is simply not fun.

 

It is not in the spirit of play to create a dice engine that leaves players frustrated and upset, particularly when for many, games are a form of escapism from difficult times in their life. If a player is breaking down in tears because they have repeatedly and consistently failed to achieve success due to the randomisation of a dice engine, the dice engine is failing in its duty to the player.

 

True random or not, this is an unacceptable user experience.

 

Tabletop gaming is about people playing games together, not computers; the tools must operate in service of the people and the games they are playing, and account for the infallibility of human nature in some way. Expecting people to operate like computers and accept computational outputs as gospel is the antithesis of user experience and human-centred design.

THE SOLUTION

So if the Quantum Dice Engine is not a suitable tool, what is?

As many have stated, even in the best circumstances, true random for the sake of TTRPGs is overkill. That level of accuracy in random number generation is rarely required outside of scientific research applications. Indeed, even physical RPG dice that started the genre are not that accurate.

Pseudo-random number generation is more than sufficient for the purposes of most tabletop gaming, and many Discord applications (known as 'bots') operate on pseudo-random number generation (or PRNG) for this reason.

Many tabletop gaming groups that play online do so through Discord, as it is designed to facilitate online gaming communication, and have opted to add bots to their servers in order to roll dice within Discord rather than Roll20.

 

Many of these bots, however, contain unnecessary features, particular aesthetic choices, or questionable development origins that make them unsuitable for many users.

As a result, I decided to make my own.

THE GOAL

Defining the goal for the look and feel of the bot was the first step.

As my primary goal was to create something as soon as possible for use in games, my goal was to take an already existing code base, learn what each part did, and then create my own that built upon this pre-existing code.

Originally I chose Dicebag by smarekp on GitHub. I wanted something simple with barely any features so that I could focus on the code required for the psuedo-random dice rolling. Dicebag was a basic JavaScript bot that used the RPG Dice Roller codebase by GreenImp, with a handful of extra utilitarian commands.

THE PROCESS

As this bot was intended to replace the functionality of Roll20's Quantum Dice Engine, I wanted the method of writing out the command to replicate the experience of Roll20.

As such, the bot needed to follow the parameters of a prefix - in this case '/r' or '/roll', followed by the dice notation, e.g. "/r 1d20+5" or "/r 5d6". This would keep the bot in line with current user habits, expectations and behaviours that had been built by the Roll20 system, allowing for easy adoption of the new system.

 

It also needed to be able to accept modifiers and parameters to change the behaviour and resulting output of the dice roll. Fortunately the rpg-dice-roller code already handles all of the requirements for many mainstream and obscure tabletop game systems, including 'exploding dice', where a specific value on a die 'explodes' and allows additional dice to be rolled and their results added to the dice pool.

 

All I needed to do was use Node Package Manager to set up the workspace, set a config file with the discord API token and '/' prefix, and create a basic javascript command to listen for user messages that met the right conditions, and serve the answer from the rpg-dice-roller.

THE CODE

// Load up the appropriate libraries and dependencies

const fs = require('node:fs');

const path = require('node:path');

const { Client, Collection, GatewayIntentBits, Partials } = require('discord.js');

const { DiceRoll } = require('@dice-roller/rpg-dice-roller');

const { prefix, token } = require('./config.json');

 

// Create the Bot as a Discord client with appropriate permissions

const client = new Client({

    intents: [

        GatewayIntentBits.Guilds,

        GatewayIntentBits.MessageContent,

        GatewayIntentBits.GuildMessages,

        GatewayIntentBits.DirectMessages

    ],

    partials: [

        Partials.Channel,

        Partials.Message

    ]

});

 

// When bot is loaded and ready to take commands, print message to the console

client.once('ready', () => {

    console.log('Ready!');

});
 

// Prevent recursion by exiting early if message author is a bot or doesn't start with designated command prefix

client.on("messageCreate", (message) => {

    if (!message.content.startsWith(prefix) || message.author.bot)

        return;

    // Listen for command and execute if command meets argument parameters, otherwise display an error to user and exit

    const args = message.content.slice(prefix.length).trim().split(/ +/g);

    const command = args.shift().toLowerCase();

    if (command === "roll" || command === "r") {

        if (!args.length)

            return;

        try {

            const roll = new DiceRoll(args[0]);

            message.reply({ content: `You rolled ${roll.output}` });

        }

        catch (_b) {

            message.reply("Invalid roll");

            return;

        }

    }

});
 

// Log in the client into Discord using the API token contained in the config file

client.login(token);

OUTCOMES

The bot surpassed expectations and has been in use for over three years, completely replacing the Roll20 dice engine for players in my game groups.

Dicey has become the main virtual dice solution for players in my game groups due to its ease of use, centralising the roleplay experience within Discord alongside the voice chat, and eliminating the issue of a bad gameplay experience by offering the same functionality and pRNG of physical dice.

Even for players who primarily use physical dice during online games, if they are in a position where they don't have access to physical dice, their first choice is to use Dicey, not Roll20's dice engine.

I later obtained and set up a Raspberry Pi computer to host the dice code on so that the bot could remain online 24/7.

REFLECTIONS

"If you want your users to fall in love with your design, fall in love with your users." - Dana Chisnell

Perhaps the most indicitive evidence that true random is not necessary, is the fact that the players that that have used Dicey have had no reason to return to Roll20's dice engine in the four years since its introduction.

Even in the case where true random was a necessary or valuable use of resources, there are other ways to mitigate the effect of Gambler's Fallacy without resorting to blaming it on user error.
 

If Roll20 had been focused on delivering a human-centred experience with their services, the wise thing would have been to lean into Gambler's Fallacy and implement a 'dice shaming' feature that is a common cultural habit amongst players, with everything from 'dice jails' to dice-sized dunce caps - this would have allowed users to 'rectify' the perceived error, and allowed them to better manage their emotional expectations for the RNG without actually having to change the way the RNG works at all.

Another solution would be to allow a toggle between the Quantum Dice Engine and a standard pRNG option, to allow players to choose if one RNG type was not delivering a positive user experience.

 

These are just some of the many solutions I can think of without even conducting participatory user research. Any one of these options could be explored if there was appetite to do so and would take comparatively minimal resources to implement.

 

Unfortunately, even four years on from this project's inception, and almost ten years since the first reports of poor user experience, there have been no further changes or additions to the Quantum Dice Engine.

 

Until such a time comes when Roll20 begins to listen to and value the experiences of their players and take a human-centred design approach to improving user experiences with their products and services, Dicey and other pRNG dice bots remain an essential part of the current landscape of virtual tabletop gaming.

bottom of page