			output	work:huntwindows

			;no includes - i use them all preassembled!

			;.... nearly all ....

			incdir	"sys:devpac/include/"
			include "workbench/startup.i"
			include "workbench/workbench.i"
	
;WHERE ARE THE INCLUDES FOR THIS??????
_LVOFreeDiskObject	= -90
_LVOGetDiskObject	= -78
_LVOFindToolType	= -96

			;Some helpful macros
CALL			macro
			jsr	_LVO\1(a6)
			endm
Push			macro
			movem.l	\1,-(sp)
			endm
Pull			macro
			movem.l	(sp)+,\1
			endm
RSave			macro
			movem.l	a0-a6/d0-d7,-(sp)
			endm
RLoad			macro
			movem.l	(sp)+,a0-a6/d0-d7
			endm

		;Bits for Arguments
ArgMove			equ	0
ArgFront		equ	1
ArgQuit			equ	2
ArgAlways		equ	3
ArgWBOnly		equ	4
ArgWFront		equ	5
ArgPDef			equ	6

		;Bits for Communication
SignalWindow		equ	0
SignalScreen		equ	1

			move.l	$04,a6
			lea	DosName(pc),a1
			moveq.l	#36,d0		;2.0 Only
			CALL	OpenLibrary	
			move.l	d0,DosBase
			beq	Error2

			move.l	ThisTask(a6),a1
			tst.l	pr_CLI(a1)
			bne	CliStart
			lea	pr_MsgPort(a1),a2
			move.l	a2,a0
			CALL	WaitPort
			move.l	a2,a0
			CALL	GetMsg
			move.l	d0,WBMessage
			move.l	d0,a3
		
			move.l	$04,a6
			lea	IconName(pc),a1
			moveq.l	#33,d0
			CALL	OpenLibrary
			move.l	d0,IconBase
			beq	Error2

			move.l	sm_ArgList(a3),d0
			beq.s	SkipReadArgs
			move.l	d0,a0
			move.l	a0,-(sp)
			move.l	wa_Lock(a0),d1
			move.l	DosBase,a6
			CALL	CurrentDir
			move.l	(sp)+,a0

			move.l	IconBase,a6
			move.l	wa_Name(a0),a0
			CALL	GetDiskObject
			move.l	d0,DObject
			beq	Error2

			lea	WBTemplate(pc),a3
			lea	$0300,a4

			move.l	d0,a0
			move.l	do_ToolTypes(a0),a0
			
GetEmLoop		move.l	(a3)+,a1
			move.l	a1,d0
			beq.s	SkipReadArgs
			move.l	a0,-(sp)
			CALL	FindToolType
			move.l	(sp)+,a0
			move.l	(a3)+,a2
			move.l	d0,(a2)
			move.l	d0,(a4)+
			bra.s	GetEmLoop

CliStart		move.l	DosBase,a6

			move.l	#Template,d1
			move.l	#TemplateArray,d2
			moveq.l	#0,d3
			CALL	ReadArgs	;Get options
			tst.l	d0
			beq	Error3
			move.l	d0,Args

SkipReadArgs		move.l	DosBase,a6
			CALL	Output
			move.l	d0,d6		;Remember for all outputs

			move.l	$04,a6
			lea	intuition(pc),a1
			moveq.l	#36,d0
			CALL	OpenLibrary
			move.l	d0,IntBase
			beq	Error2
			lea	GraphicsName(pc),a1
			moveq.l	#36,d0
			CALL	OpenLibrary
			move.l	d0,GfxBasis
			beq	Error2

			tst.l	TempNoMove		;Set the Bits according
			beq.s	NoSet1			;to the parameters given
			bset	#ArgMove,ArgFlag
NoSet1			tst.l	TempNoFront
			beq.s	NoSet2
			bset	#ArgFront,ArgFlag
NoSet2			tst.l	TempQuit
			beq.s	NoSet3
			bset	#ArgQuit,ArgFlag

NoSet3			bclr	#ArgAlways,ArgFlag
			tst.l	TempAlways
			beq.s	NoAlways
			bset	#ArgAlways,ArgFlag

