📄 grview.asm
字号:
TITLE GRVIEW - Graphics VIEW Support
;***
; GRVIEW - Graphics VIEW Support
;
; Copyright <C> 1986 - 1988, Microsoft Corporation
;
;Purpose:
;
; BASIC Syntax mapping to included runtime entry points:
;
; - VIEW Statement - Generates 1 call if no parameters, or 3 calls:
;
; VIEW [[SCREEN][(x1,y1)-(x2,y2) [,[color] [,[boundary]]]] ]
;
; Possibilities:
;
; VIEW [SCREEN] (x1,y1)-(x2,y2) [,[color] [,[boundary]]]
; |
; B$VIEW
;
;
; VIEW
; |
; B$VEW0
;
;
; - VIEW PRINT Statement
;
;
; VIEW PRINT [top screen line TO bottom screen line]
; |
; B$VWPT
;
;******************************************************************************
INCLUDE switch.inc
INCLUDE rmacros.inc ; Runtime Macro Defintions
USESEG _DATA
USESEG _BSS
USESEG GR_TEXT
INCLUDE seg.inc ; segment definitions
INCLUDE const.inc ; b$IOFLAG field definitions
sBegin _DATA
externB b$LINCNT ; support VIEW PRINT statement
externB b$WDOTOP
externB b$WDOBOT
externB b$IOFLAG ; Misc. IO flags. Defined in GWINI.ASM
sEnd _DATA
sBegin _BSS
;
;****************************************************************************
; External low-level function vectors
;****************************************************************************
;
externW b$SetAttr
externB b$KEY_SW ;defined in GWDATA.ASM
externW B$VXSIZ ;defined in GRINIT.ASM
externW B$VYSIZ ;defined in GRINIT.ASM
externW B$VXMIN ;defined in GRINIT.ASM
externW B$VYMIN ;defined in GRINIT.ASM
externW B$VXMAX ;defined in GRINIT.ASM
externW B$VYMAX ;defined in GRINIT.ASM
externW B$VXOFF ;defined in GRINIT.ASM
externW B$VYOFF ;defined in GRINIT.ASM
externW B$GXPOS ;defined in GRINIT.ASM
externW B$GYPOS ;defined in GRINIT.ASM
externW B$GRPACX ;defined in GWDATA.ASM
externW B$GRPACY ;defined in GWDATA.ASM
externB B$VIEWSW ;defined in GWDATA.ASM
externB B$VIEWSC ;defined in GWDATA.ASM
sEnd _BSS
assumes CS,GR_TEXT
sBegin GR_TEXT
externNP B$ERR_FC
externNP B$ERR_AFE
externNP B$SCINIT ; initialize screen
SUBTTL VIEW - Define Viewport transformation
; SYNTAX: VIEW [SCREEN] [(vx1,vy1)-(vx2,vy2) [,[fill] [,[border]]]]
; VIEW defines the "viewport" transformation from
; vx1,vy1 (upper left x,y coordinates) to vx2,vy2
; (lower right x,y coordinates). The x and y coordinates
; must be within the physical bounds of the screen and
; define the rectangle within the screen that graphics
; will map into.
; Initially, RUN (or VIEW with no arguments) define the
; entire screen as the viewport. The 'fill' attribute
; allows the user to fill the VIEW area with a color.
; If fill is omitted, the VIEW area is not filled.
; The 'border' attribute allows the user to draw a line
; surrounding the viewport if space for a border is
; available. If border is omitted, no border is drawn.
externNP B$VWMAPC
externNP B$VEWINI
externNP B$VWFILL
externNP B$GRMODE
externNP B$BOXNOF
externNP B$SCNLOC ; update and display user cursor
;***
;ViewCoord1 - Process first coordinate pair for VIEW statement
;
;Purpose:
; Process first coordinate pair for VIEW statement by saving in
; B$VXMIN and B$VYMIN. CALL B$VEWINI to initialize VIEW statement variables.
;Entry:
; BX=first x coordinate = Vx1
; DX=first y coordinate = Vy1
;Exit:
; View variables updated
;Uses:
; Per convention
;Exceptions:
; Control may be transfered to B$ERR_FC
;****
cProc ViewCoord1,<NEAR>
cBegin
PUSH BX ;Save x coord
PUSH DX ;Save y coord
CALL B$VEWINI ;initialize VIEW variables
POP DX ;Restore x coord
POP BX ;Restore y coord
MOV B$VXMIN,BX ;B$VXMIN:=BX=vx1
MOV B$VYMIN,DX ;B$VYMIN:=DX=vy1
cEnd ;Return
;***
;ViewCoord2 - process second coordinate pair for VIEW statement
;
;Purpose:
; Process second coordinate pair for VIEW statement. Compare
; Vx1 and Vx2, storing the largest of the two in B$VXMAX and the smallest
; in B$VXMIN. Compare vy1 and vy2, storing the largest of the two in
; B$VYMAX and the smallest in B$VYMIN. Issue a function call error if
; VX1=VX2 or if VY1=VY2.
;Entry:
; BX=second x coordinate = VX2
; DX=second y coordinate = VY2
;Exit:
; B$VXMIN,B$VYMIN,B$VXMAX,B$VYMAX updated
;Uses:
; Per convention.
;Exceptions:
; Control may be transfered to B$ERR_FC
;****
cProc ViewCoord2,<NEAR>
cBegin
;Make Vx1 .lt. Vx2 and Vy1 .lt. Vy2
;If Vx1=Vx2 or Vy1=Vy2, then error.
MOV AX,B$VYMIN ;AX:=B$VYMIN
CMP AX,DX ;Compare B$VYMIN to VY2
JZ VEWFCE ;Error if Vy1=Vy2
JB VY1LT2 ;Brif Vy1 .lt. Vy2
XCHG AX,DX ; else exchange
VY1LT2:
MOV B$VYMIN,AX ;Store Vy1
MOV B$VYMAX,DX ; and Vy2
CMP B$VYSIZ,DX ;Screen y max cannot be
JB VEWFCE ;less than Vy2
MOV AX,B$VXMIN
CMP AX,BX ;Compare B$VXMIN(=VX1) to Vx2
JZ VEWFCE ;Error if Vx1=Vx2
JB VX1LT2 ;Brif Vx1 .lt. Vx2
XCHG AX,BX ; else exchange
VX1LT2:
MOV B$VXMIN,AX ;Store Vx1
MOV B$VXMAX,BX ; and Vx2
CMP B$VXSIZ,BX ;Screen x max cannot be
JB VEWFCE ;less than Vx2
cEnd
VEWFCE:
JMP B$ERR_FC ;Error
;***
;B$VIEW - Process VIEW statement with parameters
;
;Purpose:
; Set viewport as specified by current values of (B$VXMIN,B$VYMIN) and
; (B$VXMAX,B$VYMAX) which get initialized in ViewCoord1 and ViewCoord2.
; Update B$VXOFF and B$VYOFF if the SCREEN option was not specified.
; If fill was requested, fill the viewport with the desired color
; by calling B$VWFILL. If a border was requested, draw the border
; by calling B$BOXNOF in the LINE statement code in GENG86.
; Update B$VIEWSC and B$VIEWSW to reflect the current active VIEW option.
; B$VIEWSC = 0 means the most recent VIEW statement was not a VIEW SCREEN
; = 1 means the most recent VIEW statement was a VIEW SCREEN
; B$VIEWSW = 0 means the most recent VIEW statement was a VIEW w/ no parms
; = 1 means the most recent VIEW statement was a VIEW with parms
;Entry:
; x1,y1,x2,y2 - I2 coordinate pairs defining new viewport.
; Color - fill color or -1 if default
; Border - border color or -1 if default
; fScreen - screen flag: NZ if VIEW SCREEN option
;Exit:
; Variables updated as noted above
;Uses:
; Per convention.
;Exceptions:
; Control may be transfered to B$ERR_FC
;****
cProc B$VIEW,<PUBLIC,FAR>
parmW X1
parmW Y1
parmW X2
parmW Y2
parmW Color
parmW Border
parmW fScreen
cBegin
CALL B$SCINIT ; init screen if not already done
MOV BX,X1
MOV DX,Y1
cCall ViewCoord1 ;process first coord pair
MOV BX,X2
MOV DX,Y2
cCall ViewCoord2 ;process second coord pair
CALL B$GRMODE ;Legal graphics mode?
JZ VEWFCE ;Function call error if not in graphics mode
MOV BL,1 ;default is VIEW SCREEN active
CMP fScreen,0 ;VIEW SCREEN option specified?
JNZ VEWSCR ;Brif so, don't set offsets
DEC BL ;no VIEW SCREEN
MOV AX,B$VXMIN ;AX:=B$VXMIN
MOV B$VXOFF,AX ;B$VXOFF:=B$VXMIN for VIEW no SCREEN
MOV AX,B$VYMIN ;AX:=B$VYMIN
MOV B$VYOFF,AX ;B$VYOFF:=B$VYMIN for VIEW no SCREEN
VEWSCR:
MOV B$VIEWSC,BL ;Set VIEW SCREEN active
MOV AX,Color ;get color attribute
INC AX ;default fill attribute?
JZ VBRDR ;Yes: don't fill but check border
DEC AX ;recover correct attribute
CALL B$VWFILL ;No: fill viewport with color
VBRDR: ;Check border parameter
MOV AX,Border ;get border color
INC AX ;default border color?
JZ VEWRET ;Yes: don't draw border
DEC AX ;recover real border color
CALL [b$SetAttr] ;set border attr
JB VEWFCE ;ERROR IF ILLEGAL ATTRIBUTE
CALL DrawBorder ;draw border to view region
VEWRET:
MOV B$VIEWSW,1 ;Set Viewport active
CALL B$VWMAPC ;Set up View "C" bounds for PAINT.
; and Graphics cursor to VIEW center
cEnd
;***
;DrawBorder - Draw border for viewport
;
;Purpose:
; Draw viewport border by calling B$BOXNOF in GENG86. B$BOXNOF
; is a routine in the code for the LINE statement which FG_DRAW
; an unfilled box.
;Entry:
; None.
;Exit:
; None.
;Uses:
; Per convention
;Exceptions:
; None.
;****
cProc DrawBorder,<NEAR>
cBegin
MOV AX,B$VXMAX
PUSH AX
INC AX ;Line outside viewport
MOV B$GRPACX,AX
MOV B$GXPOS,AX ;vx2
MOV AX,B$VYMAX
PUSH AX
INC AX ;Line outside viewport
MOV B$GRPACY,AX
MOV B$GYPOS,AX ;vy2
MOV CX,B$VXMIN
PUSH CX
DEC CX ;Line outside viewport
MOV DX,B$VYMIN
PUSH DX
DEC DX ;Line outside viewport
XOR AX,AX
MOV B$VXMIN,AX ;Vx1= 0
MOV B$VYMIN,AX ;Vy1= 0
MOV AX,B$VXSIZ
MOV B$VXMAX,AX ;Vx2= x max
MOV AX,B$VYSIZ
MOV B$VYMAX,AX ;Vy2= Y max
CALL B$BOXNOF ;Draw Viewport Border
POP B$VYMIN ;vy1
POP B$VXMIN ;vx1
POP B$VYMAX ;vy2
POP B$VXMAX ;vx2
cEnd
;***
;B$VEW0 - process VIEW statement with no parameters
;
;Purpose:
; Process a VIEW statement that has no parameters.
; Call B$VEWINI to initialize viewport to the entire screen.
;Entry:
; None.
;Exit:
; None.
;Uses:
; Per Convention.
;Exceptions:
; Control may be transfered to B$ERR_FC
;****
cProc B$VEW0,<PUBLIC,FAR,FORCEFRAME>
cBegin
CALL B$SCINIT ; init screen if not already done
CALL B$GRMODE ;Legal graphics mode?
JZ VWFERR ;Function call error if not in graphics mode
CALL B$VEWINI ;viewport := screen
cEnd
VWFERR:
JMP B$ERR_FC ;Function call error
;***
;B$VWPT - VIEW PRINT statement
;
;Purpose:
; VIEW PRINT statement for setting the boundaries of the text
; window.
;
; SYNTAX:
; VIEW PRINT [<top line> TO <bot line>][,<left col> TO <right col>]
;
; Note that each TO clause which is present must have both numbers
; present.
; "VIEW PRINT" alone will reset the text window to whole screen.
; "VIEW PRINT x TO y" will set top and bottom only.
; "VIEW PRINT ,x TO y" will set left and right only.
; An illegal function call will result
; -if <top line> is .GT. <bot line>,
; -if <left col> is .GT. <right col>,
; -if any parameter is larger than current screen dimensions,
;
; ------------------------ NOTE -----------------------------
; Since the screen editor does not yet support the arbitrary
; setting of the right and left margins of the screen window,
; the second TO clause of the VIEW PRINT statement is not yet
; allowed and will make for a syntax error if present.
; -----------------------------------------------------------
;
;Entry:
; TopLine = Top line (default -1)
; BotLine = Bottom line (default -1)
;Exit:
; WDOTOP and WDOBOT
;Uses:
; Per convention.
;Exceptions:
; Control may be transfered to B$ERR_FC
;****
cProc B$VWPT,<PUBLIC,FAR>
parmW TopLine
parmW BotLine
cBegin
TEST b$IOFLAG,RED_OUT ; Is output redirected?
JNZ VWPT_XIT ; brif so -- do nothing.
MOV AH,b$KEY_SW
MOV AL,b$LINCNT
MOV BX,TopLine
MOV DX,BotLine
INC BX ;default?
JZ DEFAULT ;brif so
DEC BX ;top line = 0?
JZ VPFCE ;brif so
JS VPFCE ;or if < 0
CMP BX,DX ;top line > bottom line
JA VPFCE ;brif so .... error
PUSH DX ;save [dx]
ADD DL,AH ;make sure bottom line is not off screen and
CMP DL,AL ;does'nt include function key display line (if ON)
POP DX ;restore [dx]
JA VPFCE ;brif above .... error
JMP SHORT NOTDEF
DEFAULT:
INC BX ; [bx] = 1
XOR DX,DX
MOV DL,AL ;[dl] = line count
SUB DL,AH ;[dl] = line count or line count - 1
NOTDEF:
MOV b$WDOTOP,BL ;set text window top
MOV b$WDOBOT,DL ;set text window bottom
MOV DL,BL ;[dl] = window top , cursor top
MOV DH,1 ;[dh] = window left , cursor left
CALL B$SCNLOC ; update b$CURSOR and display user cursor
VWPT_XIT:
cEnd
VPFCE:
JMP B$ERR_FC ;function call error
externNP B$PCOPYS
;***
;B$PCPY - PCOPY STATEMENT
;
;Entry:
; FromPage - 'FROM' PAGE
; ToPage - 'TO' PAGE
;Exit:
; None.
;Uses:
; Per convention.
;Exceptions:
; B$ERR_AFE,B$ERR_FC
; Illegal Function Call Error in case of any error if PCOPY is supported
; Else Advanced Function Error is issued
;
;****
cProc B$PCPY,<PUBLIC,FAR>
parmW FromPage
parmW ToPage
cBegin
;No range checks are necessary - $PCOPY does it
MOV AX,FromPage ; AX = source page number
MOV CX,ToPage ; AX = destination page number
CALL B$PCOPYS ;Do the move
JNC OKRET ; everything ok so return
; carry is set so something is wrong
JMP B$ERR_FC ; Illegal function call
;(never returns)
OKRET:
cEnd
sEnd GR_TEXT
END
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -