home *** CD-ROM | disk | FTP | other *** search
- /*
- * MandelVroom 2.0
- *
- * (c) Copyright 1987,1989 Kevin L. Clague, San Jose, CA
- *
- * All rights reserved.
- *
- * Permission is hereby granted to distribute this program's source
- * executable, and documentation for non-comercial purposes, so long as the
- * copyright notices are not removed from the sources, executable or
- * documentation. This program may not be distributed for a profit without
- * the express written consent of the author Kevin L. Clague.
- *
- * This program is not in the public domain.
- *
- * Fred Fish is expressly granted permission to distribute this program's
- * source and executable as part of the "Fred Fish freely redistributable
- * Amiga software library."
- *
- * Permission is expressly granted for this program and it's source to be
- * distributed as part of the Amicus Amiga software disks, and the
- * First Amiga User Group's Hot Mix disks.
- *
- * contents: this file contains the routines to calculate Mandelbrot and
- * Julia pictures in Amiga Fast Floating Point.
- */
-
- #include "mandp.h"
-
- extern SHORT MaxOrbit;
-
- static LONG MaxIter;
-
- /*
- * Fast Floating Point Mandelbrot Generator
- */
- MandelbrotFFP( Pict, StartX, StartY, GapX, GapY )
- /*
- * These parameters are IEEE 32 bit floating point numbers
- */
-
- struct Picture *Pict;
-
- LONG StartX, StartY, GapX, GapY;
- {
- register int i, j, k;
- register SHORT *CountPtr;
-
- register float curx, cury;
-
- float startx, starty, gapx, gapy;
- float SPFieee();
-
- UBYTE MandFlag;
-
- /* Here we convert the IEEE parameters into FFP format */
-
- startx = SPFieee( StartX );
- starty = SPFieee( StartY );
- gapx = SPFieee( GapX );
- gapy = SPFieee( GapY );
-
- MaxIter = Pict->MaxIteration;
-
- if (Pict->Flags & NO_RAM_GENERATE)
- CountPtr = Pict->Counts;
- else
- CountPtr = Pict->Counts + Pict->CurLine*Pict->CountX;
-
- /* start in the upper left hand corner */
-
- cury = starty;
-
- /*
- * for each row
- */
- for (i = Pict->CurLine; i < Pict->CountY; i++) {
-
- curx = startx;
-
- MandFlag = 0;
-
- if ( Pict->Flags & NO_RAM_GENERATE )
- CountPtr = Pict->Counts;
-
- /*
- * for each collumn
- */
-
- for (j = 0; j < Pict->CountX; j++) {
-
- /* if we've hit a Mandelbrot point, then use the convergence detector,
- * to reduce compute time
- */
-
- if (*CountPtr == 0) {
-
- if ( MandFlag ) {
-
- k = FFP_Trace_Height( 0.0, 0.0, curx, cury );
-
- } else {
-
- k = FFP_Height( 0.0, 0.0, curx, cury ); /* Normal calculator */
- }
-
- MandFlag = k == Pict->MaxIteration;
-
- *CountPtr = k; /* save it in ram for recoloring */
- }
- CountPtr++;
-
- curx += gapx;
-
- ChildPause( Pict );
- }
- cury += gapy;
-
- CheckEOL( Pict );
- }
- } /* Mandelbrot */
-
- /***************************************************************************
- *
- * Julia Curve Generator that uses Amiga Fast Floating Point
- *
- **************************************************************************/
-
- /*
- * Fast Floating Point Julia Generator
- */
- JuliaFFP( Pict, JuliaX, JuliaY, StartX, StartY, GapX, GapY )
-
- /*
- * These parameters are IEEE 32 bit floating point numbers
- */
-
- register struct Picture *Pict;
- LONG JuliaX, JuliaY;
- LONG StartX, StartY;
- LONG GapX, GapY;
- {
- register int i, j, k;
- register float curx, cury;
-
- register SHORT *CountPtr;
-
- float juliax, juliay, gapx, gapy,startx;
- float SPFieee();
-
- UBYTE ConvFlag;
-
- MaxIter = Pict->MaxIteration;
-
- if (Pict->Flags & NO_RAM_GENERATE)
- CountPtr = Pict->Counts;
- else
- CountPtr = Pict->Counts + Pict->CurLine*Pict->CountX;
-
- /* Here we convert the IEEE parameters into FFP format */
-
- juliax = SPFieee( JuliaX );
- juliay = SPFieee( JuliaY );
-
- gapx = SPFieee( GapX );
- gapy = SPFieee( GapY );
-
- /* start in the upper left hand corner */
-
- startx = SPFieee(StartX);
- cury = SPFieee(StartY);
-
- /* move down to next not generated line */
-
- cury += Pict->CurLine*gapy;
-
- /*
- * for each row
- */
- for (i = Pict->CurLine; i < Pict->CountY; i++) {
-
- curx = startx;
- ConvFlag = 0;
-
- if ( Pict->Flags & NO_RAM_GENERATE )
- CountPtr = Pict->Counts;
-
- /*
- * for each collumn
- */
-
- for (j = 0; j < Pict->CountX; j++) {
-
- /* if we've hit a Mandelbrot point, then use the convergence detector,
- * to reduce compute time
- */
-
- if (*CountPtr == 0) {
-
- if (ConvFlag) {
- /* try the convergence method */
- k = FFP_Trace_Height( curx, cury, juliax, juliay);
- } else {
- k = FFP_Height( curx, cury, juliax, juliay); /* Normal calc */
- }
-
- ConvFlag = k == Pict->MaxIteration;
-
- *CountPtr = k; /* save it in ram for recoloring */
- }
- CountPtr++;
-
- curx += gapx;
-
- ChildPause( Pict );
- }
- cury += gapy;
-
- CheckEOL( Pict );
- }
- } /* JuliaFFP */
-
- /*
- * This function calculated the 'potential' of a given location
- * in the complex plane.
- */
- int
- FFP_Height( posx, posy, juliax, juliay )
- float posx; /* Location in screen coordinate space */
- float posy; /* Location in screen coordinate space */
- float juliax; /* Real part of location on complex plane */
- float juliay; /* Imaginary part of location on complex plane */
- {
- register float cura, curb;
- register float cura2, curb2;
- register LONG k;
-
- #ifdef CHECK_TASK_STACK
-
- CheckStack();
-
- #endif
-
- cura = cura2 = posx;
- curb = curb2 = posy;
-
- cura2 *= cura2;
- curb2 *= curb2;
-
- for (k = 0; k < MaxIter; k ++ ) {
-
- curb *= cura; /* b = 2 * a * b + juliay */
- curb += curb + juliay;
-
- cura = cura2 - curb2 + juliax; /* a = a2 - b2 + juliax */
-
- cura2 = cura * cura; /* a2 = a * a */
- curb2 = curb * curb; /* b2 = b * b */
-
- if (cura2+curb2 >= 16.0) /* quit if a2+b2 is too big */
- return( k );
- }
- return( k );
- }
-
- /*
- * this is also a Mandelbrot potential calculator, that is tailored to
- * identify points that are 'in' the Mandelbrot set. Points outside the
- * Mandelbrot set diverge. Points inside converge.
- * This code uses a trace table mechanism to detect convergence.
- */
- int
- FFP_Trace_Height( posx, posy, curx, cury )
-
- float posx; /* Real part of location on complex plane */
- float posy; /* Imaginary part of location on complex plane */
-
- float curx; /* Real part of location on complex plane */
- float cury; /* Imaginary part of location on complex plane */
- {
- LONG k, l;
-
- LONG TraceSize = 32;
-
- float olda[32], oldb[32]; /* Convergence trace table */
-
- register float cura, curb, cura2, curb2;
- register float *RealTrace, *ImagTrace;
-
- #ifdef CHECK_TASK_STACK
-
- CheckStack();
-
- #endif
-
- cura = cura2 = posx;
- curb = curb2 = posy;
-
- cura2 *= cura2;
- curb2 *= curb2;
-
- for (k = 0; k < MaxIter; k += TraceSize) {
-
- RealTrace = olda;
- ImagTrace = oldb;
-
- for (l = 0; l < TraceSize; l++) {
-
- *(RealTrace++) = cura;
- *(ImagTrace++) = curb;
-
- curb *= cura;
- curb += curb + cury;
-
- cura = cura2 - curb2 + curx;
-
- cura2 = cura * cura;
- curb2 = curb * curb;
-
- if (cura2+curb2 >= 16.0)
- return( k + l );
- }
-
- /* Scope out trace table for convergence */
-
- RealTrace = olda;
- ImagTrace = oldb;
-
- for (l = 0; l < TraceSize; l++)
-
- if (cura == *(RealTrace++) && curb == *(ImagTrace++)) {
- k += MaxIter;
- return( MaxIter );
- }
- }
- return( MaxIter );
- }
-
- DrawOrbitFFP( Pict, creal, cimag, zreal, zimag )
- register struct Picture *Pict;
- LONG zreal, zimag, creal, cimag;
- {
- register struct RastPort *Rp;
- register float cura, curb;
- float cura2, curb2;
- float Creal, Cimag;
-
- float x_scale, y_scale;
- int x_center, y_center;
- int width, height;
- int x, y;
- register int k;
-
- struct Window *Window;
-
- Window = OrbitWind;
-
- Rp = Window->RPort;
-
- width = (Window->Width-Pict->LeftMarg-Pict->RightMarg);
- height = (Window->Height-Pict->TopMarg-Pict->BotMarg);
-
- x_center = width/2 + Pict->LeftMarg;
- y_center = height/2 + Pict->TopMarg;
-
- y_scale = x_scale = (float) height / 2.0;
- /*x_scale *= AspectRatio( Pict );*/
-
- if ( Pict->pNode.ln_Type == MANDPICT ) {
-
- Creal = SPFieee(creal);
- Cimag = SPFieee(cimag);
-
- cura = cura2 = SPFieee(zreal);
- curb = curb2 = SPFieee(zimag);
-
- } else {
-
- Creal = SPFieee(zreal);
- Cimag = SPFieee(zimag);
-
- cura = cura2 = SPFieee(creal);
- curb = curb2 = SPFieee(cimag);
-
- }
-
- cura2 *= cura2;
- curb2 *= curb2;
-
- SetAPen( Rp, 0 );
- RectFill( Rp, Pict->LeftMarg, Pict->TopMarg, width+Pict->LeftMarg-1, height+Pict->TopMarg-1);
-
- SetAPen( Rp, HIGHLIGHTPEN);
-
- for (k = 0; k < MaxOrbit; k++ ) {
-
- curb *= cura;
- curb += curb + Cimag;
-
- cura = cura2 - curb2 + Creal;
-
- cura2 = cura * cura;
- curb2 = curb * curb;
-
- if (cura2+curb2 >= 16.0)
- return( k );
-
- /* map real and imaginary parts into window coordinates */
-
- x = x_center + (int)(x_scale*cura);
- y = y_center + (int)(y_scale*curb);
-
- if ( x >= Pict->LeftMarg && x < Window->Width-Pict->RightMarg &&
- y >= Pict->TopMarg && y < Window->Height-Pict->BotMarg ) {
-
- /* plot pixel location */
- WritePixel( Rp, x, y);
- }
-
- }
- return( k );
- }
-
-
-
-