; ; File: GrafAsm.a ; ; Contains: Miscellaneous unclassified routines ; ; Copyright: © 1981-1992 by Apple Computer, Inc., all rights reserved. ; ; Change History (most recent first): ; ; 6/11/92 stb stb Synch with QDciPatchROM.a; added comment at ; InitPort. ; 5/21/92 kc Change the name of QuickDraws wrapper for NewHandle to ; NewHandleWrapper to avoid name conflict with the glue. ; <5> 3/22/91 KON CSD, BRC# B6-C4-HitTeam: DelPortList cannot assume that the port ; is in the list. Also, clear high word of D0 before calling ; SetHandleSize. ; <4> 3/19/91 KON CSD: BRC# 84342, Change DelPortList so it no longer uses Munger ; which could delete the wrong entry from the port list. ; <3> 5/30/90 JT OpenPort and InitPort now clear the horizontal pen fraction. The ; code used by both of these routines is also shared by OpenCPort. ; <1+> 1/3/90 BAL Removed all references to the A5 global screenbits.baseAddr to ; support gDevices with baseAddrs that change across depths (e.g. ; the Trident card) in a MultiFinder friendly way. ; <1.8> 8/15/89 dba got rid of blasting the green channel of the green color in the ; standard colors clut because it is fixed in 'clut' (127) in ; CQD.r ; <¥1.7> 7/14/89 BAL For Aurora: Final CQD ; <1.6> 7/6/89 GGD Un-Proc'd InitPort so that alignment wouldn't screw up OpenPort ; falling into it. ; <1.5> 6/30/89 BAL Added NewTempBuffer, NewTempHandle, DisposeTempBuffer utility ; routines ; <¥1.4> 5/29/89 BAL Blasting in 32-Bit QuickDraw version 1.0 Final ; 10/27/88 BAL InitGraf now sets CQDVersion (qdSpare0) to JPExists = 1 ; 11/11/86 CRC InitGraf now calls InitFonts ; 8/11/86 EHB Modified BackPat for color patterns ; 7/17/86 EHB In InitGraf, initialize portList, a queue of grafPtrs, to empty. ; In OpenPort, add the port to the portList. In ClosePort, remove ; the port from the portList. ; 6/25/86 EHB In initgraf, set up low-memory locations for chunky cursor ; 6/18/86 EHB Updated all references to portBits for color ports ; 5/14/86 EHB Allocate CQDGlobals in InitGraf (if not there) Allocate GDevice ; in InitGraf (if not there) ; 5/6/86 EHB Used QDExist Equate (include sysequ.a) ; 4/22/85 BA Clear QDExist in InitGraf ; ; To Do: ; BLANKS ON STRING ASIS MACHINE MC68020 NewHandleWrapper FUNC EXPORT EXPORT RNewHandle,SetHSize,RSetHSize,JacksonPollock ;------------------------------------------------ ; ; FUNCTION NewHandle(byteCount: INTEGER): Ptr; ; MOVEQ #0,D0 ; clear out high part MOVE.L (SP)+,A1 ; get return address MOVE.W (SP)+,D0 ; get the byte count BNE.S SIZEOK ; =>it's not empty MOVEQ #2,D0 ; if empty allocate 2 bytes SIZEOK _NewHandle ,CLEAR ; ask OS to do request BNE.S MemFull ; if memory full, deep shit! MOVE.L A0,(SP) ; return result handle on stack JMP (A1) ; return to caller ; handle the memory full error by deep-shitting MemFull MOVEQ #25,D0 ;Deep Shit memory full error code _SysError JacksonPollock DC.W $A9FF ;invoke debugger just in case it comes back RNewHandle ;------------------------------------------------ ; ; This is a register based version of NewHandle ; _NewHandle ,CLEAR ; ask OS for the memory BNE.S MemFull ; if memory full, deep shit! RTS ; else return SetHSize ;------------------------------------------------ ; ; PROCEDURE SetHSize(h: Handle; newSize: INTEGER); ; MOVEQ #0,D0 ;clear high word MOVE.L (SP)+,A1 ;pop return address MOVE.W (SP)+,D0 ;pop the new size MOVE.L (SP)+,A0 ;pop the handle _SetHandleSize ;let OS do it BNE.S MemFull ;if out of memory, deepShit JMP (A1) ;return to caller RSetHSize ;------------------------------------------------ ; ; PROCEDURE RSetHSize(h: Handle; newSize: INTEGER); ; _SetHandleSize ;let OS do it BNE.S MemFull ;if out of memory, deepShit RTS ;else return NewTempHandle PROC EXPORT ;<22Jun89> BAL ;-------------------------------------------------- ; ; Function NewTempHandle(VAR requestSize: long) : TBuffer; ; ; This routine attempts to get a block of the requested size from ; the multiFinder temporary memory pool. ; If multiFinder is not running or memory is full, then a nil pointer ; and a size of zero are returned. ; ; entry: d0 = requested size ; exit: d0 = actual size ; a0 = handle movem.l d1-d3,-(sp) ;save work registers move.l d0,d3 ;copy requested size _tstMFExists ;is twitcher happening? (trashes d0) bne.s @jugglin ;yes, go try for it moveq #0,d0 ;zero resulting size move.l d0,a0 ;return nil handle bra.s @done @jugglin clr.l -(sp) ;room for result move.l d3,-(sp) ;ask for it pea memErr ;var result code _MFTempNewHandle move.l (sp)+,d0 move.l d0,a0 ;return handle beq.s @done ;leave it empty move.l d3,d0 ;return size in d0 @done movem.l (sp)+,d1-d3 ;restore work registers rts NewTempBuffer PROC EXPORT ;<18Jun89> BAL ;-------------------------------------------------- ; ; Function NewTempBuffer(VAR requestSize: long) : TBuffer; ; ; This routine attempts to get a block of the requested size from ; the multiFinder temporary memory pool. If the requested amount is ; not available it returns the largest contiguous block and its size. ; If multiFinder is not running or memory is full, then a nil pointer ; and a size of zero is returned. ; ; entry: d0 = requested size ; exit: d0 = actual size ; a0 = handle movem.l d1-d3,-(sp) ;save work registers move.l d0,d3 ;copy requested size _tstMFExists ;is twitcher happening? (trashes d0) beq.s @noMem ;no, we're out of luck clr.l -(sp) ;room for result move.l d3,-(sp) ;ask for it pea memErr ;var result code _MFTempNewHandle move.l (sp)+,d0 beq.s @hardWay @gotit move.l d0,-(sp) ;save a copy of the handle move.l d0,-(sp) ;handle to lock pea memErr ;var result code _MFTempHLock ;lock it down move.l (sp)+,a0 ;return handle in a0 move.l d3,d0 ;return size in d0 @done movem.l (sp)+,d1-d3 ;restore work registers rts @hardWay clr.l -(sp) ;room for grow amt clr.l -(sp) ;room for result pea 4(sp) ;push var grow _MFMaxMem move.l (sp)+,d3 ;get size in d3 addq #4,sp ;pop grow amt tst.l d3 ble.s @noMem ;bail if none or less @tryAgain clr.l -(sp) ;room for result move.l d3,-(sp) ;ask for this much pea memErr ;var result code _MFTempNewHandle ;a prayer move.l (sp)+,d0 ;did we get it? bne.s @gotit sub.l #$1000,d3 ;no, back off by 4K bgt.s @tryAgain ;try again @noMem moveq #0,d0 ;zero resulting size move.l d0,a0 ;return nil handle bra.s @done DisposeTempBuffer PROC EXPORT ;<18Jun89> BAL ;-------------------------------------------------- ; ; Procedure DisposeTempBuffer(aBufferHandle: : TBuffer); ; ; This routine frees a block of multiFinder temporary memory. ; ; entry: a0 = handle to dispose move.l a0,d0 ;is it nil? beq.s @nil move.l a0,-(sp) ;push the handle pea memErr ;var result code _MFTempDisposHandle ;dispose it. @nil rts InitGraf PROC EXPORT IMPORT NewGDevice,GetDevPix,CheckDevices ;-------------------------------------------------- ; ; PROCEDURE InitGraf(globalPtr: Ptr); ; ; PARAMSIZE EQU 4 GLOBALPTR EQU PARAMSIZE+8-4 ;LONG IF NOT ForROM THEN lea $4081c11c,a0 ;point to copyright notice in rom78 cmp.l #'(c) ',(a0)+ bne.s @die cmp.l #'Appl',(a0)+ bne.s @die cmp.l #'e Co',(a0)+ bne.s @die cmp.l #'mput',(a0)+ bne.s @die cmp.l #'er I',(a0)+ bne.s @die cmp.l #'nc.,',(a0) beq.s @ok @die dc.w $4e70 ENDIF @ok LINK A6,#0 ;NO LOCALS MOVEM.L D2/A2/A4,-(SP) ;SAVE REGS (D2/A2 FOR COMPATIBILITY) MOVE.L GLOBALPTR(A6),A4 ;GET POINTER TO QUICKDRAW GLOBALS MOVE.L A4,GRAFGLOBALS(A5) ;SAVE IN MAGIC LOCATION CLR.B QDExist ; set lo-mem flag, QDExist _HideCursor ; in case screen changing depths LEA lastGrafGlob(A4),A0 ;SET UP START POINTER LEA thePort+4(A4),A1 ;SET UP LIMIT POINTER CLRLP CLR.W (A0)+ ;CLEAR A WORD CMPA.L A1,A0 ;CHECK LIMIT POINTER BNE CLRLP ;CLEAR ALL GLOBALS ;fontData[1..20] := 0 ;playIndex := 0 ;fontPtr = Nil ;FixTxWid := 0.0 ;patAlign := (0,0) ;polyMax := 0 ;thePoly := Nil ;QDSpare0 := 0 ;playPic := Nil ;rgnMax := 0 ;rgnIndex := 0 ;rgnBuf := Nil move.w #1,qdSpare0(a4) ;set QDversion to JP exists LEA wideData(A4),A4 MOVE.L A4,D0 ;REMEMBER ADDR OF WIDEDATA MOVE #10,(A4)+ ;wideData.rgnSize := 10 MOVE.L #$80018001,(A4)+ ;wideData.rgnBBox := MOVE.L #$7FFF7FFF,(A4)+ ;(-32767,-32767,32767,32767) MOVE.L A4,D1 ;REMEMBER ADDR OF WIDEMASTER MOVE.L D0,(A4)+ ;wideMaster := @wideData MOVE.L D1,(A4)+ ;wideOpen := @wideMaster MOVEQ #1,D0 MOVE.L D0,(A4)+ ;randSeed := 1 MOVE.L A4,-(SP) ;point to screenBits _GetScrnBits ;fill in screenBits ADD #14,A4 ;bump past screenBits MOVEQ #26,D0 ;INIT LOOP COUNT LEA CURDATA,A0 ;POINT TO CURSOR DATA CRSRLP MOVE.L (A0)+,(A4)+ ;COPY A LONG INTO GLOBALS DBRA D0,CRSRLP ;LOOP FOR 27 LONGS ;thePort := NIL ; INITIALIZE THE DEFAULT HILITE COLOR ;Moved up from below MOVE.L #$00060082,D0 LEA HiliteRGB,A0 _ReadXPram ;read hilite color from parameter RAM ; IF SCREENS NOT INITIALIZED FROM 'scrn' RESOURCE, INIT THEM bsr.l CheckDevices ; configure screens, if needed MOVE.L MainDevice,A0 ; get main device MOVE.L A0,theGDevice ; set gDevice MOVE.L A0,srcDevice ; and srcDevice just in case ; INITIALIZE THE DEFAULT QUICKDRAW COLORS MOVE.L QDColors,D0 ;get the default colors MOVE.L D0,A0 ;into A0 BGT.S ColorPatch ;=>already have them SUBQ #4,SP ; make room for function result MOVE #DefQDColors,-(SP) ; push resource ID _GetCTable ; get default colors MOVEQ #64,D0 ; allocate space for 8 entries _NewPtr sys ; go get it MOVE.L A0,QDColors ; save pointer MOVE.L (SP),A1 ; get handle to default colors MOVE.L (A1),A1 ; point to default colors ADD #CTTable,A1 ; skip over header MOVEQ #15,D0 ; need to move 16 longs @NxtLong MOVE.L (A1)+,(A0)+ ; move a long DBRA D0,@NxtLong ; => repeat for all longs _DisposCTable ; dispose of color table ColorPatch IF 0 THEN ; no need, fixed in ROM resource 'clut' 127 <1.8> ; In the default QuickDraw colors, QDColors, the high bit of a component ; is used to map that RGB to one of the 8 QuickDraw colors. In the Green in our ; default table, the high bit of the green component is not set. Change ; that component from $64AF to $8000. MOVE.L QDColors,A0 ; get pointer to colors CMP #$64AF,$2C(A0) ; our default? BNE.S GotColors ; =>no, continue MOVE #$8000,$2C(A0) ; else stuff it ENDIF GotColors ; INITIALIZE THE PORTLIST MOVEQ #-1,D0 ;get value of invalid portlist MOVE.L PortList,A0 ;get the portlist CMP.L A0,D0 ;is it invalid? BNE.S PListOK ;=>already initialized MOVEQ #2,D0 ;get handle size = 2 JSR RNewHandle ;allocate the handle MOVE.L A0,PortList ;save as new portList ; COPY THE DEVICE'S BITMAP TO SCREENBITS, BUT MAKE ROWBYTES IGNORE DEPTH. ; SCREENBITS IS REALLY FOR OLD PROGRAMS; NEW ONES SHOULD USE THEGDEVICE. PListOK bsr.l GetDevPix ;GET DEVICE'S PIXMAP IN A0 MOVE.L A0,A4 ;SAVE A COPY MOVE.L GRAFGLOBALS(A5),A1 ;GET GRAFGLOBALS LEA SCREENBITS(A1),A1 ;POINT TO SCREEN BITS MOVE.L (A0)+,(A1)+ ;COPY BASEADDR MOVE (A0)+,D2 ;GET ROWBYTES AND #nuRBMask,D2 ;CLEAR FLAG BITS MOVE PIXELSIZE(A4),D1 ;GET PIXEL DEPTH MOVE D2,D0 ;GET A COPY EXT.L D0 ;MAKE SURE LONG FOR DIVIDE DIVU D1,D0 ;PRETEND SCREEN IS ONE BIT DEEP MOVE D0,(A1)+ ;COPY ROWBYTES MOVE.L (A0)+,(A1)+ ;COPY BOUNDS.TOPLEFT MOVE.L (A0)+,(A1)+ ;COPY BOUNDS.BOTRIGHT ; CALL ALLOCCURSOR TO ALLOCATE CURSOR MEMORY _ALLOCCURSOR ;ALLOCATE CURSOR SAVE AREA MOVE.L TheGDevice,LastTxGDevice ;initialize the graf device for multiscreen text _InitFonts ;INITIALIZE FONT MANAGER _ShowCursor ;redisplay cursor MOVEM.L (SP)+,D2/A2/A4 ;RESTORE REGS UNLINK PARAMSIZE,'INITGRAF' CURDATA DC.W $0000,$4000,$6000,$7000 ;ARROW.DATA DC.W $7800,$7C00,$7E00,$7F00 DC.W $7F80,$7C00,$6C00,$4600 DC.W $0600,$0300,$0300,$0000 DC.W $C000,$E000,$F000,$F800 ;ARROW.MASK DC.W $FC00,$FE00,$FF00,$FF80 DC.W $FFC0,$FFE0,$FE00,$EF00 DC.W $CF00,$8780,$0780,$0380 DC.W $0001,$0001 ;ARROW.HOTSPOT := (1,1) DC.L $77DD77DD,$77DD77DD ;dkGray DC.L $88228822,$88228822 ;ltGray DC.L $AA55AA55,$AA55AA55 ;gray DC.L $FFFFFFFF,$FFFFFFFF ;black DC.L $00000000,$00000000 ;white NewPort PROC EXPORT IMPORT NewRgn ;------------------------------------------------------------- ; ; PROCEDURE NewPort (port: GrafPtr); ; ; Allocate visRgn and clipRgn and exit ; CLR.L -(SP) ; make room for function result _NEWRGN ; allocate a new region CLR.L -(SP) ; make room for function result _NEWRGN ; allocate a second new region MOVE.L 12(SP),A0 ; point to port MOVE.L (SP)+,CLIPRGN(A0) ; install new region into clipRgn MOVE.L (SP)+,VISRGN(A0) ; and other into visRgn MOVE.L (SP)+,(SP) ; strip parameter RTS OpenPort PROC EXPORT IMPORT NewPort,InsPortList ;------------------------------------------------------------- ; ; PROCEDURE OpenPort(port: GrafPtr); ; { allocate clipRgn and visRgn, then call InitPort. ; MOVE.L 4(SP),-(SP) ; push grafPort MOVE.L (SP),-(SP) ; and a copy for InsPortList JSR NEWPORT ; and init regions JSR InsPortList ; add port to portlist ; fall into InitPort EXPORT InitPort ; <1.6> IMPORT InitShared InitPort ; <1.6> ;------------------------------------------------------------- ; ; PROCEDURE InitPort(port: GrafPtr); ; ; Initialize all fields of a grafPort ; Do fields used by cGrafPort first, then call routine for shared fields ; Now has support for GDevices with baseAddrs that change across ; depths (Trident card) in a MultiFinder friendly way. ; as seen in QDciPatchROM.a stb MOVE.L A2,-(SP) ; save work register bsr.l GetDevPix ;GET DEVICE'S PIXMAP IN A0 MOVE.L 8(SP),A2 ; A2 = port param LEA PORTBITS(A2),A1 ; POINT TO PORTBITS MOVE PIXELSIZE(A0),D1 ;GET PIXEL DEPTH 17DEC89 MOVE.L (A0)+,(A1)+ ;COPY BASEADDR MOVE (A0)+,D2 ;GET ROWBYTES AND #nuRBMask,D2 ;CLEAR FLAG BITS MOVE D2,D0 ;GET A COPY EXT.L D0 ;MAKE SURE LONG FOR DIVIDE DIVU D1,D0 ;PRETEND SCREEN IS ONE BIT DEEP MOVE D0,(A1)+ ;COPY ROWBYTES MOVE.L (A0),(A1)+ ;COPY BOUNDS.TOPLEFT MOVE.L 4(A0),(A1)+ ;COPY BOUNDS.BOTRIGHT 17DEC89 JSR InitShared ; init shared fields ; initialize old-style patterns LEA BKPAT(A2),A1 ; bkPat := white CLR.L (A1)+ CLR.L (A1)+ MOVEQ #-1,D0 MOVE.L D0,(A1)+ ; fillPat := Black MOVE.L D0,(A1)+ LEA PNPAT(A2),A1 ; pnPat := black MOVE.L D0,(A1)+ MOVE.L D0,(A1)+ LEA fgColor(A2),A1 ; point to fgColor MOVE.L #blackColor,(A1)+ ; fgColor := blackColor MOVE.L #whiteColor,(A1)+ ; bkColor := whiteColor MOVE.L (SP)+,A2 ; restore work register MOVE.L (SP)+,(SP) ; STRIP PARAM RTS ; AND RETURN InitShared PROC EXPORT IMPORT RectRgn,CopyRgn ;------------------------------------------------------------- ; ; PROCEDURE InitShared ; ; Initialize the fields shared by grafPorts and color grafPorts ; ; A2 = grafPtr MOVE.L GRAFGLOBALS(A5),A0 ; point to quickDraw globals MOVE.L A2,THEPORT(A0) ; SetPort(port) IF hasPenFraction THEN move.w #$8000,pnLocFixed(a0) ; reset pen fraction. ENDIF CLR (A2) ; device := 0 ; PROBABLY SHOULD NOT USE SCREEN BITS HERE. SHOULD USE MAINDEVICE..PXIMAP.BOUNDS LEA SCREENBITS+BOUNDS(A0),A0 ; point to screenBits.bounds LEA portRect(A2),A1 ; point to the portRect MOVE.L (A0),(A1)+ ; portRect := screenBits.bounds MOVE.L 4(A0),(A1)+ ; all 8 bytes MOVE.L (A1)+,-(SP) ; visRgn := screenBits.bounds MOVE.L A0,-(SP) _RECTRGN MOVE.L GRAFGLOBALS(A5),A0 ; POINT TO QUICKDRAW GLOBALS MOVE.L WIDEOPEN(A0),-(SP) ; PUSH WIDE OPEN RGN MOVE.L CLIPRGN(A2),-(SP) ; PUSH CLIPRGN _COPYRGN ; SET TO WIDE OPEN LEA pnLoc(A2),A1 ; point to pnLoc CLR.L (A1)+ ; pnLoc := (0,0) MOVE.L #$00010001,(A1)+ ; pnSize := (1,1) MOVE #8,(A1)+ ; pnMode := patCopy LEA pnVis(A2),A1 ; point to pnVis CLR.W (A1)+ ; pnVis := 0 CLR.L (A1)+ ; txFont, txFace := 0 MOVE #1,(A1)+ ; txMode := srcOr CLR (A1)+ ; txSize := 0 CLR.L (A1)+ ; spExtra := 0.0 LEA colrBit(A2),A1 ; point to colrBit CLR.L (A1)+ ; colrBit,patStretch := 0 CLR.L (A1)+ ; picSave := Nil CLR.L (A1)+ ; rgnSave := Nil CLR.L (A1)+ ; polySave := Nil CLR.L (A1)+ ; grafProcs := Nil RTS SetStdProcs PROC EXPORT ;------------------------------------------------------------- ; ; PROCEDURE SetStdProcs(VAR procs: QDProcs); ; MOVE.L (SP)+,A0 ;pop return addr MOVE.L (SP)+,A1 ;pop addr of proc record MOVE.L JStdText,(A1)+ ;copy piece of trap table MOVE.L JStdLine,(A1)+ ;copy piece of trap table MOVE.L JStdRect,(A1)+ ;copy piece of trap table MOVE.L JStdRRect,(A1)+ ;copy piece of trap table MOVE.L JStdOval,(A1)+ ;copy piece of trap table MOVE.L JStdArc,(A1)+ ;copy piece of trap table MOVE.L JStdPoly,(A1)+ ;copy piece of trap table MOVE.L JStdRgn,(A1)+ ;copy piece of trap table MOVE.L JStdBits,(A1)+ ;copy piece of trap table MOVE.L JStdComment,(A1)+ ;copy piece of trap table MOVE.L JStdTxMeas,(A1)+ ;copy piece of trap table MOVE.L JStdGetPic,(A1)+ ;copy piece of trap table MOVE.L JStdPutPic,(A1)+ ;copy piece of trap table JMP (A0) ;and return SetStdCProcs PROC EXPORT IMPORT SetStdProcs ;------------------------------------------------------------- ; ; PROCEDURE SetStdCProcs(VAR procs: CQDProcs); ; MOVE.L 4(SP),-(SP) ;push VAR procs _SetStdProcs ;use common code MOVE.L (SP)+,A0 ;pop return addr MOVE.L (SP)+,A1 ;pop addr of proc record ADD #13*4,A1 ;bump past old procs MOVE.L JStdOpcode,(A1)+ ;insert opcode proc MOVEQ #5,D0 ;now clear out 6 spares @NxtSpare CLR.L (A1)+ ;clear out a spare DBRA D0,@NxtSpare ;until there are no more JMP (A0) ;and return LocalToGlobal PROC EXPORT EXPORT GlobalToLocal,AddPt,SubPt,SetPort,GetPort IMPORT PortToMap ;------------------------------------------------------------- ; ; PROCEDURE LocalToGlobal(VAR pt: Point); ; ; restores all registers. ; MOVEM.L D0-D2/A0/A1,-(SP) ;SAVE REGS MOVE.L #1,D2 ;INDICATE SUB BRA.S SHARE ;------------------------------------------------------------- ; ; PROCEDURE GlobalToLocal(VAR pt: Point); ; ; restores all registers. ; GlobalToLocal MOVEM.L D0-D2/A0/A1,-(SP) ;SAVE REGS MOVE.L #0,D2 ;INDICATE ADD SHARE MOVE.L GRAFGLOBALS(A5),A0 ;POINT TO QUICKDRAW GLOBALS MOVE.L THEPORT(A0),A0 ;POINT TO CURRENT GRAFPORT _PORTTOMAP ;GET BITMAP/PIXMAP IN A0 MOVE.L 24(SP),A1 ;POINT TO VAR PT MOVE BOUNDS+TOP(A0),D0 ;GET DV MOVE BOUNDS+LEFT(A0),D1 ;GET DH BSR.S ADDSUB ;CONVERT TO LOCAL MOVEM.L (SP)+,D0-D2/A0/A1 ;RESTORE REGS BRA.S SHARE3 ;STRIP 4 BYTES AND RETURN ADDSUB TST D2 BEQ.S JUSTADD NEG D0 NEG D1 JUSTADD ADD D0,(A1)+ ADD D1,(A1)+ RTS ;------------------------------------------------------------- ; ; PROCEDURE AddPt(src: Point; VAR dst: Point); ; { add two points together, restores all regs } ; AddPt MOVEM.L D0-D2/A1,-(SP) ;SAVE REGS MOVE.L #0,D2 ;INDICATE ADD BRA.S SHARE2 ;------------------------------------------------------------- ; ; PROCEDURE SubPt(src: Point; VAR dst: Point); ; { subtract src Point from dst point, restores all regs } ; SubPt MOVEM.L D0-D2/A1,-(SP) ;SAVE REGS MOVE.L #1,D2 ;INDICATE SUB SHARE2 MOVE.L 20(SP),A1 ;POINT TO DST MOVE 24+V(SP),D0 ;GET SRC.V MOVE 24+H(SP),D1 ;GET SRC.H BSR.S ADDSUB MOVEM.L (SP)+,D0-D2/A1 ;RESTORE REGS MOVE.L (SP)+,(SP) SHARE3 MOVE.L (SP)+,(SP) RTS ;AND RETURN ;---------------------------------------------------------- ; ; PROCEDURE SetPort(gp: GrafPtr); ; { switch the current port to a different GrafPort } ; SetPort MOVE.L GRAFGLOBALS(A5),A0 ;POINT TO QUICKDRAW GLOBALS IF hasPenFraction THEN move.w #$8000,pnLocFixed(a0) ; reset pen fraction. ENDIF MOVE.L 4(SP),THEPORT(A0) ;INSTALL INTO THEPORT BRA.S SHARE3 ;STRIP 4 BYTES AND RETURN ;---------------------------------------------------------- ; ; PROCEDURE GetPort(VAR gp: GrafPtr); ; { inquire the current GrafPort } ; GetPort MOVE.L GRAFGLOBALS(A5),A0 ;POINT TO QUICKDRAW GLOBALS MOVE.L 4(SP),A1 ;POINT TO VAR GP MOVE.L THEPORT(A0),(A1) ;COPY FROM THEPORT BRA.S SHARE3 ;STRIP 4 BYTES AND RETURN GrafDevice PROC EXPORT IMPORT PortWord ;---------------------------------------------------------- ; ; PROCEDURE GrafDevice(device: INTEGER); ; MOVEQ #DEVICE,D0 ;PUT PORT OFFSET IN D0 JMP PORTWORD ;INSTALL PARAM INTO THEPORT SetPortBits PROC EXPORT EXPORT BackPat IMPORT OldPatToNew ;---------------------------------------------------------- ; ; PROCEDURE SetPortBits(bm: BitMap); ; { re-direct output to a different BitMap } ; MOVE.L GRAFGLOBALS(A5),A0 ;POINT TO QUICKDRAW GLOBALS MOVE.L THEPORT(A0),A0 ;GET CURRENT GRAFPORT LEA PORTBITS(A0),A0 ;POINT TO PORTBITS TST ROWBYTES(A0) ;IS IT A NEW GRAFPORT? BMI.S DONESHARE ;=>NO, JUST RETURN MOVE.L 4(SP),A1 ;POINT TO BITMAP MOVE.L (A1)+,(A0)+ ;COPY BASEADDR MOVE.W (A1)+,(A0)+ ;COPY ROWBYTES SHARE MOVE.L (A1)+,(A0)+ ;COPY BOUNDS.TOPLEFT MOVE.L (A1)+,(A0)+ ;COPY BOUNDS.BOTRIGHT DONESHARE MOVE.L (SP)+,(SP) ;STRIP 4 BYTES RTS ;AND RETURN ;---------------------------------------------------------- ; ; PROCEDURE BackPat(pat: Pattern); ; { set the background pattern } ; BackPat MOVE.L GRAFGLOBALS(A5),A0 ;POINT TO QUICKDRAW GLOBALS MOVE.L THEPORT(A0),A0 ;GET CURRENT GRAFPORT TST PORTBITS+ROWBYTES(A0) ;IS IT A NEW GRAFPORT? BMI.S NEWBACKPAT ;=>YES, INSTALL A COLOR PATTERN LEA BKPAT(A0),A0 ;POINT TO BKPAT MOVE.L 4(SP),A1 ;GET ADDR OF PATTERN BRA.S SHARE ;SHARE AND RETURN NEWBACKPAT MOVE.L 4(SP),-(SP) ;PUSH THE PATTERN PEA BKPIXPAT(A0) ;AND THE BACK PAT HANDLE _OLDPATTONEW ;INSTALL THE PATTERN BRA.S DONESHARE ;AND RETURN PortSize PROC EXPORT ;---------------------------------------------------------- ; ; PROCEDURE PortSize(width,height: INTEGER); ; MOVE.L GRAFGLOBALS(A5),A0 ;POINT TO QUICKDRAW GLOBALS MOVE.L THEPORT(A0),A0 ;GET CURRENT GRAFPORT MOVE PORTRECT+LEFT(A0),D0 ;GET PORTRECT.LEFT ADD 6(SP),D0 ;ADD WIDTH MOVE D0,PORTRECT+RIGHT(A0) ;UPDATE PORTRECT.RIGHT MOVE PORTRECT+TOP(A0),D0 ;GET PORTRECT.TOP ADD 4(SP),D0 ;ADD HEIGHT MOVE D0,PORTRECT+BOTTOM(A0) ;UPDATE PORTRECT.BOTTOM MOVE.L (SP)+,(SP) ;STRIP 4 BYTES RTS ;AND RETURN MovePortTo PROC EXPORT EXPORT SetOrigin,ClipRect IMPORT OffsetRgn,RectRgn IMPORT PortToMap ;---------------------------------------------------------- ; ; PROCEDURE MovePortTo(leftGlobal,topGlobal: INTEGER); ; { move portRect to a different part of the bitmap } ; MOVE.L GRAFGLOBALS(A5),A0 ;POINT TO QUICKDRAW GLOBALS MOVE.L THEPORT(A0),A0 ;GET CURRENT GRAFPORT MOVE PORTRECT+LEFT(A0),D0 ;GET PORTRECT.LEFT MOVE PORTRECT+TOP(A0),D1 ;GET PORTRECT.TOP _PORTTOMAP ;GET BITMAP/PIXMAP IN AO SUB BOUNDS+LEFT(A0),D0 ;CONVERT TO GLOBAL SUB 6(SP),D0 ;SUB LEFTGLOBAL FOR DH SUB BOUNDS+TOP(A0),D1 ;CONVERT TO GLOBAL SUB 4(SP),D1 ;SUB TOPGLOBAL FOR DV MOVE.L (SP)+,(SP) ;STRIP 4 BYTES OFSPORT ADD #BOUNDS,A0 ;POINT TO BOUNDS OFSRECT ADD D1,(A0)+ ;OFFSET TOP ADD D0,(A0)+ ;OFFSET LEFT ADD D1,(A0)+ ;OFFSET BOTTOM ADD D0,(A0)+ ;OFFSET RIGHT RTS ;AND RETURN ;---------------------------------------------------------- ; ; PROCEDURE SetOrigin(h,v: INTEGER); ; { re-define the local coords by adjusting portBits.bounds, } ; { portRect, and visRgn } ; SetOrigin MOVE.L GRAFGLOBALS(A5),A0 ;POINT TO QUICKDRAW GLOBALS MOVE.L THEPORT(A0),A0 ;GET CURRENT GRAFPORT MOVE.L 4(SP),D0 ;GET V AND H BOTH CMP.L PORTRECT+TOPLEFT(A0),D0 ;SAME AS ALREADY IN THEPORT ? BEQ.S DONE ;YES, QUIT MOVE 6(SP),D0 ;GET H SUB PORTRECT+LEFT(A0),D0 ;DH:=H-PORTRECT.LEFT MOVE 4(SP),D1 ;GET V SUB PORTRECT+TOP(A0),D1 ;DV:=V-PORTRECT.TOP MOVE.L VISRGN(A0),-(SP) ;PUSH FOR OFFSETRGN MOVE D0,-(SP) ;PUSH FOR OFFSETRGN MOVE D1,-(SP) ;PUSH FOR OFFSETRGN PEA PORTRECT(A0) ;PUSH FOR OFSRECT _PORTTOMAP ;GET BITMAP/PIXMAP IN AO BSR.S OFSPORT ;OFFSET PORTBITS/PIX.BOUNDS MOVE.L (SP)+,A0 ;POINT A0 AT PORTRECT BSR.S OFSRECT ;OFFSET PORTRECT _OFSETRGN ;OFFSET THE VISRGN DONE MOVE.L (SP)+,(SP) ;STRIP 4 BYTES RTS ;AND RETURN ;---------------------------------------------------------- ; ; PROCEDURE ClipRect(r: Rect); ; { Make the current grafport's clipRgn match a given rectangle } ; ClipRect MOVE.L GRAFGLOBALS(A5),A0 ;POINT TO QUICKDRAW GLOBALS MOVE.L THEPORT(A0),A0 ;GET CURRENT GRAFPORT MOVE.L CLIPRGN(A0),-(SP) ;PUSH CLIPRGN MOVE.L 8(SP),-(SP) ;PUCH ADDR OF RECT _RECTRGN BRA.S DONE ;AND RETURN SetClip PROC EXPORT EXPORT GetClip IMPORT CopyRgn ;---------------------------------------------------------- ; ; PROCEDURE SetClip(rgn: RgnHandle); ; ; copy rgn into theport^.clipRgn ; MOVE.L (SP)+,A0 ;POP RETURN ADDR MOVE.L GRAFGLOBALS(A5),A1 ;POINT TO QUICKDRAW GLOBALS MOVE.L THEPORT(A1),A1 ;GET CURRENT GRAFPORT MOVE.L CLIPRGN(A1),-(SP) ;PUSH THEPORT^.CLIPRGN BRA.S SHARE ;SHARE AND RETURN ;---------------------------------------------------------- ; ; PROCEDURE GetClip(rgn: RgnHandle); ; ; copy from theport^.clipRgn into rgn. ; GetClip MOVE.L (SP)+,A0 ;POP RETURN ADDR MOVE.L (SP)+,D0 ;POP RGN HANDLE MOVE.L GRAFGLOBALS(A5),A1 ;POINT TO QUICKDRAW GLOBALS MOVE.L THEPORT(A1),A1 ;GET CURRENT GRAFPORT MOVE.L CLIPRGN(A1),-(SP) ;PUSH THEPORT^.CLIPRGN MOVE.L D0,-(SP) ;PUSH RGN SHARE MOVE.L A0,-(SP) ;RESTORE RETURN ADDR JMP COPYRGN ;AND GO TO COPYRGN SetPt PROC EXPORT ;------------------------------------------------------------- ; ; PROCEDURE SetPt(VAR pt: Point; h,v: INTEGER); ; MOVE.L (SP)+,A0 ;POP RETURN ADDR MOVE.L (SP)+,D0 ;POP H,V MOVE.L (SP)+,A1 ;POP VAR ADDR OF PT MOVE.L D0,(A1) ;STORE H,V INTO PT JMP (A0) ;RETURN EqualPt FUNC EXPORT ;---------------------------------------------------------- ; ; FUNCTION EqualPt(pt1,pt2: Point): BOOLEAN; ; ; CLOBBERS D0,A0. ; MOVE.L (SP)+,A0 ;POP RETURN ADDR MOVE.L (SP)+,D0 ;pop point1 CMP.L (SP)+,D0 ;is point2 = point1 ? SEQ (SP) ;IF YES, SET TO TRUE NEG.B (SP) ;CONVERT -1 TO 1 JMP (A0) ;RETURN InsPortList PROC EXPORT ;---------------------------------------------------------- ; ; PROCEDURE InsPortList(grafptr); ; ; Add the specified grafPtr to the portList ; CLR.L -(SP) ;room for long result MOVE.L portList,-(SP) ;pass the portList MOVEQ #2,D0 ;insert after length MOVE.L D0,-(SP) CLR.L -(SP) ;PTR1 = NIL CLR.L -(SP) ;LEN1 = 0 PEA 24(SP) ;PTR2 = GrafPtr MOVEQ #4,D0 ;LEN2 = 4 bytes MOVE.L D0,-(SP) _Munger MOVE.L (SP)+,D0 ;strip result MOVE.L portList,A0 ;get portList MOVE.L (A0),A0 ;point to it ADD #1,(A0) ;bump the count MOVE.L (SP)+,(SP) ;strip param RTS ;and return DelPortList PROC EXPORT ;---------------------------------------------------------- ; ; PROCEDURE DelPortList(grafPtr); ; ; Delete the specified grafPtr from the portList ; MOVE.L portList,A0 ;get the portList MOVE.L (A0),A0 ;point to it TST (A0) ;any elements? BEQ.S DONE ;=> no ; SUBQ #1,(A0) ;else decrement count ; ; Find the port and delete it from the list. NOTE: The item is assumed to be in the list. ; ; a0 points to the beginning of the list ; move.w (a0)+,d0 ;get length >= 1 subq #1,d0 ;get length >= 0 move.l 4(sp),d1 ;grafPtr to match @loop cmp.l (a0)+,d1 dbeq.w d0,@loop ;fall through if found ; ; found it: delete the item and shrink the handle by 4 bytes ; ; a0 points 4 bytes past the item to delete ; bne.s Done ;port was not found bra.s @MoveLoopEntry ;yes, move the others up @moveLoop move.l (a0),-4(a0) ;move the next item over this one addq.l #4,a0 @MoveLoopEntry dbra.w d0,@moveLoop @DoSetHandleSize move.l portList,a0 ;handle to portList move.l (a0),a1 ;point to it subq #1,(a1) ;decrement count to remove 1 item moveq #0,d0 move.w (a1),d0 ;get size lsl.w #2,d0 ;*4 addq.w #2,d0 _SetHandleSize ;set the new size ; ;size word in portlist was decremented above ; DONE MOVE.L (SP)+,(SP) ;strip param RTS ;and return ENDPROC ; end of file grafasm.a