From: sparky4 Date: Tue, 20 May 2014 15:35:40 +0000 (-0500) Subject: modified: 16/DOS_GFX.EXE X-Git-Url: http://4ch.mooo.com/gitweb/?a=commitdiff_plain;h=fc7d63d3fc9f520cbd6c95ef2e070733dae4400d;hp=ec9980912cecfec9f20e6b41fb86c6af6af51b0f;p=16.git modified: 16/DOS_GFX.EXE modified: 16/Project 16.bfproject new file: 16/VGA8X8.FNT modified: 16/dos_gfx.cpp modified: 16/dos_gfx.h modified: 16/lib/lib_com.h deleted: 16/lib/x/MAKEFILE~ new file: 16/w_modex/BUDDHA.PCX new file: 16/w_modex/FIXED32.CPP new file: 16/w_modex/FIXED32.HPP new file: 16/w_modex/M.BAT new file: 16/w_modex/MODEX.CPP new file: 16/w_modex/MODEX.HPP new file: 16/w_modex/MONSTER.PCX new file: 16/w_modex/SINTAB.DAT new file: 16/w_modex/SPOCK.PCX new file: 16/w_modex/TEST.CPP new file: 16/w_modex/TEST.EXE new file: 16/w_modex/VGA8X8.FNT new file: 16/w_modex/XBLITBUF.CPP new file: 16/w_modex/XBLITBUF.HPP new file: 16/w_modex/XPAL.CPP new file: 16/w_modex/XPAL.HPP new file: 16/w_modex/XPRIM.CPP new file: 16/w_modex/XPRIM.HPP new file: 16/w_modex/XTYPES.HPP --- diff --git a/16/DOS_GFX.EXE b/16/DOS_GFX.EXE index f7e5dd4f..a7e672a4 100644 Binary files a/16/DOS_GFX.EXE and b/16/DOS_GFX.EXE differ diff --git a/16/Project 16.bfproject b/16/Project 16.bfproject index e408d429..5b217448 100644 --- a/16/Project 16.bfproject +++ b/16/Project 16.bfproject @@ -1,17 +1,19 @@ c2e.convert_special: 0 e2c.convert_num: 0 -openfiles: /dos/z/16/16/dos_gfx.cpp:10521:10066:1: -openfiles: /dos/z/16/16/dos_gfx.h:764:0:0: +openfiles: /dos/z/16/16/dos_gfx.cpp:17694:17368:1: +openfiles: /dos/z/16/16/dos_gfx.h:1182:0:0: openfiles: /dos/z/16/16/dos_kb.c:892:395:0: openfiles: /dos/z/16/16/dos_kb.h:60:0:0: openfiles: /dos/z/16/16/lib/lib_com.cpp:0:0:0: -openfiles: /dos/z/16/16/lib/lib_com.h:2523:1479:0: +openfiles: /dos/z/16/16/lib/lib_com.h:2553:1914:0: openfiles: /dos/z/16/16/scroll.txt:5307:5103:0: -openfiles: /dos/z/16/16/project16.txt:1675:0:0: +openfiles: /dos/z/16/16/project16.txt:1675:950:0: openfiles: /dos/z/16/16/16.txt:0:0:0: -openfiles: /dos/z/16/16/lib/x/MXSM.ASM:12781:12781:0: -openfiles: /dos/z/16/16/lib/x/MODEX.H:1768:1601:0: -openfiles: /dos/z/16/16/lib/x/MXPN.ASM:652:649:0: +openfiles: /dos/z/16/16/w_modex/MODEX.CPP:474:0:0: +openfiles: /dos/z/16/16/w_modex/MODEX.HPP:777:246:0: +openfiles: /dos/z/16/16/w_modex/TEST.CPP:12070:11735:0: +openfiles: /dos/z/16/16/w_modex/XPRIM.CPP:0:0:0: +openfiles: /dos/z/16/16/w_modex/XPRIM.HPP:83:0:0: snr_recursion_level: 0 convertcolumn_horizontally: 0 adv_open_matchname: 0 @@ -23,10 +25,10 @@ view_left_panel: 0 default_mime_type: text/plain e2c.convert_xml: 1 c2e.convert_iso: 0 -opendir: file:///dos/z/16/16/lib/x +opendir: file:///dos/z/16/16/w_modex wrap_text_default: 0 bookmarks_filename_mode: 1 -ssearch_text: mxWaitDisplay +ssearch_text: waiyt snr_casesens: 0 view_blocks: 1 name: project 16 @@ -73,6 +75,13 @@ recent_files: file:///dos/z/16/16/project16.txt recent_files: file:///dos/z/16/16/lib/x/MODEX.H recent_files: file:///dos/z/16/16/16.txt recent_files: file:///dos/z/16/16/lib/x/MXSM.ASM +recent_files: file:///dos/z/16/16/lib/x/MODEX.DEF +recent_files: file:///dos/z/16/16/lib/x/MXVS.ASM +recent_files: file:///dos/z/16/16/w_modex/MODEX.HPP +recent_files: file:///dos/z/16/16/w_modex/MODEX.CPP +recent_files: file:///dos/z/16/16/w_modex/TEST.CPP +recent_files: file:///dos/z/16/16/w_modex/XPRIM.HPP +recent_files: file:///dos/z/16/16/w_modex/XPRIM.CPP snr_replacetype: 0 savedir: file:///dos/z/16/16 spell_check_default: 1 @@ -84,21 +93,21 @@ snr_escape_chars: 0 htmlbar_view: 0 spell_lang: en ssearch_dotmatchall: 0 -searchlist: unsigned -searchlist: word -searchlist: play -searchlist: rand -searchlist: x6 -searchlist: x86 -searchlist: 86 -searchlist: asm -searchlist: size -searchlist: SIZE -searchlist: 80 -searchlist: size -searchlist: widthBytes -searchlist: size -searchlist: mxWaitDisplay +searchlist: addr +searchlist: 0x3DA +searchlist: wait +searchlist: loadfontX( +searchlist: font +searchlist: text +searchlist: putstringX +searchlist: putchX +searchlist: Xfont, +searchlist: // Waits for vertical retrace +searchlist: wait +searchlist: ding +searchlist: font +searchlist: wi +searchlist: waiyt autocomplete: 1 outputb_show_all_output: 0 bookmarks_show_mode: 0 diff --git a/16/VGA8X8.FNT b/16/VGA8X8.FNT new file mode 100644 index 00000000..d2bcc392 Binary files /dev/null and b/16/VGA8X8.FNT differ diff --git a/16/dos_gfx.cpp b/16/dos_gfx.cpp index cd45ae84..4fe962e6 100644 --- a/16/dos_gfx.cpp +++ b/16/dos_gfx.cpp @@ -57,7 +57,8 @@ //code from old library! /*src\lib\*/ #include "dos_gfx.h" -#include "lib\x\modex.h" +//#include "lib\x\modex.h" +//#include "XPRIM.HPP" int old_mode; //color ‚Ä‚·‚Æ @@ -65,7 +66,7 @@ int gq = LGQ; //‚Ä‚·‚Æ int q = 0; int bakax = 0, bakay = 0; -int xx = rand()&0%320, yy = rand()&0%240, sx = 0, sy = 0; +cord xx = rand()&0%320, yy = rand()&0%240, sx = 0, sy = 0; byte coor; /* @@ -81,6 +82,14 @@ byte coor; #define SEQU_ADDR 0x3c4 /* Base port of the Sequencer */ #define GRAC_ADDR 0x3ce /* Base port of the Graphics Controller */ +#define STATUS_ADDR 0x3DA + +unsigned char *RowsX[600]; +unsigned char write_plane, read_plane; +unsigned short text_mask[16] = { 0x0002, 0x0102, 0x0202, 0x0302, + 0x0402, 0x0502, 0x0602, 0x0702, + 0x0802, 0x0902, 0x0A02, 0x0B02, + 0x0C02, 0x0D02, 0x0E02, 0x0F02 }; /* @@ -89,7 +98,6 @@ byte coor; */ byte *vga = (byte *) MK_FP(0xA000, 0); -//fontAddr = getFont(); /* * width and height should specify the mode dimensions. widthBytes @@ -184,10 +192,8 @@ OUT value TO PORT 3C0H (where "value" is the number of pixels to offset) ----------------------------------------------- */ -// -// inp(0x3DA); -// outp(0x3C0, 0x13); +//mxSetVirtualScreen(480,360); } /* @@ -287,32 +293,18 @@ void set320x240x256_X(void) } -/*-----------XXXX-------------*/ - +/*-----------XXXX-------------*/ + ///////////////////////////////////////////////////////////////////////////// // // // WaitRetrace() - This waits until you are in a Verticle Retrace. // // // ///////////////////////////////////////////////////////////////////////////// +void wait_for_retrace(void) +{ + while (!(inp(STATUS_ADDR) & 0x08)); +} -void WaitRetrace() { - -// register char qy; - - in.h.dx = 0x03DA; - in.h.al = in.h.dx; - - in.h.al &= 0x08; - int86(0x10, &in, &out); - - - /*l1: asm { - in al,0x03DA; - and al,0x08; - jnz l2; - }*/ -} - ///////////////////////////////////////////////////////////////////////////// // // // MoveTo() - This moves to position X*4 on a chain 4 screen. // @@ -320,10 +312,10 @@ void WaitRetrace() { // will be better documented. - Snowman // // // ///////////////////////////////////////////////////////////////////////////// - +/* void MoveTo (word X, word Y) { -// word O = Y*SIZE*2+X; +// word O = Y*SIZE*2+X; word O = Y*widthBytes*2+X; asm { @@ -338,8 +330,8 @@ void MoveTo (word X, word Y) { mov al, 0x0D mov dx, 0x3D4 out dx, ax - } - + } + ;----------------------------------------------------------- ; ; MXPN.ASM - Panning function @@ -400,10 +392,10 @@ mxPan ENDP MX_TEXT ENDS END - -} - + +} + //Procedure Play; void Play() { @@ -415,15 +407,15 @@ void Play() moveto(0,0,Size); // { This moves the view to the top left hand corner } -/* for(loop1=0;loop1<=3;loop1++) - for(loop2=0;loop2<=5;loop2++) - Putpic (loop1*160,loop2*66); // { This places the picture all over the +// for(loop1=0;loop1<=3;loop1++) +// for(loop2=0;loop2<=5;loop2++) +// Putpic (loop1*160,loop2*66); // { This places the picture all over the // chain-4 screen } - getch(); - ch=0x0;*/ +// getch(); +// ch=0x0; // xpos=rand (78)+1; -// ypos=rand (198)+1; // { Random start positions for the view } - xpos=0; +// ypos=rand (198)+1; // { Random start positions for the view } + xpos=0; ypos=0; xdir=1; ydir=1; @@ -440,8 +432,8 @@ void Play() // if(ch==0x71)break; // 'q' // if(ch==0x1b)break; // 'ESC' // } -} - +} +*/ /*tile*/ //king_crimson's code void putColorBox_X(int x, int y, int w, int h, byte color) { @@ -482,11 +474,12 @@ void scrolly(int bongy) //king_crimson's code void hScroll(int Cols) { - inp(0x3DA); + wait_for_retrace(); outp(0x3C0, 0x13); outp(0x3C0, Cols & 3); outp(0x3D4, 0x13); - outp(0x3D5, Cols/* >> 2*/); + outp(0x3D5, Cols >> 2); + outp(0x3D4, Cols); //setVisibleStart(visStart + (Cols * height)); setVisibleStart(visStart + (Cols * width)); } @@ -586,63 +579,77 @@ I'm sorry about this being so confusing but it's a bit difficult to explain. */ -//--------------------------------------------------- -// -// Use the bios to get the address of the 8x8 font -// -// You need a font if you are going to draw text. -// -/* -int far * -getFont() +int loadfontX(char *fname) { - union REGPACK rg; - int seg; - int off; - memset(&rg, 0, sizeof(rg)); - - rg.w.ax = 0x1130; - rg.h.bh = 0x03; - intr(0x10, &rg); - seg = rg.w.es; - off = rg.w.bp; - - - return (int far *)MK_FP(seg, off); + FILE *fp; + + fp = fopen(fname, "rb"); + + if (fp == NULL) { + return 0; + } else { + fread(Xfont, 8, 256, fp); + fclose(fp); + return 1; + } } -void drawChar(int x, int y, int color, byte c) +void putchX(cord x, cord y, char c, byte color) { - int i, j; - int mask; - int far *font = getFont() + (c * 8); - - for (i = 0; i < 8; i++) - { - mask = *font; - for (j = 0; j < 8; j++) - { - if (mask & 0x80) - { - //pixel(x + j, y + i, color); - putPixel_X(x + j, y + i, color); - } - mask <<= 1; - } - font++; - } + int i; + byte *vga_ptr; + byte *font_ptr; + byte temp; + + // 8x8 font + vga_ptr = RowsX[y << 3] + (x << 1) + actStart; + write_plane = -1; + + font_ptr = Xfont + (c << 3); + + i=8; + while (i--) { + temp = *font_ptr++; + outpw(SEQU_ADDR, text_mask[temp & 0x0F]); + *vga_ptr++ = color; + + outpw(SEQU_ADDR, text_mask[temp >> 4]); + *vga_ptr-- = color; + vga_ptr += widthBytes; + } } -void drawText(int x, int y, int color, byte string) +void putstringX(cord x, cord y, char *str, byte color) { - while (string) - { - drawChar(x, y, color, string); - x += 8; - string++; + int i, skip; + byte *vga_ptr; + byte *font_ptr; + byte c, temp; + + // 8x8 font + vga_ptr = RowsX[y << 3] + (x << 1) + actStart; + write_plane = -1; + + skip = 2 - (widthBytes << 3); + + while (c = *str++) { + font_ptr = Xfont + (c << 3); + + i=8; + while (i--) { + temp = *font_ptr++; + outpw(SEQU_ADDR, text_mask[temp & 0x0F]); + *vga_ptr++ = color; + + outpw(SEQU_ADDR, text_mask[temp >> 4]); + *vga_ptr-- = color; + vga_ptr += widthBytes; } + + vga_ptr += skip; + } } -*/ + ///////////////////////////////////////////////////////////////////////////// // // // setvideo() - This function Manages the video modes // @@ -936,6 +943,7 @@ void doTest(void) int main(void) { int key,d; + //short int temp; // main variables d=1; // switch variable key=4; // default screensaver number @@ -953,7 +961,12 @@ int main(void) //++++0000 setvideo(1); -//mxInit(); + /*temp = loadfontX("vga8x8.fnt"); + + if (temp) { + putstringX(0, 0, "bakapi!", 2); + } + getch();*/ // screen savers /*while(d!=0){ // on! @@ -970,7 +983,7 @@ int main(void) } }*/ // else off while(!kbhit()){ // conditions of screen saver - ding(4); + ding(2); } //end of screen savers // doTest(); @@ -978,9 +991,9 @@ int main(void) while(!kbhit()){ // conditions of screen saver // hScroll(1); -// scrolly(1); -// delay(100); - Play(); + scrolly(1); + delay(100); +// Play(); } //++++0000 setvideo(0); diff --git a/16/dos_gfx.h b/16/dos_gfx.h index 2368faee..bc536945 100644 --- a/16/dos_gfx.h +++ b/16/dos_gfx.h @@ -15,8 +15,7 @@ // Size = 80 = 2 across, 2 down // Size = 160 = 4 across, 1 down*/ //#define VMEM 0xA000 // = vga -//int width = 320; -//int height = 240; +byte Xfont[2048]; void drawChar(int x, int y, int color, byte c); void drawText(int x, int y, int color, byte string); @@ -30,7 +29,8 @@ void cls(byte color, byte *Where); void putPixel_X(int x, int y, byte color); void putColorBox_X(int x, int y, int w, int h, byte color); void vScroll(int rows); -void scrolly(int bong); +void scrolly(int bong); +void wait_for_retrace(void); // Waits for vertical retrace //void BlockMove(); //void eraseplayer(int x, int y); //void drawplayer(int x, int y, int color); diff --git a/16/lib/lib_com.h b/16/lib/lib_com.h index 232d4270..2910d687 100644 --- a/16/lib/lib_com.h +++ b/16/lib/lib_com.h @@ -97,7 +97,8 @@ typedef unsigned char byte; -typedef unsigned int word; +typedef unsigned int word; +typedef unsigned short cord; void wait(clock_t wait); diff --git a/16/lib/x/MAKEFILE~ b/16/lib/x/MAKEFILE~ deleted file mode 100644 index c5b20124..00000000 --- a/16/lib/x/MAKEFILE~ +++ /dev/null @@ -1,82 +0,0 @@ -# -# MODEX library makefile (for Borland MAKE) -# Copyright (c) 1993,1994 by Alessandro Scotti -# -LIBINCS = MODEX.DEF - -LIBOBJS = MXBB.OBJ - MXCC.OBJ - MXCG.OBJ - MXCL.OBJ - MXCR.OBJ - MXFB.OBJ - MXFP.OBJ - MXGC.OBJ - MXGI.OBJ - MXGM.OBJ - MXGP.OBJ - MXGV.OBJ - MXHL.OBJ - MXIT.OBJ - MXLL.OBJ - MXLN.OBJ - MXOT.OBJ - MXPB.OBJ - MXPF.OBJ - MXPG.OBJ - MXPI.OBJ - MXPN.OBJ - MXPP.OBJ - MXPT.OBJ - MXRA.OBJ - MXRP.OBJ - MXSA.OBJ - MXSC.OBJ - MXSI.OBJ - MXSL.OBJ - MXSM.OBJ - MXSP.OBJ - MXSS.OBJ - MXTL.OBJ - MXVS.OBJ - MXWD.OBJ - MXWM.OBJ - MXWP.OBJ - MXWR.OBJ - -# -# ASM compiler -# -ASMC = JWASMR -ASMO = -Zm -0 - -# -# PAS compiler -# -#PASC = bpc -#PASO = /m -$D- -$L- -$S- - -# -# LIB maker, uses response file -# -LIBC = JWlibd - -.asm.obj: - $(ASMC) $(ASMO) $< - -target: modex.lib -#modex.tpu modex.tpp - -#modex.tpu: $(LIBOBJS) modex.pas -# $(PASC) $(PASO) modex -# copy modex.tpu .. -# copy modex.pas .. - -#modex.tpp: $(LIBOBJS) modex.pas -# $(PASC) /cp $(PASO) modex -# copy modex.tpp .. - -modex.lib: modex.lib $(LIBOBJS) - $(LIBC) modex.lib# @modex.lbr - -$(LIBOBJS): modex.def diff --git a/16/w_modex/BUDDHA.PCX b/16/w_modex/BUDDHA.PCX new file mode 100644 index 00000000..687beebf Binary files /dev/null and b/16/w_modex/BUDDHA.PCX differ diff --git a/16/w_modex/FIXED32.CPP b/16/w_modex/FIXED32.CPP new file mode 100644 index 00000000..ae06630e --- /dev/null +++ b/16/w_modex/FIXED32.CPP @@ -0,0 +1,114 @@ +#include + +#include "fixed32.hpp" + +Fixed32 SinTab[256]; +Fixed32 CosTab[256]; + + +void +initFixed32(void) +{ + FILE *fp; + + fp = fopen("sintab.dat", "rb"); + fread(SinTab, 4, 256, fp); + fread(CosTab, 4, 256, fp); + fclose(fp); +} + + +Fixed32 +FixedMul(Fixed32 num1, Fixed32 num2) +{ + long Mm1, Mm2; + short int MM, mm; + short int hi1, hi2, lo1, lo2; + + hi1 = (num1 >> 16); + hi2 = (num2 >> 16); + lo1 = (num1 & 0xFFFF); + lo2 = (num2 & 0xFFFF); + + MM = (hi1 * hi2); + Mm1 = (lo2 * hi1); + Mm2 = (lo1 * hi2); + mm = (lo1 * lo2); + + return (Mm1 + Mm2 + mm + (((long)MM) << 16)); +} + + +Fixed32 +FixedDiv(Fixed32 numer, Fixed32 denom) +{ + return (numer / ROUND_FIXED_TO_INT(denom)); +} + + +void +CosSin(Iangle theta, Fixed32 *Cos, Fixed32 *Sin) +{ + *Sin = SinTab[theta]; + *Cos = CosTab[theta]; +} + + +/* ASM fixedpoint math routines +;-------------------------------------------------- +; Sqrt - Fixed Point Square Root (High/Normal Precision) +; IN : ecx +; OUT : eax +; Modified : ebx,ecx,edx +Sqrt PROC + +;This is the High Precision version for the sqrt. +;It gives the optimal 8.16 precision but takes +;a little longer (24 iterations, 48 bits intead of +;16 iterations and 32 bits) + + xor eax,eax ;eax is root + mov ebx,40000000h +sqrt1: + mov edx,ecx ;edx = val + sub edx,ebx ;val - bitsqr + jb sqrt2 + sub edx,eax ;val - root + jb sqrt2 + mov ecx,edx ;val >= (root+bitsqr) -> accept subs + shr eax,1 ;root >> 1 + or eax,ebx ;root | bitsqr + shr ebx,2 ;bitsqr>>2 + jnz sqrt1 + jz sqrt5 +sqrt2: + shr eax,1 ;val < (root+bitsqr) -> dont change val + shr ebx,2 ;bitsqr>>2 + jnz sqrt1 +; we now have the 8.8 precision + +sqrt5: + mov ebx,00004000h + shl eax,16 + shl ecx,16 +sqrt3: + mov edx,ecx ;edx = val + sub edx,ebx ;val - bitsqr + jb sqrt4 + sub edx,eax ;val - root + jb sqrt4 + mov ecx,edx ;val >= (root+bitsqr) -> accept subs + shr eax,1 ;root >> 1 + or eax,ebx ;root | bitsqr + shr ebx,2 ;bitsqr>>2 + jnz sqrt3 + ret +sqrt4: + shr eax,1 ;val < (root+bitsqr) -> dont change val + shr ebx,2 ;bitsqr>>2 + jnz sqrt3 + ret + +Sqrt ENDP +*/ + diff --git a/16/w_modex/FIXED32.HPP b/16/w_modex/FIXED32.HPP new file mode 100644 index 00000000..49a084fe --- /dev/null +++ b/16/w_modex/FIXED32.HPP @@ -0,0 +1,41 @@ +#ifndef FIXEDPOINT_HPP + #define FIXEDPOINT_HPP + +typedef long Fixed32; // 16.16 FixedPoint +typedef unsigned char Iangle; // Integer angle (0..255) + +/* Macros for Type Conversion */ +#define INT_TO_FIXED(x) ((x) << 16) +#define FIXED_TO_INT(x) ((x) >> 16) +#define ROUND_FIXED_TO_INT(x) (((x) + 0x8000) >> 16) + +// Loads Fixed32 datafiles +void initFixed32(void); + +// Common math functions +Fixed32 FixedMul(Fixed32 num1, Fixed32 num2); +Fixed32 FixedDiv(Fixed32 numer, Fixed32 denom); +void CosSin(Iangle theta, Fixed32 *Cos, Fixed32 *Sin); + +Fixed32 FixedMulASM(Fixed32 num1, Fixed32 num2); +#pragma aux FixedMulASM = \ + "imul edx" \ + "add eax, 8000h" \ + "adc edx, 0" \ + "shrd eax, edx, 16" \ + parm caller [eax] [edx] \ + value [eax] \ + modify [eax edx]; + +Fixed32 FixedDivASM(Fixed32 numer, Fixed32 denom); // No rounding! +#pragma aux FixedDivASM = \ + "xor eax, eax" \ + "shrd eax, edx, 16" \ + "sar edx, 16" \ + "idiv ebx" \ + parm caller [edx] [ebx] \ + value [eax] \ + modify [eax ebx edx]; + +#endif + diff --git a/16/w_modex/M.BAT b/16/w_modex/M.BAT new file mode 100644 index 00000000..5bcb63a5 --- /dev/null +++ b/16/w_modex/M.BAT @@ -0,0 +1,2 @@ +wcl386 test modex xprim xpal xblitbuf fixed32 +erase *.obj diff --git a/16/w_modex/MODEX.CPP b/16/w_modex/MODEX.CPP new file mode 100644 index 00000000..f266a986 --- /dev/null +++ b/16/w_modex/MODEX.CPP @@ -0,0 +1,913 @@ +#include +#include +#include + +#include "modex.hpp" + +#define ATTRCON_ADDR 0x3C0 +#define MISC_ADDR 0x3C2 +#define VGAENABLE_ADDR 0x3C3 +#define SEQU_ADDR 0x3C4 +#define GRACON_ADDR 0x3CE +#define CRTC_ADDR 0x3D4 +#define STATUS_ADDR 0x3DA + +unsigned short width, height, widthBytes, num_pages; +unsigned short pageSize, activeStart, visibleStart; +unsigned char write_plane, read_plane; +unsigned char *RowsX[600]; +unsigned char line_head[4] = { 0xFF, 0x0E, 0x0C, 0x08 }; +unsigned char line_tail[4] = { 0x00, 0x01, 0x03, 0x07 }; +unsigned short plane_mask[4] = { PLANE_0, PLANE_1, PLANE_2, PLANE_3 }; +unsigned short read_mask[4] = { READ_PLANE_0, READ_PLANE_1, + READ_PLANE_2, READ_PLANE_3 }; +unsigned short text_mask[16] = { 0x0002, 0x0102, 0x0202, 0x0302, + 0x0402, 0x0502, 0x0602, 0x0702, + 0x0802, 0x0902, 0x0A02, 0x0B02, + 0x0C02, 0x0D02, 0x0E02, 0x0F02 }; +unsigned short page_offset[5]; +unsigned short page_mask_high[5]; +unsigned short page_mask_low[5]; + + +unsigned short ModeX_256x224regs[75] = +{ + 0x3c2, 0x00, 0xe3, + 0x3d4, 0x00, 0x5f, + 0x3d4, 0x01, 0x3f, + 0x3d4, 0x02, 0x40, + 0x3d4, 0x03, 0x82, + 0x3d4, 0x04, 0x4a, + 0x3d4, 0x05, 0x9a, + 0x3d4, 0x06, 0x0b, + 0x3d4, 0x07, 0x3e, + 0x3d4, 0x08, 0x00, + 0x3d4, 0x09, 0x41, + 0x3d4, 0x10, 0xda, + 0x3d4, 0x11, 0x9c, + 0x3d4, 0x12, 0xbf, + 0x3d4, 0x13, 0x20, + 0x3d4, 0x14, 0x00, + 0x3d4, 0x15, 0xc7, + 0x3d4, 0x16, 0x04, + 0x3d4, 0x17, 0xe3, + 0x3c4, 0x01, 0x01, + 0x3c4, 0x04, 0x06, + 0x3ce, 0x05, 0x40, + 0x3ce, 0x06, 0x05, + 0x3c0, 0x10, 0x41, + 0x3c0, 0x13, 0x00 +}; + +unsigned short ModeX_256x240regs[75] = +{ + 0x3c2, 0x00, 0xe3, + 0x3d4, 0x00, 0x5f, + 0x3d4, 0x01, 0x3f, + 0x3d4, 0x02, 0x40, + 0x3d4, 0x03, 0x82, + 0x3d4, 0x04, 0x4e, + 0x3d4, 0x05, 0x96, + 0x3d4, 0x06, 0x0d, + 0x3d4, 0x07, 0x3e, + 0x3d4, 0x08, 0x00, + 0x3d4, 0x09, 0x41, + 0x3d4, 0x10, 0xea, + 0x3d4, 0x11, 0xac, + 0x3d4, 0x12, 0xdf, + 0x3d4, 0x13, 0x20, + 0x3d4, 0x14, 0x00, + 0x3d4, 0x15, 0xe7, + 0x3d4, 0x16, 0x06, + 0x3d4, 0x17, 0xe3, + 0x3c4, 0x01, 0x01, + 0x3c4, 0x04, 0x06, + 0x3ce, 0x05, 0x40, + 0x3ce, 0x06, 0x05, + 0x3c0, 0x10, 0x41, + 0x3c0, 0x13, 0x00 +}; + +unsigned short ModeX_256x256regs[75] = +{ + 0x3c2, 0x00, 0xe3, + 0x3d4, 0x00, 0x5f, + 0x3d4, 0x01, 0x3f, + 0x3d4, 0x02, 0x40, + 0x3d4, 0x03, 0x82, + 0x3d4, 0x04, 0x4a, + 0x3d4, 0x05, 0x9a, + 0x3d4, 0x06, 0x23, + 0x3d4, 0x07, 0xb2, + 0x3d4, 0x08, 0x00, + 0x3d4, 0x09, 0x61, + 0x3d4, 0x10, 0x0a, + 0x3d4, 0x11, 0xac, + 0x3d4, 0x12, 0xff, + 0x3d4, 0x13, 0x20, + 0x3d4, 0x14, 0x00, + 0x3d4, 0x15, 0x07, + 0x3d4, 0x16, 0x1a, + 0x3d4, 0x17, 0xe3, + 0x3c4, 0x01, 0x01, + 0x3c4, 0x04, 0x06, + 0x3ce, 0x05, 0x40, + 0x3ce, 0x06, 0x05, + 0x3c0, 0x10, 0x41, + 0x3c0, 0x13, 0x00 +}; + +unsigned short ModeX_256x480regs[75] = +{ + 0x3c2, 0x00, 0xe3, + 0x3d4, 0x00, 0x5f, + 0x3d4, 0x01, 0x3f, + 0x3d4, 0x02, 0x40, + 0x3d4, 0x03, 0x82, + 0x3d4, 0x04, 0x4e, + 0x3d4, 0x05, 0x96, + 0x3d4, 0x06, 0x0d, + 0x3d4, 0x07, 0x3e, + 0x3d4, 0x08, 0x00, + 0x3d4, 0x09, 0x40, + 0x3d4, 0x10, 0xea, + 0x3d4, 0x11, 0xac, + 0x3d4, 0x12, 0xdf, + 0x3d4, 0x13, 0x20, + 0x3d4, 0x14, 0x00, + 0x3d4, 0x15, 0xe7, + 0x3d4, 0x16, 0x06, + 0x3d4, 0x17, 0xe3, + 0x3c4, 0x01, 0x01, + 0x3c4, 0x04, 0x06, + 0x3ce, 0x05, 0x40, + 0x3ce, 0x06, 0x05, + 0x3c0, 0x10, 0x41, + 0x3c0, 0x13, 0x00 +}; + +unsigned short ModeX_320x200regs[75] = +{ + 0x3c2, 0x00, 0x63, + 0x3d4, 0x00, 0x5f, + 0x3d4, 0x01, 0x4f, + 0x3d4, 0x02, 0x50, + 0x3d4, 0x03, 0x82, + 0x3d4, 0x04, 0x54, + 0x3d4, 0x05, 0x80, + 0x3d4, 0x06, 0xbf, + 0x3d4, 0x07, 0x1f, + 0x3d4, 0x08, 0x00, + 0x3d4, 0x09, 0x41, + 0x3d4, 0x10, 0x9c, + 0x3d4, 0x11, 0x8e, + 0x3d4, 0x12, 0x8f, + 0x3d4, 0x13, 0x28, + 0x3d4, 0x14, 0x00, + 0x3d4, 0x15, 0x96, + 0x3d4, 0x16, 0xb9, + 0x3d4, 0x17, 0xe3, + 0x3c4, 0x01, 0x01, + 0x3c4, 0x04, 0x06, + 0x3ce, 0x05, 0x40, + 0x3ce, 0x06, 0x05, + 0x3c0, 0x10, 0x41, + 0x3c0, 0x13, 0x00 +}; + +unsigned short ModeX_320x240regs[75] = +{ + 0x3c2, 0x00, 0xe3, + 0x3d4, 0x00, 0x5f, + 0x3d4, 0x01, 0x4f, + 0x3d4, 0x02, 0x50, + 0x3d4, 0x03, 0x82, + 0x3d4, 0x04, 0x54, + 0x3d4, 0x05, 0x80, + 0x3d4, 0x06, 0x0d, + 0x3d4, 0x07, 0x3e, + 0x3d4, 0x08, 0x00, + 0x3d4, 0x09, 0x41, + 0x3d4, 0x10, 0xea, + 0x3d4, 0x11, 0xac, + 0x3d4, 0x12, 0xdf, + 0x3d4, 0x13, 0x28, + 0x3d4, 0x14, 0x00, + 0x3d4, 0x15, 0xe7, + 0x3d4, 0x16, 0x06, + 0x3d4, 0x17, 0xe3, + 0x3c4, 0x01, 0x01, + 0x3c4, 0x04, 0x06, + 0x3ce, 0x05, 0x40, + 0x3ce, 0x06, 0x05, + 0x3c0, 0x10, 0x41, + 0x3c0, 0x13, 0x00 +}; + +unsigned short ModeX_320x400regs[75] = +{ + 0x3c2, 0x00, 0x63, + 0x3d4, 0x00, 0x5f, + 0x3d4, 0x01, 0x4f, + 0x3d4, 0x02, 0x50, + 0x3d4, 0x03, 0x82, + 0x3d4, 0x04, 0x54, + 0x3d4, 0x05, 0x80, + 0x3d4, 0x06, 0xbf, + 0x3d4, 0x07, 0x1f, + 0x3d4, 0x08, 0x00, + 0x3d4, 0x09, 0x40, + 0x3d4, 0x10, 0x9c, + 0x3d4, 0x11, 0x8e, + 0x3d4, 0x12, 0x8f, + 0x3d4, 0x13, 0x28, + 0x3d4, 0x14, 0x00, + 0x3d4, 0x15, 0x96, + 0x3d4, 0x16, 0xb9, + 0x3d4, 0x17, 0xe3, + 0x3c4, 0x01, 0x01, + 0x3c4, 0x04, 0x06, + 0x3ce, 0x05, 0x40, + 0x3ce, 0x06, 0x05, + 0x3c0, 0x10, 0x41, + 0x3c0, 0x13, 0x00 +}; + +unsigned short ModeX_320x480regs[75] = +{ + 0x3c2, 0x00, 0xe3, + 0x3d4, 0x00, 0x5f, + 0x3d4, 0x01, 0x4f, + 0x3d4, 0x02, 0x50, + 0x3d4, 0x03, 0x82, + 0x3d4, 0x04, 0x54, + 0x3d4, 0x05, 0x80, + 0x3d4, 0x06, 0x0d, + 0x3d4, 0x07, 0x3e, + 0x3d4, 0x08, 0x00, + 0x3d4, 0x09, 0x40, + 0x3d4, 0x10, 0xea, + 0x3d4, 0x11, 0xac, + 0x3d4, 0x12, 0xdf, + 0x3d4, 0x13, 0x28, + 0x3d4, 0x14, 0x00, + 0x3d4, 0x15, 0xe7, + 0x3d4, 0x16, 0x06, + 0x3d4, 0x17, 0xe3, + 0x3c4, 0x01, 0x01, + 0x3c4, 0x04, 0x06, + 0x3ce, 0x05, 0x40, + 0x3ce, 0x06, 0x05, + 0x3c0, 0x10, 0x41, + 0x3c0, 0x13, 0x00 +}; + +unsigned short ModeX_360x200regs[75] = +{ + 0x3c2, 0x00, 0x67, + 0x3d4, 0x00, 0x6b, + 0x3d4, 0x01, 0x59, + 0x3d4, 0x02, 0x5a, + 0x3d4, 0x03, 0x8e, + 0x3d4, 0x04, 0x5e, + 0x3d4, 0x05, 0x8a, + 0x3d4, 0x06, 0xbf, + 0x3d4, 0x07, 0x1f, + 0x3d4, 0x08, 0x00, + 0x3d4, 0x09, 0x41, + 0x3d4, 0x10, 0x9c, + 0x3d4, 0x11, 0x8e, + 0x3d4, 0x12, 0x8f, + 0x3d4, 0x13, 0x2d, + 0x3d4, 0x14, 0x00, + 0x3d4, 0x15, 0x96, + 0x3d4, 0x16, 0xb9, + 0x3d4, 0x17, 0xe3, + 0x3c4, 0x01, 0x01, + 0x3c4, 0x04, 0x06, + 0x3ce, 0x05, 0x40, + 0x3ce, 0x06, 0x05, + 0x3c0, 0x10, 0x41, + 0x3c0, 0x13, 0x00 +}; + +unsigned short ModeX_360x240regs[75] = +{ + 0x3c2, 0x00, 0xe7, + 0x3d4, 0x00, 0x6b, + 0x3d4, 0x01, 0x59, + 0x3d4, 0x02, 0x5a, + 0x3d4, 0x03, 0x8e, + 0x3d4, 0x04, 0x5e, + 0x3d4, 0x05, 0x8a, + 0x3d4, 0x06, 0x0d, + 0x3d4, 0x07, 0x3e, + 0x3d4, 0x08, 0x00, + 0x3d4, 0x09, 0x41, + 0x3d4, 0x10, 0xea, + 0x3d4, 0x11, 0xac, + 0x3d4, 0x12, 0xdf, + 0x3d4, 0x13, 0x2d, + 0x3d4, 0x14, 0x00, + 0x3d4, 0x15, 0xe7, + 0x3d4, 0x16, 0x06, + 0x3d4, 0x17, 0xe3, + 0x3c4, 0x01, 0x01, + 0x3c4, 0x04, 0x06, + 0x3ce, 0x05, 0x40, + 0x3ce, 0x06, 0x05, + 0x3c0, 0x10, 0x41, + 0x3c0, 0x13, 0x00 +}; + +unsigned short ModeX_360x270regs[75] = +{ + 0x3c2, 0x00, 0xe7, + 0x3d4, 0x00, 0x6b, + 0x3d4, 0x01, 0x59, + 0x3d4, 0x02, 0x5a, + 0x3d4, 0x03, 0x8e, + 0x3d4, 0x04, 0x5e, + 0x3d4, 0x05, 0x8a, + 0x3d4, 0x06, 0x30, + 0x3d4, 0x07, 0xf0, + 0x3d4, 0x08, 0x00, + 0x3d4, 0x09, 0x61, + 0x3d4, 0x10, 0x20, + 0x3d4, 0x11, 0xa9, + 0x3d4, 0x12, 0x1b, + 0x3d4, 0x13, 0x2d, + 0x3d4, 0x14, 0x00, + 0x3d4, 0x15, 0x1f, + 0x3d4, 0x16, 0x2f, + 0x3d4, 0x17, 0xe3, + 0x3c4, 0x01, 0x01, + 0x3c4, 0x04, 0x06, + 0x3ce, 0x05, 0x40, + 0x3ce, 0x06, 0x05, + 0x3c0, 0x10, 0x41, + 0x3c0, 0x13, 0x00 +}; + +unsigned short ModeX_360x360regs[75] = +{ + 0x3c2, 0x00, 0x67, + 0x3d4, 0x00, 0x6b, + 0x3d4, 0x01, 0x59, + 0x3d4, 0x02, 0x5a, + 0x3d4, 0x03, 0x8e, + 0x3d4, 0x04, 0x5e, + 0x3d4, 0x05, 0x8a, + 0x3d4, 0x06, 0xbf, + 0x3d4, 0x07, 0x1f, + 0x3d4, 0x08, 0x00, + 0x3d4, 0x09, 0x40, + 0x3d4, 0x10, 0x88, + 0x3d4, 0x11, 0x85, + 0x3d4, 0x12, 0x67, + 0x3d4, 0x13, 0x2d, + 0x3d4, 0x14, 0x00, + 0x3d4, 0x15, 0x6d, + 0x3d4, 0x16, 0xba, + 0x3d4, 0x17, 0xe3, + 0x3c4, 0x01, 0x01, + 0x3c4, 0x04, 0x06, + 0x3ce, 0x05, 0x40, + 0x3ce, 0x06, 0x05, + 0x3c0, 0x10, 0x41, + 0x3c0, 0x13, 0x00 +}; + +unsigned short ModeX_360x400regs[75] = +{ + 0x3c2, 0x00, 0x67, + 0x3d4, 0x00, 0x6b, + 0x3d4, 0x01, 0x59, + 0x3d4, 0x02, 0x5a, + 0x3d4, 0x03, 0x8e, + 0x3d4, 0x04, 0x5e, + 0x3d4, 0x05, 0x8a, + 0x3d4, 0x06, 0xbf, + 0x3d4, 0x07, 0x1f, + 0x3d4, 0x08, 0x00, + 0x3d4, 0x09, 0x40, + 0x3d4, 0x10, 0x9c, + 0x3d4, 0x11, 0x8e, + 0x3d4, 0x12, 0x8f, + 0x3d4, 0x13, 0x2d, + 0x3d4, 0x14, 0x00, + 0x3d4, 0x15, 0x96, + 0x3d4, 0x16, 0xb9, + 0x3d4, 0x17, 0xe3, + 0x3c4, 0x01, 0x01, + 0x3c4, 0x04, 0x06, + 0x3ce, 0x05, 0x40, + 0x3ce, 0x06, 0x05, + 0x3c0, 0x10, 0x41, + 0x3c0, 0x13, 0x00 +}; + +unsigned short ModeX_360x480regs[75] = +{ + 0x3c2, 0x00, 0xe7, + 0x3d4, 0x00, 0x6b, + 0x3d4, 0x01, 0x59, + 0x3d4, 0x02, 0x5a, + 0x3d4, 0x03, 0x8e, + 0x3d4, 0x04, 0x5e, + 0x3d4, 0x05, 0x8a, + 0x3d4, 0x06, 0x0d, + 0x3d4, 0x07, 0x3e, + 0x3d4, 0x08, 0x00, + 0x3d4, 0x09, 0x40, + 0x3d4, 0x10, 0xea, + 0x3d4, 0x11, 0xac, + 0x3d4, 0x12, 0xdf, + 0x3d4, 0x13, 0x2d, + 0x3d4, 0x14, 0x00, + 0x3d4, 0x15, 0xe7, + 0x3d4, 0x16, 0x06, + 0x3d4, 0x17, 0xe3, + 0x3c4, 0x01, 0x01, + 0x3c4, 0x04, 0x06, + 0x3ce, 0x05, 0x40, + 0x3ce, 0x06, 0x05, + 0x3c0, 0x10, 0x41, + 0x3c0, 0x13, 0x00 +}; + +unsigned short ModeX_376x282regs[75] = +{ + 0x3c2, 0x00, 0xe7, + 0x3d4, 0x00, 0x6e, + 0x3d4, 0x01, 0x5d, + 0x3d4, 0x02, 0x5e, + 0x3d4, 0x03, 0x91, + 0x3d4, 0x04, 0x62, + 0x3d4, 0x05, 0x8f, + 0x3d4, 0x06, 0x62, + 0x3d4, 0x07, 0xf0, + 0x3d4, 0x08, 0x00, + 0x3d4, 0x09, 0x61, + 0x3d4, 0x10, 0x37, + 0x3d4, 0x11, 0x89, + 0x3d4, 0x12, 0x33, + 0x3d4, 0x13, 0x2f, + 0x3d4, 0x14, 0x00, + 0x3d4, 0x15, 0x3c, + 0x3d4, 0x16, 0x5c, + 0x3d4, 0x17, 0xe3, + 0x3c4, 0x01, 0x01, + 0x3c4, 0x04, 0x06, + 0x3ce, 0x05, 0x40, + 0x3ce, 0x06, 0x05, + 0x3c0, 0x10, 0x41, + 0x3c0, 0x13, 0x00 +}; + +unsigned short ModeX_376x564regs[75] = +{ + 0x3c2, 0x00, 0xe7, + 0x3d4, 0x00, 0x6e, + 0x3d4, 0x01, 0x5d, + 0x3d4, 0x02, 0x5e, + 0x3d4, 0x03, 0x91, + 0x3d4, 0x04, 0x62, + 0x3d4, 0x05, 0x8f, + 0x3d4, 0x06, 0x62, + 0x3d4, 0x07, 0xf0, + 0x3d4, 0x08, 0x00, + 0x3d4, 0x09, 0x60, + 0x3d4, 0x10, 0x37, + 0x3d4, 0x11, 0x89, + 0x3d4, 0x12, 0x33, + 0x3d4, 0x13, 0x2f, + 0x3d4, 0x14, 0x00, + 0x3d4, 0x15, 0x3c, + 0x3d4, 0x16, 0x5c, + 0x3d4, 0x17, 0xe3, + 0x3c4, 0x01, 0x01, + 0x3c4, 0x04, 0x06, + 0x3ce, 0x05, 0x40, + 0x3ce, 0x06, 0x05, + 0x3c0, 0x10, 0x41, + 0x3c0, 0x13, 0x00 +}; + +unsigned short ModeX_400x300regs[78] = +{ + 0x3c2, 0x00, 0xa7, + 0x3d4, 0x00, 0x71, + 0x3d4, 0x01, 0x63, + 0x3d4, 0x02, 0x64, + 0x3d4, 0x03, 0x92, + 0x3d4, 0x04, 0x65, + 0x3d4, 0x05, 0x82, + 0x3d4, 0x06, 0x46, + 0x3d4, 0x07, 0x1f, + 0x3d4, 0x08, 0x00, + 0x3d4, 0x09, 0x40, + 0x3d4, 0x10, 0x31, + 0x3d4, 0x11, 0x80, + 0x3d4, 0x12, 0x2b, + 0x3d4, 0x13, 0x32, + 0x3d4, 0x14, 0x00, + 0x3d4, 0x15, 0x2f, + 0x3d4, 0x16, 0x44, + 0x3d4, 0x17, 0xe3, + 0x3c4, 0x01, 0x01, + 0x3c4, 0x02, 0x0f, + 0x3c4, 0x04, 0x06, + 0x3ce, 0x05, 0x40, + 0x3ce, 0x06, 0x05, + 0x3c0, 0x10, 0x41, + 0x3c0, 0x13, 0x00 +}; + +unsigned short ModeX_400x600regs[78] = +{ + 0x3c2, 0x00, 0xe7, + 0x3d4, 0x00, 0x70, + 0x3d4, 0x01, 0x63, + 0x3d4, 0x02, 0x64, + 0x3d4, 0x03, 0x92, + 0x3d4, 0x04, 0x65, + 0x3d4, 0x05, 0x82, + 0x3d4, 0x06, 0x70, + 0x3d4, 0x07, 0xf0, + 0x3d4, 0x08, 0x00, + 0x3d4, 0x09, 0x60, + 0x3d4, 0x10, 0x5b, + 0x3d4, 0x11, 0x8c, + 0x3d4, 0x12, 0x57, + 0x3d4, 0x13, 0x32, + 0x3d4, 0x14, 0x00, + 0x3d4, 0x15, 0x58, + 0x3d4, 0x16, 0x70, + 0x3d4, 0x17, 0xe3, + 0x3c4, 0x01, 0x01, + 0x3c4, 0x02, 0x0f, + 0x3c4, 0x04, 0x06, + 0x3ce, 0x05, 0x40, + 0x3ce, 0x06, 0x05, + 0x3c0, 0x10, 0x41, + 0x3c0, 0x13, 0x00 +}; + + +void +calc_rows(void) +{ + int i; + + // Each byte addresses four pixels, so the width of a scan line + // in *bytes* is one fourth of the number of pixels on a line. + widthBytes = width / 4; + + pageSize = (widthBytes * height); + + for (i=0; i < height; i++) { + RowsX[i] = (unsigned char *)((0xA000 << 4) + (widthBytes * i)); + } + + // Clear entire video memory, by selecting all four planes, then + // writing 0 to entire segment. + outpw(SEQU_ADDR, ALL_PLANES); + memset((unsigned char *)(0xA000 << 4), 0x00, 0x00010000); + + // By default we want screen refreshing and drawing operations + // to be based at offset 0 in the video segment. + activeStart = visibleStart = 0; + + // Set current plane to invalid value + write_plane = -1; + read_plane = -1; + + // How many pages fit in 256K VGA Card? + num_pages = ((64 * 1024) / pageSize); + + for (i=0; i < num_pages; i++) { + page_offset[i] = (pageSize * i); + page_mask_high[i] = (0x0C | (page_offset[i] & 0xFF00)); + page_mask_low[i] = (0x0D | ((page_offset[i] & 0x00FF) << 8)); + } +} + + +// setBaseXMode() does the initialization to make the VGA ready to +// accept any combination of configuration register settings. This +// involves enabling writes to index 0 to 7 of the CRT controller (port +// 0x3D4), by clearing the most significant bit (bit 7) of index 0x11. +void +setBaseXMode(void) +{ + int temp; + union REGS r; + + r.x.eax = 0x0013; + int386(0x10, &r, &r); + + outp(0x3D4, 0x11); + temp = inp(0x3D5) & 0x7F; + outp(0x3D4, 0x11); + outp(0x3D5, temp); +} + + +void +outReg(unsigned short *r) +{ + switch (r[0]) { + // First handle special cases: + + case ATTRCON_ADDR: + // reset read/write flip-flop + inp(STATUS_ADDR); + outp(ATTRCON_ADDR, r[1] | 0x20); + // ensure VGA output is enabled + outp(ATTRCON_ADDR, r[2]); + break; + + case MISC_ADDR: + case VGAENABLE_ADDR: + // Copy directly to port + outp(r[0], r[2]); + break; + + case SEQU_ADDR: + case GRACON_ADDR: + case CRTC_ADDR: + default: + // Index to port + outp(r[0], r[1]); + // Value to port+1 + outp(r[0] + 1, r[2]); + break; + } +} + +void +outRegArray(unsigned short *r, int n) +{ + while (n--) { + outReg(r); + r += 3; + } +} + + +void +set80x25(void) +{ + union REGS r; + r.x.eax = 0x0003; + + int386(0x10, &r, &r); +} + +void +set256x224x256_X(void) +{ + setBaseXMode(); + outRegArray(ModeX_256x224regs, 25); + + width = 256; + height = 224; + + calc_rows(); +} + +void +set256x240x256_X(void) +{ + setBaseXMode(); + outRegArray(ModeX_256x240regs, 25); + + width = 256; + height = 240; + + calc_rows(); +} + +void +set256x256x256_X(void) +{ + setBaseXMode(); + outRegArray(ModeX_256x256regs, 25); + + width = 256; + height = 256; + + calc_rows(); +} + +void +set256x480x256_X(void) +{ + setBaseXMode(); + outRegArray(ModeX_256x480regs, 25); + + width = 256; + height = 480; + + calc_rows(); +} + +void +set320x200x256_X(void) +{ + setBaseXMode(); + outRegArray(ModeX_320x200regs, 25); + + width = 320; + height = 200; + + calc_rows(); +} + +void +set320x240x256_X(void) +{ + setBaseXMode(); + outRegArray(ModeX_320x240regs, 25); + + width = 320; + height = 240; + + calc_rows(); +} + +void +set320x400x256_X(void) +{ + setBaseXMode(); + outRegArray(ModeX_320x400regs, 25); + + width = 320; + height = 400; + + calc_rows(); +} + +void +set320x480x256_X(void) +{ + setBaseXMode(); + outRegArray(ModeX_320x480regs, 25); + + width = 320; + height = 480; + + calc_rows(); +} + +void +set360x200x256_X(void) +{ + setBaseXMode(); + outRegArray(ModeX_360x200regs, 25); + + width = 360; + height = 200; + + calc_rows(); +} + +void +set360x240x256_X(void) +{ + setBaseXMode(); + outRegArray(ModeX_360x240regs, 25); + + width = 360; + height = 240; + + calc_rows(); +} + +void +set360x270x256_X(void) +{ + setBaseXMode(); + outRegArray(ModeX_360x270regs, 25); + + width = 360; + height = 270; + + calc_rows(); +} + +void +set360x360x256_X(void) +{ + setBaseXMode(); + outRegArray(ModeX_360x360regs, 25); + + width = 360; + height = 360; + + calc_rows(); +} + +void +set360x400x256_X(void) +{ + setBaseXMode(); + outRegArray(ModeX_360x400regs, 25); + + width = 360; + height = 400; + + calc_rows(); +} + +void +set360x480x256_X(void) +{ + setBaseXMode(); + outRegArray(ModeX_360x480regs, 25); + + width = 360; + height = 480; + + calc_rows(); +} + +void +set376x282x256_X(void) +{ + setBaseXMode(); + outRegArray(ModeX_376x282regs, 25); + + width = 376; + height = 282; + + calc_rows(); +} + +void +set376x564x256_X(void) +{ + setBaseXMode(); + outRegArray(ModeX_376x564regs, 25); + + width = 376; + height = 564; + + calc_rows(); +} + +void +set400x300x256_X(void) +{ + setBaseXMode(); + outRegArray(ModeX_400x300regs, 26); + + width = 400; + height = 300; + + calc_rows(); +} + +void +set400x600x256_X(void) +{ + setBaseXMode(); + outRegArray(ModeX_400x600regs, 26); + + width = 400; + height = 600; + + calc_rows(); +} + + +COORD +get_xres(void) +{ + return width; +} + + +COORD +get_yres(void) +{ + return height; +} + + +void +set_write_plane(unsigned short int plane_mask) +{ + write_plane = -1; + outpw(SEQU_ADDR, plane_mask); +} + + +void +set_read_plane(unsigned short int plane_mask) +{ + read_plane = -1; + outpw(GRACON_ADDR, plane_mask); +} + diff --git a/16/w_modex/MODEX.HPP b/16/w_modex/MODEX.HPP new file mode 100644 index 00000000..d17c93b3 --- /dev/null +++ b/16/w_modex/MODEX.HPP @@ -0,0 +1,63 @@ +#ifndef MODEX_HPP + #define MODEX_HPP + +#include "xtypes.hpp" + +// Some defines +#define PLANE_0 0x0102 +#define PLANE_1 0x0202 +#define PLANE_2 0x0402 +#define PLANE_3 0x0802 +#define ALL_PLANES 0x0F02 +#define READ_PLANE_0 0x0004 +#define READ_PLANE_1 0x0104 +#define READ_PLANE_2 0x0204 +#define READ_PLANE_3 0x0304 + + +// External Variables needed by graphics routines +extern unsigned short width, height, widthBytes, num_pages; +extern unsigned short activeStart, visibleStart, pageSize; +extern unsigned char write_plane, read_plane; +extern unsigned char *RowsX[600]; +extern unsigned char line_head[4]; +extern unsigned char line_tail[4]; +extern unsigned short plane_mask[4]; +extern unsigned short read_mask[4]; +extern unsigned short text_mask[16]; +extern unsigned short page_offset[5]; +extern unsigned short page_mask_high[5]; +extern unsigned short page_mask_low[5]; + + +// Return to text mode +void set80x25(void); + +// Set various ModeX resolutions +void set256x224x256_X(void); +void set256x240x256_X(void); +void set256x256x256_X(void); +void set256x480x256_X(void); +void set320x200x256_X(void); +void set320x240x256_X(void); +void set320x400x256_X(void); +void set320x480x256_X(void); +void set360x200x256_X(void); +void set360x240x256_X(void); +void set360x270x256_X(void); +void set360x360x256_X(void); +void set360x400x256_X(void); +void set360x480x256_X(void); +void set376x282x256_X(void); +void set376x564x256_X(void); +void set400x300x256_X(void); +void set400x600x256_X(void); + +COORD get_xres(void); +COORD get_yres(void); + +void set_write_plane(unsigned short int plane_mask); +void set_read_plane(unsigned short int plane_mask); + +#endif + diff --git a/16/w_modex/MONSTER.PCX b/16/w_modex/MONSTER.PCX new file mode 100644 index 00000000..59b8a3b8 Binary files /dev/null and b/16/w_modex/MONSTER.PCX differ diff --git a/16/w_modex/SINTAB.DAT b/16/w_modex/SINTAB.DAT new file mode 100644 index 00000000..51b9d4e9 Binary files /dev/null and b/16/w_modex/SINTAB.DAT differ diff --git a/16/w_modex/SPOCK.PCX b/16/w_modex/SPOCK.PCX new file mode 100644 index 00000000..459f7a9e Binary files /dev/null and b/16/w_modex/SPOCK.PCX differ diff --git a/16/w_modex/TEST.CPP b/16/w_modex/TEST.CPP new file mode 100644 index 00000000..d62d5b35 --- /dev/null +++ b/16/w_modex/TEST.CPP @@ -0,0 +1,634 @@ +#include +#include +#include +#include +#include +#include + +#include "fixed32.hpp" +#include "modex.hpp" +#include "xprim.hpp" +#include "xpal.hpp" +#include "xblitbuf.hpp" + +#define FIRE_DEMO 1 +#define ROTATE_DEMO 1 +#define MONSTER_DEMO_ONE 1 +#define MONSTER_DEMO_TWO 1 +#define MATH_DEMO 0 + +int +monster_demo1(void) +{ + clock_t begin, end; + short int i; + blitbuf sprite_image, blit_image; + + clearX(0); + + load_blitbufPCX("monster.pcx", &sprite_image); + aligned_bitblitX(0, 20, &sprite_image); + getch(); + + blit_image.image = NULL; + + i=99; + + begin = clock(); + + while (i > 0) { + scale_blitbuf(120 + (i << 1), (i << 1), &sprite_image, &blit_image); + boxX((99 - i), (119 - i), (220 + i), (120 + i), 0); + vanilla_bitblitX(100 - i, 120 - i, &blit_image); + i--; + } + + end = clock(); + + i=120; + while (i > 0) { + scale_blitbuf(i, 2, &sprite_image, &blit_image); + + putpixelX(159 - (i >> 1), 119, 0); + putpixelX(159 - (i >> 1), 120, 0); + putpixelX(160 + (i >> 1), 119, 0); + putpixelX(160 + (i >> 1), 120, 0); + + vanilla_bitblitX(160 - (i >> 1), 119, &blit_image); + delay(10); + i -= 2; + } + + filledboxX(156, 119, 163, 120, 0); + putpixelX(159, 120, 1); + delay(250); + putpixelX(159, 120, 0); + + filledboxX(156, 119, 163, 120, 0); + clear_blitbuf(&sprite_image); + clear_blitbuf(&blit_image); + + getch(); + + return (end - begin); +} + + +void +monster_demo2(void) +{ + short int i; + blitbuf sprite_image, blit_image; + + clearX(0); + + load_blitbufPCX("monster.pcx", &sprite_image); + aligned_bitblitX(0, 20, &sprite_image); + getch(); + + blit_image.image = NULL; + + i=99; + while (i) { + vertical_scale_blitbuf((i << 1), &sprite_image, &blit_image); + boxX(0, (119 - i), 319, (120 + i), 0); + aligned_bitblitX(0, 120 - i, &blit_image); + i--; + } + + filledboxX(0, 120, 319, 120, 0); + + i=318; + while (i > 0) { + scale_blitbuf(i, 1, &blit_image, &sprite_image); + + putpixelX(159 - (i >> 1), 119, 0); + putpixelX(159 - (i >> 1), 120, 0); + putpixelX(160 + (i >> 1), 119, 0); + putpixelX(160 + (i >> 1), 120, 0); + + vanilla_bitblitX(160 - (i >> 1), 119, &sprite_image); + delay(5); + i -= 2; + } + + filledboxX(156, 119, 163, 120, 0); + putpixelX(159, 120, 1); + delay(250); + putpixelX(159, 120, 0); + filledboxX(156, 119, 163, 120, 0); + clear_blitbuf(&sprite_image); + clear_blitbuf(&blit_image); + + getch(); +} + + +void +fire_demo(void) +{ + #define V_WIDTH 80 + #define V_HEIGHT 50 + #define BUF_WIDTH 80 + #define BUF_HEIGHT 56 + #define REWIND (V_WIDTH * 3) + #define BUF_SIZE (BUF_WIDTH * BUF_HEIGHT) + +unsigned char fire_pal[768] = { + 0, 0, 0, 0, 0, 24, 0, 0, 24, 0, 0, 28, + 0, 0, 32, 0, 0, 32, 0, 0, 36, 0, 0, 40, + 8, 0, 40, 16, 0, 36, 24, 0, 36, 32, 0, 32, + 40, 0, 28, 48, 0, 28, 56, 0, 24, 64, 0, 20, + 72, 0, 20, 80, 0, 16, 88, 0, 16, 96, 0, 12, + 104, 0, 8, 112, 0, 8, 120, 0, 4, 128, 0, 0, + 128, 0, 0, 132, 0, 0, 136, 0, 0, 140, 0, 0, + 144, 0, 0, 144, 0, 0, 148, 0, 0, 152, 0, 0, + 156, 0, 0, 160, 0, 0, 160, 0, 0, 164, 0, 0, + 168, 0, 0, 172, 0, 0, 176, 0, 0, 180, 0, 0, + 184, 4, 0, 188, 4, 0, 192, 8, 0, 196, 8, 0, + 200, 12, 0, 204, 12, 0, 208, 16, 0, 212, 16, 0, + 216, 20, 0, 220, 20, 0, 224, 24, 0, 228, 24, 0, + 232, 28, 0, 236, 28, 0, 240, 32, 0, 244, 32, 0, + 252, 36, 0, 252, 36, 0, 252, 40, 0, 252, 40, 0, + 252, 44, 0, 252, 44, 0, 252, 48, 0, 252, 48, 0, + 252, 52, 0, 252, 52, 0, 252, 56, 0, 252, 56, 0, + 252, 60, 0, 252, 60, 0, 252, 64, 0, 252, 64, 0, + 252, 68, 0, 252, 68, 0, 252, 72, 0, 252, 72, 0, + 252, 76, 0, 252, 76, 0, 252, 80, 0, 252, 80, 0, + 252, 84, 0, 252, 84, 0, 252, 88, 0, 252, 88, 0, + 252, 92, 0, 252, 96, 0, 252, 96, 0, 252, 100, 0, + 252, 100, 0, 252, 104, 0, 252, 104, 0, 252, 108, 0, + 252, 108, 0, 252, 112, 0, 252, 112, 0, 252, 116, 0, + 252, 116, 0, 252, 120, 0, 252, 120, 0, 252, 124, 0, + 252, 124, 0, 252, 128, 0, 252, 128, 0, 252, 132, 0, + 252, 132, 0, 252, 136, 0, 252, 136, 0, 252, 140, 0, + 252, 140, 0, 252, 144, 0, 252, 144, 0, 252, 148, 0, + 252, 152, 0, 252, 152, 0, 252, 156, 0, 252, 156, 0, + 252, 160, 0, 252, 160, 0, 252, 164, 0, 252, 164, 0, + 252, 168, 0, 252, 168, 0, 252, 172, 0, 252, 172, 0, + 252, 176, 0, 252, 176, 0, 252, 180, 0, 252, 180, 0, + 252, 184, 0, 252, 184, 0, 252, 188, 0, 252, 188, 0, + 252, 192, 0, 252, 192, 0, 252, 196, 0, 252, 196, 0, + 252, 200, 0, 252, 200, 0, 252, 204, 0, 252, 208, 0, + 252, 208, 0, 252, 208, 0, 252, 208, 0, 252, 208, 0, + 252, 212, 0, 252, 212, 0, 252, 212, 0, 252, 212, 0, + 252, 216, 0, 252, 216, 0, 252, 216, 0, 252, 216, 0, + 252, 216, 0, 252, 220, 0, 252, 220, 0, 252, 220, 0, + 252, 220, 0, 252, 224, 0, 252, 224, 0, 252, 224, 0, + 252, 224, 0, 252, 228, 0, 252, 228, 0, 252, 228, 0, + 252, 228, 0, 252, 228, 0, 252, 232, 0, 252, 232, 0, + 252, 232, 0, 252, 232, 0, 252, 236, 0, 252, 236, 0, + 252, 236, 0, 252, 236, 0, 252, 240, 0, 252, 240, 0, + 252, 240, 0, 252, 240, 0, 252, 240, 0, 252, 244, 0, + 252, 244, 0, 252, 244, 0, 252, 244, 0, 252, 248, 0, + 252, 248, 0, 252, 248, 0, 252, 248, 0, 252, 252, 0, + 252, 252, 4, 252, 252, 8, 252, 252, 12, 252, 252, 16, + 252, 252, 20, 252, 252, 24, 252, 252, 28, 252, 252, 32, + 252, 252, 36, 252, 252, 40, 252, 252, 40, 252, 252, 44, + 252, 252, 48, 252, 252, 52, 252, 252, 56, 252, 252, 60, + 252, 252, 64, 252, 252, 68, 252, 252, 72, 252, 252, 76, + 252, 252, 80, 252, 252, 84, 252, 252, 84, 252, 252, 88, + 252, 252, 92, 252, 252, 96, 252, 252, 100, 252, 252, 104, + 252, 252, 108, 252, 252, 112, 252, 252, 116, 252, 252, 120, + 252, 252, 124, 252, 252, 124, 252, 252, 128, 252, 252, 132, + 252, 252, 136, 252, 252, 140, 252, 252, 144, 252, 252, 148, + 252, 252, 152, 252, 252, 156, 252, 252, 160, 252, 252, 164, + 252, 252, 168, 252, 252, 168, 252, 252, 172, 252, 252, 176, + 252, 252, 180, 252, 252, 184, 252, 252, 188, 252, 252, 192, + 252, 252, 196, 252, 252, 200, 252, 252, 204, 252, 252, 208, + 252, 252, 208, 252, 252, 212, 252, 252, 216, 252, 252, 220, + 252, 252, 224, 252, 252, 228, 252, 252, 232, 252, 252, 236, + 252, 252, 240, 252, 252, 244, 252, 252, 248, 252, 252, 252 +}; + + unsigned char *screen; + unsigned char *flamebuf_ptr; + unsigned char *flamebuf; + unsigned char temp; + unsigned short int i, j, skip; + unsigned char temp_byte; + + set_paletteX(fire_pal); + set_write_plane(ALL_PLANES); + flamebuf = new unsigned char[BUF_SIZE]; + skip = V_WIDTH; + + // Initialize the video buffer to 0's + memset(flamebuf, 0, BUF_SIZE); + + while (!kbhit()) { + // Transform current buffer + flamebuf_ptr = flamebuf; + i = (BUF_HEIGHT - 2); + while (i--) { + *flamebuf_ptr = (*(flamebuf_ptr + BUF_WIDTH) + + *(flamebuf_ptr + (BUF_WIDTH - 1)) + + *(flamebuf_ptr + (BUF_WIDTH + 1)) + + *(flamebuf_ptr + (BUF_WIDTH * 2))) >> 2; + + flamebuf_ptr += BUF_WIDTH; + temp = *flamebuf_ptr; + if (temp > 11) { + *flamebuf_ptr -= 12; + } else if (temp > 3) { + *flamebuf_ptr -= 4; + } else { + *flamebuf_ptr = 0; + } + flamebuf_ptr += (1 - BUF_WIDTH); + + j = (BUF_WIDTH - 2); + while (j--) { + *flamebuf_ptr = (*(flamebuf_ptr + BUF_WIDTH) + + *(flamebuf_ptr + (BUF_WIDTH - 1)) + + *(flamebuf_ptr + (BUF_WIDTH + 1)) + + *(flamebuf_ptr + (BUF_WIDTH * 2))) >> 2; + + flamebuf_ptr += BUF_WIDTH; + temp = *flamebuf_ptr; + if (temp > 11) { + *flamebuf_ptr -= 12; + } else if (temp > 3) { + *flamebuf_ptr -= 4; + } else { + *flamebuf_ptr = 0; + } + flamebuf_ptr += (1 - BUF_WIDTH); + } + + *flamebuf_ptr = (*(flamebuf_ptr + BUF_WIDTH) + + *(flamebuf_ptr + (BUF_WIDTH - 1)) + + *(flamebuf_ptr + (BUF_WIDTH * 2)) + + *(flamebuf_ptr + (BUF_WIDTH * 2) + + (BUF_WIDTH - 1))) >> 2; + + flamebuf_ptr += BUF_WIDTH; + temp = *flamebuf_ptr; + if (temp > 11) { + *flamebuf_ptr -= 12; + } else if (temp > 3) { + *flamebuf_ptr -= 4; + } else { + *flamebuf_ptr = 0; + } + flamebuf_ptr += (1 - BUF_WIDTH); + } + + // Set new bottom line with random white or black + temp = 0; + flamebuf_ptr = flamebuf + (BUF_WIDTH * (BUF_HEIGHT - 2)); + + j = BUF_WIDTH; + temp = 0; + while (j--) { + // We change the value 1/4 of the time + if ((rand() & 0x03) == 3) { + temp = (255 - temp); + } + + *(flamebuf_ptr + BUF_WIDTH) = temp; + *flamebuf_ptr++ = temp; + } + + // Write the buffer to the screen +// wait_for_retrace(); + screen = RowsX[40]; + flamebuf_ptr = flamebuf; + i = V_HEIGHT; + while (i--) { + j = V_WIDTH; + while (j--) { + temp_byte = *flamebuf_ptr++; + *screen = temp_byte; + screen += skip; + *screen = temp_byte; + screen += skip; + *screen = temp_byte; + screen += skip; + *screen++ = temp_byte; + screen -= REWIND; + } + screen += REWIND; + } + } + + getch(); + + delete flamebuf; +} + + +void +main(void) +{ + FILE *fp; + char ch; + unsigned char pal[768]; + COORD x1, y1, x2, y2; + Iangle theta1, theta2; + Fixed32 trigSin, trigCos; + blitbuf blit_image, sprite_image; + clock_t begin, end; + short int x, y, temp, done; + long i, time1, time2, time3, count, mtime; + BYTE *ptr1; + BYTE *ptr2; + + set320x240x256_X(); + clearX(0); + + getch(); + + temp = loadfontX("vga8x8.fnt"); + + if (temp) { + putstringX(0, 0, "Hello!", 2); + } else { + return; + } + + getch(); + +#if ROTATE_DEMO + get_BIOSpaletteX(pal, 0); + set_paletteX(pal, 0); + + clearX(0); + for (x=0; x < 320; x++) { + for (y=0; y < 240; y++) { + putpixelX(x, y, (x & 0xFF)); + } + } + + getch(); + + while (!kbhit()) { + wait_for_retrace(); + rot_palette(-1); + } + + getch(); +#endif + + load_blitbufPCX("spock.pcx", &blit_image); + scale_blitbuf(160, 100, &blit_image); + aligned_bitblitX(0, 0, &blit_image); + + getch(); + + clearX(0); + + getch(); + + scale_blitbuf(224, 140, &blit_image); + aligned_bitblitX(0, 0, &blit_image); + + getch(); + + greyscale_blitbuf(&blit_image); + grey_paletteX(); + aligned_bitblitX(0, 0, &blit_image); + + getch(); + + clearX(0); + + getch(); + + scale_blitbuf(160, 100, &blit_image); + aligned_bitblitX(0, 0, &blit_image); + + getch(); + + clear_blitbuf(&blit_image); + load_blitbufPCX("spock.pcx", &blit_image); + greyscale_blitbuf(&blit_image); + smooth64_paletteX(1, 0, 1); + aligned_bitblitX(0, 0, &blit_image); + + getch(); + + flip_vertical_blitbuf(&blit_image); + aligned_bitblitX(0, 0, &blit_image); + + getch(); + + clear_blitbuf(&blit_image); + load_blitbufPCX("spock.pcx", &blit_image); + aligned_bitblitX(0, 0, &blit_image); + + done = 0; + while (!done) { + ch = getch(); + switch (ch) { + case 'q': + case 'Q': + done = 1; + break; + + case '+': + brighten_paletteX(1, 1, 1); + break; + + case '-': + brighten_paletteX(-1, -1, -1); + break; + + case '<': + stretch_paletteX(11, 11, 11); + break; + + case '>': + stretch_paletteX(24, 24, 24); + break; + + case 'S': + case 's': + save_blitbufPCX("dump.pcx", &blit_image); + break; + + case 'L': + case 'l': + load_blitbufPCX("spock.pcx", &blit_image); + break; + + case 'R': + brighten_paletteX(1, 0, 0); + break; + + case 'G': + brighten_paletteX(0, 1, 0); + break; + + case 'B': + brighten_paletteX(0, 0, 1); + break; + + case 'r': + brighten_paletteX(-1, 0, 0); + break; + + case 'g': + brighten_paletteX(0, -1, 0); + break; + + case 'b': + brighten_paletteX(0, 0, -1); + break; + + } + } + + clearX(0); + srand(0); + grey_paletteX(); + + begin = clock(); + + for (i=0; i < 10000; i++) { + x1 = rand() % 320; + y1 = rand() % 200; + x2 = rand() % 320; + y2 = rand() % 200; + + lineX(x1, y1, x2, y2, (i & 0x3F)); + } + + end = clock(); + + time1 = (end - begin); + + begin = end; + + for (i=0; i < 10000; i++) { + x1 = rand() % 320; + y1 = rand() % 200; + x2 = rand() % 320; + y2 = rand() % 200; + + temp = ((x1 + x2 + y1 + y2) & 0x3F); + } + + end = clock(); + + time2 = (end - begin); + + getch(); + + for (i=0; i < 120; i++) { + filledboxX(i, i, (319-i), (239-i), (i & 0x3F)); + } + + getch(); + + load_blitbufPCX("buddha.pcx", &sprite_image); + transparent_bitblitX(100, 100, &sprite_image); + + getch(); + + clearX(0); + clear_blitbuf(&blit_image); + scale_blitbuf(152, 168, &sprite_image); + alloc_blitbuf(&blit_image, 152, 168); + + // 152x168 image + aligned_bitblitX(84, 36, &sprite_image); + getch(); + + initFixed32(); + + theta1=0; + count=0; + + begin = clock(); + + while (!kbhit()) { + ptr1 = sprite_image.image; + ptr2 = blit_image.image; + theta2 = theta1; + + y=168; + while (y--) { + CosSin(theta2, &trigCos, &trigSin); + scale_scanline(ptr1, ptr2, 152, 152, (trigCos >> 10) + 88); +#if 0 + memcpy(ptr2+152, ptr2, 152); + ptr1 += 304; + ptr2 += 304; + theta2 += 4; + y--; +#else + ptr1 += 152; + ptr2 += 152; + theta2 += 2; +#endif + } + + theta1 += 2; + + aligned_bitblitX(84, 36, &blit_image); + count++; + } + + end = clock(); + + getch(); + getch(); + + clear_blitbuf(&blit_image); + clear_blitbuf(&sprite_image); + +#if FIRE_DEMO + clearX(0); + fire_demo(); +#endif + +#if MONSTER_DEMO_ONE + mtime = monster_demo1(); +#endif + +#if MONSTER_DEMO_TWO + monster_demo2(); +#endif + + set80x25(); + +#if MATH_DEMO + Fixed32 c1, c2, c3, a1, a2, a3; + + c1 = INT_TO_FIXED(50); + c2 = INT_TO_FIXED(70); + c3 = INT_TO_FIXED(50 * 70); + + a1 = FixedMul(c1, c2); + a2 = FixedMulASM(c1, c2); + + printf("MUL C version = %d\n", FIXED_TO_INT(a1)); + printf("MUL ASM version = %d\n", FIXED_TO_INT(a2)); + + getch(); + + a1 = FixedDiv(c3, c1); + a2 = FixedDivASM(c3, c1); + + printf("DIV C version = %d\n", FIXED_TO_INT(a1)); + printf("DIV ASM version = %d\n", FIXED_TO_INT(a2)); + + getch(); +#endif + + temp = (time1 - time2); + printf("10000 lines took %4d ticks\n", time1); + printf("rand() overhead = %4d ticks\n", time2); + printf("Time in lineX = %4d ticks\n", temp); + printf("%d lines per second!\n\n", (10000 * 1000) / (55 * temp)); + + temp = (end-begin); + printf("Buddha = %4d blits\n", count); + printf(" = %4d per second\n", (count * 1000) / (55 * temp)); + printf("Buddha = %4d scanline stretches\n", (count * 168)); + printf(" = %4d per second!\n\n", (count * 168000) / (55 * temp)); + + printf("Monster took %d ticks for 99 frames\n", mtime); +} + diff --git a/16/w_modex/TEST.EXE b/16/w_modex/TEST.EXE new file mode 100644 index 00000000..c130bf50 Binary files /dev/null and b/16/w_modex/TEST.EXE differ diff --git a/16/w_modex/VGA8X8.FNT b/16/w_modex/VGA8X8.FNT new file mode 100644 index 00000000..d2bcc392 Binary files /dev/null and b/16/w_modex/VGA8X8.FNT differ diff --git a/16/w_modex/XBLITBUF.CPP b/16/w_modex/XBLITBUF.CPP new file mode 100644 index 00000000..98528326 --- /dev/null +++ b/16/w_modex/XBLITBUF.CPP @@ -0,0 +1,1027 @@ +#include +#include +#include + +#include "xtypes.hpp" +#include "modex.hpp" +#include "xpal.hpp" +#include "xblitbuf.hpp" + +#define SEQU_ADDR 0x3C4 +#define GRACON_ADDR 0x3CE + + +void +clear_blitbuf(blitbuf *buf) +{ + buf->xsize = 0; + buf->ysize = 0; + + delete buf->image; +} + + +void +fill_blitbuf(BYTE color, blitbuf *buf) +{ + memset(buf->image, color, buf->xsize * buf->ysize); +} + + +void +alloc_blitbuf(blitbuf *buf, DIST xsize, DIST ysize) +{ + buf->xsize = xsize; + buf->ysize = ysize; + buf->image = new BYTE[xsize * ysize]; +} + + +void +lin_2_pln_blitbuf(blitbuf *buf) +{ + int i, j, size; + BYTE *oldbuf; + BYTE *newbuf; + BYTE *src_ptr; + BYTE *dest_ptr; + + oldbuf = buf->image; + + size = (buf->xsize * buf->ysize); + newbuf = new BYTE[size]; + size = (size >> 2); + + dest_ptr = newbuf; + + for (i=0; i < 4; i++) { + src_ptr = oldbuf + i; + + j=size; + while (j--) { + *dest_ptr++ = *src_ptr; + src_ptr += 4; + } + } + + buf->image = newbuf; + delete oldbuf; +} + + +void +pln_2_lin_blitbuf(blitbuf *buf) +{ + int i, j, size; + BYTE *oldbuf; + BYTE *newbuf; + BYTE *src_ptr; + BYTE *dest_ptr; + + oldbuf = buf->image; + + size = (buf->xsize * buf->ysize); + newbuf = new BYTE[size]; + size = (size >> 2); + + src_ptr = oldbuf; + for (i=0; i < 4; i++) { + dest_ptr = newbuf + i; + + j=size; + while (j--) { + *dest_ptr = *src_ptr++; + dest_ptr += 4; + } + } + + buf->image = newbuf; + delete oldbuf; +} + + +void +vanilla_bitblitX(COORD x, COORD y, blitbuf *buf) +{ + short int ysize, plane, i, j, loop, skip, rewind, len; + short int xsize[4]; + BYTE *base_vga; + BYTE *vga_ptr; + BYTE *buf_ptr; + + // Length of bitmap in each plane + plane = (x & 3); + i = buf->xsize + plane - 1; + xsize[0] = ((i--) >> 2); + xsize[1] = ((i--) >> 2); + xsize[2] = ((i--) >> 2); + xsize[3] = (i >> 2) + 1; + + for (i=plane; i < 3; i++) { + xsize[i]++; + } + + ysize = buf->ysize; + base_vga = RowsX[y] + (x >> 2) + activeStart; + write_plane = -1; + + for (loop = 0; loop < 4; loop++) { + len = xsize[plane]; + rewind = buf->xsize - (len << 2); + skip = widthBytes - len; + buf_ptr = buf->image + loop; + vga_ptr = base_vga; + + outpw(SEQU_ADDR, plane_mask[plane++]); + if (plane == 4) { + plane = 0; + base_vga++; + } + + i=ysize; + while (i--) { + j=len; + while (j--) { + *vga_ptr++ = *buf_ptr; + buf_ptr += 4; + } + + buf_ptr += rewind; + vga_ptr += skip; + } + } +} + + +void +vanilla_getblitX(COORD x, COORD y, blitbuf *buf) +{ + // Do nothing +} + + +void +aligned_bitblitX(COORD x, COORD y, blitbuf *buf) +{ + short int i, j, plane, skip, xsize, ysize; + BYTE *base_vga; + BYTE *vga_ptr; + BYTE *buf_ptr; + + xsize = (buf->xsize >> 2); + ysize = buf->ysize; + skip = widthBytes - xsize; + base_vga = RowsX[y] + (x >> 2) + activeStart; + + for (plane=0; plane < 4; plane++) { + buf_ptr = buf->image + plane; + vga_ptr = base_vga; + + outpw(SEQU_ADDR, plane_mask[plane]); + + i=ysize; + while (i--) { + j=xsize; + while (j--) { + *vga_ptr++ = *buf_ptr; + buf_ptr += 4; + } + vga_ptr += skip; + } + } + + write_plane = 3; +} + + +void +aligned_getblitX(COORD x, COORD y, blitbuf *buf) +{ + short int i, j, plane, skip, xsize, ysize; + BYTE *base_vga; + BYTE *vga_ptr; + BYTE *buf_ptr; + + xsize = (buf->xsize >> 2); + ysize = buf->ysize; + skip = widthBytes - xsize; + base_vga = RowsX[y] + (x >> 2) + activeStart; + + for (plane=0; plane < 4; plane++) { + buf_ptr = buf->image + plane; + vga_ptr = base_vga; + + outpw(GRACON_ADDR, read_mask[plane]); + + i=ysize; + while (i--) { + j=xsize; + while (j--) { + *buf_ptr = *vga_ptr++; + buf_ptr += 4; + } + vga_ptr += skip; + } + } + + read_plane = 3; +} + + +void +transparent_bitblitX(COORD x, COORD y, blitbuf *buf) +{ + short int i, j, plane, skip, xsize, ysize; + BYTE *base_vga; + BYTE *vga_ptr; + BYTE *buf_ptr; + + xsize = (buf->xsize >> 2); + ysize = buf->ysize; + skip = widthBytes - xsize; + base_vga = RowsX[y] + (x >> 2) + activeStart; + + for (plane=0; plane < 4; plane++) { + buf_ptr = buf->image + plane; + vga_ptr = base_vga; + + outpw(SEQU_ADDR, plane_mask[plane]); + + i=ysize; + while (i--) { + j=xsize; + while (j--) { + if (*buf_ptr) { + *vga_ptr = *buf_ptr; + } + vga_ptr++; + buf_ptr += 4; + } + vga_ptr += skip; + } + } + + write_plane = 3; +} + + +void +planar_bitblitX(COORD x, COORD y, blitbuf *buf) +{ + short int i, plane, xsize, ysize; + BYTE *base_vga; + BYTE *vga_ptr; + BYTE *buf_ptr; + + xsize = (buf->xsize >> 2); + ysize = buf->ysize; + base_vga = RowsX[y] + (x >> 2) + activeStart; + buf_ptr = buf->image; + + for (plane=0; plane < 4; plane++) { + vga_ptr = base_vga; + + outpw(SEQU_ADDR, plane_mask[plane]); + + i=ysize; + while (i--) { + memcpy(vga_ptr, buf_ptr, xsize); + vga_ptr += widthBytes; + buf_ptr += xsize; + } + } + + write_plane = 3; +} + + +void +planar_getblitX(COORD x, COORD y, blitbuf *buf) +{ + short int i, plane, xsize, ysize; + BYTE *base_vga; + BYTE *vga_ptr; + BYTE *buf_ptr; + + xsize = (buf->xsize >> 2); + ysize = buf->ysize; + base_vga = RowsX[y] + (x >> 2) + activeStart; + buf_ptr = buf->image; + + for (plane=0; plane < 4; plane++) { + vga_ptr = base_vga; + + outpw(GRACON_ADDR, read_mask[plane]); + + i=ysize; + while (i--) { + memcpy(buf_ptr, vga_ptr, xsize); + vga_ptr += widthBytes; + buf_ptr += xsize; + } + } + + read_plane = 3; +} + + +void +wide_bitblitX(COORD y, blitbuf *buf) +{ + short int bufsize; + BYTE *vga_ptr; + BYTE *buf_ptr; + + write_plane = 3; + buf_ptr = buf->image; + vga_ptr = RowsX[y] + activeStart; + bufsize = (buf->ysize * widthBytes); + + outpw(SEQU_ADDR, PLANE_0); + memcpy(vga_ptr, buf_ptr, bufsize); + buf_ptr += bufsize; + + outpw(SEQU_ADDR, PLANE_1); + memcpy(vga_ptr, buf_ptr, bufsize); + buf_ptr += bufsize; + + outpw(SEQU_ADDR, PLANE_2); + memcpy(vga_ptr, buf_ptr, bufsize); + buf_ptr += bufsize; + + outpw(SEQU_ADDR, PLANE_3); + memcpy(vga_ptr, buf_ptr, bufsize); +} + + +void +wide_getblitX(COORD y, blitbuf *buf) +{ + short int bufsize; + BYTE *vga_ptr; + BYTE *buf_ptr; + + read_plane = 3; + buf_ptr = buf->image; + vga_ptr = RowsX[y] + activeStart; + bufsize = (buf->ysize * widthBytes); + + outpw(GRACON_ADDR, READ_PLANE_0); + memcpy(buf_ptr, vga_ptr, bufsize); + buf_ptr += bufsize; + + outpw(GRACON_ADDR, READ_PLANE_1); + memcpy(buf_ptr, vga_ptr, bufsize); + buf_ptr += bufsize; + + outpw(GRACON_ADDR, READ_PLANE_2); + memcpy(buf_ptr, vga_ptr, bufsize); + buf_ptr += bufsize; + + outpw(GRACON_ADDR, READ_PLANE_3); + memcpy(buf_ptr, vga_ptr, bufsize); +} + + +void +save_blitbufPCX(char *fname, blitbuf *buf) +{ + FILE *fp; + unsigned int i, size, temp_int; + BYTE VGA_pal[768]; + BYTE *buf_ptr; + BYTE temp_char, match, count; + + fp = fopen(fname, "wb"); + + if (fp != NULL) { + // Write manufacturer's byte + temp_char = 10; + fwrite(&temp_char, 1, 1, fp); + + // Write version of PCX. 5 = 256 color (PCX Version 5.0) + temp_char = 5; + fwrite(&temp_char, 1, 1, fp); + + // Write encoding type, always 1 for RLE. + temp_char = 1; + fwrite(&temp_char, 1, 1, fp); + + // Write bits_per_pixel = 8. + temp_char = 8; + fwrite(&temp_char, 1, 1, fp); + + // Write starting X and Y coords + temp_int = 0; + fwrite(&temp_int, 2, 1, fp); + fwrite(&temp_int, 2, 1, fp); + + // Write X size + temp_int = (buf->xsize - 1); + fwrite(&temp_int, 2, 1, fp); + + // Write Y size + temp_int = (buf->ysize - 1); + fwrite(&temp_int, 2, 1, fp); + + // Do HRES and VRES ** + temp_int = buf->xsize; + fwrite(&temp_int, 2, 1, fp); + temp_int = buf->ysize; + fwrite(&temp_int, 2, 1, fp); + + // Write 16 color palette, not used. + temp_int = 0; + i=24; + while (i--) { + fwrite(&temp_int, 2, 1, fp); + } + + // Write vmode byte. + temp_char = 0; + fwrite(&temp_char, 1, 1, fp); + + // Write bit_planes + temp_char = 1; + fwrite(&temp_char, 1, 1, fp); + + // Write bytes_per_line + temp_int = buf->xsize; + fwrite(&temp_int, 2, 1, fp); + + // Write palette type + temp_int = 1; + fwrite(&temp_int, 2, 1, fp); + + // Write junk filler + temp_int = 0; + i=29; + while (i--) { + fwrite(&temp_int, 2, 1, fp); + } + + // Write the actual image + buf_ptr = buf->image; + size = (buf->xsize * buf->ysize); + + count = 0; + match = *buf_ptr; + + i=size; + while (i--) { + temp_char = *buf_ptr++; + + if ((temp_char == match) && (count < 63)) { + count++; + } else { + if ((count == 1) && (match < 192)) { + // Write single byte + fwrite(&match,1,1,fp); + } else { + // Write run of pixels + count += 192; + fwrite(&count, 1, 1, fp); + fwrite(&match, 1, 1, fp); + } + count = 1; + match = temp_char; + } + } + + if ((count == 1) && (match < 192)) { + // Write single byte + fwrite(&match,1,1,fp); + } else { + // Write run of pixels + count += 192; + fwrite(&count, 1, 1, fp); + fwrite(&match, 1, 1, fp); + } + + // Write palette verification byte + temp_char = 12; + fwrite(&temp_char, 1, 1, fp); + + get_paletteX(VGA_pal); + + // Write 256 color palette + fwrite(VGA_pal, 1, 768, fp); + + fclose(fp); + } +} + + +int +load_blitbufPCX(char *fname, blitbuf *buf) +{ + FILE *fp; + int size; + BYTE VGA_pal[768]; + BYTE PCX_byte, RLE_byte; + BYTE *buf_ptr; + BYTE *end_of_buf; + + fp = fopen(fname, "rb"); + + if (fp == NULL) { + buf->xsize = 0; + buf->ysize = 0; + buf->image = NULL; + return 0; + } else { + fseek(fp, 8, SEEK_SET); + fread(&buf->xsize, 2, 1, fp); + fread(&buf->ysize, 2, 1, fp); + + buf->xsize++; + buf->ysize++; + + size = (buf->xsize * buf->ysize); + + buf->image = new BYTE[size]; + buf_ptr = buf->image; + end_of_buf = buf_ptr + size; + + // Load 256 color PCX palette + fseek(fp, -768, SEEK_END); + fread(VGA_pal, 1, 768, fp); + + set_paletteX(VGA_pal); + + fseek(fp, 128, SEEK_SET); + + while (buf_ptr < end_of_buf) { + // Read next packet + fread(&PCX_byte, 1, 1, fp); + + if (PCX_byte < 192) { + // Raw Pixel + *buf_ptr++ = PCX_byte; + } else { + // RLE Pixels + PCX_byte = PCX_byte & 0x3F; + fread(&RLE_byte, 1, 1, fp); + memset(buf_ptr, RLE_byte, PCX_byte); + buf_ptr += PCX_byte; + } + } + + fclose(fp); + return 1; + } +} + + +void +scale_blitbuf(DIST dest_x, DIST dest_y, blitbuf *buf1, blitbuf *buf2) +{ + unsigned long ErrorAccX, ErrorAccY, ErrorAdjX, ErrorAdjY; + DIST oldx, oldy, newx, newy; + short int i, j, count; + BYTE *src_base; + BYTE *src_ptr; + BYTE *dest_ptr; + BYTE *newbuf; + + oldx = buf1->xsize; + oldy = buf1->ysize; + newx = dest_x; + newy = dest_y; + + newbuf = new BYTE[newx * newy]; + + src_base = buf1->image; + dest_ptr = newbuf; + + // My bitmap scaling routine. As you probably noticed, it's + // pretty Bresenhammy! + + ErrorAccY = 0x8000; + + if (newx > oldx) { + // Biggering + ErrorAdjX = ((((unsigned long)newx) << 16) / + (((unsigned long)oldx))); + + ErrorAdjY = ((((unsigned long)newy) << 16) / + (((unsigned long)oldy))); + + i=oldy; + while (i--) { + ErrorAccX = 0x8000; + src_ptr = src_base; + + j=oldx; + while (j--) { + ErrorAccX += ErrorAdjX; + if (count = (ErrorAccX >> 16)) { + ErrorAccX &= 0xFFFFL; + while (count--) { + *dest_ptr++ = *src_ptr; + } + } + src_ptr++; + } + + ErrorAccY += ErrorAdjY; + count = (ErrorAccY >> 16) - 1; + while (count--) { + memcpy(dest_ptr, dest_ptr - newx, newx); + dest_ptr += newx; + } + ErrorAccY &= 0xFFFFL; + src_base += oldx; + } + } else { + // Smallering + ErrorAdjX = ((((unsigned long)oldx) << 16) / + (((unsigned long)newx))); + + ErrorAdjY = ((((unsigned long)oldy) << 16) / + (((unsigned long)newy))); + + i=newy; + while (i--) { + ErrorAccX = 0x8000; + src_ptr = src_base; + + j=newx; + while (j--) { + *dest_ptr++ = *src_ptr; + ErrorAccX += ErrorAdjX; + src_ptr += (ErrorAccX >> 16); + ErrorAccX &= 0xFFFFL; + } + + ErrorAccY += ErrorAdjY; + src_base += (oldx * (ErrorAccY >> 16)); + ErrorAccY &= 0xFFFFL; + } + } + + if (buf2 == NULL) { + delete buf1->image; + buf1->xsize = newx; + buf1->ysize = newy; + buf1->image = newbuf; + } else { + if (buf2->image != NULL) { + delete buf2->image; + } + buf2->xsize = newx; + buf2->ysize = newy; + buf2->image = newbuf; + } +} + + +void +vertical_scale_blitbuf(DIST dest_y, blitbuf *buf1, blitbuf *buf2) +{ + unsigned long ErrorAccY, ErrorAdjY; + DIST xsize, oldy, newy; + short int i, count; + BYTE *src_ptr; + BYTE *dest_ptr; + BYTE *newbuf; + + xsize = buf1->xsize; + oldy = buf1->ysize; + newy = dest_y; + + newbuf = new BYTE[xsize * newy]; + + src_ptr = buf1->image; + dest_ptr = newbuf; + + // My bitmap scaling routine. As you probably noticed, it's + // pretty Bresenhammy! + + ErrorAccY = 0x8000; + ErrorAdjY = ((((unsigned long)newy) << 16) / + (((unsigned long)oldy))); + + if (newy >= oldy) { + // Biggering + i=oldy; + while (i--) { + ErrorAccY += ErrorAdjY; + if (count = (ErrorAccY >> 16)) { + ErrorAccY &= 0xFFFFL; + + while (count--) { + memcpy(dest_ptr, src_ptr, xsize); + dest_ptr += xsize; + } + } + + src_ptr += xsize; + } + } else { + // Smallering + i=oldy; + while (i--) { + ErrorAccY += ErrorAdjY; + if (ErrorAccY & ~0xFFFFL) { + ErrorAccY &= 0xFFFFL; + memcpy(dest_ptr, src_ptr, xsize); + dest_ptr += xsize; + } + + src_ptr += xsize; + } + } + + if (buf2 == NULL) { + delete buf1->image; + buf1->ysize = newy; + buf1->image = newbuf; + } else { + if (buf2->image != NULL) { + delete buf2->image; + } + buf2->xsize = xsize; + buf2->ysize = newy; + buf2->image = newbuf; + } +} + + +void +greyscale_blitbuf(blitbuf *buf) +{ + BYTE temp_pal[768]; + BYTE *buf_ptr; + BYTE *temp; + BYTE r, g; + unsigned int i; + + buf_ptr = buf->image; + + get_paletteX(temp_pal, 0); + + for (i = (buf->xsize * buf->ysize); i; i--) { + temp = temp_pal + ((*buf_ptr) * 3); + r = *temp++; + g = *temp++; + + *buf_ptr++ = ((r * 19) + (g * 37) + (*temp << 3)) >> 6; + } +} + + +void +RGB_blitbuf(blitbuf *buf) +{ + BYTE temp_pal[768]; + BYTE *buf_ptr; + BYTE *temp; + BYTE r, g, b; + unsigned int i; + + buf_ptr = buf->image; + + get_paletteX(temp_pal, 0); + + for (i = (buf->xsize * buf->ysize); i; i--) { + temp = temp_pal + ((*buf_ptr) * 3); + r = (*temp) + 4; + temp++; + g = (*temp) + 4; + temp++; + b = (*temp) + 8; + + *buf_ptr++ = ((r >> 3) << 5) + ((g >> 3) << 2) + (b >> 4); + } +} + + +void +flip_vertical_blitbuf(blitbuf *buf) +{ + BYTE *top; + BYTE *bottom; + BYTE *temp; + DIST i, x, y;; + + x = buf->xsize; + y = buf->ysize; + + temp = new BYTE[x]; + + top = buf->image; + bottom = buf->image + (x * (y-1)); + + i = (y >> 1); + while (i--) { + memcpy(temp, top, x); + memcpy(top, bottom, x); + memcpy(bottom, temp, x); + top += x; + bottom -= x; + } + + delete temp; +} + + +void +flip_horizontal_blitbuf(blitbuf *buf) +{ + BYTE *buf_ptr; + BYTE *temp_ptr; + BYTE *temp; + DIST i, j, x; + + x = buf->xsize; + + temp = new BYTE[x]; + + buf_ptr = buf->image; + + i = buf->ysize; + while (i--) { + memcpy(temp, buf_ptr, x); + temp_ptr = temp + (x - 1); + j=x; + while (j--) { + *buf_ptr++ = *temp_ptr--; + } + } + + delete temp; +} + + +void +brighten_blitbuf(SBYTE factor, blitbuf *buf) +{ + BYTE *buf_ptr; + short int scratch; + unsigned int i; + + buf_ptr = buf->image; + + for (i = (buf->xsize * buf->ysize); i; i--) { + scratch = (*buf_ptr + factor); + if (scratch <= 0) { + *buf_ptr++ = 0; + } else if (scratch >= 63) { + *buf_ptr++ = 63; + } else { + *buf_ptr++ = scratch; + } + } +} + + +void +stretch_blitbuf(BYTE factor, blitbuf *buf) +{ + BYTE *buf_ptr; + short int scratch; + unsigned int i; + + buf_ptr = buf->image; + + for (i = (buf->xsize * buf->ysize); i; i--) { + scratch = ((((*buf_ptr - 32) * factor) + 8) >> 4) + 32; + if (scratch <= 0) { + *buf_ptr++ = 0; + } else if (scratch >= 63) { + *buf_ptr++ = 63; + } else { + *buf_ptr++ = scratch; + } + } +} + + +void +pixelize(DIST pixfactor, blitbuf *buf) +{ + // Do nothing +} + + +void +GREYconvolve_blitbuf(BYTE *kernel, blitbuf *buf) +{ + // Do nothing +} + + +void +RGBconvolve_blitbuf(BYTE *kernel, blitbuf *buf) +{ + // Do nothing +} + + +void +scale_scanline(BYTE *source, BYTE *dest, DIST smap_size, DIST dmap_size, + DIST dline_size) +{ + unsigned long ErrorAcc, ErrorAdj; + short int i, temp, invert; + + ErrorAcc = 0x8000; + + // Prepare for backwards scanlines + if (dline_size >= 0) { + invert = 0; + } else { + invert = 1; + dline_size = -dline_size; + } + + if (dline_size > smap_size) { + // Biggering + if (smap_size == 0) { + return; + } + ErrorAdj = ((((unsigned long)dline_size) << 16) / + (((unsigned long)smap_size))); + + i=smap_size; + while (i--) { + ErrorAcc += ErrorAdj; + temp = (ErrorAcc >> 16); + ErrorAcc &= 0xFFFFL; + while (temp--) { + *dest++ = *source; + } + source++; + } + } else { + // Smallering + if (dline_size == 0) { + memset(dest, 0, dmap_size); + } else { + temp = dmap_size - dline_size; + i = temp >> 1; + temp -= i; + while (i--) { + *dest++ = 0; + } + + ErrorAdj = ((((unsigned long)smap_size) << 16) / + (((unsigned long)dline_size))); + + i=dline_size; + + while (i--) { + *dest++ = *source; + ErrorAcc += ErrorAdj; + source += (ErrorAcc >> 16); + ErrorAcc &= 0xFFFFL; + } + + while (temp--) { + *dest++ = 0; + } + } + } +} + + +int +load_blitbufRAW(char *rawname, char *palname, blitbuf *buf) +{ + FILE *fp; + BYTE VGA_pal[768]; + + fp = fopen(rawname, "rb"); + + if (fp == NULL) { + buf->xsize = 0; + buf->ysize = 0; + buf->image = NULL; + return 0; + } else { + buf->xsize = 320; + buf->ysize = 200; + buf->image = new BYTE[64000L]; + + // Load image + fread(buf->image, 64000L, 1, fp); + + if (palname == NULL) { + fread(VGA_pal, 1, 768, fp); + set_paletteX(VGA_pal); + fclose(fp); + } else { + fclose(fp); + fp = fopen(palname, "rb"); + if (fp != NULL) { + fread(VGA_pal, 1, 768, fp); + set_paletteX(VGA_pal); + fclose(fp); + } + } + + return 1; + } +} + diff --git a/16/w_modex/XBLITBUF.HPP b/16/w_modex/XBLITBUF.HPP new file mode 100644 index 00000000..9907c5f3 --- /dev/null +++ b/16/w_modex/XBLITBUF.HPP @@ -0,0 +1,58 @@ +#ifndef X_BLITBUF_HPP + #define X_BLITBUF_HPP + +// Basic BlitBuf functions +void clear_blitbuf(blitbuf *buf); +void fill_blitbuf(BYTE color, blitbuf *buf); +void alloc_blitbuf(blitbuf *buf, DIST xsize, DIST ysize); +void lin_2_pln_blitbuf(blitbuf *buf); +void pln_2_lin_blitbuf(blitbuf *buf); + +// Adjust color in blitbuf +void greyscale_blitbuf(blitbuf *buf); +void RGB_blitbuf(blitbuf *buf); +void brighten_blitbuf(SBYTE factor, blitbuf *buf); +void stretch_blitbuf(BYTE factor, blitbuf *buf); // factor = 1/16 units + +// Image processing: These expect a linear blitbuf +void scale_blitbuf(DIST dest_x, DIST dest_y, + blitbuf *buf1, blitbuf *buf2 = NULL); +void vertical_scale_blitbuf(DIST dest_y, blitbuf *buf1, blitbuf *buf2 = NULL); +void flip_vertical_blitbuf(blitbuf *buf); +void flip_horizontal_blitbuf(blitbuf *buf); +void pixelize(DIST pixfactor, blitbuf *buf); // Not written yet +void scale_scanline(BYTE *source, BYTE *dest, DIST smap_size, + DIST dmap_size, DIST dline_size); + +// Image Convolution by a 3x3 kernel (linear) +void GREYconvolve_blitbuf(BYTE *kernel, blitbuf *buf); // Not written yet +void RGBconvolve_blitbuf(BYTE *kernel, blitbuf *buf); // Not written yet + +// Vanilla blits can be any size, anywhere +void vanilla_bitblitX(COORD x, COORD y, blitbuf *buf); +void vanilla_getblitX(COORD x, COORD y, blitbuf *buf); + +// Transparent blits must be aligned and 0 is the "transparent" value +void transparent_bitblitX(COORD x, COORD y, blitbuf *buf); + +// Aligned blits must have X and XSIZE evenly divisible by 4 +void aligned_bitblitX(COORD x, COORD y, blitbuf *buf); +void aligned_getblitX(COORD x, COORD y, blitbuf *buf); + +// Planar blits must be aligned and also be ordered in 4-planar fashion +void planar_bitblitX(COORD x, COORD y, blitbuf *buf); +void planar_getblitX(COORD x, COORD y, blitbuf *buf); + +// Wide blits must be planar and are assumed to be as wide as the screen +void wide_bitblitX(COORD y, blitbuf *buf); +void wide_getblitX(COORD y, blitbuf *buf); + +// PCX functions +void save_blitbufPCX(char *fname, blitbuf *buf); +int load_blitbufPCX(char *fname, blitbuf *buf); + +// RAW file functions (320x200 only) +int load_blitbufRAW(char *rawname, char *palname, blitbuf *buf); + +#endif + diff --git a/16/w_modex/XPAL.CPP b/16/w_modex/XPAL.CPP new file mode 100644 index 00000000..b052855f --- /dev/null +++ b/16/w_modex/XPAL.CPP @@ -0,0 +1,265 @@ +#include +#include +#include + +#include "modex.hpp" +#include "xpal.hpp" + +BYTE Xpal[768]; + +void +set_paletteX(BYTE *pal, FLAG downgrade) +{ + short int i; + BYTE *buf; + + memcpy(Xpal, pal, 768); + + buf = Xpal; + if (downgrade) { + i=768; + while (i--) { + *buf++ = (*buf >> 2); + } + } + + outp(0x03c8, 0); // Start with color 0 + buf = Xpal; + i=256; + while (i--) { + outp(0x03c9, *buf++); + outp(0x03c9, *buf++); + outp(0x03c9, *buf++); + } +} + + +void +get_paletteX(BYTE *pal, FLAG upgrade) +{ + int i; + + memcpy(pal, Xpal, 768); + + if (upgrade) { + i=768; + while (i--) { + *pal++ = (*pal << 2); + } + } +} + + +void +get_BIOSpaletteX(BYTE *pal, FLAG upgrade) +{ + int i; + union REGS r; + + r.x.eax = 0x1017; + r.x.ebx = 0; + r.x.ecx = 256; + r.x.edx = (unsigned long) pal; + + int386(0x10, &r, &r); + + if (upgrade) { + i=768; + while (i--) { + *pal++ = (*pal << 2); + } + } +} + + +void +photo_negativeX(void) +{ + short int i; + BYTE temp_pal[768]; + BYTE *temp; + + get_paletteX(temp_pal, 0); + temp = temp_pal; + + for (i=0; i < 256; i++) { + *temp++ = (64 - (*temp)); + *temp++ = (64 - (*temp)); + *temp++ = (64 - (*temp)); + } + + set_paletteX(temp_pal, 0); +} + + +void +grey_paletteX(void) +{ + smooth64_paletteX(1, 1, 1); +} + + +void +RGB_paletteX(void) +{ + BYTE r, g, b; + BYTE temp_pal[768]; + BYTE *temp; + + temp = temp_pal; + + for (r=0; r < 8; r++) { + for (g=0; g < 8; g++) { + for (b=0; b < 4; b++) { + *temp++ = (r << 3); + *temp++ = (g << 3); + *temp++ = (b << 4); + } + } + } + + set_paletteX(temp_pal, 0); +} + + +void +smooth64_paletteX(BYTE r, BYTE g, BYTE b) +{ + short int i; + BYTE temp_pal[768]; + BYTE *temp; + + memset(temp_pal, 0, 768); + + + if (r) { + temp = temp_pal; + for (i=0; i < 64; i++) { + *temp = i; + temp += 3; + } + } + + if (g) { + temp = temp_pal + 1; + for (i=0; i < 64; i++) { + *temp = i; + temp += 3; + } + } + + if (b) { + temp = temp_pal + 2; + for (i=0; i < 64; i++) { + *temp = i; + temp += 3; + } + } + + set_paletteX(temp_pal, 0); +} + + +void +brighten_paletteX(SBYTE r, SBYTE g, SBYTE b) +{ + short int i, j, scratch; + BYTE temp_pal[768]; + BYTE *temp; + SBYTE dummy[3]; + + get_paletteX(temp_pal, 0); + temp = temp_pal; + + dummy[0] = r; + dummy[1] = g; + dummy[2] = b; + + for (i=0; i < 256; i++) { + for (j=0; j < 3; j++) { + scratch = *temp + dummy[j]; + if (scratch <= 0) { + *temp++ = 0; + } else if (scratch >= 63) { + *temp++ = 63; + } else { + *temp++ = scratch; + } + } + } + + set_paletteX(temp_pal, 0); +} + + +void +stretch_paletteX(BYTE r, BYTE g, BYTE b) +{ + short int i, j, scratch; + BYTE temp_pal[768]; + BYTE *temp; + BYTE dummy[3]; + + get_paletteX(temp_pal, 0); + temp = temp_pal; + + dummy[0] = r; + dummy[1] = g; + dummy[2] = b; + + for (i=0; i < 256; i++) { + for (j=0; j < 3; j++) { + scratch = ((((*temp - 32) * dummy[j]) + 8) >> 4) + 32; + if (scratch <= 0) { + *temp++ = 0; + } else if (scratch >= 63) { + *temp++ = 63; + } else { + *temp++ = scratch; + } + } + } + + set_paletteX(temp_pal, 0); +} + + +void +rot_palette(BYTE dist) +{ + int shift, i; + BYTE temp_pal[768]; + + shift = (dist * 3); + memcpy(temp_pal, Xpal + shift, 768 - shift); + memcpy(temp_pal + (768 - shift), Xpal, shift); + + set_paletteX(temp_pal, 0); +} + + +BYTE +find_RGB(BYTE r, BYTE g, BYTE b) +{ + long shortest_dist, temp_dist; + short int i, shortest_pal; + + shortest_pal = 0; + shortest_dist = (r - Xpal[0]) * (r - Xpal[0]) + + (g - Xpal[1]) * (g - Xpal[1]) + + (b - Xpal[2]) * (b - Xpal[2]); + + for (i=1; i < 256; i++) { + temp_dist = (r - Xpal[(i * 3) + 0]) * (r - Xpal[(i * 3) + 0]) + + (g - Xpal[(i * 3) + 1]) * (g - Xpal[(i * 3) + 1]) + + (b - Xpal[(i * 3) + 2]) * (b - Xpal[(i * 3) + 2]); + + if (temp_dist < shortest_dist) { + shortest_dist = temp_dist; + shortest_pal = i; + } + } + + return i; +} + diff --git a/16/w_modex/XPAL.HPP b/16/w_modex/XPAL.HPP new file mode 100644 index 00000000..a04dd48c --- /dev/null +++ b/16/w_modex/XPAL.HPP @@ -0,0 +1,24 @@ +#ifndef X_PALETTE_HPP + #define X_PALETTE_HPP + +#include "xtypes.hpp" + +// Palette setting/getting functions +void set_paletteX(BYTE *pal, FLAG downgrade = 1); +void get_paletteX(BYTE *pal, FLAG upgrade = 1); +void get_BIOSpaletteX(BYTE *pal, FLAG upgrade = 1); + +// Palette adjusting functions +void photo_negativeX(void); +void grey_paletteX(void); +void RGB_paletteX(void); +void smooth64_paletteX(BYTE r, BYTE g, BYTE b); +void brighten_paletteX(SBYTE r, SBYTE g, SBYTE b); +void stretch_paletteX(BYTE r, BYTE g, BYTE b); // 1/16 units + +// Misc palette functions +void rot_palette(BYTE distance); +BYTE find_RGB(BYTE r, BYTE g, BYTE b); + +#endif + diff --git a/16/w_modex/XPRIM.CPP b/16/w_modex/XPRIM.CPP new file mode 100644 index 00000000..66e2f72a --- /dev/null +++ b/16/w_modex/XPRIM.CPP @@ -0,0 +1,561 @@ +#include +#include +#include +#include + +#include "modex.hpp" +#include "xprim.hpp" + +#define SEQU_ADDR 0x3C4 +#define GRACON_ADDR 0x3CE +#define CRTC_ADDR 0x3D4 +#define STATUS_ADDR 0x3DA + +BYTE Xfont[2048]; + + +void +wait_for_retrace(void) +{ + while (!(inp(STATUS_ADDR) & 0x08)); +} + + +void +setDrawPage(unsigned int page) +{ + activeStart = page_offset[page]; +} + + +void +setVisiblePage(unsigned int page) +{ + // setVisibleStart() tells the VGA from which byte to fetch the first + // pixel when starting refresh at the top of the screen. + visibleStart = page_offset[page]; + + // set high byte + outpw(CRTC_ADDR, page_mask_high[page]); + + // set low byte + outpw(CRTC_ADDR, page_mask_low[page]); +} + + +void +clearX(BYTE color) +{ + outpw(SEQU_ADDR, 0x0F02); + memset((unsigned char *)(0xA000 << 4) + activeStart, color, 0x00010000); +} + + +void +putpixelX(COORD x, COORD y, BYTE color) +{ + BYTE temp; + + if (write_plane != (temp = (x & 3))) { + write_plane = temp; + outpw(SEQU_ADDR, plane_mask[temp]); + } + + *(RowsX[y] + (x >> 2) + activeStart) = color; +} + + +BYTE +getpixelX(COORD x, COORD y) +{ + BYTE temp; + + if (read_plane != (temp = (x & 3))) { + read_plane = temp; + outpw(GRACON_ADDR, read_mask[temp]); + } + + return (*(RowsX[y] + (x >> 2) + activeStart)); +} + + +void +internal_vert_lineX(COORD x, COORD top_y, int len, BYTE color) +{ + BYTE *ptr; + BYTE temp; + + if (write_plane != (temp = (x & 3))) { + write_plane = temp; + outpw(SEQU_ADDR, plane_mask[temp]); + } + + ptr = RowsX[top_y] + (x >> 2) + activeStart; + + while (len--) { + *ptr = color; + ptr += widthBytes; + } +} + + +void +internal_horiz_lineX(COORD left_x, COORD y, int len, BYTE color) +{ + BYTE *ptr; + BYTE temp; + + ptr = RowsX[y] + (left_x >> 2) + activeStart; + + // Set current plane to invalid value + write_plane = -1; + + if (temp = (left_x & 3)) { + outp(SEQU_ADDR, 0x02); + outp(0x3C5, line_head[temp]); + *ptr++ = color; + len -= (4 - temp); + } + + if (temp = (len >> 2)) { + outpw(SEQU_ADDR, 0x0F02); + + len &= 3; + + memset(ptr, color, temp); + ptr += temp; + } + + if (len) { + outp(SEQU_ADDR, 0x02); + outp(0x3C5, line_tail[len]); + *ptr = color; + } +} + + +void +boxX(COORD x1, COORD y1, COORD x2, COORD y2, BYTE color) +{ + int xsize, ysize; + + xsize = (x2 - x1) + 1; + internal_horiz_lineX(x1, y1, xsize, color); + internal_horiz_lineX(x1, y2, xsize, color); + + y1++; + ysize = (y2 - y1); + + internal_vert_lineX(x1, y1, ysize, color); + internal_vert_lineX(x2, y1, ysize, color); +} + + +void +filledboxX(COORD x1, COORD y1, COORD x2, COORD y2, BYTE color) +{ + BYTE *base_ptr; + BYTE *ptr; + BYTE temp; + short int i, xsize, ysize; + + // Set current plane to invalid value + write_plane = -1; + + xsize = (x2 - x1) + 1; + ysize = (y2 - y1) + 1; + + if (ysize == 1) { + internal_horiz_lineX(x1, y1, xsize, color); + return; + } + + base_ptr = RowsX[y1] + (x1 >> 2) + activeStart; + + if (temp = (x1 & 3)) { + outp(SEQU_ADDR, 0x02); + outp(0x3C5, line_head[temp]); + ptr = base_ptr; + i=ysize; + while (i--) { + *ptr = color; + ptr += widthBytes; + } + xsize -= (4 - temp); + base_ptr++; + } + + if (temp = (xsize >> 2)) { + outpw(SEQU_ADDR, 0x0F02); + + xsize &= 3; + ptr = base_ptr; + i=ysize; + while (i--) { + memset(ptr, color, temp); + ptr += widthBytes; + } + base_ptr += temp; + } + + if (xsize) { + outp(SEQU_ADDR, 0x02); + outp(0x3C5, line_tail[xsize]); + while (ysize--) { + *base_ptr = color; + base_ptr += widthBytes; + } + } +} + + +void +circleX(COORD x, COORD y, DIST r, BYTE color) +{ + int ix, iy, d, deltaE, deltaSE; + + ix = 0; + iy = r; + d = 1 - r; + deltaE = 3; + deltaSE = (-2 * r) + 5; + + putpixelX(x + ix, y + iy, color); + putpixelX(x + ix, y - iy, color); + putpixelX(x + iy, y + ix, color); + putpixelX(x + iy, y - ix, color); + putpixelX(x - ix, y + iy, color); + putpixelX(x - ix, y - iy, color); + putpixelX(x - iy, y + ix, color); + putpixelX(x - iy, y - ix, color); + + while (iy > ix++) { + if (d < 0) { + d += deltaE; + deltaE += 2; + deltaSE += 2; + } else { + d += deltaSE; + deltaE += 2; + deltaSE += 4; + iy--; + } + + putpixelX(x + ix, y + iy, color); + putpixelX(x + ix, y - iy, color); + putpixelX(x + iy, y + ix, color); + putpixelX(x + iy, y - ix, color); + putpixelX(x - ix, y + iy, color); + putpixelX(x - ix, y - iy, color); + putpixelX(x - iy, y + ix, color); + putpixelX(x - iy, y - ix, color); + } +} + + +void +filledcircleX(COORD x, COORD y, DIST r, BYTE color) +{ + int ix, iy, d, deltaE, deltaSE; + + ix = 0; + iy = r; + d = 1 - r; + deltaE = 3; + deltaSE = (-2 * r) + 5; + + internal_horiz_lineX(x - ix, y + iy, (ix << 1) + 1, color); + internal_horiz_lineX(x - ix, y - iy, (ix << 1) + 1, color); + internal_horiz_lineX(x - iy, y + ix, (iy << 1) + 1, color); + internal_horiz_lineX(x - iy, y - ix, (iy << 1) + 1, color); + + while (iy > ix++) { + if (d < 0) { + d += deltaE; + deltaE += 2; + deltaSE += 2; + } else { + d += deltaSE; + deltaE += 2; + deltaSE += 4; + iy--; + } + + internal_horiz_lineX(x - ix, y + iy, (ix << 1) + 1, color); + internal_horiz_lineX(x - ix, y - iy, (ix << 1) + 1, color); + internal_horiz_lineX(x - iy, y + ix, (iy << 1) + 1, color); + internal_horiz_lineX(x - iy, y - ix, (iy << 1) + 1, color); + } +} + + +void +internal_xmajor(BYTE *vga_ptr, short int len, short int yskip, + unsigned long ErrorAcc, unsigned long ErrorAdj, BYTE color) +{ + if (len) { + len--; + while (len--) { + *vga_ptr++ = color; + ErrorAcc += ErrorAdj; + + if (ErrorAcc & ~0xFFFFL) { + ErrorAcc &= 0xFFFFL; + vga_ptr += yskip; + } + } + *vga_ptr = color; + } +} + + +void +internal_middle(BYTE *vga_ptr, short int len, short int yskip, + unsigned long ErrorAcc, unsigned long ErrorAdj, BYTE color) +{ + if (len) { + len--; + while (len--) { + *vga_ptr++ = color; + ErrorAcc += ErrorAdj; + vga_ptr += (yskip * (ErrorAcc >> 16)); + ErrorAcc &= 0xFFFFL; + } + *vga_ptr = color; + } +} + + +void +internal_ymajor(BYTE *vga_ptr, short int len, short int yskip, + unsigned long ErrorAcc, unsigned long ErrorAdj, BYTE color) +{ + unsigned long TinyAdj; + short int i; + + if (len) { + TinyAdj = (ErrorAdj >> 2); + ErrorAdj -= TinyAdj; + + len--; + while (len--) { + ErrorAcc += TinyAdj; + i = (ErrorAcc >> 16); + ErrorAcc &= 0xFFFFL; + + while (i--) { + *vga_ptr = color; + vga_ptr += yskip; + } + + ErrorAcc += ErrorAdj; + vga_ptr += (yskip * (ErrorAcc >> 16)) + 1; + ErrorAcc &= 0xFFFFL; + } + ErrorAcc += TinyAdj; + i = (ErrorAcc >> 16); + while (i--) { + *vga_ptr = color; + vga_ptr += yskip; + } + } +} + + +void +lineX(COORD x1, COORD y1, COORD x2, COORD y2, BYTE color) +{ + unsigned long ErrorAcc, ErrorAdj, TinyAdj; + short int i, DeltaX, DeltaY, yskip; + short int len[4]; + BYTE *vga_ptr; + COORD temp; + + // Mode X 4-way folded Bresenham line function - by David Boeren + + // Set invalid plane, because we're screwing with the plane mask + write_plane = -1; + + // Make sure the line runs left to right + if (x1 > x2) { + temp = x1; x1 = x2; x2 = temp; + temp = y1; y1 = y2; y2 = temp; + } + + DeltaX = (x2 - x1); + DeltaY = (y2 - y1); + + if (DeltaY >= 0) { + yskip = widthBytes; + } else { + DeltaY = -DeltaY; // Make DeltaY positive + yskip = -widthBytes; + } + + if (DeltaX == 0) { + // Vertical Line (and one pixel lines) + if (yskip > 0) { + internal_vert_lineX(x1, y1, (DeltaY + 1), color); + } else { + internal_vert_lineX(x1, y2, (DeltaY + 1), color); + } + return; + } + + if (DeltaY == 0) { + // Horizontal Line + internal_horiz_lineX(x1, y1, (DeltaX + 1), color); + return; + } + + vga_ptr = RowsX[y1] + (x1 >> 2) + activeStart; + ErrorAcc = 0x8000; + + // Length of sub-line in each plane + temp = (x1 & 3); + i = DeltaX + temp; + len[0] = ((i--) >> 2); + len[1] = ((i--) >> 2); + len[2] = ((i--) >> 2); + len[3] = (i >> 2) + 1; + + for (i=temp; i < 3; i++) { + len[i]++; + } + + if ((DeltaX >> 2) >= DeltaY) { + // X-Major line (0.00 < slope <= 0.25) + ErrorAdj = ((((unsigned long)DeltaY << 18) / (unsigned long)DeltaX)); + TinyAdj = (ErrorAdj >> 2); + while (i--) { + outpw(SEQU_ADDR, plane_mask[temp]); + internal_xmajor(vga_ptr, len[temp++], yskip, ErrorAcc, ErrorAdj, color); + if (temp == 4) { + temp = 0; + vga_ptr++; + } + ErrorAcc += TinyAdj; + if (ErrorAcc & ~0xFFFFL) { + ErrorAcc &= 0xFFFFL; + vga_ptr += yskip; + } + } + outpw(SEQU_ADDR, plane_mask[temp]); + internal_xmajor(vga_ptr, len[temp], yskip, ErrorAcc, ErrorAdj, color); + } else if (DeltaX >= DeltaY) { + // Middle line (0.25 < slope <= 1.00) + ErrorAdj = ((((unsigned long)DeltaY << 18) / (unsigned long)DeltaX)); + TinyAdj = (ErrorAdj >> 2); + while (i--) { + outpw(SEQU_ADDR, plane_mask[temp]); + internal_middle(vga_ptr, len[temp++], yskip, ErrorAcc, ErrorAdj, color); + if (temp == 4) { + temp = 0; + vga_ptr++; + } + ErrorAcc += TinyAdj; + if (ErrorAcc & ~0xFFFFL) { + vga_ptr += yskip; + ErrorAcc &= 0xFFFFL; + } + } + outpw(SEQU_ADDR, plane_mask[temp]); + internal_middle(vga_ptr, len[temp], yskip, ErrorAcc, ErrorAdj, color); + } else { + // Y-Major line (slope > 1) + ErrorAdj = ((((unsigned long)(DeltaY+1) << 18) / + (unsigned long)(DeltaX+1))); + TinyAdj = (ErrorAdj >> 2); + while (i--) { + outpw(SEQU_ADDR, plane_mask[temp]); + internal_ymajor(vga_ptr, len[temp++], yskip, ErrorAcc, ErrorAdj, color); + if (temp == 4) { + temp = 0; + vga_ptr++; + } + ErrorAcc += TinyAdj; + vga_ptr += (yskip * (ErrorAcc >> 16)); + ErrorAcc &= 0xFFFFL; + } + outpw(SEQU_ADDR, plane_mask[temp]); + internal_ymajor(vga_ptr, len[temp], yskip, ErrorAcc, ErrorAdj, color); + } +} + + +int +loadfontX(char *fname) +{ + FILE *fp; + + fp = fopen(fname, "rb"); + + if (fp == NULL) { + return 0; + } else { + fread(Xfont, 8, 256, fp); + fclose(fp); + return 1; + } +} + + +void +putchX(COORD x, COORD y, char c, BYTE color) +{ + int i; + BYTE *vga_ptr; + BYTE *font_ptr; + BYTE temp; + + // 8x8 font + vga_ptr = RowsX[y << 3] + (x << 1) + activeStart; + write_plane = -1; + + font_ptr = Xfont + (c << 3); + + i=8; + while (i--) { + temp = *font_ptr++; + outpw(SEQU_ADDR, text_mask[temp & 0x0F]); + *vga_ptr++ = color; + + outpw(SEQU_ADDR, text_mask[temp >> 4]); + *vga_ptr-- = color; + vga_ptr += widthBytes; + } +} + + +void +putstringX(COORD x, COORD y, char *str, BYTE color) +{ + int i, skip; + BYTE *vga_ptr; + BYTE *font_ptr; + BYTE c, temp; + + // 8x8 font + vga_ptr = RowsX[y << 3] + (x << 1) + activeStart; + write_plane = -1; + + skip = 2 - (widthBytes << 3); + + while (c = *str++) { + font_ptr = Xfont + (c << 3); + + i=8; + while (i--) { + temp = *font_ptr++; + outpw(SEQU_ADDR, text_mask[temp & 0x0F]); + *vga_ptr++ = color; + + outpw(SEQU_ADDR, text_mask[temp >> 4]); + *vga_ptr-- = color; + vga_ptr += widthBytes; + } + + vga_ptr += skip; + } +} + diff --git a/16/w_modex/XPRIM.HPP b/16/w_modex/XPRIM.HPP new file mode 100644 index 00000000..e9948369 --- /dev/null +++ b/16/w_modex/XPRIM.HPP @@ -0,0 +1,31 @@ +#ifndef X_PRIMITIVES_HPP + #define X_PRIMITIVES_HPP + +#include "xtypes.hpp" + +// Waits for vertical retrace +void wait_for_retrace(void); + +// Page setting functions +void setDrawPage(unsigned int page); +void setVisiblePage(unsigned int page); + +// Screen clearing functions +void clearX(BYTE color); + +// Drawing functions +void putpixelX(COORD x, COORD y, BYTE color); +BYTE getpixelX(COORD x, COORD y); +void boxX(COORD x1, COORD y1, COORD x2, COORD y2, BYTE color); +void filledboxX(COORD x1, COORD y1, COORD x2, COORD y2, BYTE color); +void circleX(COORD x, COORD y, DIST r, BYTE color); +void filledcircleX(COORD x, COORD y, DIST r, BYTE color); +void lineX(COORD lx1, COORD ly1, COORD lx2, COORD ly2, BYTE color); + +// Text output functions +int loadfontX(char *fname); +void putchX(COORD x, COORD y, char c, BYTE color); +void putstringX(COORD x, COORD y, char *str, BYTE color); + +#endif + diff --git a/16/w_modex/XTYPES.HPP b/16/w_modex/XTYPES.HPP new file mode 100644 index 00000000..1a0d8e69 --- /dev/null +++ b/16/w_modex/XTYPES.HPP @@ -0,0 +1,17 @@ +#ifndef XTYPES_HPP + #define XTYPES_HPP + +typedef unsigned char BYTE; +typedef signed char SBYTE; +typedef unsigned char FLAG; +typedef unsigned short COORD; +typedef unsigned short DIST; + +struct blitbuf { + DIST xsize; + DIST ysize; + BYTE *image; +}; + +#endif +