Mandelbrot Perturbator

Claude Heiland-Allen

2021-09-13

Mandelbrot Perturbator

Efficient deep zooming for the Mandelbrot set with graphical user interface for annotations.

https://mathr.co.uk/mandelbrot/perturbator

Example image

Quick Start

The main program is m-perturbator-gtk.

Prerequisites

sudo apt install git build-essential pkg-config \
  libmpc-dev libpari-dev libgtk-3-dev libglew-dev libgflw3-dev

Build

This will install to ~/opt/ by default:

git clone https://github.com/cktan/tomlc99.git
git clone https://code.mathr.co.uk/mandelbrot-numerics.git
git clone https://code.mathr.co.uk/mandelbrot-symbolics.git
git clone https://code.mathr.co.uk/mandelbrot-perturbator.git
make -C tomlc99 install prefix=${HOME}/opt
make -C mandelbrot-numerics/c/lib install
make -C mandelbrot-symbolics/c/lib install
make -C mandelbrot-perturbator/c/lib install
make -C mandelbrot-perturbator/c/bin install

Run

PATH=${PATH}:${HOME}/opt/bin
export LD_LIBRARY_PATH=${HOME}/opt/lib
m-perturbator-gtk

User Manual

This section describes m-perturbator-gtk, the other programs are undocumented.

Overview

There is a menu bar at the top, with File, Explore, Feature menus, followed by Period, n-Fold, Depth, Rays entry boxes. Then there are widgets that control the appearance of annotations: line dash combo box, fill pattern combo box and colour selection button.

Below the menu bar on the top left is the fractal display.

Below the fractal display is the log panel, which displays information. The default size of the fractal display is optimized for 16:9 display aspect. The aspect ratio is designed for printing on landscape A4 paper with a 2cm border on all sides.

The top right has the annotation list, which can be sorted by clicking on its header. The appearance widgets control the current annotation and future annotations, the widgets are updated on selecting an annotation. Selecting an annotation highlights it in the fractal display.

Bottom right is the task queue, which displays progress of computations and allows them to be cancelled.

The program version is displayed in the title bar and is also saved in parameter files (if you need to copy/paste for bug reports).

To quit the program use the window close button.

File Menu

Open

Load parameters from a file. Existing annotations are deleted first. TOML format is tried first, the legacy line-based format (pre-v0.2) is tried if TOML parsing fails.

Save

Save parameters to a file. The format is based on TOML. Annotations are saved as specifications so (for example) rays will be recalculated on load.

Save PDF

Save image as displayed to a PDF file. Parameters are not yet saved to document metadata, so save the parameters too if you want to be able to reload. A detached key will appear as a second page.

Save PNG

Save image as displayed to a PNG file. Parameters are not yet saved to image metadata, so save the parameters too if you want to be able to reload. A detached key will appear as a second file with extension .key.png.

Save SVG

Save image as displayed to an SVG file. Parameters are not yet saved to image metadata, so save the parameters too if you want to be able to reload. A detached key will appear as a second file with extension .key.svg.

Theme: Dark / Light

Switch overall theme between dark on light and light on dark. Colours black and white are inverted when changing theme, but other colours are not touched.

Colour: Monochrome / Low Colour / Full Colour

Switch colour theme between three levels. The lower colour levels may be useful for economical low-ink printing.

Key: None / Overlay / Detached

Optionally display a key on the image or a second page (an additional file for PNG and SVG export).

Explore Menu

Home

Reset view to the initial top level view.

Zoom Out

Zoom out by a factor of 10.

Zoom

Activate zoom tool. When zoom tool is active, dragging with the left mouse button on the fractal marks a rectangle which will be zoomed to when the left button is released. Press the right mouse button before releasing the left mouse button to cancel the action.

Zoom To

When a nucleus annotation is selected, activating this menu item opens a dialog to enter a power and multiplier for the size of the atom. Power 0.75 is usually near the embedded Julia set (though the Zoom To Domain tool described below may be more appropriate), 1.0 is at the mu-atom. The multiplier provides a convenient way to fine-tune the size of the target region.

Zoom To Domain

When a nucleus or Misiurewicz annotation is selected, activating this menu item opens a dialog to enter a power and multiplier for the size of the domain. Power 1.0 is at the domain. The multiplier provides a convenient way to fine-tune the size of the target region.

Info

Activate info tool. When info tool is active, clicking with the left mouse button on the fractal prints information about the point in the log pane at the bottom of the window.

Pixel

Pixel coordinates, origin top left.

Real

Fractal coordinates.

Imag

Fractal coordinates.

Dwell N

Integer part of the iteration count, or the period of the containing component when negative. Note: deep zooms don’t yet have interior checking, so Dwell N and the other values will be 0 instead of a finite negative number.

Dwell F

Fractional part of the iteration count, or the radius within the containing component when Dwell N is negative.

Angle F

Argument of the final iterate, or the internal angle within the containing component when Dwell N is negative.

Distance

Distance estimate in pixels. Positive for exterior distance estimate, negative for interior distance estimate. The boundary of the Mandelbrot set is within a factor of two of this distance, approximately.

Domain N

Atom domain index, the iteration count that minimizes |Z_n|.

Domain X, Domain Y

Atom domain coordinates (0 at the center, magnitude 1 at the boundary of the atom domain).

Select

Activate select tool. When select tool is active, clicking on an annotation in the fractal display will select it in the annotation list.

Increase / Decrease Iterations

Adjust the maximum iteration count used to calculate the fractal. Deeper zooms typically need more iterations.

Feature Menu

Nucleus

Activate nucleus tool. When nucleus tool is active, dragging with the left mouse button in the fractal display marks a circle. On releasing the button, the lowest period atom in the circle is found and annotated. If no atom could be found then nothing happens. Press the right button before releasing the left button to cancel the action.