NoAlways		tst.l	TempHADJ
			beq.s	NoSet4
			move.l	TempHADJ,a0
			move.b	(a0),d0
			or.b	#$20,d0
			move.b	d0,SecondFlag

NoSet4			tst.l	TempVADJ
			beq.s	NoSet5
			move.l	TempVADJ,a0
			move.b	(a0),d0
			or.b	#$20,d0
			move.b	d0,SecondFlag+1

NoSet5			tst.l	TempWBOnly
			beq.s	NoSet6
			bset	#ArgWBOnly,ArgFlag

NoSet6			tst.l	TempWFront
			beq.s	NoSet7
			bset	#ArgWFront,ArgFlag

NoSet7			tst.l	TempPDef
			beq.s	NoSet8
			bset	#ArgPDef,ArgFlag

NoSet8			move.l	$04,a6
			CALL	Forbid			;Have a look if we are
			lea	PortName(pc),a1		;already running
			CALL	FindPort		
			tst.l	d0
			beq	FirstInstall
			move.l	d0,a3
			move.l	#MEMF_CLEAR!MEMF_PUBLIC,d1
			move.l	#MN_SIZE+4,d0		;Memory for the message
			CALL	AllocMem
			move.l	d0,a1
			tst.l	d0
			beq	QuitPrg
			move.w	ArgFlag,MN_SIZE(a1)
			move.w	SecondFlag,(MN_SIZE+2)(a1)
			move.l	a3,a0
			move.b	#PA_SIGNAL,MP_FLAGS(a0)	;Necessary, but why like this?
			CALL	PutMsg			;Send message
			CALL	Permit
			bra	ErrorPort

FirstInstall		btst	#ArgQuit,ArgFlag	;Quitting without being
			bne	QuitPrg			;installed means nothing
			CALL	CreateMsgPort
			move.l	d0,MyPort
			move.l	d0,a1
			CALL	Permit
			move.l	#PortName,LN_NAME(a1)
			CALL	AddPort			;Rendevousport
			move.l	MyPort,a0
			moveq.l	#0,d0
			move.b	MP_SIGBIT(a0),d0
			move.l	SignalMask,d1		;Enter signal into
			bset	d0,d1			;mask for waiting
			move.l	d1,SignalMask

			lea	Texth(pc),a0		;Print out who we are
			bsr	PrintText

			move.l	$04,a6			;Build interrupt-server

			sub.l	a1,a1
			jsr	_LVOFindTask(a6)
			move.l	d0,OwnTask

	                moveq   #-1,d0			;A Signal for telling
	                jsr     _LVOAllocSignal(a6)	;our task that sth happened
	                tst.l   d0
	                bmi     Error2
	                move.l  d0,Signal
			move.l	SignalMask,d1
	                bset    d0,d1
	                move.l	d1,SignalMask

			lea	MyInterrupt(pc),a1
			move.l	#Interrupt3,IS_CODE(a1)
			clr.l	IS_DATA(a1)
			move.b	#NT_INTERRUPT,LN_TYPE(a1)
			move.b	#0,LN_PRI(a1)
			move.l	#HandlerName,LN_NAME(a1)
			move.l	#5,d0	;INTB_VERTB
			jsr	_LVOAddIntServer(a6)

WaitOn			move.l	$04,a6
			move.l	SignalMask,d0		;Wait for Port and Break
			CALL	Wait
			btst	#SIGBREAKB_CTRL_C,d0	;This means quit
			bne	QuitPrg
			move.l	Signal,d1
			btst	d1,d0			;Signal from Interrupt?
			beq.s	TryNextMsg

			move.l	IntBase,a0
			btst	#SignalWindow,What
			beq.s	NoWindowStuff
			
			move.l	ib_ActiveWindow(a0),a0
			bsr	DoYourJob
			bclr	#SignalWindow,What

