Assembly Language Help (alang.hlp) (
Table of Contents;
Topic list)
Important Notice
The pages on this site contain documentation for very old MS-DOS software,
purely for historical purposes.
If you're looking for up-to-date documentation, particularly for programming,
you should not rely on the information found here, as it will be woefully
out of date.
WinOpen
◄Map► ◄Up► ◄Contents► ◄Index► ◄Back►
────────────────────────────────────────────────────────────────────────────
;* WinOpen - Saves portion of screen to allocated memory, then opens a window
;* with specified fill attribute. See also the WinClose procedure.
;*
;* Shows: DOS Function - 48h (Allocate Memory Block)
;* Instructions - movsw stosw rep
;*
;* Uses: vconfig - Video configuration structure (initialized
;* by calling the GetVidConfig procedure)
;*
;* Params: Row1 - Row at top of window
;* Col1 - Column at left edge of window
;* Row2 - Row at bottom of window
;* Col2 - Column at right edge of window
;* Attr - Fill attribute for window
;*
;* Return: Short integer with segment address of allocated buffer, or
;* 0 if unable to allocate memory
WinOpen PROC USES ds di si,
Row1:WORD, Col1:WORD, Row2:WORD, Col2:WORD, Attr:WORD
GetVidOffset Row1, Col1 ; Get offset in video segment
mov si, ax ; SI = video offset for window
mov bx, Row2
sub bx, Row1
inc bx ; BX = number of window rows
mov cx, Col2
sub cx, Col1
inc cx ; CX = number of columns
mov ax, cx ; Compute number of video
mul bl ; cells in window
add ax, 3 ; Plus 3 additional entries
shr ax, 1 ; Shift right 3 times to
shr ax, 1 ; multiply by 2 bytes/cell,
shr ax, 1 ; divide by 16 bytes/para
inc ax ; Add a paragraph
push bx ; Save number of rows
mov bx, ax ; BX = number of paragraphs
mov ah, 48h ; Request DOS Function 48h
int 21h ; Allocate Memory Block
pop bx
.IF carry? ; If unsuccessful:
sub ax, ax ; Return null pointer
.ELSE
mov es, ax ; Point ES:DI to allocated
sub di, di ; buffer
mov ax, si
stosw ; Copy video offset to buffer
mov ax, bx
stosw ; Number of rows to buffer
mov ax, cx
stosw ; Number of cols to buffer
mov ax, 160 ; Number of video cells/row
mov ds, vconfig.sgmnt ; DS = video segment
.REPEAT
push si ; Save ptr to start of line
push cx ; and number of columns
; For CGA adapters, WinOpen avoids screen "snow" by disabling the video prior
; to block memory moves, then reenabling it. Although this technique can
; result in brief flickering, it demonstrates the fastest way to access a
; block in the CGA video buffer without causing display snow. See also the
; StrWrite procedure for another solution to the problem of CGA snow.
.IF vconfig.adapter == CGA ; If not CGA adapter,
INVOKE DisableCga ; disable video
.ENDIF
rep movsw ; Copy one row to buffer
.IF vconfig.adapter == CGA ; If CGA adapter,
INVOKE EnableCga ; reenable CGA video
.ENDIF
pop cx ; Recover number of columns
pop si ; and start of line
add si, ax ; Point to start of next line
dec bx ; Decrement row counter
.UNTIL zero? ; Until no rows remain
; Screen contents (including display attributes) are now copied to buffer.
; Next open window, overwriting the screen portion just saved.
mov ax, 0600h ; Scroll service
mov bh, BYTE PTR Attr ; Fill attribute
mov cx, Col1 ; CX = row/col for upper left
mov ch, BYTE PTR Row1
mov dx, Col2 ; DX = row/col for lower right
mov dh, BYTE PTR Row2
int 10h ; Blank window area on screen
mov ax, es ; Return address of allocated
.ENDIF ; segment
ret
WinOpen ENDP
-♦-