From: sparky4 <sparky4@cock.li>
Date: Wed, 3 May 2017 18:31:28 +0000 (-0500)
Subject: 16_ca needs huge amounts of work and I should remember what needs to be done soon... 
X-Git-Url: http://4ch.mooo.com/gitweb/?a=commitdiff_plain;h=0e305ed530c51bad26fa3048c8e1c138d547d946;p=16.git

16_ca needs huge amounts of work and I should remember what needs to be done soon[going to port rest of code to borland c some time so we can use the core components of id engine here ][going to add 16_us.c eventually but the debug system and CA_ PM_ and MM_ usage is priority now]older zcroll renamed to xcroll][zcroll is now the pre menu game loop system with PROPER data usage with CAMMPM] added 1st scroll back [i work on CA] palette debug show values added wwww and i need to know how to see vrs/vrl imaage data palette index numbers [i am trying to find out how the hell you get the index number values of VRL/VRS]
---

diff --git a/XCROLL.LOG b/XCROLL.LOG
index 6bc68838..b1501b6a 100755
--- a/XCROLL.LOG
+++ b/XCROLL.LOG
@@ -9,9 +9,42 @@ Object 4's name: 'stump'
                      "walkable":"0"
                     }
 		walkable: 0
+DrawVRL:
+[00]	85
+[01]	00
+[02]	0b
+[03]	86
+[04]	00
+[05]	02
+[06]	88
+[07]	01
+[08]	0b
+[09]	88
+[10]	04
+[11]	0b
+[12]	ff
+[13]	84
+[14]	00
+[15]	0b
+[16]	06
+[17]	00
+[18]	02
+[19]	06
+[20]	04
+[21]	04
+[22]	03
+[23]	02
+[24]	87
+[25]	01
+[26]	0b
+[27]	01
+[28]	02
+[29]	05
+[30]	02
+[31]	01
 
 Project 16 xcroll.exe. This is just a test file!
-version May  1 2017 13:37:18
+version May  3 2017 13:29:21
 page[0]dxy: 16x16
 
 player vars:
diff --git a/data/chistnd.pcx b/data/chistnd.pcx
new file mode 100755
index 00000000..39a969d2
Binary files /dev/null and b/data/chistnd.pcx differ
diff --git a/data/spri/CHUBFCW0.VRL b/data/spri/CHUBFCW0.VRL
index 75d5a6e4..af1b4956 100755
Binary files a/data/spri/CHUBFCW0.VRL and b/data/spri/CHUBFCW0.VRL differ
diff --git a/data/spri/chistnd.h b/data/spri/chistnd.h
new file mode 100755
index 00000000..fa9eae82
--- /dev/null
+++ b/data/spri/chistnd.h
@@ -0,0 +1,9 @@
+// header file for sprite sheet. AUTO GENERATED, do not edit
+// 
+// source PCX: ../chistnd.pcx
+// sheet script: chistnd.sht
+// palette file: chistnd.pal
+
+#define _chistnd_CHUBFCW0 11U
+
+// end list
diff --git a/data/spri/chistnd.pal b/data/spri/chistnd.pal
new file mode 100755
index 00000000..38ec968d
Binary files /dev/null and b/data/spri/chistnd.pal differ
diff --git a/data/spri/chistnd.sht b/data/spri/chistnd.sht
new file mode 100755
index 00000000..a4f57806
--- /dev/null
+++ b/data/spri/chistnd.sht
@@ -0,0 +1,26 @@
+# CHISTND.PCX demo sprite sheet compiler script
+# (C) 2016 Jonathan Campbell
+
+# *spritesheet declares the section used by the sprite sheet cutting tool
+#
+# Sprites are declared by name (which becomes the .VRL file) at the + in the form:
+# +NAME@ID
+#
+# Sprite names are meant for temporary use when compiling the sprite sheet into VRLs.
+# At some point a longer name might be provided for use in your code.
+# This will fill the CURRENT WORKING DIRECTORY with .VRL files as directed when you
+# run PCXSSCUT, make sure your makefile does this in a temporary directory when
+# you integrate into your build and that your cleanup commands delete these files,
+# and that your .gitignore does not attempt to commit these files.
+
+# this format is a bit crap, but we'll improve it as needed. be patient.
+
+# begin spritesheet section
+*spritesheet
+
+# ---------------- player, walking, blue shirt with white cross. Frame 2/3 could be used for standing still
+
+# player, forward, frame 1/3
++CHUBFCW0@11
+xy=0,0
+wh=16,32
diff --git a/data/spri/chistnd.vrl b/data/spri/chistnd.vrl
new file mode 100755
index 00000000..af1b4956
Binary files /dev/null and b/data/spri/chistnd.vrl differ
diff --git a/data/spri/chistnd.vrs b/data/spri/chistnd.vrs
new file mode 100755
index 00000000..401ca63b
Binary files /dev/null and b/data/spri/chistnd.vrs differ
diff --git a/src/lib/16_ca.c b/src/lib/16_ca.c
index ccab39ba..f6ffafb6 100755
--- a/src/lib/16_ca.c
+++ b/src/lib/16_ca.c
@@ -1451,7 +1451,7 @@ cachein:
 //===========================================================================
 
 //????#if GRMODE == EGAGR