NoWindowStuff		btst	#SignalScreen,What
			beq.s	TryNextMsg
			move.l	IntBase,a0
			move.l	ib_FirstScreen(a0),a0
			bsr	AdjustScreen
			bclr	#SignalScreen,What

TryNextMsg		move.l	MyPort,a0		;Get the message awaiting
			CALL	GetMsg
			tst.l	d0
			bne.s	GotMsg
			bra.s	WaitOn

GotMsg			move.l	d0,a1
			move.w	MN_SIZE(a1),ArgFlag
			move.w	(MN_SIZE+2)(a1),SecondFlag
			move.l	#MN_SIZE+4,d0
			CALL	FreeMem			;Replying is much to
			btst	#ArgQuit,ArgFlag	;complicated - lets just free
			bne.s	QuitPrg
			bra	TryNextMsg

ErrorPort		lea	TextP(pc),a0		;Tell the user we passed
			bsr	PrintText		;the arguments to a 
			bra.s	QuitPrg			;running version

Error3			lea	Text1(pc),a0		;Seems there is an error
			bsr	PrintText		;in the given arguments
			bra.s	QuitPrg

Error2			lea	Text2(pc),a0		;Tell the user something
			bsr	PrintText		;went wrong with the libs
			bra.s	QuitPrg

QuitPrg			move.l	$04,a6	
			CALL	Permit
			move.l	#5,d0
			lea	MyInterrupt(pc),a1
			tst.l	IS_CODE(a1)
			beq.s	NoHandler
			CALL	RemIntServer		;Remove the Interrupt-Server

NoHandler		move.l	Signal,d0		;Free the signal
			beq.s	DontFreeS
	                CALL	FreeSignal

DontFreeS		tst.l	Args
			beq.s	HmmNoArgs
			move.l	DosBase,a6
			move.l	Args,d1
			CALL	FreeArgs

HmmNoArgs		move.l	$04,a6
			move.l	MyPort,d0
			beq.s	NoPort
			move.l	d0,a1			;Remove the message port
			CALL	RemPort
			move.l	MyPort,a0
			CALL	DeleteMsgPort		;and free it

NoPort			tst.l	IntBase			;Close librarys
			beq.s	ErrorX2
			move.l	IntBase,a1
			CALL	CloseLibrary
ErrorX2			tst.l	GfxBasis
			beq.s	Error
			move.l	GfxBasis,a1
			CALL	CloseLibrary

Error			move.l	$0004.w,a6
			tst.l	WBMessage
			beq.s	NoWB
			move.l	WBMessage,a1
			CALL	ReplyMsg

NoWB			
			move.l	IconBase,a6
			move.l	DObject,a0
			move.l	a0,d0
			beq.s	SkipFD
			CALL	FreeDiskObject
SkipFD			move.l	$04,a6
			move.l	IconBase,d0
			beq.s	NoIconLib
			move.l	d0,a1
			CALL	CloseLibrary
			
NoIconLib		move.l	DosBase,a1
			CALL	CloseLibrary
			moveq.l	#0,d0
			rts

			;Subroutine to print a text to stdout
PrintText		Push	d0-d4/a0-a1/a6
			move.l	a0,a1
			moveq.l	#0,d0
TestLen			tst.b	(a1)+
			beq.s	LaengeOk
			addq	#1,d0
			bra.s	TestLen
LaengeOk		move.l	DosBase,a6
			move.l	d6,d1
			beq.s	SkipWrite
			move.l	a0,d2
			move.l	d0,d3
			CALL	Write
SkipWrite		Pull	d0-d4/a0-a1/a6
			rts

			;MainPart: does the scrolling if necessary
			;Gets window in a0
DoYourJob		RSave
			move.l	a0,d0		;No Window - let it be!
			beq	LeaveIt
			move.l	a0,a5

			move.l	wd_WScreen(a5),a0
			move.l	a0,d0		;Screen not valid? - let it be!
			beq	LeaveIt
			move.l	a0,a4
			btst	#ArgWBOnly,ArgFlag
			beq.s	NoMatter
			move.w	sc_Flags(a4),d0
			and.w	#$f,d0
			cmp.w	#WBENCHSCREEN,d0
			bne	LeaveIt