Bond

Activate bond tool. When bond tool is active, clicking on a child bulb (a circle-like component) will annotate its root with the internal angle from its parent.

Misiurewicz

Activate Misiurewicz point tool. When Misiurewicz point tool is active, dragging with the left button in the fractal display marks a square. On releasing the button, the lowest (pre)period Misiurewicz point in the square is found and annotated. The Period entry box in the menu bar can be used to limit the search. If no Misiurewicz point is found nothing happens. Press the right button before releasing the left button to cancel the action.

Ray Out

Activate ray out tool. When ray out tool is active, clicking in the fractal display traces an external ray outwards towards infinity. The ray is listed in the annotation list as a string of binary digits.

Rays Of

If an annotation is selected, trace the rays landing at the feature. For Misiurewicz points, set the Period field at the top to the ray angle period (it may be a multiple of the point period), and set the Rays field to the number of rays that land on the point. For example, the 4p1 Misiurewicz point at the center of the spokes above the upper period 3 bulb, should have Period and Rays both set to 3.

Ray In

Opens a dialog where an angle can be entered in binary form, for example .(01) for a periodic ray or .001100(001) for a pre-periodic ray. Alternatively a string of binary digits can be entered with the pre-period and period entered in decimal in the boxes below. This latter form is useful when combined with the ray out tool, as any annotation selected when the ray in menu is activated will be copied to the angle entry box, so only the pre(periods) need to be entered. The depth of the ray can be adjusted if desired.

Extend Ray

When a ray in annotation is selected, open a dialog to give a new depth. If the new depth is higher than the current depth, the ray will be extended.

Wake ← / →

When a ray in annotation is selected, and another ray in annotation with the same pre(period) lands at the same point, annotate the wake between them. The second ray is the next ray in the anti-clockwise direction from the selected ray for Wake ←, clockwise for Wake →.

Atom

When a nucleus or annotation is selected, annotate the corresponding atom by tracing its boundary and filling the resulting polygon.

Domain

When a nucleus or Misiurewicz annotation is selected, annotate the corresponding domain by tracing its boundary, resulting in a polygon. Atom domains are typically much bigger than atoms for cardioid-like atoms, around four times the size for circle-like atoms. Misiurewicz domains are typically around the size where the spiralling starts to dominate.

Domain Estimate

When a nucleus or Misiurewicz annotation is selected, annotate the corresponding domain size estimate as a circle.

Mu-Unit

When a nucleus annotation is selected, annotate the nuclei in its tuned mu-unit up to a certain period multiplier. It works by tracing rays and finding nuclei relative to the top level cardioid, then using atom coordinates (based on the derivative of the multiplier) to translate to the desired nucleus. The process is not perfect, so some nuclei may be marked incorrectly.

Filaments

When a nucleus annotation is selected, annotate its filaments (when the Period entry box in the menu bar has its period) or the filaments of its embedded Julia set (when the Period entry box in the menu bar has the period of its influencing island). The n-Fold entry box in the menu bar selects how deep towards the central island the rays should go (it increases by 1 for each factor of 2 of rotational symmetry). The Depth entry box in the menu bar sets how many ray pairs to draw (it increases by 1 for each doubling of ray count).

Delete

Delete the currently selected annotation. There is no undo.

Command Line

Example:

m-perturbator-gtk --dpi=300 -i=example.toml -o=example.pdf

Note: flags must be specified with =, separate arguments with spaces are not supported.

--dpi

Sets resolution of fractal raster image in dots per inch, relative to landscape A4 paper with 2cm borders on each side.

-i

Chooses a file to load.

-o

Chooses an image file to save. Type is detected by extension, one of .pdf, .png, .svg. If this option is specified then the program exits automatically; however the graphical window is still opened which needs a display. This option can be specified multiple times.

Library

c/lib contains the Mandelbrot set rendering library, implemented in C++ with C API.

Rendering Methods

Different rendering methods used for different zoom depths:

kind number maxdepth
plain f32 1e-7
plain f64 1e-15
plain f80 1e-??
perturb f32 1e-38
perturb f64 1e-308
perturb f80 1e-4932
perturb f??i16 1e-9864
perturb f??i32 1e-646456993
perturb f??i64 1e-2776511644261678080
rescaled f?? + f??i?? (hybrid approach for speed)

Not all of them are currently implemented.

API design notes

(This is a bit out-dated.)

struct buffer
buffer      *create(int width, int height)
void         destroy(buffer *)
const float *get_data(const buffer *)
int          get_width(const buffer *)
int          get_height(const buffer *)

struct view
view        *create()
void         destroy(view *)
void         set_x(view *, const mpfr_t)
void         set_y(view *, const mpfr_t)
void         set_r(view *, const mpfr_t)
void         get_x(const view *, mpfr_t)
void         get_y(const view *, mpfr_t)
void         get_r(const view *, mpfr_t)

struct options
options     *create()
void         destroy(options *)
void         set_threads(options *, int)
void         set_maxiters(options *, int)
void         set_maxperiod(options *, int)
void         set_escape_radius(options *, double)
void         set_glitch_radius(options *, double)

struct context
context     *create(enum formula, int order)
void         destroy(context *)
void         start(context *, buffer *, const view *, const options *)
bool         done(context *)
void         wait(context *)
void         stop(context *)

TODO

(This is a bit out-dated.)

Phase 1

Phase 2

Phase 3

Phase 4

Phase 5

Bugs

Changes

v0.2

2021-09-13

v0.1

2019-10-14

Legal

Copyright (C) 2015-2021 Claude Heiland-Allen

License AGPLv3 (only) https://www.gnu.org/licenses/agpl-3.0.html


https://mathr.co.uk