-#if 0
+#if 1
 
 /*
 ======================
@@ -1465,9 +1465,10 @@ cachein:
 
 unsigned	static	sheight,swidth;
 boolean static dothemask;
+unsigned	*shifttabletable[8];
 
 void CAL_ShiftSprite (unsigned segment,unsigned source,unsigned dest,
-	unsigned width, unsigned height, unsigned pixshift, boolean domask)
+	unsigned width, unsigned height, unsigned pixshift, boolean domask, global_game_variables_t *gvar)
 {
 
 	sheight = height;		// because we are going to reassign bp
@@ -1484,6 +1485,7 @@ void CAL_ShiftSprite (unsigned segment,unsigned source,unsigned dest,
 		mov	bp,[pixshift]
 		shl	bp,1
 		mov	bp,WORD PTR [shifttabletable+bp]	// bp holds pointer to shift table
+//		mov	bp,WORD PTR [gvar->video.shifttabletable+bp]	// bp holds pointer to shift table
 
 		cmp	[ss:dothemask],0
 		je		skipmask
@@ -1593,8 +1595,8 @@ dodatabyte:
 =
 ======================
 */
-/*++++
-void CAL_CacheSprite (int chunk, byte far *compressed)
+
+void CAL_CacheSprite (int chunk, byte far *compressed, global_game_variables_t *gvar)
 {
 	int i;
 	unsigned shiftstarts[5];
@@ -1602,11 +1604,12 @@ void CAL_CacheSprite (int chunk, byte far *compressed)
 	spritetabletype far *spr;
 	spritetype _seg *dest;
 
-#if GRMODE == CGAGR
+#if 0
+//GRMODE == CGAGR
 //
 // CGA has no pel panning, so shifts are never needed
 //
-	spr = &spritetable[chunk-STARTSPRITES];
+	spr = &gvar->video.spritetable[chunk-STARTSPRITES];
 	smallplane = spr->width*spr->height;
 	MM_GetPtr (&grsegs[chunk],smallplane*2+MAXSHIFTS*6);
 	if (mmerror)
@@ -1624,12 +1627,12 @@ void CAL_CacheSprite (int chunk, byte far *compressed)
 #endif
 
 
-#if GRMODE == EGAGR
+//#if GRMODE == EGAGR
 
 //
 // calculate sizes
 //
-	spr = &spritetable[chunk-STARTSPRITES];
+	spr = &gvar->video.spritetable[chunk-STARTSPRITES];
 	smallplane = spr->width*spr->height;
 	bigplane = (spr->width+1)*spr->height;
 
@@ -1640,10 +1643,10 @@ void CAL_CacheSprite (int chunk, byte far *compressed)
 	shiftstarts[4] = shiftstarts[3] + bigplane*5;	// nothing ever put here
 
 	expanded = shiftstarts[spr->shifts];
-	MM_GetPtr (&grsegs[chunk],expanded);
-	if (mmerror)
+	MM_GetPtr (MEMPTRCONV gvar->ca.grsegs[chunk],expanded, gvar);
+	if (gvar->mm.mmerror)
 		return;
-	dest = (spritetype _seg *)grsegs[chunk];
+	dest = (spritetype _seg *)gvar->ca.grsegs[chunk];
 
 //
 // expand the unshifted shape
@@ -1677,8 +1680,8 @@ void CAL_CacheSprite (int chunk, byte far *compressed)
 			dest->planesize[i] = bigplane;
 			dest->width[i] = spr->width+1;
 		}
-		CAL_ShiftSprite ((unsigned)grsegs[chunk],dest->sourceoffset[0],
-			dest->sourceoffset[2],spr->width,spr->height,4,true);
+		CAL_ShiftSprite ((unsigned)gvar->ca.grsegs[chunk],dest->sourceoffset[0],
+			dest->sourceoffset[2],spr->width,spr->height,4,true,gvar);
 		break;
 
 	case	4:
@@ -1689,20 +1692,20 @@ void CAL_CacheSprite (int chunk, byte far *compressed)
 		dest->sourceoffset[1] = shiftstarts[1];
 		dest->planesize[1] = bigplane;
 		dest->width[1] = spr->width+1;
-		CAL_ShiftSprite ((unsigned)grsegs[chunk],dest->sourceoffset[0],
-			dest->sourceoffset[1],spr->width,spr->height,2,true);
+		CAL_ShiftSprite ((unsigned)gvar->ca.grsegs[chunk],dest->sourceoffset[0],
+			dest->sourceoffset[1],spr->width,spr->height,2,true,gvar);
 
 		dest->sourceoffset[2] = shiftstarts[2];
 		dest->planesize[2] = bigplane;
 		dest->width[2] = spr->width+1;
-		CAL_ShiftSprite ((unsigned)grsegs[chunk],dest->sourceoffset[0],
-			dest->sourceoffset[2],spr->width,spr->height,4,true);
+		CAL_ShiftSprite ((unsigned)gvar->ca.grsegs[chunk],dest->sourceoffset[0],
+			dest->sourceoffset[2],spr->width,spr->height,4,true,gvar);
 
 		dest->sourceoffset[3] = shiftstarts[3];
 		dest->planesize[3] = bigplane;
 		dest->width[3] = spr->width+1;
-		CAL_ShiftSprite ((unsigned)grsegs[chunk],dest->sourceoffset[0],
-			dest->sourceoffset[3],spr->width,spr->height,6,true);
+		CAL_ShiftSprite ((unsigned)gvar->ca.grsegs[chunk],dest->sourceoffset[0],
+			dest->sourceoffset[3],spr->width,spr->height,6,true,gvar);
 
 		break;
 
@@ -1710,8 +1713,8 @@ void CAL_CacheSprite (int chunk, byte far *compressed)
 		Quit (gvar, "CAL_CacheSprite: Bad shifts number!");
 	}
 
-#endif
-}*/
+//#endif
+}
 
 //===========================================================================
 
