This page contains a simple D20 roller. Click on the hexagon below to get a random number and click again to clear the last result.
How it works
The problem is that JS is so awesome that people started using it everywhere. While you really do need JS in order to create dynamic webpages, it isn’t necessary in most places; the term “website obesity crisis” came to be used to describe the fact that most websites nowadays focus too much on fluff and unnecessary dynamism, and too little on content and accessibility.
CSS to the rescue
Besides JS, another major component of web development is CSS, which describes how everything should look on the page. But what does this have to do with the dice roller? Well, for starters, CSS is super light and 100% secure, however it has a often overlooked feature called Animations.
I almost didn’t believe my eyes when I first read Creating randomness with pure CSS. The gist of the article is that you can use CSS to move an image back and forth behind a virtual slit and stop it only when the user clicks a button. If your image is a bunch of playing cards stitched together, only one of them will show through the slit once the animation stops.
The genius insight is that, if the animation is fast enough, the slight variations in the user’s clicks will effectively make the slit show a random card each time!
This was the JS substitute I needed. Now all I had to do was apply this method to a list of numbers instead of an image. It did take some time, but I scoured the web for a solution and eventually found it in iokaravas’ JS-free slot machine.
Their code takes three lists of numbers and animantes them up and down until they land on the combination set by the programmer. Despite being deterministic, this could seamlessly be integrated with Creating randomness’ technique to create exactly what you see at the top of this page.
TL;DR: in the dice roller above, there is actually an invisible list of numbers being animated up and down which stops when you click it. The randomness comes from the fact that it’s moving too fast for anyone to be able to time it.
A few key facts:
It’s light. While Google’s dice roller is 2.6MB and loads in 1.6s, this one is 7.1kB (~360x lighter) and loads in 50ms (~30x faster).
It’s fair. I ran a Chi-squared test with 1000 samples taken at random time intervals and it is in fact fair (p = 0.7575).
Thanks for reading!