added debug reg sprite plane support (fixes some issues in overdrive 2 demo)
authorkub <derkub@gmail.com>
Sun, 26 Jan 2020 19:43:05 +0000 (20:43 +0100)
committerkub <derkub@gmail.com>
Sun, 26 Jan 2020 19:43:05 +0000 (20:43 +0100)
pico/draw.c

index 652b9df..01153f3 100644 (file)
@@ -223,6 +223,14 @@ TileFlipMakerAS(TileFlipAS_onlymark, pix_sh_as_onlymark)
 TileNormMaker(TileNorm_and, pix_and)\r
 TileFlipMaker(TileFlip_and, pix_and)\r
 \r
+// forced sprite draw (through debug reg)\r
+#define pix_sh_and(x) /* XXX is there S/H with forced draw? */ \\r
+  if (t>=0xe) pd[x]=(pd[x]&0x3f)|(t<<6); /* c0 shadow, 80 hilight */ \\r
+  else pd[x] = (pd[x] & 0xc0) | (pd[x] & (pal | t))\r
\r
+TileNormMaker(TileNormSH_and, pix_sh_and)\r
+TileFlipMaker(TileFlipSH_and, pix_sh_and)\r
+\r
 // --------------------------------------------\r
 \r
 #ifndef _ASM_DRAW_C\r
@@ -1045,6 +1053,66 @@ static void DrawSpritesHiAS(unsigned char *sprited, int sh)
   }\r
 }\r
 \r
+static void DrawSpritesForced(unsigned char *sprited)\r
+{\r
+  void (*fTileFunc)(unsigned char *pd, unsigned int pack, int pal);\r
+  unsigned char *pd = Pico.est.HighCol;\r
+  unsigned char *p;\r
+  int entry, cnt;\r
+\r
+  cnt = sprited[0] & 0x7f;\r
+  if (cnt == 0) return;\r
+\r
+  p = &sprited[4];\r
+  if ((sprited[1] & (SPRL_TILE_OVFL|SPRL_HAVE_MASK0)) == (SPRL_TILE_OVFL|SPRL_HAVE_MASK0))\r
+    return; // masking effective due to tile overflow\r
+\r
+  // Go through sprites:\r
+  for (entry = 0; entry < cnt; entry++)\r
+  {\r
+    int *sprite, code, pal, tile, sx, sy;\r
+    int offs, delta, width, height, row;\r
+\r
+    offs = (p[entry] & 0x7f) * 2;\r
+    sprite = HighPreSpr + offs;\r
+    code = sprite[1];\r
+    pal = (code>>9)&0x30;\r
+\r
+    if (code&0x800) fTileFunc = TileFlipSH_and;\r
+    else            fTileFunc = TileNormSH_and;\r
+\r
+    // parse remaining sprite data\r
+    sy=sprite[0];\r
+    sx=code>>16; // X\r
+    width=sy>>28;\r
+    height=(sy>>24)&7; // Width and height in tiles\r
+    sy=(sy<<16)>>16; // Y\r
+\r
+    row=Pico.est.DrawScanline-sy; // Row of the sprite we are on\r
+\r
+    if (code&0x1000) row=(height<<3)-1-row; // Flip Y\r
+\r
+    tile=code + (row>>3); // Tile number increases going down\r
+    delta=height; // Delta to increase tile by going right\r
+    if (code&0x0800) { tile+=delta*(width-1); delta=-delta; } // Flip X\r
+\r
+    tile &= 0x7ff; tile<<=4; tile+=(row&7)<<1; // Tile address\r
+    delta<<=4; // Delta of address\r
+\r
+    if (entry+1 == cnt) width = p[entry+1]; // last sprite width limited?\r
+    for (; width; width--,sx+=8,tile+=delta)\r
+    {\r
+      unsigned int pack;\r
+\r
+      if(sx<=0)   continue;\r
+      if(sx>=328) break; // Offscreen\r
+\r
+      pack = *(unsigned int *)(PicoMem.vram + (tile & 0x7fff));\r
+      fTileFunc(pd + sx, pack, pal);\r
+    }\r
+  }\r
+}\r
+\r
 \r
 // Index + 0  :    ----hhvv -lllllll -------y yyyyyyyy\r
 // Index + 4  :    -------x xxxxxxxx pccvhnnn nnnnnnnn\r
@@ -1529,6 +1597,8 @@ static int DrawDisplay(int sh)
     DrawTilesFromCacheForced(HighCacheB);\r
   else if (pvid->debug_p & PVD_FORCE_A)\r
     DrawTilesFromCacheForced(HighCacheA);\r
+  else if (pvid->debug_p & PVD_FORCE_S)\r
+    DrawSpritesForced(sprited);\r
 \r
 #if 0\r
   {\r
@@ -1621,7 +1691,7 @@ static void PicoLine(int line, int offs, int sh, int bgc)
     return;\r
   }\r
 \r
-  if (Pico.video.debug_p & (PVD_FORCE_A | PVD_FORCE_B))\r
+  if (Pico.video.debug_p & (PVD_FORCE_A | PVD_FORCE_B | PVD_FORCE_S))\r
     bgc = 0x3f;\r
 \r
   // Draw screen:\r