diff --git a/src/lib/16_dbg.c b/src/lib/16_dbg.c
index 28cc6d01..5a9173f7 100755
--- a/src/lib/16_dbg.c
+++ b/src/lib/16_dbg.c
@@ -252,10 +252,8 @@ static	char	buf[10];
 //#define SHOWPALVARIMODQUAD	((spv.i)%QUADWH)
 #define SHOWPALVARIMOD			((spv.i)%TILEWH)
 #define SHOWPALVARIDIV			((spv.i)/TILEWH)
-#define SHOWPALVARIMODCOND		(!SHOWPALVARIMOD)
-#define SHOWPALVARIDIVCOND		(!SHOWPALVARIDIV)
-#define SHOWPALVARIMODIFCOND	if(SHOWPALVARIMODCOND && spv.i)
-#define SHOWPALVARIDIVIFCOND		if(SHOWPALVARIDIVCOND && spv.i)
+#define SHOWPALVARIMODIFCOND	if((!SHOWPALVARIMOD) && spv.i)
+#define SHOWPALVARIDIVIFCOND		if((!SHOWPALVARIDIV) && spv.i)
 //<PAL_SIZE/3 && spv.i)
 #define SHOWPALVARPALSIZELIMIT	255
 
diff --git a/src/lib/16_in.h b/src/lib/16_in.h
index aa57e395..c2b4b622 100755
--- a/src/lib/16_in.h
+++ b/src/lib/16_in.h
@@ -138,8 +138,10 @@
 #define	key_LSuper			0x5b
 #define	key_RSuper			0x5c
 #define	key_Menu			0x5d
-#define	sc_LBrkt
-#define	sc_RBrkt
+#define	sc_LBrkt		0x1a	//	[
+#define	sc_RBrkt		0x1b	//	]
+#define	sc_BackSlash	0x2b	//	|
+#define	sc_ForeSlash	0x35	//	/ ?
 
 // 	Stuff for the mouse
 #define	MReset		0
diff --git a/src/lib/16_spri.c b/src/lib/16_spri.c
index 62c01aa4..c7c2b99d 100755
--- a/src/lib/16_spri.c
+++ b/src/lib/16_spri.c
@@ -21,6 +21,64 @@
  */
 
 #include "src/lib/16_spri.h"
