; Hi there freaks !
;
; In this month's (small) article a really fast Mandelbrot fractals drawer.
; For people who don't know nothing about fractals: STOP READING.
; (Sorry but I had no time to write a whole article about Fractals)
;
;
; This little source uses coordinates like Analytic-Art.
; Just take some coordinates from AA and multiply them by 4096.
; Put them in the 'equ' of XC & YC (Centre) and XW & YW
; (Width). The 'Window' can be changed with XS & YS
;
; Just load this article in your assembler, assemble and run it ...
;
;
; Note for the insiders :This routine skips a part of the inside of the
; mandelbrot for speed improvement.
;
;
; I just wanted to share this little routine with you.
; So you'll have to make your own screen save routine etc.
;
; Note how easy it is to 'allocate' memory with BSS hunks !
; (You already knew that, but I was just checking)
;
; Note: This is a DEVPAC 2.14 source !
; Note2: Propably won't work on other assemblers like SEKA (yek) without
;        making some changes. (READ: demolishing my source)
;
;
; If you have any questions, lose change, new ideas, etc. then send
; them to:
;
; P. de Boer
; Zeeloodsenlaan 79
; 1785 BM  Den Helder
; Holland
;
;--------------------------------------------------------------------------
;
; HY MAN   (HYperfast MANdelbrots)
; written for UGA by P. de Boer
;
; Notice that my TAB is set on 16  (Gives Clean and Spacy sources !)
;--------------------------------------------------------------------------
	opt o+		;optimize

ExecBase	equ	$4
Forbid	equ	-132
Permit	equ	-138
OpenLibrary	equ	-552
CloseLibrary	equ	-414

COP1LCH	equ	$080
COPJMP1	equ	$088

DIWSTRT	equ	$08E
DIWSTOP	equ	$090
DDFSTRT	equ	$092
DDFSTOP	equ	$094
DMACON	equ	$096

BPL1PTH	equ	$0E0
BPL1PTL	equ	$0E2
BPL2PTH	equ	$0E4
BPL2PTL	equ	$0E6
BPL3PTH	equ	$0E8
BPL3PTL	equ	$0EA
BPL4PTH	equ	$0EC
BPL4PTL	equ	$0EE
BPL5PTH	equ	$0F0
BPL5PTL	equ	$0F2
BPLCON0	equ	$100
BPLCON1	equ	$102
BPLCON2	equ	$104
BPL1MOD	equ	$108
BPL2MOD	equ	$10A

COLOR00	equ	$180
COLOR02	equ	$184
COLOR04	equ	$188
COLOR06	equ	$18C
COLOR08	equ	$190
COLOR10	equ	$194
COLOR12	equ	$198
COLOR14	equ	$19C
COLOR16	equ	$1A0
COLOR18	equ	$1A4
COLOR20	equ	$1A8
COLOR22	equ	$1AC
COLOR24	equ	$1B0
COLOR26	equ	$1B4
COLOR28	equ	$1B8
COLOR30	equ	$1BC

CUSTOM	equ	$DFF000
CIAAPRA	equ	$BFE001
;--------------------------------------------------------------------------
	SECTION	MainProgram,CODE

StartMain	movea.l 	(ExecBase).w,a6
	jsr 	Forbid(a6)

OpenGfxLibrary	lea 	GfxName(pc),a1
	clr.l 	d0
	jsr 	OpenLibrary(a6)
	move.l 	d0,GfxBase
	beq 	Einde

;--------------------------------------------------------------------------
MakeCopperList	lea	CList,a0
	move.l 	#Screen,d0

	move.w	#BPL1PTH,(a0)+
	swap	d0
	move.w	d0,(a0)+
	move.w	#BPL1PTL,(a0)+
	swap	d0
	move.w	d0,(a0)+

	add.l	#40*256,d0
	move.w	#BPL2PTH,(a0)+
	swap	d0
	move.w	d0,(a0)+
	move.w	#BPL2PTL,(a0)+
	swap	d0
	move.w	d0,(a0)+

	add.l	#40*256,d0
	move.w	#BPL3PTH,(a0)+
	swap	d0
	move.w	d0,(a0)+
	move.w	#BPL3PTL,(a0)+
	swap	d0
	move.w	d0,(a0)+

	add.l	#40*256,d0
	move.w	#BPL4PTH,(a0)+
	swap	d0
	move.w	d0,(a0)+
	move.w	#BPL4PTL,(a0)+
	swap	d0
	move.w	d0,(a0)+

	add.l	#40*256,d0
	move.w	#BPL5PTH,(a0)+
	swap	d0
	move.w	d0,(a0)+
	move.w	#BPL5PTL,(a0)+
	swap	d0
	move.w	d0,(a0)+

	move.l	#$fffffffe,(a0)
;--------------------------------------------------------------------------
InstallCopper	lea	CUSTOM,a6
	move.w 	#$07E0,DMACON(a6)

	move.l 	#CList,COP1LCH(a6)
	clr.w 	COPJMP1(a6)

ScreenSettings	move.l 	#$298129C1,DIWSTRT(a6)	;move.l
	move.l 	#$003800D0,DDFSTRT(a6)	;is faster
	move.w 	#$5000,BPLCON0(a6)	;than two
	clr.l	BPLCON1(a6)		;move.w 's
	clr.l	BPL1MOD(a6)	;clr.l is saver
			;then moveq #0

SetColors	move.l	#$00000005,COLOR00(a6)
	move.l	#$00060007,COLOR02(a6)
	move.l	#$00180029,COLOR04(a6)
	move.l	#$003A004B,COLOR06(a6)
	move.l	#$015C036D,COLOR08(a6)
	move.l	#$058E079F,COLOR10(a6)
	move.l	#$09BF0BCF,COLOR12(a6)
	move.l	#$0DDF0EEF,COLOR14(a6)
	move.l	#$0FFF0EEF,COLOR16(a6)
	move.l	#$0DDF0BBF,COLOR18(a6)
	move.l	#$09AF078F,COLOR20(a6)
	move.l	#$057E036D,COLOR22(a6)
	move.l	#$015C004B,COLOR24(a6)
	move.l	#$003A0029,COLOR26(a6)
	move.l	#$00180007,COLOR28(a6)
	move.l	#$00060005,COLOR30(a6)


StartDMA	move.w	#$8380,DMACON(a6)
		;Only BitPlane & Copper DMA
;--------------------------------------------------------------------------
ItMax	equ	31	;maximum iteration
XS	equ	320	;'Window' width
YS	equ	256	;'Window' height
XW	equ	20480	;Zoom Wnd Width (x 4096)
YW	equ	XW*4/5	;Zoom Wnd Height (x 4096)
XC	equ	0	;Zoom Centre x
YC	equ	0	;Zoom Centre y
DX	equ	XW/XS	;Step size X
DY	equ	YW/YS	;Step size Y
MaxX	equ	XC+XW/2	;Max value x
MinY	equ	YC-YW/2	;Min value y

Start	movea.w	#MaxX,a0
	movea.w	#MinY,a1
	movea.w	#DX,a2
	movea.w	#DY,a3
	movea.w	a0,a4
	lea	Screen,a5

	move.w	#YS-1,d1
ForY	move.w	#XS-1,d0
ForX	move.w	a0,d2	;x=0
	move.w	a1,d3	;y=0
	move.w	#ItMax,d7	;itr=max

CheckIt	move.w	d2,d4	;xq=x*x
	move.w	d3,d5	;yq=y*y
	muls	d4,d4
	muls	d5,d5

	move.l	d5,d6
	add.l	d4,d6	;xq+yq>>>
	swap	d6
	cmp.w	#$0400,d6
	bgt.s	OutOfRange	;yes ->Out of Range

	tst.w	d2
	bpl.s	JumpIn

	cmp.w	#$0060,d6	;skip part
	bge.s	JumpIn

	clr.w	d7	;replace this if you want to
	bra.s	OutOfRange	;see what is skipped

Iteration	move.w	d2,d4	;xq=x*x
	move.w	d3,d5	;yq=y*y
	muls	d4,d4
	muls	d5,d5

	move.l	d5,d6
	add.l	d4,d6	;xq+yq>>>
	swap	d6
	cmp.w	#$0400,d6
	bgt.s	OutOfRange	;yes ->Out of Range

JumpIn	exg	d4,d2
	sub.l	d5,d2	;x=xq-yq
	asl.l	#4,d2	;rescale number
	swap	d2
	add.w	a0,d2	;x=x+xc
	bvs.s	OutOfRange

	muls	d4,d3	;y=z*y
	asl.l	#5,d3	;rescale number
	swap	d3
	add.w	a1,d3	;y=y+yc
	dbvs	d7,Iteration

	bvc.s	StaysBlack

OutOfRange	bsr.s	SetPoint

StaysBlack	suba.w	a2,a0
	dbf	d0,ForX

	movea.w	a4,a0
	adda.w	a3,a1

	btst	#6,CIAAPRA	;quit if left mouse-button
	beq.s	Recover	;is pressed

	dbf	d1,ForY

;--------------------------------------------------------------------------
Wacht	btst	#6,CIAAPRA
	bne.s	Wacht
;--------------------------------------------------------------------------
Recover	movea.l	GfxBase(pc),a4
	move.l 	38(a4),COP1LCH(a6)
	clr.w 	COPJMP1(a6)
	move.w 	#$83E0,DMACON(a6)

CloseGfx	movea.l 	(ExecBase).W,a6
	movea.l 	GfxBase(pc),a1
	jsr 	CloseLibrary(a6)

Einde	jsr 	Permit(a6)
	clr.l 	d0
 	rts
;--------------------------------------------------------------------------
SetPoint	lea	Screen,a5
	move.w	d0,d2
	move.w	d1,d3

	lsl.w	#3,d3
	adda.w	d3,a5
	lsl.w	#2,d3
	adda.w	d3,a5

	move.w	d0,d6
	lsr.w	#3,d6
	adda.w	d6,a5

	moveq	#$F,d6
	and.w	d6,d2
	eor.w	d6,d2

Plane1	btst	#0,d7
	beq.s	Plane2
	bset	d2,(a5)

Plane2	adda.w	#40*256,a5
	btst	#1,d7
	beq.s	Plane3
	bset	d2,(a5)
	
Plane3	adda.w	#40*256,a5
	btst	#2,d7
	beq.s	Plane4
	bset	d2,(a5)

Plane4	adda.w	#40*256,a5
	btst	#3,d7
	beq.s	Plane5
	bset	d2,(a5)

Plane5	adda.w	#40*256,a5
	btst	#4,D7
	beq.s	Out
	bset	d2,(a5)

Out	rts
;--------------------------------------------------------------------------
GfxBase	dc.l 	0
GfxName	dc.b 	"graphics.library",0	
	even
;--------------------------------------------------------------------------
	SECTION	Memory,BSS_C

CList	ds.w	100	;This is a fast way to get
Screen	ds.b	256*40*5	;your memory 'allocated'
;--------------------------------------------------------------------------