NoMatter		move.l	GfxBasis,a6		;Get the visible size
			lea	sc_ViewPort(a4),a0	;of the screen to
			CALL	GetVPModeID		;determine when a window
			move.l	d0,d2			;is visible and when not
			lea	DisplayInfer(pc),a1
			move.l	#dim_SIZEOF,d0
			move.l	#DTAG_DIMS,d1
			sub.l	a0,a0
			CALL	GetDisplayInfoData
			lea	DisplayInfer(pc),a0
			lea	dim_TxtOScan(a0),a0
			move.w	ra_MaxX(a0),d0
			sub.w	ra_MinX(a0),d0
			addq	#1,d0
			move.w	d0,VisualX

			move.w	ra_MaxY(a0),d0
			sub.w	ra_MinY(a0),d0
			addq	#1,d0
			move.w	d0,VisualY

			move.l	a4,a0
			move.l	IntBase,a6
			btst	#ArgFront,ArgFlag	;do we want screentofront?
			bne.s	NoFront
			CALL	ScreenToFront
			bset	#SignalScreen,What	;ScreenChange!

NoFront			move.l	wd_Flags(a5),d0
			and.l	#WFLG_BACKDROP,d0
			bne	LeaveIt		;Not with backdrops!

			btst	#ArgWFront,ArgFlag
			beq.s	NoFront2
			move.l	a5,a0
			move.l	wd_Flags(a0),d0
			and.l	#WBENCHWINDOW,d0	;does not work - but why?
			bne.s	NoFront2
			CALL	WindowToFront

NoFront2		btst	#ArgMove,ArgFlag
			bne	LeaveIt
			move.l	wd_WScreen(a5),a0	;If the screen is smaller
			move.w	sc_Width(a0),d0		;that the visible size
			cmp.w	VisualX,d0		;in any way, we use the
			bcc.s	NoMat1			;original screen-size
			move.w	sc_Width(a0),VisualX
NoMat1			move.w	sc_Height(a0),d0
			cmp.w	VisualY,d0
			bcc.s	NoMat2
			move.w	sc_Height(a0),VisualX
			

NoMat2			moveq.l	#0,d7
			moveq.l	#0,d6
			moveq.l	#0,d0
			moveq.l	#0,d2
			move.w	wd_LeftEdge(a5),d0
			add.w	wd_Width(a5),d0
			move.w	sc_LeftEdge(a0),d2
			neg.w	d2
			add.w	VisualX,d2
			sub.w	d0,d2
			beq.s	SeemsOk2
			bpl.s	SeemsOk
			move.w	d2,d7		;MOVEX!
			ext.l	d7
SeemsOk			move.w	wd_LeftEdge(a5),d0
			move.w	sc_LeftEdge(a0),d2
			neg.w	d2
			sub.w	d2,d0
			bne.s	TestAgain
			moveq.l	#0,d7
TestAgain		bpl.s	SeemsOk2
			move.w	d0,d7		;MOVEX!	- Prefer Leftedge
			ext.l	d7
			neg.l	d7
SeemsOk2		move.w	wd_TopEdge(a5),d0
			move.w	sc_TopEdge(a0),d2
			neg.w	d2
			sub.w	d2,d0
			beq.s	SeemsOk4
			bpl.s	SeemsOk3
			move.w	d0,d6
			ext.l	d6		;MOVEY!
			neg.l	d6
SeemsOk3		move.w	wd_TopEdge(a5),d0
			add.w	wd_Height(a5),d0
			move.w	sc_TopEdge(a0),d2
			neg.w	d2
			add.w	VisualY,d2
			sub.w	d0,d2
			bne.s	TestAgain2
			moveq.l	#0,d6
TestAgain2		bpl.s	SeemsOk4
			move.w	d2,d6		;MOVEY! - Prefer bottom
			ext.l	d6
SeemsOk4		btst	#ArgAlways,ArgFlag
			bne.s	DOOO
			tst.l	d7
			bne.s	DOOO
			tst.l	d6
			beq	LeaveIt

