Updated 2017-04-05 23:11:38 by sergiol

Arjen Markus (25 august 2003) I got to know them during the hype in the late 1980s: pictures of the Mandelbrot set -- beautiful, enigmatic and so easy to create!

Later, I learned their counterpart too: Julia sets. And now, more than a decade later, I have finally taken the time to do them in Tcl too.

Here is a quickly written script - I will use it in one of the chapters for the young programmers' tutorial/booklet ...

(I have not cleaned up the code and there is no GUI to select between the two types, or to change the parameters or to zoom in ...)

Mandelbrot: Julia:
 # Mandelbrot and Julia pictures
 proc det_iteration { zx zy cx cy maxiter } {
    set znx $zx
    set zny $zy
    set noiter -1

    for { set i 0 } { $i < $maxiter } { incr i } {
       if { hypot($znx,$zny) > 2.0 } {
          set noiter $i
       set znnx [expr {$znx*$znx-$zny*$zny+$cx}]
       set znny [expr {2.0*$znx*$zny+$cy}]
       set znx  $znnx
       set zny  $znny

    return $noiter

 proc setpixel { image xpix ypix noiter } {
    if { $noiter >= 0 } {
       set noiter [expr {$noiter%11}]
       set colour [lindex {white lightblue blue green yellow orange red purple magenta black} $noiter]
    } else {
       set colour black
    $image put $colour -to $xpix $ypix

 # Create the canvas and the image and fill it
 set width  200
 set height 200

 canvas .c -width $width -height $height
 pack   .c -fill both

 set image [image create photo -width $width -height $height]
 $image blank

 .c create image 0 0 -image $image -anchor nw

 set cdx [expr {4.0/$width}]
 set cdy [expr {4.0/$height}]
 proc mandelbrot_row {cdx cdy row width height} {
    set cy [expr {-2.0+$cdy*$row}]
    for {set col 0} {$col < $width} {incr col} {
       set cx [expr {-2.0+$cdx*$col}]
       set zx 0.0
       set zy 0.0
       set noiter [det_iteration $zx $zy $cx $cy 200]
       setpixel $::image $col $row $noiter
    if { $row < $height } {
       after 1 [list mandelbrot_row $cdx $cdy [incr row] $width $height]
 proc julia_row {cx cy zdx zdy row width height} {
    set zy [expr {-2.0+$zdy*$row}]
    for {set col 0} {$col < $width} {incr col} {
       set zx [expr {-2.0+$zdx*$col}]
       set noiter [det_iteration $zx $zy $cx $cy 200]
       setpixel $::image $col $row $noiter
    if { $row < $height } {
       after 1 [list julia_row $cx $cy $zdx $zdy [incr row] $width $height]

 set row 0
 after 1 [list mandelbrot_row $cdx $cdy $row $width $height]

 #set cx  0.0
 #set cy  0.75
 #after 1 [list julia_row $cx $cy $cdx $cdy $row $width $height]

sergiol I've made a code golf submission on http://codegolf.stackexchange.com/a/113329/29325 which is unintentionally beautiful:

Why does (zero-indexed) iteration 3 always seem a bike saddle?