Web Monkey n'at

Apocalypse Survival is Easy.

I'm quite suprized at how easy it is to survive the end-times as predicted by mediums, prophets, clergy, mathemeticians, charlatans, and true-believers. In 2012, it was the Mayan Calendar predictions, which were largely ignored - and later denounced - especially by Mayans living today. In 2011, it was Harold Camping predicting first May 21st, and when that fell through October 21st, would be the end-times as seen in Revelations. In ancient Rome there was a prophecy that 12 eagles revealed to Romulus the lifespan of Rome. Many believed each eagle to represent 10 years, bringing the end in 634 BCE; others thought the eagles represented days in a year setting the end in 389 BCE. These sorts of predictions are often made, and sometimes become popular in some circles but hardly ever come true. Some people are unduly distressed when they find themselves soon to be facing the end of the universe as we know it in a massive cosmic event, so I've decided to try and quell their fears. Maybe knowing you've likely survived a dozen or more moments of universal doom will also give you solace, knowing that the next time the world faces the final judgement probably won't be the last.

Apocalypse Survival

This single-page app fetches a JSON feed from wikipedia's List of dates predicted for apocalyptic events and parses out years, comparing them with the input year and tallying the number of failed predictions since then. It stores this data locally on initial load, and loads it from the local

So, find out how many apocalypses you've survived, today! or view the source on github

Glitchy 3bit dither

I'd like to officially introduce my latest pet project, Glitchy 3bit Dither, A project I started to help me emulate glitch art. In the past I've tried my hand at circuit bending, creatively short-circuiting and modifying physical devices. I've even played with more traditional glitches, but was inspired to create my own software to do so after seeing rumblesan. His cuttr project glitches images found on tumblr and posts them to another tumblog, . I quickly set out and created a python script using PIL to start glitching images from instagram. I started writing the tumblr code, but I didn't like the lack of control, and I didn't really want to make a rumblesan clone. Besides, how can you create art without the artist's input? After seeing caman.js, I knew I could do it in javascript, thanks to canvas. During my research I found 3bitdither, forked it, and set out to bend it to my will.


Here's a short list of some of the functions I've implemented.

  1. Random dithering rates each pixel against a random value, if it's higher than that value it's a white pixel, if it's lower it's black. I've also colorized it by rating each channel value of the pixel.
  2. Color shifting will play with the values by boosting or re-arranging the red, green, or blue channels.
  3. Slices move chunks of pixel and channel values in interesting ways, sometimes shifting colors as well.
  4. Sorts Sort chunks of pixels in place, producing gradient-like stripes of colors within the image.

This is a work in progress, so all of the code is subject to change; also I'm working on updating this to work with node.js on a separate branch, so all the code will have to be adjusted for that anyhow.


There are 4 different pages here, each offering their own unique take on the task,

  1. Demo will run each function against the original image once
  2. Glitch Only will apply a random set of glitches to the original image several times
  3. Glitch Cruiser displays 8 optional glitches surrounding your original image, selecting a glitched image will replace your original image in the center and use the selected image to create 8 new glitches surrounding it. Selecting your original image in the center will apply the next 8 functions to the original image, selecting any of the 8 images surrounding it will replace the center image and apply 8 more functions ontop of the one you just selected, this way you can follow a path through your options or make no changes at all. Lena, and 8 possibilities
  4. Glitch Chooser this allows you to select functions from a drop-down list to apply to an image, you can either apply a tranformation, or reset it to the way it was before, you can even reset it to the original image. Unliked Glitch Cruiser, you won't be able to see the results of a function before selecting it, but you can replace the latest image transformation again and again until you can see your desired results.

Technical Notes

imageData.data is a Uint8ClampedArray, one of the new Typed Arrays in javascript. They're part of the WebGL spec and should be available in all modern browsers. This array holds all the data for every pixel in the image, however it's stores 8-bit values, channel-by-channel instead of pixel-by-pixel, that is to say Uint8ClampedArray stores the image data like [R,G,B,A,R,G,B,A,R,G...]. This means that to deal with this array, you're going to have to increment the loop by 4, and handle the channel-values each time like this

var Uint8Arr = imageData.data;
for(var i = 0; i < Uint8Arr.length; i += 4){
    /* simple invert */
    Uint8Arr[i] -= 255;
    Uint8Arr[i+1] -= 255;
    Uint8Arr[i+2] -= 255;

This is a slow & tedious task, but there are other typed arrays, like Uint32Array which stores 32-bit values, converting an 8-bit array to a 32-bit array would cut the size of the array by a quarter. So Uint32Arrays store their data like [RGBA, RGBA, RGBA, RGBA....

var Uint32Arr = new Uint32Array(imageData.data.buffer);
for(var i = 0; i < Uint32Arr.length; i++){
    /* bitwise invert */
    Uint32Arr[i] = ~Uint32Arr[i] | 0xFF000000;

Here, a bitwise NOT (~) inverts the bits, and OR | applies a mask to keep the alpha channel at 100%. You may also notice that I'm using the imageData.data.buffer to make a 32-bit view of the 8-bit data, this means that you don't have to set the data back into the array, because it passes through to the original variable naturally.

While all the above is true for most personal computers which store data in Little Endian, some other machines may use Big Endian notations, which would reverse the order of the data from RGBA to ABGR. If you were making imaging software you'd probably want to account for that, but since the point of this project is to maim images it's only mildly important to ensure the alpha channel is applied correctly (or just set to 100%.)