Home Search   What's New Index Books Links Q & A Newsletter Banners   Feedback Tip Jar MSDN Visual Basic Community

Title Draw a fractal Mandelbrot set This example shows how to draw a fractal Mandelbrot set in Visual Basic. fractal, Mandelbrot, Mandelbrot set Graphics

The Mandelbrot set uses an iterated equation to calculate colors for the points in a region. The equation is:

`    Z(n) = Z(n-1)^2 + C`

Here the Z(n) and C are complex numbers.

It can be shown that if the magnitude of Z(n) ever exceeds 2, then it eventually diverges towards infinity.

To find the color for the point (x, y), the program sets Z(0) = 0 and C = x + y * i. It then generates values for Z(n) until Z(n)'s magnitude exceeds 2 or it reaches some predetermined maximum number of iterations. At that point, the program uses the number of iterations it performed to assign the point's color. For example, if the program is using K colors and it performed I iterations, then it assigns the point color number I Mod K.

The following code shows how the program draws the Mandelbrot set.

```' Draw the Mandelbrot set.
Private Sub DrawMandelbrot()
' Work until the magnitude squared > 4.
Const MAX_MAG_SQUARED = 4

Dim bitmap_info As BITMAPINFO
Dim pixels() As Byte
Dim bytes_per_scanLine As Integer

Dim wid As Long
Dim hgt As Long
Dim clr As Long
Dim X As Integer
Dim Y As Integer
Dim ReaC As Double
Dim ImaC As Double
Dim dReaC As Double
Dim dImaC As Double
Dim ReaZ As Double
Dim ImaZ As Double
Dim ReaZ2 As Double
Dim ImaZ2 As Double
Dim r As Integer
Dim b As Integer
Dim g As Integer

picCanvas.Line (0, 0)-(picCanvas.ScaleWidth, _
picCanvas.ScaleHeight), vbBlack, BF
DoEvents

' Prepare the bitmap description.
.biSize = 40
.biWidth = picCanvas.ScaleWidth
' Use negative height to scan top-down.
.biHeight = -picCanvas.ScaleHeight
.biPlanes = 1
.biBitCount = 32
.biCompression = BI_RGB
bytes_per_scanLine = ((((.biWidth * .biBitCount) + _
31) \ 32) * 4)
pad_per_scanLine = bytes_per_scanLine - (((.biWidth _
* .biBitCount) + 7) \ 8)
.biSizeImage = bytes_per_scanLine * Abs(.biHeight)
End With

' Load the bitmap's pixel data.
ReDim pixels(1 To 4, 1 To picCanvas.ScaleWidth, 1 To _
picCanvas.ScaleHeight)
GetDIBits picCanvas.hdc, picCanvas.Image, _
0, picCanvas.ScaleHeight, pixels(1, 1, 1), _
bitmap_info, DIB_RGB_COLORS

' Adjust the coordinate bounds to fit picCanvas.

' dReaC is the change in the real part
' (X value) for C. dImaC is the change in the
' imaginary part (Y value).
wid = picCanvas.ScaleWidth
hgt = picCanvas.ScaleHeight
dReaC = (m_Xmax - m_Xmin) / (wid - 1)
dImaC = (m_Ymax - m_Ymin) / (hgt - 1)

' Calculate the values.
ReaC = m_Xmin
For X = 1 To wid
ImaC = m_Ymin
For Y = 1 To hgt
ReaZ = Zr
ImaZ = Zim
ReaZ2 = Z2r
ImaZ2 = Z2im
clr = 1
Do While clr < MaxIterations And _
ReaZ2 + ImaZ2 < MAX_MAG_SQUARED
' Calculate Z(clr).
ReaZ2 = ReaZ * ReaZ
ImaZ2 = ImaZ * ImaZ
ImaZ = 2 * ImaZ * ReaZ + ImaC
ReaZ = ReaZ2 - ImaZ2 + ReaC
clr = clr + 1
Loop

clr = m_Colors(1 + clr Mod NumColors)
pixels(pixR, X, Y) = clr And &HFF&
pixels(pixG, X, Y) = (clr And &HFF00&) \ &H100&
pixels(pixB, X, Y) = (clr And &HFF0000) \ _
&H10000

ImaC = ImaC + dImaC
Next Y
ReaC = ReaC + dReaC

' Let the user know we're not dead.
If X Mod 10 = 0 Then
picCanvas.Line (0, 0)-(X, hgt), vbWhite, BF
picCanvas.Refresh
End If
Next X

' Update the image.
SetDIBits picCanvas.hdc, picCanvas.Image, _
0, picCanvas.ScaleHeight, pixels(1, 1, 1), _
bitmap_info, DIB_RGB_COLORS
picCanvas.Picture = picCanvas.Image

Caption = "Mandelbrot (" & Format\$(m_Xmin, "0.000000") _
& ", " & _
Format\$(m_Ymin, "0.000000") & ")-(" & _
Format\$(m_Xmax, "0.000000") & ", " & _
Format\$(m_Ymax, "0.000000") & ")"
End Sub```

The program allows you to zoom in on areas of the set and to pick the color palette it uses to draw. If you resize the program or change the colors, use the Scale menu's Refresh command to redraw the fractal.

For more information on fractals, including information about the fascinating Julia set that uses the Mandelbrot set as a map, see my book Visual Basic Graphics Programming.