You’ve probably seen the visualization below, but if not, it’s called the Mandelbrot set1. Generally, this is referred to as a fractal, which is a geometric structure that contains detail at arbitrary scales.

Mandelbrot visualization

I won’t write too much about this as there are already many wonderful resources on the topic2. The focus of this post is more about visualization using bare-bones Go. Without pulling in a third-party dependency, or even having to define a complex number type, you are able to implement a full video sequence zooming in on the Mandelbrot set!

As a primer, the Mandelbrot set is defined in the complex plane. The set is defined for some complex number, cc, for which the following does not diverge to infinity when iterated (starting at z=0z = 0):

fc(z)=z2+c\begin{align*} f_c(z) = z^2 + c \end{align*}

It is also known that the set is bounded by an absolute value of 22 (Specifically, the complex number with the largest magnitude in the set is 2-2).

So, for the visualization, set c to each coordinate3 in the image and iterate (up until a hand-picked maximum) to determine whether the point is in the set. If at any point the magnitude of the complex number is greater than 22, you can stop iterating. We can actually scale the iteration count to a value between zero and one to indicate how quickly it shoots off to infinity. Zero means almost immediately, and one means it’s likely within the set. Here’s the entire snippet for calculating this ratio for a given pixel:

// In the source, you'll see that this scales based on the
// zoom factor, but it's otherwise the same idea.
c := complex(
  scale(float64(x)/float64(WIDTH), -2.3, 0.5),
  scale(float64(y)/float64(HEIGHT), -1.14, 1.14),
)


z := complex(0, 0)
var steps int
for steps = range MAX_STEPS {
  if cmplx.Abs(z) > 2 {
    break
  }
  z = z*z + c
}

intensity := (float64(steps) / float64(MAX_STEPS-1))

Go is not my personal first choice for most projects, but the standard library really supports the freedom of demoing visualizations like this. Within Go, you have image/png and math/complex (and the associated packages) which is enough to iterate on the Mandelbrot set and render out a PNG sequence. From there, you can use something like FFmpeg to render the sequence to video. In my case, I used the following settings:

ffmpeg -i out/mandelbrot-%03d.png \
       -framerate 25 \
       -c:v libx264 \
       -pix_fmt yuv420p \
       -vf scale=1280:-1 \
       out/output.mp4

With that, you arrive at the following:

You’ll notice the video has more color-banding. This is simply because I rendered the images with fewer iterations. Increasing the iteration count reduces the banding.

  1. GitHub link

Footnotes

  1. https://en.wikipedia.org/wiki/Mandelbrot_set 

  2. Such as: https://acko.net/blog/how-to-fold-a-julia-fractal/ 

  3. Specifically, coordinates of the image scaled to the range of the Mandelbrot set (which is within the absolute range of 2 in both directions).