;=============================================
; EDNUM version 3.001e
; programmation commande numerique Num 750/760F
; Copyright (S) 1997-2010
; programmeur du logiciel A.Ara
; 64150 Mourenx ville France.
; Licence d'utilisation accord dans un but démonstratif
; la vente du logiciel et interdite.
; Numero de serie 00-331-7431-A1133071e
;=============================================
;=========== FICHIER DE EDNUM ================
; Fichier WIN_BOX.ASM
; Fichier assembleur utilise par l'unit Box13.pas
;=============================================
TITLE WIN_BOX
LOCALS @@
;=====================================
; Structure de donnees pour les coordonnees
;=====================================
X EQU (BYTE PTR 0)
Y EQU (BYTE PTR 1)
;=====================================
; Equivalences de l'espace de travail BIOS
;=====================================
CrtMode EQU (BYTE PTR 49H)
CrtWidth EQU (BYTE PTR 4AH)
DATA SEGMENT WORD PUBLIC
;===========================
; Donnees externes de l'unite Crt
;===========================
EXTRN CheckSnow:BYTE,WindMin:WORD,WindMax:WORD,TextAttr:BYTE
EXTRN GetMaxX:BYTE,GetMaxY:BYTE
DATA ENDS
CODE SEGMENT BYTE PUBLIC
ASSUME CS:CODE,DS:DATA
;=====================================
; PROCEDURE Writexy(X, Y: Byte; S: String);
;=====================================
PUBLIC Writexy
Writexy:
PUSH BP
MOV BP,SP
LES BX,[BP+6] ;charge le pointeur de la chaine S
MOV CL,ES:[BX] ;charge dans CL la longeur de la chaine
MOV DL,[BP+12] ;charche X
MOV DH,[BP+10] ;charche Y
MOV SI,OFFSET CS:CrtWriteStr
CALL CrtWrite
POP BP
RETF 8
;==================================
; PROCEDURE Putxy(X, Y: Byte; S: String);
;==================================
PUBLIC Putxy
Putxy:
PUSH BP
MOV BP,SP
LES BX,[BP+6] ;charge le pointeur de la chaine S
MOV CL,ES:[BX] ;charge dans CL la longeur de la chaine
MOV DL,[BP+12] ;charche X
MOV DH,[BP+10] ;charche Y
MOV SI,OFFSET CS:CrtWriteStr
CALL CrtEcran
POP BP
RETF 8
;==================================
; PROCEDURE WriteCn(Y: Byte; S: String);
;==================================
PUBLIC WriteCn
WriteCn:
PUSH BP
MOV BP,SP
LES BX,[BP+6] ;charge le pointeur de la chaine S
MOV CL,ES:[BX] ;charge dans CL la longeur de la chaine
MOV AL,windmax.X ;Charge la cordone x max d'ecran
INC AL
MOV AH,WindMin.X
INC AH
SUB AL,AH
INC AL
XOR AH,AH
SUB AL,CL ;soustrait la longeur de la chaine
JC Resul0
MOV DL,2 ;charge 2 pour diviseur
Div DL ;divise AL/2
INC AL
MOV DL,AL ;charche X
XOR AX,AX ;remet AX ? 0
MOV DH,[BP+10] ;charche Y
MOV SI,OFFSET CS:CrtWriteStr
CALL CrtWrite
Resul0: POP BP
RETF 6
;==============================================
; PROCEDURE WriteChar(X, Y, Count: Byte; Ch: Char);
;==============================================
PUBLIC WriteChar
WriteChar:
PUSH BP
MOV BP,SP
MOV CL,[BP+8]
MOV DL,[BP+12] ;X
MOV DH,[BP+10] ;y
MOV SI,OFFSET CS:CrtWriteChar
CALL CrtWrite
POP BP
RETF 8
;========================================
; PROCEDURE BoxFill(x1,y1,x2,y2:Byte; Ch: Char);
; BP+14,12,10 8] [BP+6]
;========================================
PUBLIC BOXFill
BOXFill:
MOV SI,OFFSET CS:CrtWriteChar
JMP SHORT CommonFill
;=========================================
; PROCEDURE ReadBuf(x1,y1,x2,y2:Byte; var Buf);
; BP+16,14,12,10] [BP+6]
;=========================================
PUBLIC ReadBuf
ReadBuf:
MOV SI,OFFSET CS:CrtReadWin
JMP SHORT CommonWin
; PROCEDURE WriteBuf(x1,y1,x2,y2:Byte; var Buf);
; BP+16,14,12,10] [BP+6]
PUBLIC WriteBuf
WriteBuf:
MOV SI,OFFSET CS:CrtWriteWin
JMP SHORT CommonWin
;====================================
; Routine commune pour ReadWin/WriteWin
;====================================
CommonWin:
PUSH BP
MOV BP,SP
MOV AL,[BP+12] ;X2
MOV AH,[BP+10] ;Y2
MOV CL,[BP+16] ;X1
MOV CH,[BP+14] ;Y1
CALL ControlBox
CMP AL,0
JE FinBuf
XOR AL,AL
XOR CX,CX
MOV DL,[BP+16] ;X1
DEC DL
MOV DH,[BP+14] ;Y1
DEC DH
MOV CL,[BP+12] ;X2
DEC CL
SUB CL,DL ;CL = X2-X1
INC CX
@@1: PUSH CX
PUSH DX
PUSH SI
CALL CrtBlock
POP SI
POP DX
POP CX
Mov AH,[BP+10] ;Y2
Dec AH
INC DH
CMP DH,AH ;Y1 <= Y2
JBE @@1
Finbuf: POP BP
RETF 12
;============================
; Block Apele par FillBox
;============================
CommonFill:
PUSH BP
MOV BP,SP
MOV AL,[BP+10] ;X2
MOV AH,[BP+8] ;Y2
MOV CL,[BP+14] ;X1
MOV CH,[BP+12] ;Y1
CALL ControlBox
CMP AL,0
JE FinFil
XOR AL,AL
XOR CX,CX
MOV DL,[BP+14] ;Charge X1
DEC DL
MOV DH,[BP+12] ;Charge Y1
DEC DH
MOV CL,[BP+10] ;Charge X2
DEC CL
SUB CL,DL
INC CX
@@1: PUSH CX
PUSH DX
PUSH SI
CALL CrtBlock
POP SI
POP DX
POP CX
Mov AH,[BP+8] ;Charge Y2
Dec AH
INC DH
CMP DH,AH
JBE @@1
FinFil: POP BP
RETF 10
;==============================================
; Cordones: AL = X2 AH = Y2
; CL = X1 CH = Y1
; Returne: AL = 1 si cordones son bonnes sino AL = 0
;==============================================
ControlBox:
CMP AL,GetMaxX ;80d
JG Exit
CMP AH,GetMaxY ;25d ou 50d
JG Exit
CMP CL,1
JL Exit
CMP CH,1
JL Exit
CMP CL,AL
JG Exit
CMP CH,AH
JG Exit
XOR CX,CX
XOR AH,AH
MOV AL,1
Ret
Exit: XOR CX,CX
XOR AX,AX
Ret
;===========================
; Envoie chaine vers l'ecran
;===========================
CrtWriteStr:
PUSH DS
MOV AH,TextAttr
LDS SI,[BP+6]
INC SI
JC @@4
@@1: LODSB
MOV BX,AX
@@2: IN AL,DX
TEST AL,1
JNE @@2
CLI
@@3: IN AL,DX
TEST AL,1
JE @@3
MOV AX,BX
STOSW
STI
LOOP @@1
POP DS
RET
@@4: LODSB
STOSW
LOOP @@4
POP DS
RET
;===============================
; Ecriture de caracteres vers l'ecran
;===============================
CrtWriteChar:
MOV AL,[BP+6]
MOV AH,TextAttr
JC @@4
MOV BX,AX
@@1: IN AL,DX
TEST AL,1
JNE @@1
CLI
@@2: IN AL,DX
TEST AL,1
JE @@2
MOV AX,BX
STOSW
STI
LOOP @@1
RET
@@4: REP STOSW
RET
;=====================================
; Lecture de l'ecran vers le tampon fenetre
;=====================================
CrtReadWin:
PUSH DS
PUSH ES
POP DS
MOV SI,DI
LES DI,[BP+6] ;Charge dans DI le pointeur
CALL CrtCopyWin
MOV [BP+6],DI
POP DS
RET
;=====================================
; Recopie du tampon de fenetre vers l'ecran
;=====================================
CrtWriteWin:
PUSH DS
LDS SI,[BP+6]
CALL CrtCopyWin
MOV [BP+6],SI
POP DS
RET
;===============================
; Routine de copie de tampon fenetre
;===============================
CrtCopyWin:
JC @@4
@@1: LODSW ;charge dans AX bouble mot
MOV BX,AX
@@2: IN AL,DX
TEST AL,1
JNE @@2
CLI
@@3: IN AL,DX
TEST AL,1
JE @@3
MOV AX,BX
STOSW
STI
LOOP @@1
RET
@@4: REP MOVSW
RET
;========================================
; Realise operation ecran rapor a la fenetre active
; In CL = Longueur tampon
; SI = Pointeur sur procedure Write
; BP = Pointeur sur cadre de pile
; DL = cordone X
; DH = cordone Y
;========================================
CrtWrite:
DEC DL
ADD DL,WindMin.X
JC CrtExit
CMP DL,WindMax.X
JA CrtExit
DEC DH
ADD DH,WindMin.Y
JC CrtExit
CMP DH,WindMax.Y
JA CrtExit
XOR CH,CH
JCXZ CrtExit
MOV AL,WindMax.X
SUB AL,DL
INC AL
CMP CL,AL
JB CrtBlock
MOV CL,AL
;==============================
; Realise l'operation ecran
; In CL = Longueur tampon
; DX = Coordonnees ecran
; SI = Pointeur sur procedure
;=============================
CrtBlock:
MOV AX,40H
MOV ES,AX
MOV AL,DH
MUL ES:CrtWidth
XOR DH,DH
ADD AX,DX
SHL AX,1
MOV DI,AX
MOV AX,0B800H
CMP ES:CrtMode,7
JNE @@1
MOV AH,0B0H
@@1: MOV ES,AX
MOV DX,03DAH
CLD
CMP CheckSnow,1
JMP SI
; Sortie des routines ecran
CrtExit:
RET
;============================================
; Realise operation ecran rapor a la fenetre 80x25
; In CL = Longueur tampon
; SI = Pointeur sur procedure Write
; BP = Pointeur sur cadre de pile
; DL = cordone X DH = cordone Y
;=============================================
CrtEcran:
CMP DL,1 ; cordone X
JB CrtExit ; saut si inferieur a 1
CMP DH,1 ; cordone Y
JB CrtExit ; saut si inferieur a 1
CMP DL,80
JA CrtExit ; saut si superieur a 80
Dec DL ; DL contien X
DEC DH ; Dh contien Y
CMP DH,GetMaxY
JA CrtExit ; saut si superieur a 25
XOR CH,CH
JCXZ CrtExit
MOV AL,GetMaxX ; charge AL 80
SUB AL,DL ; sustrait , AL = (AL-DL)
INC AL
CMP CL,AL
JB CrtBlock
MOV CL,AL
JMP SHORT CrtBlock
;========================================
; function CrtSize(x1,y1,x2,y2:Byte): Word;
; BP+ 12,10,8, 6
;========================================
PUBLIC CrtSize
CrtSize:
PUSH BP
MOV BP,SP
PUSH BX
MOV AL,[BP+8]
DEC AL
MOV AH,[BP+6]
DEC AH
MOV BL,[BP+12]
DEC BL
MOV BH,[BP+10]
DEC BH
;AX contien X2,Y2
SUB AX,BX ;BX contien X1,Y1
ADD AX,101H
MUL AH
SHL AX,1
POP BX
POP BP
RETF 8
;================ Debut BoxChar ===================
;PROCEDURE Rectangle(X1, Y1, X2, Y2: Byte; Cadre:Cadreforme);
PUBLIC Rectangle
Rectangle:
PUSH BP
MOV BP,SP
PUSH DI
PUSH SI
MOV AL,[BP+10] ;y2
MOV AH,[BP+14] ;y1
CMP AL,AH
JNA @@3 ;si Al<=AH / y2 <= Y1 fin
DEC AL ;initialise cordones Ecran Max = 0,0 et 79,24
DEC AH
MOV [BP+10],AL ;ecri les cordonees su la pile decrementes
MOV [BP+14],AH
MOV AL,[BP+12] ;cordonee X2
MOV AH,[BP+16] ;cordonee X1
CMP AL,AH ;si AL<=AH / X2 <= X1 fin
JNA @@3
DEC AL
DEC AH
MOV [BP+12],AL
MOV [BP+16],AH
LES DI,[BP+6] ;forme de cadre simple ou double
Call BlockRectangle1
@@3: POP SI
POP DI
POP BP
RETF 12
BlockRectangle1: ;block depandant de procedure Rectangle
MOV DL,[BP+16] ;X1 Affiche angle1 haut Gauche
MOV DH,[BP+14] ;y1
XOR CX,CX
MOV CL,01
MOV AL,ES:[DI+0]
Call BlockWrite1
MOV DL,[BP+16] ;X1 Trace ligne horizontal Haut
MOV DH,[BP+14] ;y1
INC DL
XOR CX,CX
MOV CL,[BP+12] ;nonbre de fois ? afficher
SUB CL,[BP+16] ;CL = X2-X1
MOV AL,ES:[DI+1]
Call BlockWrite1
MOV DL,[BP+12] ;X2 Affiche angle2 haut droite
MOV DH,[BP+14] ;y1
XOR CX,CX
MOV CL,1
MOV AL,ES:[DI+2]
Call BlockWrite1
MOV DL,[BP+16] ;X1 Affiche angle3 bas gauche
MOV DH,[BP+10] ;y2
XOR CX,CX
MOV CL,01
MOV AL,ES:[DI+3]
Call BlockWrite1
MOV DL,[BP+16] ;X1 Trace ligne horizontal Bas
MOV DH,[BP+10] ;y2
INC DL
XOR CX,CX
MOV CL,[BP+12] ;nonbre de fois ? afficher
SUB CL,[BP+16] ;CL = X2-X1
MOV AL,ES:[DI+1]
Call BlockWrite1
MOV DL,[BP+12] ;X2 Affiche angle4 bas droite
MOV DH,[BP+10] ;y2
XOR CX,CX
MOV CL,1
MOV AL,ES:[DI+4]
Call BlockWrite1
MOV DL,[BP+16] ;X1 Traze ligne Hauteur Gauche
MOV DH,[BP+14] ;y1
INC DH
XOR CX,CX
MOV CL,1
MOV AL,ES:[DI+5]
Call BlockWriteHaut
MOV DL,[BP+12] ;X2 Trace ligne Hauteur Droite
MOV DH,[BP+14] ;y1
INC DH
XOR CX,CX
MOV CL,1
MOV AL,ES:[DI+5]
Call BlockWriteHaut
MOV AH,2 ;positione curseur interieur de cadre
MOV BH,0
MOV DL,[BP+16] ;X1
MOV DH,[BP+14] ;y1
INC DL
INC DH
INT 10h
RET
;====================================
; Entrees: DL cordonee " X "
; DH cordonee " Y "
; CX nombre de caracteres ? ecrire
; AL Caractere ASCII
;====================================
BlockWrite1: ;block depandant de procedure BoxChar
MOV AH,2 ;fonction positione curseur sur l'ecran
MOV BH,0
INT 10h
MOV AH,9 ;fonction ecrire sur l'ecran
MOV BH,0
MOV BL,TextAttr
INT 10h
RET
;======================================
; Entrees: DH cordonee: " Y1"
; DL cordonee: " X1 ou X2 "
; AL caractere ASCII
; CX nombre de caracteres ? ecrire
; Sortie: Cant Y1 >= Y2
;======================================
BlockWriteHaut: ;block depandant procedure BoxChar
@@2: CMP DH,[BP+10] ;controle si y1 < que Y2
JGE @@1
MOV AH,2 ;foction positione curseur
MOV BH,0
INT 10h
MOV AH,9 ;foction ecrire ecran
MOV BH,0 ;page ecran ? ecrire
MOV BL,TextAttr ;atribut de caractere
INT 10h
INC DH ;incremente cordonee Y1
JMP @@2 ;saut
@@1: RET
;==== End Rectangle ====
;================================================
; Function GetkeyByte:Byte revoit le nø de la touche Tape
;================================================
PUBLIC GetKeyByte
GetKeyByte:
MOV AH,1
Int 16h
Jz @@2 ;PasCaractere Disponibles
MOV AH,0
Int 16h
CMP AL,0
Je @@1 ;Si AL =0 Saut
RetF ;Sino Resulta dans AL
@@1: MOV AL,AH
RetF
@@2: MOV AX,0000H
RetF
;==========================
;Function GetPrn:Boolean
;==========================
PUBLIC GetPrn
GetPrn:
MOV AH,2
MOV DX,0
Int 17h
CMP AH,90h
JNE @@1
MOV AL,01
RETF
@@1: MOV AL,00
RETF
;========================
;Function TestPrn:Integer
;========================
PUBLIC TestPrn
TestPrn:
MOV AH,2
MOV DX,0
Int 17h
MOV AL,AH
RETF
;===========================================
;Procedure ClearBufKey vide le buffer du clavier
;===========================================
PUBLIC ClearBufKey
ClearBufKey:
MOV AH,1 ;fonction: encore caracteres dans buffer ?
Int 16h ;appeler interruction clavier BIOS
JE @@1 ;plus de daractere dans le buffer -->Fin
XOR AH,AH ;fonction retire caractere du buffer
Int 16h
JMP ClearBufKey ;tester si encore des caracteres
@@1: XOR AX,AX ;tout est en ordre
RETF ;retour au programme d'appel
;================================
; Function GetTexte:Byte;
;================================
PUBLIC GetTexte
GetTexte:
XOR AX,AX
MOV AL,[TextAttr]
SHL AL,1
SHL AL,1
SHL AL,1
SHL AL,1
XOR AH,AH
SHR AL,1
SHR AL,1
SHR AL,1
SHR AL,1
RETF
;==========================
;Function GetFond:Byte;
;==========================
PUBLIC GetFond
GetFond:
XOR AX,AX
MOV AL,[TextAttr]
SHL AL,1
XOR AH,AH
SHR AL,1
SHR AL,1
SHR AL,1
SHR AL,1
SHR AL,1
RETF
;========================
;Function SegEcran:Word;
;========================
PUBLIC SegEcran
SegEcran:
MOV AH,0FH ;Focntion lire parametres video du BIOS
INT 10H
CMP AL,7 ;est une carte mono
JNE @@1 ;nom ----> @@1
MOV AX,0B000h ;carte Mono
RET
@@1: MOV AX,0B800h ;carte Couleur
RETF
;===============================
;Function OfsEcran(X,Y:Byte):Word;
;===============================
PUBLIC OfsEcran
OfsEcran:
PUSH BP
MOV BP,SP
PUSH ES
MOV DL,[BP+8] ;cordone "X"
MOV DH,[BP+6] ;cordone "Y"
DEC DL
DEC DH
MOV AX,40H ;Segment variables video du BIOS
MOV ES,AX ;ES Segment variables Bios
MOV AL,DH ;AL cordonnee ligne =(Y-1)
MUL ES:Byte Ptr [4AH] ;ES:4Ah = nonbre de colones par ligne BIOS
XOR DH,DH ;resutat de multiplication dans AX
ADD AX,DX ;addition la cordonnee (X-1)
SHL AX,1 ;decalage ? gauche de 1 bit = AX * 2
POP ES
POP BP
RETF 4
;========================================
;Procedure HigthBox(x1,y1,x2,y2:Byte;Color:Byte);
;========================================
PUBLIC HighBox
HighBox:
PUSH BP
MOV BP,SP
MOV CL,[BP+14] ;cordone X1
MOV CH,[BP+12] ;cordone Y1
MOV AL,[BP+10] ;cordonee X2
MOV AH,[BP+8] ;cordonee Y2
CALL ControlBox
MOV DL,[BP+14] ;cordonee X1
MOV DH,[BP+12] ;Cordonee Y1
DEC DL
DEC DH
MOV AL,50H ;calcule l'adresse de x1,y1
MUL DH
XOR DH,DH
ADD AX,DX
Shl AX,1
INC AX ; AX + 1 pour l'attribut du caractere
MOV DI,AX ;Adresse de X1,Y1
MOV BX,AX ;Adresse de reserve
MOV AX,0B800H ;ecran couleur
PUSH AX
POP ES
MOV DL,[BP+12] ;cordonee Y1
MOV DH,[BP+8] ;cordonee Y2
@@3: CMP DL,DH ;texte Y1 et Y2
JNLE @@2 ;fin si y1 > Y2
MOV CL,[BP+10] ;cordonee X2
SUB CL,[BP+14] ;cordonee X1
INC CL
XOR CH,CH ;CL = longeur de la ligne
JCXZ @@2 ;Fin si CX = zero
MOV AL,17d
MOV AH,[BP+6] ;Code couleur pour l'inversement
MUL AH
MOV AH,AL
@@1: MOV AL,ES:[DI]
XOR AL,AH ;77H ;change le attribut du l'octet
MOV ES:[DI],AL
INC DI ;Incremente de deux pour trouver l'attribut suivant
INC DI
LOOP @@1
ADD BX,00A0H ;Adresse de reserve + 160d change de ligne
MOV DI,BX
INC DL ;y1 := y1+1
JMP @@3 ;Boucle
@@2: POP BP ;Fin
RETF 10
;=======================================
;Procedure BoxColor(x1,y1,x2,y2:Byte;Color:Byte);
;=======================================
PUBLIC BoxColor
BoxColor:
PUSH BP
MOV BP,SP
MOV DL,[BP+14] ;cordonee X1
MOV DH,[BP+12] ;Cordonee Y1
DEC DL
DEC DH
MOV AL,50H ;calcule l'adresse de x1,y1
MUL DH
XOR DH,DH
ADD AX,DX
Shl AX,1
INC AX ; AX + 1 pour l'attribut du caractere
MOV DI,AX ;Adresse de X1,Y1
MOV BX,AX ;Adresse de reserve
MOV AX,0B800H ;ecran couleur
PUSH AX
POP ES
MOV DL,[BP+12] ;cordonee Y1
MOV DH,[BP+8] ;cordonee Y2
@@3: CMP DL,DH ;texte Y1 et Y2
JNLE @@2 ;fin si y1 > Y2
MOV CL,[BP+10] ;cordonee X2
SUB CL,[BP+14] ;cordonee X1
INC CL
XOR CH,CH ;CL = longeur de la ligne
JCXZ @@2 ;Fin si CX = zero
MOV AL,17d
MOV AH,[BP+6] ;Code couleur
;MUL AH
;MOV AH,AL
@@1: MOV AL,ES:[DI]
Mov AL,AH ;77H ;change le attribut du l'octet
MOV ES:[DI],AL
INC DI ;Incremente de deux pour trouver l'attribut suivant
INC DI
LOOP @@1
ADD BX,00A0H ;Adresse de reserve + 160d change de ligne
MOV DI,BX
INC DL ;y1 := y1+1
JMP @@3 ;Boucle
@@2: POP BP ;Fin
RETF 10
CODE ENDS
END
;============================
; End de Fichier WIN_BOX.ASM
;============================