[Back to TEXTWNDW SWAG index] [Back to Main SWAG index] [Original]
{
=======================================
CRT-DEMO (c) AVC Software
Cardware
Souce in Pascal to show how we can
manipulate EGA/VGA register for
obtain some cool effects in text
mode 80*25.
=======================================
The purpose of this program is to show how we can make some cools effect
in text mode by manipulating the EGA/VGA registers.
I have writte almost all procedure in assembler for the quick effect and
for the creation of OBJ file if you want.
Some code cames from severall books.
Sorry for the French comments.
ÉÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍ»
º º°
º AVONTURE CHRISTOPHE º°
º AVC SOFTWARE º°
º BOULEVARD EDMOND MACHTENS 157/53 º°
º B-1080 BRUXELLES º°
º BELGIQUE º°
º º°
ÈÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍͼ°
°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°°
}
{$G+}
Uses Crt;
Var I : Byte;
Ch : Char;
Delai : Byte;
Procedure Wait_Retrace; Assembler;
Asm
Mov Dx, 3dah
@Wait1:
In Al, Dx
Test Al, 8h
Jnz @Wait1
@Wait2:
In Al, Dx
Test Al, 8h
Jnz @Wait2
End;
Procedure Wait_In_Retrace;
Begin
Asm
Mov Dx, 3dah
@Wait2:
In al, dx
Test Al, 8h
Jnz @Wait2
End;
End;
Procedure Deplace_par_Pixel; Assembler;
Asm
{ Je m'adresse au contr“leur d'attributs (Attribute Controller : ATC)
qui s'adresse via le port 3c0h. Je lui envoi la valeur 110011b
qui lui indique que je ne d‚sire pas que le CPU accŠde … la m‚moire
de la palette et que le d‚placement doit se faire au pixel prŠs }
Mov Dx, 3c0h
Mov Al, 110011b
Out Dx, Al
Mov Al, 10100b
Out Dx, Al
End;
Procedure Smooth_Scrolling (Sens : Byte);
{ Sens = 0 => d‚filement vers le bas
1 => D‚filement vers le haut (1 ou tout autre) }
Var Tempo : Word;
Begin
If Sens = 0 then Tempo := 1 Else Tempo := 9;
Repeat
Asm
Mov Al, 8
Mov Dx, 3d4h
Out Dx, Al
Mov Dx, 3d5h
In Al, Dx
Inc Al
And Al, 15
Out Dx, Al
{ Les bits 0 … 4 repr‚sente le Initial Row Adress : indiquent au CRTC
la ligne de d‚clenchement du retour du balayage vertical, normalement
0. Si on augmente ce paramŠtre, le CRTC commence par une ligne situ‚e
plus bas, ce qui d‚place le contenu de l'‚cran vers le haut.
Ce registre fonctionne de la mˆme fa‡on en mode texte qu'en mode
graphique, de sorte que grƒce … lui on peut r‚aliser un d‚filement
continu vertical (qu'on appelle Smooth Scrolling).
Si la ligne de d‚part est ‚gale … 15, cela signifie que je vais traiter
le dernier pixel du caractŠre, et l'apparition de parasites se fera
sentir. Je r‚initalise donc … 0 grƒce … un AND 15. }
End;
Delay (Tempo);
Until KeyPressed;
Ch := ReadKey; If Ch = #0 then Ch := ReadKey;
Asm
xor al, al
mov dx, 3d5h
out dx, al
End;
{ R‚initialisation … sa valeur d'origine pour ‚viter les mauvaises surprises}
End;
Procedure EGA2VGA (OnOff : Byte); Assembler;
{ 0 pour que les caractŠres aient 9 pixels ou 1 pour qu'il en aient 8 }
Asm
Mov Al, 1
Mov Dx, 3c4h
Out Dx, Al
Mov Dx, 3c5h
In Al, Dx
Or Al, OnOff
Out Dx, Al
End;
Procedure Minimize_Char;
Begin
Repeat
Asm
Mov Al, 9
Mov Dx, 3d4h
Out Dx, Al
Mov Dx, 3d5h
In Al, Dx
Inc Al
And Al, 14
Or Al, 1
Out Dx, Al
End;
Delay (100);
Until KeyPressed;
Ch := ReadKey; If Ch = #0 then Ch := ReadKey;
Asm
Mov Dx, 3d5h
Mov Al, 15
Out Dx, Al
End;
End;
Procedure Mazimize_Char;
Begin
Repeat
Delay (100);
Asm
Mov Al, 9
Mov Dx, 3d4h
Out Dx, Al
Mov Dx, 3d5h
In Al, Dx
Inc Al
Or Al, 128
Out Dx, Al
End;
Until KeyPressed;
Ch := ReadKey; If Ch = #0 then Ch := ReadKey;
Asm Mov Al, 15; Out Dx, Al; End;
End;
Procedure Dedouble;
Begin
Port[$3d4] := $09; { Je m'adresse au registre 08h du CRTC }
Port[$3d5] := (Port[$3d5] or 128) ;
{ Positionne … 1 le bit 7 qui divise le rythme d'horloe vertical (clock
rate) par deux, ce qui a pour effet de d‚doubler l'affichage de chaque
ligne. Pr‚vu pour la g‚n‚ration des modes 200 lignes dans une r‚solution
physique de 400 lignes. }
Ch := ReadKey; If Ch = #0 then Ch := ReadKey;
Port[$3d5] := (Port[$3d5] and not 128) ;
{ Remet … 0 le bit 7 }
End;
Procedure Deplacement_Gauche;
{ Cette proc‚dure d‚cale tout l'‚cran vers la gauche pixel par pixel.
Le d‚but de la ligne qui commence … disparaitre fait place au d‚but de la
ligne suivante. Par cons‚quent, la ligne nø 25 (non visible) doit contenir
le mˆme texte que la ligne 24 pour une question d'esth‚tique. }
Var Nbr : Word;
Begin
Nbr := 0;
Repeat
Nbr := (Nbr + 1) mod 80;
Asm
Mov Dx, 3d4h { Je m'adresse au port du CRTC : 3d4h }
Mov Al, 0ch
{ Registre 0ch : Linear Starting Address : d‚finit l'offset …
l'int‚rieur de la m‚moire d'‚cran o— le CRTC commence … lire
les donn‚es graphiques }
Mov Ah, Byte Ptr Nbr + 1
Out Dx, Ax
{ En manipulant cette adresse, on peut provoquer un d‚filement
horizontal en incr‚mentant sans cesse cette valeur de une
position sup‚rieure }
Mov Al, 0dh
Mov Ah, Byte Ptr Nbr
Out Dx, Ax
End;
Delay (Delai);
Until KeyPressed;
Ch := ReadKey; If Ch = #0 then Ch := ReadKey;
End;
Procedure Split (Row, Mouv : Byte); Assembler;
Asm
Mov Bl, Row
Xor Bh, Bh
Shl Bx, 1
Mov Cx, BX
Mov Dx, 3d4h
Mov Al, 07h
Out Dx, Al
Inc Dx
In Al, Dx
And Al, 11101111b
Shr Cx, 4
And Cl, 16
Or Al, Cl
Out Dx, Al
Dec Dx
Mov Al, 09h
Out Dx, Al
Inc Dx
In Al, Dx
And Al, 10111111b
Shr Bl, 3
And Bl, 64
Or Al, Bl
Out Dx, Al
Dec Dx
Mov Al, 18h
Mov Ah, Row
Shl Ah, 1
Out Dx, Ax
Cmp Mouv, 0
Je @Fin
Mov Al, 8
Mov Dx, 3d4h
Out Dx, Al
Mov Dx, 3d5h
In Al, Dx
Inc Al
And Al, 15
Out Dx, Al
@Fin:
End;
Procedure CopyPage (Source, Cible : Byte);
{ Copy le contenu de la page Source dans la page Cible. Permet de sauver
une page avant sa modification et de la restaurer le moment venu}
Type VRam = Array [0..7,0..4095] of byte;
Vptr = ^VRam;
Var RVideo : Vptr;
i : Word;
Begin
RVideo := ptr ($B800,$0000);
Move (RVideo^[Source, 0],RVideo^[Cible, 0], 4096);
End;
Procedure Superpose (fond, active, buffer : byte);
{ Affiche en superposition la page ‚cran active sur la page ‚cran fond.
La page ‚cran buffer servira de zone de stockage temporaire.
Ces deux pages ‚cran doivent ˆtre pr‚par‚es … l'avance }
Begin
CopyPage(Fond, Buffer);
CopyPage(Active, Fond);
CopyPage(Buffer, Active);
{ Change the active page }
Asm
Mov Ah, 05h
Mov Al, Active
Int 10h
End;
Repeat
For I := 200 downto 50 do Begin
Wait_Retrace;
Split(I,I Xor 1);
Wait_Retrace;
Delay (Delai);
If KeyPressed then Delai := 0;
End;
For i := 50 to 200 do Begin
Wait_Retrace;
Split(I,I xor 1);
Wait_Retrace;
Delay (Delai);
If KeyPressed then Delai := 0;
End;
Until KeyPressed;
Ch := ReadKey; If Ch = #0 then Ch := ReadKey;
End;
var tempo, row : byte;
Begin
Delai := 15;
TextAttr:= 19;
For I := 0 to 25 Do
Writeln ('Wow!!! What a cool effect!!! Ha! Ha! Ha! Yes, it''s possible in text mode!!! ');
EGA2VGA(1);
Smooth_Scrolling(0);
Smooth_Scrolling(1);
Dedouble;
Minimize_Char;
Mazimize_Char;
Deplace_par_Pixel;
Deplacement_Gauche;
TextAttr := 45;
For I := 0 to 24 Do
Writeln ('Hello to you, Man. This demo has been coded by AVONTURE Christophe');
SuperPose (0,1,2);
EGA2VGA(0);
{ Pour r‚initialiser correctement les paramŠtres du port 3d4h }
Asm
Mov Ax, 0003h
Int 10h
End;
ClrScr;
Writeln ('');
Writeln ('Cette petite d‚mo n''a aucune pr‚tention si ce n''est celle de prouver');
Writeln ('que le mode commun‚ment appel‚ texte n''est pas aussi idiot que cela.');
Writeln ('');
Writeln ('');
Writeln ('Oui, on peut faire de jolies choses tout en restant dans le mode texte!!!');
Writeln ('');
End.
[Back to TEXTWNDW SWAG index] [Back to Main SWAG index] [Original]