DOOO			move.l	d7,d0
			btst	#ArgAlways,ArgFlag
			bne.s	DoAlways1
			tst.l	d0
			beq.s	NoMoveAny1
DoAlways1		cmp.b	#"c",SecondFlag
			bne.s	NoCentering1

			moveq.l	#0,d0
			move.w	wd_Width(a5),d0
			lsr.w	#1,d0
			add.w	wd_LeftEdge(a5),d0
			moveq.l	#0,d2
			move.w	VisualX,d2
			lsr.w	#1,d2
			move.w	sc_LeftEdge(a0),d3
			neg.w	d3
			add.w	d3,d2
			sub.w	d0,d2
			move.l	d2,d0
			ext.l	d0
			bra	NoMoveAny1
			
NoCentering1		cmp.b	#"l",SecondFlag
			bne.s	RightAdj
			moveq.l	#0,d0
			move.w	wd_LeftEdge(a5),d0
			add.w	sc_LeftEdge(a0),d0
			neg.w	d0
			ext.l	d0
			bra.s	NoMoveAny1

RightAdj		cmp.b	#"r",SecondFlag
			bne.s	NoMoveAny1
			move.w	wd_LeftEdge(a5),d0
			add.w	wd_Width(a5),d0
			move.w	sc_LeftEdge(a0),d2
			neg.w	d2
			add.w	VisualX,d2
			sub.w	d0,d2
			move.l	d2,d0
			ext.l	d0

NoMoveAny1		move.l	d6,d1
			btst	#ArgAlways,ArgFlag
			bne.s	DoAlways2
			tst.l	d1
			beq.s	NoMoveAny2
DoAlways2		cmp.b	#"c",SecondFlag+1
			bne.s	NoCentering2

			moveq.l	#0,d1
			move.w	wd_Height(a5),d1
			lsr.w	#1,d1
			add.w	wd_TopEdge(a5),d1
			moveq.l	#0,d2
			move.w	VisualY,d2
			lsr.w	#1,d2
			move.w	sc_TopEdge(a0),d3
			neg.w	d3
			add.w	d3,d2
			sub.w	d1,d2
			move.l	d2,d1
			ext.l	d1
			bra	NoMoveAny2

NoCentering2		cmp.b	#"t",SecondFlag+1
			bne.s	BotAdj
			moveq.l	#0,d1
			move.w	wd_TopEdge(a5),d1
			add.w	sc_TopEdge(a0),d1
			neg.w	d1
			ext.l	d1
			bra.s	NoMoveAny2

BotAdj			cmp.b	#"b",SecondFlag+1
			bne.s	NoMoveAny2
			move.w	wd_TopEdge(a5),d1
			add.w	wd_Height(a5),d1
			move.w	sc_TopEdge(a0),d2
			neg.w	d2
			add.w	VisualY,d2
			sub.w	d1,d2
			move.l	d2,d1
			ext.l	d1

NoMoveAny2		CALL	MoveScreen
LeaveIt			RLoad
			rts

			;ScreenID in a0
AdjustScreen		RSave
			btst	#ArgPDef,ArgFlag
			beq.s	Skip_NoPub
			bsr	GetPubFromID
			move.l	a0,d0
			beq.s	Skip_NoPub
			move.l	IntBase,a6
			CALL	SetDefaultPubScreen
Skip_NoPub		RLoad
			rts

			;ScreenID in a0	;Return a0=PubScreenName or Zero
GetPubFromID		Push	d0/a3/a6
			move.l	a0,a3
			move.l	IntBase,a6
			CALL	LockPubScreenList

CarryListOn		move.l	d0,a0
			cmp.l	psn_Screen(a0),a3
			beq.s	ScreenFound
			move.l	LN_SUCC(a0),d0
			bne.s	CarryListOn
			sub.l	a0,a0
			bra.s	ENDPS

ScreenFound		move.l	LN_NAME(a0),a0
ENDPS			move.l	a0,-(sp)
			CALL	UnlockPubScreenList
			move.l	(sp)+,a0
			Pull	d0/a3/a6
			rts

