
#include <exec/types.h>
#include <math.h>

#ifdef __SASC
	#define M_PI PI
#endif
#ifdef __VBCC__
#define   M_PI 3.14159265358979323846
#endif

float rnd(float max);
float sgn(float val);
float trnc(float value);

extern ULONG TimeWave;
extern ULONG LineToCalc;
extern WORD	 *PluginSamples;

float A0, A1, A2, A3, A4, A5, A6, A7, A8, A9;

void PrepareConstants(UBYTE FieldNum) {
	switch(FieldNum) {
		case 0:
		break;
		case 1:
		break;
		case 2:
		break;
		case 3:
		break;
		case 4:
			A0 = rnd(M_PI);
			A1 = .01*(.5 + rnd(.5) + rnd(.5));
			A2 =  .1*(.5 + rnd(.5) + rnd(.5));
		break;
		case 5:
		break;
		case 6:
		break;
		case 7:
			A0 = 2    + rnd(30);
			A1 = 0.01 + rnd(0.05);
		break;
		case 8:
			A0 = 14;
			A1 = 0.08;
			A2 = 3 + rnd(3);
			A3 = 0.01;
		break;
		case 9:
		break;
		case 10: // Radial Breakaway
		break;
		case 11: // SOLs Waves
		break;
		case 12: // SOLs Growth Formula
			A0 = 2.0 * ( 2.0 + rnd(12));
			A1 = 0.01 + rnd(0.03);
		break;
		case 13: // Tiles
			A0 = 1.90  * (1.0 + rnd(2.0));
			A1 = 0.005 * (1.0 + rnd(1.0));
		break;
		case 14: // In or out, inner Turn
			A0 = 0.95 + rnd(.06);
		break;
		case 15: // Slidering
			A0 = 8.0  + rnd(16);
			A1 = 0.03 + rnd(.05);
			A2 = (0.006 + rnd( .006 )) * sgn(0.5-rnd(1.0));
			A3 = A0 / 2.0;
		break;
		case 16: // Sine Multi-Circ
		break;
		case 17: // Noise
		break;

		case 18: // The MAW
		break;
	}
}