+#include <hw/vga/vrl1xdrc.h>
+//void draw_vrl1_vgax_modex_strip(unsigned char far *draw,unsigned char far *s);
+
+//===========================================================================
+
+//#define NEWVRSDRAWFUN
+void DrawVRL (unsigned int x,unsigned int y,struct vrl1_vgax_header *hdr,vrl1_vgax_offset_t *lineoffs/*array hdr->width long*/,unsigned char *data,unsigned int datasz) {
+	unsigned char far *draw;
+	unsigned int vram_offset = (y * vga_state.vga_draw_stride) + (x >> 2),sx;
+	unsigned int vramlimit = vga_state.vga_draw_stride_limit;
+	unsigned char vga_plane = (x & 3);
+	unsigned char *s;
+
+//	byte	outputvars[72][128];
+	word a;//,by,bxmax,bymax;
+
+	printf("DrawVRL:\n");
+
+	/* draw one by one */
+	for (sx=0;sx < hdr->width;sx++) {
+		draw = vga_state.vga_graphics_ram + vram_offset;
+		vga_write_sequencer(0x02/*map mask*/,1 << vga_plane);
+		s = data + lineoffs[sx];
+		draw_vrl1_vgax_modex_strip(draw,s);
+
+		if(!sx)
+		for(a=0;a<hdr->height;a++)//hdr->width*
+		{
+//			if((*(s+a)==0x0) && (*(s+(a+1))==0x20) && (*(s+(a+2))==0xff)) a+=2;
+//			if(*(s+a)<=13)
+//				if (!(a%4) && a ) printf("\n");
+//				sprintf(outputvars[sx][by], "%02x", *(s+a));
+				printf("[%02u]	%02x\n", a, *(s+a));
+//				by++;
+		}
+
+		/* end of a vertical strip. next line? */
+		if ((++vga_plane) == 4) {
+			if (--vramlimit == 0) break;
+			vram_offset++;
+			vga_plane = 0;
+		}
+	}
+#if 0
+	bxmax = sx; bymax = by;
+	for(by=0;by<bymax;by++)
+	{
+		for(sx=0;sx<bxmax;sx++)
+		{
+//			if (!(sx%hdr->width) && sx ) printf("\n	");
+			printf("%02x ", outputvars[sx][by]);
+		}
+		printf("\n	");
+	}
+#endif
+}
+
+//===========================================================================
 
 char* get_curr_anim_name(struct sprite *spri)
 {
@@ -188,7 +246,12 @@ void animate_spri(entity_t *enti, video_t *video)
 #ifndef SPRITE
 	modexClearRegion(&video->page[0], x, y, 16, 32, 1);
 #else
-	draw_vrl1_vgax_modex(
+#ifndef NEWVRSDRAWFUN
+	draw_vrl1_vgax_modex
+#else
+	DrawVRL
+#endif
+	(
 		x-rx,
 		y-ry,
 		enti->spri.sprite_vrl_cont.vrl_header,
diff --git a/src/lib/16_spri.h b/src/lib/16_spri.h
index 0e29ebeb..a170795a 100755
--- a/src/lib/16_spri.h
+++ b/src/lib/16_spri.h
@@ -25,6 +25,8 @@
 #include "src/lib/16_vrs.h"
 #include "src/lib/scroll16.h"
 
+void DrawVRL (unsigned int x,unsigned int y,struct vrl1_vgax_header *hdr,vrl1_vgax_offset_t *lineoffs/*array hdr->width long*/,unsigned char *data,unsigned int datasz);
+
 //moved to 16_tdef.h
 // struct sprite
 // {
diff --git a/src/lib/16_t.h b/src/lib/16_t.h
index 764bf51e..ff738657 100755
--- a/src/lib/16_t.h
+++ b/src/lib/16_t.h
@@ -89,6 +89,7 @@ typedef void _seg * memptr;
 
 #define _argv __argv
 #define _argc __argc
+#define EINVFMT EMFILE
 #define geninterrupt(n) int86(n,&CPURegs,&CPURegs);
 
 #define peekb(segm,ofs) (*(byte far*)MK_FP((segm),(ofs)))
diff --git a/src/lib/16_tail.c b/src/lib/16_tail.c
index b56a6600..b92facef 100755
--- a/src/lib/16_tail.c
+++ b/src/lib/16_tail.c
@@ -450,6 +450,128 @@ void DebugMemory_(global_game_variables_t *gvar, boolean q)
 //	if(q) MM_ShowMemory (gvar);
 }
 
+/*
+===================
+=
+= TestSprites
+=
+===================
+*/
+
+#if 0
+#define DISPWIDTH	110
+#define	TEXTWIDTH   40
+void TestSprites(void)
+{
+	int hx,hy,sprite,oldsprite,bottomy,topx,shift;
+	spritetabletype far *spr;
+	spritetype _seg	*block;
+	unsigned	mem,scan;
+
+
+	VW_FixRefreshBuffer ();
+	US_CenterWindow (30,17);
+
+	US_CPrint ("Sprite Test");
+	US_CPrint ("-----------");
+
+	hy=PrintY;
+	hx=(PrintX+56)&(~7);
+	topx = hx+TEXTWIDTH;
+
+	US_Print ("Chunk:\nWidth:\nHeight:\nOrgx:\nOrgy:\nXl:\nYl:\nXh:\nYh:\n"
+			  "Shifts:\nMem:\n");
+
+	bottomy = PrintY;
+
+	sprite = STARTSPRITES;
+	shift = 0;
+
+	do
+	{
+		if (sprite>=STARTTILE8)
+			sprite = STARTTILE8-1;
+		else if (sprite<STARTSPRITES)
+			sprite = STARTSPRITES;
+
+		spr = &spritetable[sprite-STARTSPRITES];
+		block = (spritetype _seg *)grsegs[sprite];
+
+		VWB_Bar (hx,hy,TEXTWIDTH,bottomy-hy,WHITE);
+
+		PrintX=hx;
+		PrintY=hy;
+		US_PrintUnsigned (sprite);US_Print ("\n");PrintX=hx;
+		US_PrintUnsigned (spr->width);US_Print ("\n");PrintX=hx;
+		US_PrintUnsigned (spr->height);US_Print ("\n");PrintX=hx;
+		US_PrintSigned (spr->orgx);US_Print ("\n");PrintX=hx;
+		US_PrintSigned (spr->orgy);US_Print ("\n");PrintX=hx;
+		US_PrintSigned (spr->xl);US_Print ("\n");PrintX=hx;
+		US_PrintSigned (spr->yl);US_Print ("\n");PrintX=hx;
+		US_PrintSigned (spr->xh);US_Print ("\n");PrintX=hx;
+		US_PrintSigned (spr->yh);US_Print ("\n");PrintX=hx;
+		US_PrintSigned (spr->shifts);US_Print ("\n");PrintX=hx;
+		if (!block)
+		{
+			US_Print ("-----");
+		}
+		else
+		{
+			mem = block->sourceoffset[3]+5*block->planesize[3];
+			mem = (mem+15)&(~15);		// round to paragraphs
+			US_PrintUnsigned (mem);
+		}
+
+		oldsprite = sprite;
+		do
+		{
+		//
+		// draw the current shift, then wait for key
+		//
+			VWB_Bar(topx,hy,DISPWIDTH,bottomy-hy,WHITE);
+			if (block)
+			{
+				PrintX = topx;
+				PrintY = hy;
+				US_Print ("Shift:");
+				US_PrintUnsigned (shift);
+				US_Print ("\n");
+				VWB_DrawSprite (topx+16+shift*2,PrintY,sprite);
+			}
+
+			VW_UpdateScreen();
+
+			scan = IN_WaitForKey ();
+
+			switch (scan)
+			{
+			case sc_UpArrow:
+				sprite++;
+				break;
+			case sc_DownArrow:
+				sprite--;
+				break;
+			case sc_LeftArrow:
+				if (--shift == -1)
+					shift = 3;
+				break;
+			case sc_RightArrow:
+				if (++shift == 4)
+					shift = 0;
+				break;
+			case sc_Escape:
+				return;
+			}
+
+		} while (sprite == oldsprite);
+
+  } while (1);
+
+
+}
+
+#endif
+
 /*
 ==========================
 =
diff --git a/src/lib/16_tdef.h b/src/lib/16_tdef.h
index ffc4ae6f..b1e68e10 100755
--- a/src/lib/16_tdef.h
+++ b/src/lib/16_tdef.h
@@ -360,9 +360,29 @@ typedef struct
 } kurokku_t;
 
 //===================================//
-#define PALSIZE	768
-#define NUMCHUNKS	416	//keen
-#define MAXSCANLINES	240			// size of ylookup table
+#define PALSIZE			768	//vga
+#define NUMCHUNKS		416	//keen
+#define MAXSCANLINES	240	// size of ylookup table
+
+#define MAXSHIFTS		4
+#define STARTSPRITES	0	//temp
+
+typedef struct
+{
+	int	width,
+		height,
+		orgx,orgy,
+		xl,yl,xh,yh,
+		shifts;
+} spritetabletype;
+
+typedef	struct
+{
+	unsigned	sourceoffset[MAXSHIFTS];
+	unsigned	planesize[MAXSHIFTS];
+	unsigned	width[MAXSHIFTS];
+	byte		data[];
+} spritetype;		// the memptr for each sprite points to this
 
 typedef struct
 {
@@ -434,6 +454,8 @@ typedef struct
 	boolean	fastpalette;
 	byte		far	palette1[256][3],far palette2[256][3];
 	pictabletype	_seg *pictable;
+	spritetabletype _seg *spritetable;
+	unsigned	*shifttabletable[8];
 } video_t;
 
 //from scroll16
@@ -751,7 +773,10 @@ typedef struct {
 	vidsw_t vsw;
 } sw_t;*/
 
-
+#ifdef __WATCOMC__
+extern char global_temp_status_text[512];
+extern char global_temp_status_text2[512];
+#endif
 
 typedef struct glob_game_vars
 {
@@ -768,9 +793,4 @@ typedef struct glob_game_vars
 	boolean	DLStarted;
 } global_game_variables_t;
 
-#ifdef __WATCOMC__
-extern char global_temp_status_text[512];
-extern char global_temp_status_text2[512];
-#define EINVFMT EMFILE
-#endif
 #endif /* _TYPEDEFSTRUCT_H_ */
diff --git a/src/lib/16_vrs.c b/src/lib/16_vrs.c
index 6e733c58..834754dd 100755
--- a/src/lib/16_vrs.c
+++ b/src/lib/16_vrs.c
@@ -21,11 +21,15 @@
  */
 #include "src/lib/16_vrs.h"
 
+#define VRS_USECAMMPM
+
 void VRS_ReadVRS(char *filename, entity_t *enti, global_game_variables_t *gvar){	VRS_OpenVRS(filename, enti, 1, gvar);	}
 void VRS_LoadVRS(char *filename, entity_t *enti, global_game_variables_t *gvar){	VRS_OpenVRS(filename, enti, 0, gvar);	}
 void VRS_OpenVRS(char *filename, entity_t *enti, boolean rlsw, global_game_variables_t *gvar)
 {
+#ifndef VRS_USECAMMPM
 	vrl1_vgax_offset_t **vrl_line_offsets;
+#endif
 	uint16_t far *vrl_id_iter;
 	uint32_t far *vrl_headers_offsets;
 	struct vrl1_vgax_header far *curr_vrl;
@@ -53,9 +57,12 @@ void VRS_OpenVRS(char *filename, entity_t *enti, boolean rlsw, global_game_varia
 	}
 
 	// Allocate memory for vrl line offsets table
-//	MM_GetPtr(MEMPTRCONV gvar->ca.grsegs[0], sizeof(vrl1_vgax_offset_t *)*num_of_vrl, gvar);
-//	enti->spri.spritesheet.vrl_line_offsets = (vrl1_vgax_offset_t **)gvar->ca.grsegs[0];
+#ifndef VRS_USECAMMPM
 	vrl_line_offsets = malloc(sizeof(vrl1_vgax_offset_t *)*num_of_vrl);//TODO: USE MM_ CA_ AND PM_
+#else
+	MM_GetPtr(MEMPTRCONV gvar->ca.grsegs[0], sizeof(vrl1_vgax_offset_t *)*num_of_vrl, gvar);
+	enti->spri.spritesheet.vrl_line_offsets = (vrl1_vgax_offset_t **)gvar->ca.grsegs[0];
+#endif
 
 	vrl_headers_offsets = (uint32_t far *)(enti->spri.spritesheet.buffer + enti->spri.spritesheet.vrs_hdr->offset_table[VRS_HEADER_OFFSET_VRS_LIST]);
 	// Calculate line offsets for each vrl
@@ -70,10 +77,85 @@ void VRS_OpenVRS(char *filename, entity_t *enti, boolean rlsw, global_game_varia
 		else{
 			vrl_size = enti->spri.spritesheet.vrs_hdr->offset_table[VRS_HEADER_OFFSET_SPRITE_ID_LIST] - vrl_headers_offsets[i] - sizeof(struct vrl1_vgax_header);
 		}
+#ifndef VRS_USECAMMPM
 		vrl_line_offsets[i] = vrl1_vgax_genlineoffsets(curr_vrl, (byte *)curr_vrl + sizeof(struct vrl1_vgax_header), vrl_size);
-//		enti->spri.spritesheet.vrl_line_offsets[i] = vrl1_vgax_genlineoffsets(curr_vrl, (byte *)curr_vrl + sizeof(struct vrl1_vgax_header), vrl_size);
+#else
+		enti->spri.spritesheet.vrl_line_offsets[i] = vrl1_vgax_genlineoffsets(curr_vrl, (byte *)curr_vrl + sizeof(struct vrl1_vgax_header), vrl_size);
+#endif
 	}
+#ifndef VRS_USECAMMPM
 	enti->spri.spritesheet.vrl_line_offsets = vrl_line_offsets;
+#endif
+}
+
+void VRS_ReadVRL(char *filename, entity_t *enti, global_game_variables_t *gvar){	VRS_OpenVRL(filename, enti, 1, gvar);	}
+void VRS_LoadVRL(char *filename, entity_t *enti, global_game_variables_t *gvar){	VRS_OpenVRL(filename, enti, 0, gvar);	}
+void VRS_OpenVRL(char *filename, entity_t *enti, boolean rlsw, global_game_variables_t *gvar)
+{
+	vrl1_vgax_offset_t *vrl_line_offsets;
+//	struct vrl1_vgax_header *vrl_header;
+//	uint16_t far *vrl_id_iter;
+//	uint32_t far *vrl_headers_offsets;
+//	struct vrl1_vgax_header far *curr_vrl;
+	uint32_t vrl_size;
+//	int num_of_vrl,i;
+	int size=0;
+
+	switch(rlsw)
+	{
+		case 1:
+			CA_ReadFile(filename, &gvar->ca.spribuff, gvar);
+		break;
+		case 0:
+			CA_LoadFile(filename, &gvar->ca.spribuff, gvar);
+		break;
+	}
+
+	// Insert sanity cheks later
+	enti->spri.sprite_vrl_cont.buffer = gvar->ca.spribuff;
+	enti->spri.sprite_vrl_cont.data_size = size - sizeof(struct vrl1_vgax_header);
+
+	vrl_size = enti->spri.sprite_vrl_cont.buffer - enti->spri.sprite_vrl_cont.buffer - sizeof(struct vrl1_vgax_header);
+//	vrl_header = (struct vrl1_vgax_header far *)(enti->spri.sprite_vrl_cont.buffer + enti->spri.sprite_vrl_cont.buffer);
+#if 0
+	num_of_vrl = 0;
+	while(vrl_id_iter[num_of_vrl]){
+		num_of_vrl++;
+	}
+
+	// Allocate memory for vrl line offsets table
+//#ifndef VRS_USECAMMPM
+	vrl_line_offsets = malloc(sizeof(vrl1_vgax_offset_t *)*num_of_vrl);//TODO: USE MM_ CA_ AND PM_
+//#else
+	MM_GetPtr(MEMPTRCONV gvar->ca.grsegs[0], sizeof(vrl1_vgax_offset_t *)*num_of_vrl, gvar);
+	enti->spri.sprite_vrl_cont.vrl_line_offsets = (vrl1_vgax_offset_t **)gvar->ca.grsegs[0];
+//#endif
+
+	vrl_headers_offsets = (uint32_t far *)(enti->spri.sprite_vrl_cont.buffer + enti->spri.sprite_vrl_cont.vrs_hdr->offset_table[VRS_HEADER_OFFSET_VRS_LIST]);
+	// Calculate line offsets for each vrl
+	for(i = 0; i < num_of_vrl; i++){
+		curr_vrl = (struct vrl1_vgax_header far *)(enti->spri.sprite_vrl_cont.buffer + vrl_headers_offsets[i]);
+
+		// Calc. vrl size as (next_offset - curr_offset)
+		if (i != num_of_vrl - 1){
+			vrl_size = vrl_headers_offsets[i+1] - vrl_headers_offsets[i] - sizeof(struct vrl1_vgax_header);
+		}
+		// If it's the last vrl, size is (next_vrs_struct_offset - curr_offset)
+		else{
+			vrl_size = enti->spri.sprite_vrl_cont.vrs_hdr->offset_table[VRS_HEADER_OFFSET_SPRITE_ID_LIST] - vrl_headers_offsets[i] - sizeof(struct vrl1_vgax_header);
+		}
+#ifndef VRS_USECAMMPM
+		vrl_line_offsets = vrl1_vgax_genlineoffsets(curr_vrl, (byte *)curr_vrl + sizeof(struct vrl1_vgax_header), vrl_size);
+#else
+		enti->spri.sprite_vrl_cont.vrl_line_offsets[i] = vrl1_vgax_genlineoffsets(curr_vrl, (byte *)curr_vrl + sizeof(struct vrl1_vgax_header), vrl_size);
+#endif
+	}
+#endif
+
+		vrl_line_offsets = vrl1_vgax_genlineoffsets(enti->spri.sprite_vrl_cont.vrl_header,	(byte *)enti->spri.sprite_vrl_cont.buffer + sizeof(struct vrl1_vgax_header),	vrl_size);
+#ifndef VRS_USECAMMPM
+	enti->spri.sprite_vrl_cont.vrl_line_offsets = vrl_line_offsets;
+#endif
 }
 
 // Seek and return a specified .vrl blob from .vrs blob in far memory
diff --git a/src/lib/16_vrs.h b/src/lib/16_vrs.h
index 07e75321..eae13673 100755
--- a/src/lib/16_vrs.h
+++ b/src/lib/16_vrs.h
@@ -64,6 +64,9 @@ struct vrl_container{
 void VRS_ReadVRS(char *filename, entity_t *enti, global_game_variables_t *gvar);
 void VRS_LoadVRS(char *filename, entity_t *enti, global_game_variables_t *gvar);
 void VRS_OpenVRS(char *filename, entity_t *enti, boolean rlsw, global_game_variables_t *gvar);
+void VRS_ReadVRL(char *filename, entity_t *enti, global_game_variables_t *gvar);
+void VRS_LoadVRL(char *filename, entity_t *enti, global_game_variables_t *gvar);
+void VRS_OpenVRL(char *filename, entity_t *enti, boolean rlsw, global_game_variables_t *gvar);
 
 /* Seek and return a specified .vrl blob from .vrs blob in memory
 * In:
diff --git a/src/xcroll.c b/src/xcroll.c
index cea17795..e31ff558 100755
--- a/src/xcroll.c
+++ b/src/xcroll.c
@@ -27,7 +27,6 @@
 #define FADE
 //#define NOMAPLOAD
 
-//map_view_t mv[4];
 static map_t map;
 float t;
 
@@ -47,21 +46,26 @@ memptr pal;
 #define FILENAME_1P	"data/spri/chikyuu.pal"
 #define FILENAME_2	"data/spri/me.vrs"
 #define FILENAME_2P	"data/spri/me.pal"
+#define FILENAME_3	"data/spri/chistnd.vrl"
 
 void main(int argc, char *argv[])
 {
 	static global_game_variables_t gvar;
 	struct glob_game_vars *ggvv;
-	char bakapee1[64] = FILENAME_1;
-	char bakapee1p[64] = FILENAME_1P;
+
+//	static entity_t enti;
+
+	char bakapee[64] = FILENAME_1;
+	char bakapeep[64] = FILENAME_1P;
+	char bakapee3[64] = FILENAME_3;
 
 	Startup16(&gvar);
 
 	ggvv=&gvar;
 
 	if (argc >= 2) {
-		if(argv[1]){ strcpy(bakapee1, argv[1]);
-		if(argv[2]) strcpy(bakapee1p, argv[2]); }
+		if(argv[1]){ strcpy(bakapee, argv[1]);
+		if(argv[2]) strcpy(bakapeep, argv[2]); }
 	}
 
 	// OK, this one takes hellova time and needs to be done in farmalloc or MM_...
@@ -81,7 +85,8 @@ void main(int argc, char *argv[])
 	//initMap(&map);
 #endif
 	// data
-	VRS_LoadVRS(bakapee1, &gvar.player[0].enti, &gvar);
+	VRS_LoadVRS(bakapee, &gvar.player[0].enti, &gvar);
+//	VRS_LoadVRS(bakapee3, &enti, &gvar);
 
 	// input!
 	IN_Default(0, &gvar.player[0],ctrl_Keyboard1, &gvar);
@@ -104,7 +109,7 @@ void main(int argc, char *argv[])
 	//printf("1:	%d\n", paloffset);
 	map.tiles->data->offset=(paloffset/3);
 	modexPalUpdate(map.tiles->data, &paloffset, 0, 0);*/
-	VL_LoadPalFile(bakapee1p, &gvar.video.palette, &gvar);
+	VL_LoadPalFile(bakapeep, &gvar.video.palette, &gvar);
 	//VL_LoadPalFile("data/default.pal", &gvar.video.palette);
 
 #ifdef FADE
@@ -121,7 +126,7 @@ void main(int argc, char *argv[])
 	modexFadeOn(4, &gvar.video.palette);
 #endif
 
-//	IN_StartAck (&gvar);	MM_ShowMemory(&gvar);	while (!IN_CheckAck (&gvar)){}
+//0000	IN_StartAck (&gvar);	MM_ShowMemory(&gvar);	while (!IN_CheckAck (&gvar)){}
 #ifdef FADE
 	modexPalBlack();	//so player will not see loadings~
 #endif
@@ -191,29 +196,43 @@ void main(int argc, char *argv[])
 
 		TAIL_FUNCTIONKEYFUNCTIONS
 		TAIL_FUNCTIONKEYDRAWJUNK
-//		if(gvar.in.inst->Keyboard[sc_L]){ modexClearRegion(&gvar.video.page[0], gvar.player[0].enti.x, gvar.player[0].enti.y, 16, 16, 1); }
-		if(gvar.in.inst->Keyboard[sc_L]){ ShowPalVal (&gvar);								IN_UserInput(1, &gvar); }
+		if(gvar.in.inst->Keyboard[sc_L]){ modexClearRegion(&gvar.video.page[0], gvar.player[0].enti.x, gvar.player[0].enti.y, 16, 16, 1); }
+		if(gvar.in.inst->Keyboard[sc_LBrkt]){ ShowPalVal (&gvar);								IN_UserInput(1, &gvar); }
+
+//===============================================================================
+
+		if(gvar.in.inst->Keyboard[sc_BackSlash]){
+			VRS_ReadVRL(bakapee3, &gvar.player[0].enti, &gvar);
+			DrawVRL(
+				gvar.player[0].enti.x,
+				gvar.player[0].enti.y,
+				gvar.player[0].enti.spri.sprite_vrl_cont.vrl_header,
+				gvar.player[0].enti.spri.sprite_vrl_cont.line_offsets,
+				gvar.player[0].enti.spri.sprite_vrl_cont.buffer + sizeof(struct vrl1_vgax_header),
+				gvar.player[0].enti.spri.sprite_vrl_cont.data_size
+			);	while (!IN_CheckAck (&gvar)){}
+			VRS_ReadVRS(bakapee, &gvar.player[0].enti, &gvar);
+		IN_UserInput(1, &gvar); }
+
+//===============================================================================
+
 		if(gvar.in.inst->Keyboard[sc_J] || gvar.in.inst->Keyboard[sc_K])
 		{
 			if(gvar.in.inst->Keyboard[sc_J])
 			{
-//				bakapee1=FILENAME_1;
-//				bakapee1p=FILENAME_1P;
-				strcpy(bakapee1, FILENAME_1);
-				strcpy(bakapee1p, FILENAME_1P);
+				strcpy(bakapee, FILENAME_1);
+				strcpy(bakapeep, FILENAME_1P);
 				gvar.player[0].enti.overdraww=0;
 			}
 			if(gvar.in.inst->Keyboard[sc_K])
 			{
-//				bakapee1=FILENAME_2;
-//				bakapee1p=FILENAME_2P;
-				strcpy(bakapee1, FILENAME_2);
-				strcpy(bakapee1p, FILENAME_2P);
+				strcpy(bakapee, FILENAME_2);
+				strcpy(bakapeep, FILENAME_2P);
 				gvar.player[0].enti.overdraww=2;
 			}
-			//read_vrs(&gvar, bakapee1, gvar.player[0].enti.spri->spritesheet);
-			VRS_ReadVRS(bakapee1, &gvar.player[0].enti, &gvar);
-			VL_LoadPalFile(bakapee1p, &gvar.video.palette, &gvar);
+			//read_vrs(&gvar, bakapee, gvar.player[0].enti.spri->spritesheet);
+			VRS_ReadVRS(bakapee, &gvar.player[0].enti, &gvar);
+			VL_LoadPalFile(bakapeep, &gvar.video.palette, &gvar);
 		}//JK
 #ifdef FADE
 		if(gvar.in.inst->Keyboard[10]){ modexPalOverscan(rand()%56); modexPalUpdate(gvar.video.dpal); IN_UserInput(1, &gvar); }