Interrupt3		RSave
			move.l	IntBase,a0
			move.l	Active,d0
			cmp.l	ib_ActiveWindow(a0),d0		;New ActiveWindow?
			beq.s	DoNothing
			move.l	ib_ActiveWindow(a0),Active

			bsr	SignalMyself

			bset	#SignalWindow,What
			
DoNothing		move.l	IntBase,a0
			move.l	FirstSc,d0
			cmp.l	ib_FirstScreen(a0),d0		;New FirstScreen?
			beq.s	DoNothing2
			move.l	ib_FirstScreen(a0),FirstSc

			bsr	SignalMyself

			bset	#SignalScreen,What

DoNothing2		RLoad
			moveq.l	#0,d0
			rts

SignalMyself		move.l  $04,a6
			move.l  OwnTask,a1
			move.l  Signal,d1		;send a signal to move Screen
			moveq.l	#0,d0
			bset	d1,d0
			CALL	Signal
			rts


			;Space for displayinfo block
DisplayInfer		ds.b	dim_SIZEOF

What			dc.w	0
ArgFlag			dc.w	0
SecondFlag		dc.w	0
MyPort			dc.l	0
IntBase			dc.l	0
DosBase			dc.l	0
IconBase		dc.l	0
DObject			dc.l	0
Active			dc.l	0
FirstSc			dc.l	0
GfxBasis		dc.l	0
VisualX			dc.w	0
VisualY			dc.w	0
TemplateArray		;
TempHADJ		dc.l	0
TempVADJ		dc.l	0
TempNoFront		dc.l	0
TempNoMove		dc.l	0
TempAlways		dc.l	0
TempWBOnly		dc.l	0
TempWFront		dc.l	0
TempPDef		dc.l	0
TempQuit		dc.l	0
OwnTask			dc.l	0
Signal			dc.l	0
Args			dc.l	0
WBMessage		dc.l	0
SignalMask		dc.l	SIGBREAKF_CTRL_C
intuition		dc.b	"intuition.library",0
DosName			dc.b	"dos.library",0
GraphicsName		dc.b	"graphics.library",0
IconName		dc.b	"icon.library",0

			even
MyInterrupt		ds.b	IS_SIZE
			even

WBTemplate	dc.l	TextHADJ,TempHADJ
		dc.l	TextVADJ,TempVADJ
		dc.l	TextNoFront,TempNoFront
		dc.l	TextNoMove,TempNoMove
		dc.l	TextAlways,TempAlways
		dc.l	TextWBOnly,TempWBOnly
		dc.l	TextWFront,TempWFront
		dc.l	TextPDef,TempPDef
		dc.l	TextQuit,TempQuit
		dc.l	0

TextHADJ	dc.b	"HADJ",0
TextVADJ	dc.b	"VADJ",0
TextNoFront	dc.b	"NOFRONT",0
TextNoMove	dc.b	"NOMOVE",0
TextAlways	dc.b	"ALWAYS",0
TextWBOnly	dc.b	"WBONLY",0
TextWFront	dc.b	"WFRONT",0
TextPDef	dc.b	"DEFPUB",0
TextQuit	dc.b	"QUIT",0
Template	dc.b	"HADJ/K,VADJ/K,NOFRONT/S,NOMOVE/S,ALWAYS/S,WBONLY/S,WFRONT/S,DEFPUB/S,QUIT/S",0
PortName	dc.b	"Huntwindows1.4-Rendezvous",0
HandlerName	dc.b	"Huntwindows1.4-Watcher",0
Text1		dc.b	"Error in arguments!",$0a,0
Text2		dc.b	"Error opening V36+ librarys!",$0a,0
TextP		dc.b	"Huntwindows 1.4 - already installed, arguments passed.",$0a,0
		dc.b	"$VER: "	;for version information
Texth		dc.b	"Huntwindows 1.4 (22.11.92) by Jörg Bublath",$0a,0
		even