void CalcLine(LONG *Zoom, ULONG Width, ULONG Height, UBYTE FieldNum) {
	LONG i,xs,ys,xd,yd;

	float scale,greater;
	float xsf,ysf,xdf,ydf;
	float rsf,tsf,rdf,tdf;
	float wf,hf;

	wf=(float)Width;
	hf=(float)Height;

	greater=1.0;
	if(wf > greater) greater = wf;
	if(hf > greater) greater = hf;

	scale = 1.0 / (greater/2.0);

	yd = LineToCalc;
	for(xd=0; xd<(Width); xd++) {
		xdf = (xd - wf/2.0) * scale;
		ydf = (yd - hf/2.0) * scale;

		switch(FieldNum) {
			case 0:
				xsf = xdf - xdf * 0.075;
				ysf = ydf - ydf * 0.075;
			break;

			case 1:
				rdf = sqrt(xdf*xdf+ydf*ydf);
				tdf = atan2(ydf, xdf);
				rsf = rdf - .015;
				tsf = tdf + .02;
				xsf = rsf * cos(tsf);
				ysf = rsf * sin(tsf);
			break;

			case 2:
				rdf = sqrt(xdf*xdf+ydf*ydf);
				tdf = atan2(ydf, xdf);
				rsf = rdf - .015;
				tsf = tdf - .02;
				xsf = rsf * cos(tsf);
				ysf = rsf * sin(tsf);
			break;

			case 3:
				rdf = sqrt(xdf*xdf+ydf*ydf);
				tdf = atan2(ydf, xdf);
				rsf = rdf - .04;
				tsf = tdf - .005;
				xsf = rsf * cos(tsf);
				ysf = rsf * sin(tsf);
			break;

			case 4: {
				float d0;
				rdf = sqrt(xdf*xdf+ydf*ydf);
				tdf = atan2(ydf, xdf);

				d0  = 2.0 * tdf + 6.28 * rdf + A0;
				rsf = rdf + A1 * cos(d0);
				tsf = tdf + A2 * sin(d0);

				xsf = rsf * cos(tsf);
				ysf = rsf * sin(tsf);
			}
			break;

			case 5:
				xsf = xdf * .97;
				if(ydf < 0.0) ysf = ydf + (cos((pow(ydf+1,2.7)  ) * 10) + 1.4) / 40;
				else          ysf = ydf - (cos((pow(ydf+1,2.7)  ) * 10) + 1.4) / 40;
			break;

			case 6:
				xsf = xdf + ydf / 8.0;
				ysf = ydf - xdf / 90.0;
			break;

			case 7:
				xsf = xdf + A1 * sin(A0*ydf);
				ysf = ydf + A1 * sin(A0*xdf);
			break;

			case 8:
				xsf = xdf + A1 * sin(A2*ydf);
				ysf = ydf + A3 * sin(A0*xdf);
			break;

			case 9:
				rdf = sqrt(xdf*xdf+ydf*ydf);
				tdf = atan2(ydf, xdf);
				rsf = sin(rdf);
				tsf = tdf - ((rdf - 0.042) * rnd (0.09));
				xsf = rsf * cos(tsf);
				ysf = rsf * sin(tsf);
			break;

			case 10: // Radial Breakaway
				rdf = sqrt(xdf*xdf+ydf*ydf);
				tdf = atan2(ydf, xdf);
				rsf = rdf * (1.0+0.16*atan(0.55-rdf));
				tsf = tdf - 0.01;
				xsf = rsf * cos(tsf);
				ysf = rsf * sin(tsf);
			break;

			case 11: // SOLs Waves
				xsf = xdf * 0.97;
				ysf = ydf - (cos(pow(ydf+1.0, 2.7)*10) + 1.5) / 40.0;
			break;

			case 12: // SOLs Growth Formula
				xsf = xdf + A1 * cos(A0*xdf);
				ysf = ydf + A1 * cos(A0*ydf);
			break;

			case 13: // Tiles
				xsf = xdf + A1 * (2.0 * (fmod(((ydf+1) * A0), 2.0)) - 1.0);
				ysf = ydf + A1 * (2.0 * (fmod(((xdf+1) * A0), 2.0)) - 1.0);
			break;

			case 14: // In or out, inner Turn
				rdf = sqrt(xdf*xdf+ydf*ydf);
				tdf = atan2(ydf, xdf);
				rsf = rdf * A0;
				tsf = tdf - fabs(1.0-rdf) * 0.035;
				xsf = rsf * cos(tsf);
				ysf = rsf * sin(tsf);
			break;

			case 15: // Slidering
				rdf = sqrt(xdf*xdf+ydf*ydf);
				tdf = atan2(ydf, xdf);
				rsf = fabs(rdf + A1*sin(A0*rdf));
				tsf = tdf - (A2*sgn(sin(A3*rdf)));
				xsf = rsf * cos(tsf);
				ysf = rsf * sin(tsf);
			break;

			case 16: // Sine Multi-Circ
				rdf = sqrt(xdf*xdf+ydf*ydf);
				tdf = atan2(ydf, xdf);
				rsf = rdf * (0.87 + 0.05 * (1.0+sin(rdf * 15)));
				tsf = tdf;
				xsf = rsf * cos(tsf);
				ysf = rsf * sin(tsf);
			break;

			case 17: // Noise
				xsf = xdf + rnd(0.11) - 0.055;
				ysf = ydf + rnd(0.11) - 0.055;
			break;

			case 18: // The MAW
				rdf = sqrt(xdf*xdf+ydf*ydf);
				tdf = atan2(ydf, xdf);
				rsf = rdf + 0.0119; 
				tsf = tdf - (0.055 * ( rdf - 0.324 ) ) * ( rdf + 0.279 );
				xsf = rsf * cos(tsf);
				ysf = rsf * sin(tsf);
			break;
		}

		xs = xsf/scale + wf/2.0;
		ys = ysf/scale + hf/2.0;

		if(xs < Width/2)  xs++;
		if(ys < Height/2) ys++;

		if(xs < 0)      xs = 0;
		if(xs > Width)  xs = Width;
		if(ys < 0)      ys = 0;
		if(ys > Height) ys = Height;

		Zoom[Width * yd + xd] = Width * ys + xs;
	}
}
