]> 4ch.mooo.com Git - plz.git/commitdiff
added js file for help ww
authorsparky4 <sparky4@cock.li>
Sat, 13 Feb 2016 21:39:10 +0000 (15:39 -0600)
committersparky4 <sparky4@cock.li>
Sat, 13 Feb 2016 21:39:10 +0000 (15:39 -0600)
Plasma.js [new file with mode: 0755]

diff --git a/Plasma.js b/Plasma.js
new file mode 100755 (executable)
index 0000000..bc1ab3a
--- /dev/null
+++ b/Plasma.js
@@ -0,0 +1,1069 @@
+var SCREEN_WIDTH = 320;\r
+var SCREEN_HEIGHT = 400;\r
+var FRAME_BUFFER_WIDTH = 384;\r
+var FRAME_BUFFER_HEIGHT = 400;\r
+var PLANE_COUNT = 4;\r
+var COLOURS_PER_ENTRY = 3;\r
+var DPII = (3.1415926535*2.0);\r
+var MAXY = 280;\r
+\r
+var g_au8FrameBuffer = new Uint8Array(FRAME_BUFFER_WIDTH * FRAME_BUFFER_HEIGHT);\r
+var s_abSelectedPlanes = [ false, false, false, false ];\r
+var s_nLineCompareY = 0;\r
+var s_nHorizontalScrollOffset = 0;\r
+var s_au8Palette = new Uint8Array(256 * COLOURS_PER_ENTRY);\r
+var frame_count = 0;\r
+var cop_drop = 0;\r
+var do_pal = 0;\r
+var cop_start = 0;\r
+var cop_scrl = 0;\r
+var cop_plz = 1;\r
+var pompi = 0;\r
+var dtau = new Array();\r
+var fadepal = new Uint8Array(768 * 2);\r
+var cop_fadepal_SelectedPaletteIndex = 0;\r
+var anSelfModifyOffsets = new Uint16Array(5 * 84);\r
+\r
+// [NK 8/1/2014] The assembly code assumes the tables are sequential in memory,\r
+// [NK 8/1/2014] so merge them into one array to be safe.\r
+var psini = new Uint8Array(16384 + (8192 * 2) + (8192 * 2));\r
+var psini_DataView = new DataView(psini.buffer);\r
+var ptau = new Uint8Array(256);\r
+var pals = new Uint16Array(6 * 768);\r
+var pals_DataView = new DataView(pals.buffer);\r
+\r
+var curpal=0;\r
+var timetable=[64*6*2-45,64*6*4-45,64*6*5-45,64*6*6-45,64*6*7+90,0];\r
+var ttptr=0;\r
+\r
+var    l1=1000, l2=2000, l3=3000, l4=4000;\r
+var    k1=3500, k2=2300, k3=3900, k4=3670;\r
+\r
+var    il1=1000, il2=2000, il3=3000, il4=4000;\r
+var    ik1=3500, ik2=2300, ik3=3900, ik4=3670;\r
+\r
+var inittable = new Array();\r
+var IsComplete = false;\r
+\r
+//--------------------------------------------------------------------------------------\r
+// Variable wrappers\r
+\r
+function Palette_WriteByte(nOffset, u8Byte)\r
+{\r
+       s_au8Palette[nOffset] = u8Byte;\r
+}\r
+\r
+function Palette_ReadByte(nOffset)\r
+{\r
+       return s_au8Palette[nOffset];\r
+}\r
+\r
+function FrameBuffer_WriteByte(nOffset, u8Byte)\r
+{\r
+       g_au8FrameBuffer[nOffset] = u8Byte;\r
+}\r
+\r
+function FrameBuffer_ReadByte(nOffset)\r
+{\r
+       return g_au8FrameBuffer[nOffset];\r
+}\r
+\r
+function lsini16_GetOffset()\r
+{\r
+       return 16384 + (8192 * 2);\r
+}\r
+\r
+function lsini4_GetOffset()\r
+{\r
+       return 16384;\r
+}\r
+\r
+function cop_fadepal_SetSelectedPaletteIndex(nIndex)\r
+{\r
+       cop_fadepal_SelectedPaletteIndex = nIndex;\r
+}\r
+\r
+function cop_fadepal_ReadWord(nByteOffset)\r
+{\r
+       // Advance to the currently selected palette.\r
+       nByteOffset += (cop_fadepal_SelectedPaletteIndex * 768 * 2);\r
+\r
+       return pals_DataView.getUint16(nByteOffset);\r
+}\r
+\r
+function fadepal_ReadByte(nByteOffset)\r
+{\r
+       return fadepal[nByteOffset];\r
+}\r
+\r
+function fadepal_WriteByte(nByteOffset, nValue)\r
+{\r
+       fadepal[nByteOffset] = nValue;\r
+}\r
+\r
+function lsini4_WriteWord(nIndex, nValue)\r
+{\r
+       var nByteOffset = lsini4_GetOffset() + (nIndex * 2);\r
+       psini_WriteWord(nByteOffset, nValue);\r
+}\r
+\r
+function lsini16_WriteWord(nIndex, nValue)\r
+{\r
+       var nByteOffset = lsini16_GetOffset() + (nIndex * 2);\r
+       psini_WriteWord(nByteOffset, nValue);\r
+}\r
+\r
+function psini_WriteByte(nIndex, nValue)\r
+{\r
+       psini[nIndex] = nValue;\r
+}\r
+\r
+function psini_ReadByte(nIndex, nValue)\r
+{\r
+       return psini[nIndex];\r
+}\r
+\r
+function psini_WriteWord(nByteOffset, nValue) {\r
+       psini_DataView.setUint16(nByteOffset, nValue);\r
+}\r
+\r
+function psini_ReadWord(nByteOffset, nValue) {\r
+       return psini_DataView.getUint16(nByteOffset);\r
+}\r
+\r
+function ptau_WriteByte(nIndex, nValue)\r
+{\r
+       ptau[nIndex] = nValue;\r
+}\r
+\r
+function ptau_ReadByte(nIndex)\r
+{\r
+       return ptau[nIndex];\r
+}\r
+\r
+function pal_WriteWord(nByteOffset, nWord)\r
+{\r
+       pals_DataView.setUint16(nByteOffset, nWord);\r
+}\r
+\r
+function pal_ReadWord(nByteOffset)\r
+{\r
+       return pals_DataView.getUint16(nByteOffset);\r
+}\r
+\r
+function fadepal_Clear()\r
+{\r
+       for (var i = 0; i < 768; i++)\r
+       {\r
+               fadepal[i] = 0;\r
+       }\r
+}\r
+\r
+function fadepal_ClearToWhite() {\r
+       for (var i = 0; i < 768; i++) {\r
+               fadepal[i] = 63;\r
+       }\r
+}\r
+\r
+function anSelfModifyOffsets_ReadWord(nOffset)\r
+{\r
+       return anSelfModifyOffsets[nOffset];\r
+}\r
+\r
+function anSelfModifyOffsets_WriteWord(nOffset, nValue)\r
+{\r
+       anSelfModifyOffsets[nOffset] = nValue;\r
+}\r
+\r
+//--------------------------------------------------------------------------------------\r
+// SDL\r
+\r
+function SDL_SetPixel(x, y, color)\r
+{\r
+       var pixels = image.data;\r
+       var nOffset = (((y * 320) + x) * 4);\r
+       pixels[nOffset] = (color >> 0) & 0xFF;\r
+       nOffset++;\r
+       pixels[nOffset] = (color >> 8) & 0xFF;\r
+       nOffset++;\r
+       pixels[nOffset] = (color >> 16) & 0xFF;\r
+       nOffset++;\r
+       pixels[nOffset] = 0xFF;\r
+       nOffset++;\r
+}\r
+\r
+function SDL_SetPixelColours(x, y, nRed, nGreen, nBlue)\r
+{\r
+       var pixels = image.data;\r
+       var nOffset = (((y * 320) + x) * 4);\r
+       pixels[nOffset] = (nRed) & 0xFF;\r
+       nOffset++;\r
+       pixels[nOffset] = (nGreen) & 0xFF;\r
+       nOffset++;\r
+       pixels[nOffset] = (nBlue) & 0xFF;\r
+       nOffset++;\r
+       pixels[nOffset] = 0xFF;\r
+       nOffset++;\r
+}\r
+\r
+//--------------------------------------------------------------------------------------\r
+// VGA\r
+\r
+function VGA_SelectBitPlanes02()\r
+{\r
+       s_abSelectedPlanes[0] = true;\r
+       s_abSelectedPlanes[1] = false;\r
+       s_abSelectedPlanes[2] = true;\r
+       s_abSelectedPlanes[3] = false;\r
+}\r
+\r
+function VGA_SelectBitPlanes13()\r
+{\r
+       s_abSelectedPlanes[0] = false;\r
+       s_abSelectedPlanes[1] = true;\r
+       s_abSelectedPlanes[2] = false;\r
+       s_abSelectedPlanes[3] = true;\r
+}\r
+\r
+function VGA_SelectBitPlanes0123()\r
+{\r
+       s_abSelectedPlanes[0] = true;\r
+       s_abSelectedPlanes[1] = true;\r
+       s_abSelectedPlanes[2] = true;\r
+       s_abSelectedPlanes[3] = true;\r
+}\r
+\r
+function VGA_WriteDword(nOffset, uValue)\r
+{\r
+       // For each selected plane, calculate 4 pixel offsets and write 4 bytes.\r
+       // nOffset = 0, 4, 8, etc\r
+\r
+       for (var nPlaneIndex = 0; nPlaneIndex < PLANE_COUNT; nPlaneIndex++)\r
+       {\r
+               if (s_abSelectedPlanes[nPlaneIndex])\r
+               {\r
+                       for (var nPixelIndex = 0; nPixelIndex < 4; nPixelIndex++)\r
+                       {\r
+                               // Get byte to write.\r
+                               var u8Byte = (uValue >> (nPixelIndex * 8)) & 0xFF;\r
+\r
+                               // Calculate offset.\r
+                               var nFrameBufferOffset = nPlaneIndex + (nOffset * 4) + (nPixelIndex * 4);\r
+\r
+                               // Write pixel.\r
+                               FrameBuffer_WriteByte(nFrameBufferOffset, u8Byte);\r
+                       }\r
+               }\r
+       }\r
+}\r
+\r
+function VGA_SetLineCompare(nY)\r
+{\r
+       s_nLineCompareY = nY;\r
+}\r
+\r
+function VGA_SetPaletteEntry(nIndex, u8Red, u8Green, u8Blue)\r
+{\r
+       var nOffset = 0;\r
+\r
+       nOffset = (nIndex * 3) + 0;\r
+       Palette_WriteByte(nOffset, u8Red);\r
+\r
+       nOffset = (nIndex * 3) + 1;\r
+       Palette_WriteByte(nOffset, u8Green);\r
+\r
+       nOffset = (nIndex * 3) + 2;\r
+       Palette_WriteByte(nOffset, u8Blue);\r
+}\r
+\r
+function VGA_ShowFrameBuffer()\r
+{\r
+       copper1();\r
+       copper2();\r
+\r
+       var nFirstLineIndex = (s_nLineCompareY + 1);\r
+\r
+       // Plot the palettised frame buffer.\r
+       var nFrameBufferOffset = 0;\r
+\r
+       for (var nY = nFirstLineIndex; nY < SCREEN_HEIGHT; nY++)\r
+       {\r
+               for (var nX = 0; nX < SCREEN_WIDTH; nX++)\r
+               {\r
+                       //ASSERT(nX + s_nHorizontalScrollOffset < FRAME_BUFFER_WIDTH);\r
+                       var nPaletteIndex = FrameBuffer_ReadByte(nFrameBufferOffset + nX + s_nHorizontalScrollOffset);\r
+\r
+                       var nPaletteOffset = 0;\r
+                       nPaletteOffset = (nPaletteIndex * 3) + 0;\r
+                       var nRed = Palette_ReadByte(nPaletteOffset);\r
+                       nPaletteOffset = (nPaletteIndex * 3) + 1;\r
+                       var nGreen = Palette_ReadByte(nPaletteOffset);\r
+                       nPaletteOffset = (nPaletteIndex * 3) + 2;\r
+                       var nBlue = Palette_ReadByte(nPaletteOffset);\r
+\r
+                       // [NK 12/1/2014] VGA colours range from 0 - 63 inclusive, but\r
+                       // [NK 12/1/2014] SDL colours range from 0 - 255 inclusive, so\r
+                       // [NK 12/1/2014] account for this here.\r
+                       nRed &= 63;\r
+                       nGreen &= 63;\r
+                       nBlue &= 63;\r
+\r
+                       nRed *= 255;\r
+                       nRed /= 63;\r
+                       nGreen *= 255;\r
+                       nGreen /= 63;\r
+                       nBlue *= 255;\r
+                       nBlue /= 63;\r
+\r
+                       SDL_SetPixelColours(nX, nY, nRed, nGreen, nBlue);\r
+               }\r
+\r
+               nFrameBufferOffset += FRAME_BUFFER_WIDTH;\r
+       }\r
+}\r
+\r
+function VGA_SetHorizontalScrollOffset(nOffset)\r
+{\r
+       s_nHorizontalScrollOffset = nOffset;\r
+}\r
+\r
+function VGA_UploadPalette(Palette)\r
+{\r
+       var Source = new Uint8Array(Palette.buffer, 0, 768);\r
+       var Destination = s_au8Palette;\r
+       Destination.set(Source);\r
+}\r
+\r
+//--------------------------------------------------------------------------------------\r
+// Tweak\r
+\r
+function tw_setrgbpalette(pal, r, g, b)\r
+{\r
+       VGA_SetPaletteEntry(pal, r, g, b);\r
+}\r
+\r
+//--------------------------------------------------------------------------------------\r
+// Asmyt\r
+\r
+function plzline(y, vseg)\r
+{\r
+       // vseg represented a segment, so multiply by sixteen (shift left by 4)\r
+       // to convert into an offset.\r
+       var nVgaYOffset = vseg * 16;\r
+\r
+       var cccTable =\r
+       [\r
+               3,2,1,0,7,6,5,4,11,10,9,8,15,14,13,12,19,18,17,16,23,22,21,20,27,26,25,24,31,30,29,28,35,34,33,32,39,38,37,36,43,42,41,40,47,46,45,44,51,50,49,48,55,54,53,52,59,58,57,56,63,62,61,60,67,66,65,64,71,70,69,68,75,74,73,72,79,78,77,76,83,82,81,80\r
+       ];\r
+       var nCount = 84;\r
+\r
+       var ah = 0;\r
+       var al = 0;\r
+       var eax = 0;\r
+\r
+       for (var nIndex = 0; nIndex < nCount; nIndex++)\r
+       {\r
+               var ccc = cccTable[nIndex];\r
+\r
+               if ((ccc & 1) == 1)\r
+               {\r
+                       var nByteOffset = 0;\r
+                       var bx = 0;\r
+\r
+                       nByteOffset = (y * 2) + anSelfModifyOffsets_ReadWord((2 * 84) + ccc);\r
+                       nByteOffset &= 0xFFFF;\r
+                       bx = psini_ReadWord(nByteOffset);\r
+\r
+                       nByteOffset = bx + anSelfModifyOffsets_ReadWord((1 * 84) + ccc);\r
+                       nByteOffset &= 0xFFFF;\r
+                       ah = psini_ReadByte(nByteOffset);\r
+\r
+                       nByteOffset = (y * 2) + anSelfModifyOffsets_ReadWord((4 * 84) + ccc);\r
+                       nByteOffset &= 0xFFFF;\r
+                       bx = psini_ReadWord(nByteOffset);\r
+\r
+                       nByteOffset = bx + (y * 2) + anSelfModifyOffsets_ReadWord((3 * 84) + ccc);\r
+                       nByteOffset &= 0xFFFF;\r
+                       ah += psini_ReadByte(nByteOffset);\r
+                       ah &= 0xFF;\r
+               }\r
+               else\r
+               {\r
+                       var nByteOffset = 0;\r
+                       var bx = 0;\r
+\r
+                       nByteOffset = (y * 2) + anSelfModifyOffsets_ReadWord((2 * 84) + ccc);\r
+                       nByteOffset &= 0xFFFF;\r
+                       bx = psini_ReadWord(nByteOffset);\r
+\r
+                       nByteOffset = bx + anSelfModifyOffsets_ReadWord((1 * 84) + ccc);\r
+                       nByteOffset &= 0xFFFF;\r
+                       al = psini_ReadByte(nByteOffset);\r
+\r
+                       nByteOffset = (y * 2) + anSelfModifyOffsets_ReadWord((4 * 84) + ccc);\r
+                       nByteOffset &= 0xFFFF;\r
+                       bx = psini_ReadWord(nByteOffset);\r
+\r
+                       nByteOffset = bx + (y * 2) + anSelfModifyOffsets_ReadWord((3 * 84) + ccc);\r
+                       nByteOffset &= 0xFFFF;\r
+                       al += psini_ReadByte(nByteOffset);\r
+                       al &= 0xFF;\r
+               }\r
+\r
+               if ((ccc & 3) == 2)\r
+               {\r
+                       eax = (ah << 8) | (al << 0);\r
+                       eax <<= 16;\r
+               }\r
+\r
+               if ((ccc & 3) == 0)\r
+               {\r
+                       eax |= (ah << 8) | (al << 0);\r
+\r
+                       VGA_WriteDword(nVgaYOffset + ccc, eax);\r
+               }\r
+       }\r
+\r
+       return 0;\r
+}\r
+\r
+function setplzparas(c1, c2, c3, c4)\r
+{\r
+       var psiniOffset = 0;\r
+       var lsini16Offset = lsini16_GetOffset();\r
+       var lsini4Offset = lsini4_GetOffset();\r
+\r
+       for (var ccc = 0; ccc < 84; ccc++)\r
+       {\r
+               var lc1 = c1 + psiniOffset + (ccc * 8);\r
+               lc1 &= 0xFFFF;\r
+               anSelfModifyOffsets_WriteWord((1 * 84) + ccc, lc1);\r
+\r
+               var lc2 = (c2 * 2) + lsini16Offset - (ccc * 8) + (80 * 8); \r
+               lc2 &= 0xFFFF;\r
+               anSelfModifyOffsets_WriteWord((2 * 84) + ccc, lc2);\r
+\r
+               var lc3 = c3 + psiniOffset - (ccc * 4) + (80 * 4);\r
+               lc3 &= 0xFFFF;\r
+               anSelfModifyOffsets_WriteWord((3 * 84) + ccc, lc3);\r
+\r
+               var lc4 = (c4 * 2) + lsini4Offset + (ccc * 32);\r
+               lc4 &= 0xFFFF;\r
+               anSelfModifyOffsets_WriteWord((4 * 84) + ccc, lc4);\r
+       }       \r
+\r
+       return 0;\r
+}\r
+\r
+function set_plzstart(start)\r
+{\r
+       VGA_SetLineCompare(start);\r
+\r
+       return 0;\r
+}\r
+\r
+\r
+//--------------------------------------------------------------------------------------\r
+// Copper\r
+\r
+function init_copper()\r
+{\r
+       for (var ccc = 0; ccc < 65; ccc++)\r
+       {\r
+               dtau[ccc] = Math.floor(ccc * ccc / 4 * 43 / 128 + 60);\r
+       }\r
+\r
+       return 0;\r
+}\r
+\r
+function close_copper()\r
+{\r
+       return 0;\r
+}\r
+\r
+function pompota() {\r
+\r
+       // [NK 18/1/2014] Disable this for now, as it looks a bit jittery.\r
+       return;\r
+\r
+       // [nk] This function toggles the horizontal split point every frame\r
+       // [nk] between line 60 and 61, along with the horizontal offset.\r
+       // [nk] (since set_plzstart == 60, it's splitting at the top of the plasma)\r
+       VGA_SetLineCompare(60);\r
+       cop_scrl = 4;\r
+\r
+       pompi++;\r
+\r
+       if ((pompi & 1) != 0)\r
+       {\r
+               // [NK 12/1/2014] Moving the starting line up and down each alternate frame\r
+               // [NK 12/1/2014] doesn't look good in windowed mode.\r
+               // [NK 13/1/2014] Seems to work okay in fullscreen mode though.\r
+               //VGA_SetLineCompare(61);\r
+               cop_scrl = 0;\r
+       }\r
+}\r
+\r
+function moveplz()\r
+{\r
+       k1 += -3;\r
+       k1 &= 4095;\r
+       k2 += -2;\r
+       k2 &= 4095;\r
+       k3 += 1;\r
+       k3 &= 4095;\r
+       k4 += 2;\r
+       k4 &= 4095;\r
+       l1 += -1;\r
+       l1 &= 4095;\r
+       l2 += -2;\r
+       l2 &= 4095;\r
+       l3 += 2;\r
+       l3 &= 4095;\r
+       l4 += 3;\r
+       l4 &= 4095;\r
+}\r
+\r
+function initpparas()\r
+{\r
+       l1 = il1;\r
+       l2 = il2;\r
+       l3 = il3;\r
+       l4 = il4;\r
+\r
+       k1 = ik1;\r
+       k2 = ik2;\r
+       k3 = ik3;\r
+       k4 = ik4;\r
+}\r
+\r
+function do_drop()\r
+{\r
+       cop_drop++;\r
+\r
+       if (cop_drop <= 64)\r
+       {\r
+               VGA_SetLineCompare(dtau[cop_drop]);\r
+       }\r
+       else\r
+       {\r
+               var bShouldFade = false;\r
+\r
+               // [NK 18/1/2014] Hack for looping back to the first plasma.\r
+               if ((cop_drop == 65) && (ttptr == 0)) {\r
+                       cop_drop = 128;\r
+               }\r
+\r
+               if (cop_drop >= 256)\r
+               {\r
+               }\r
+               else if (cop_drop >= 128)\r
+               {\r
+                       bShouldFade = true;\r
+               }\r
+               else if (cop_drop > 96)\r
+               {\r
+               }\r
+               else //if (cop_drop > 64)\r
+               {\r
+                       bShouldFade = true;\r
+               }\r
+\r
+               if (bShouldFade)\r
+               {\r
+                       // [NK 15/1/2014] cop_pal always points to fadepal, so just upload fadepal.\r
+                       //cop_pal = fadepal;\r
+                       do_pal = 1;\r
+\r
+                       if (cop_drop == 65)\r
+                       {\r
+                               VGA_SetLineCompare(400);\r
+                               initpparas();\r
+                       }\r
+                       else\r
+                       {\r
+                               VGA_SetLineCompare(60);\r
+\r
+                               // [NK 9/1/2014] I think it's using 8.8 fixed point numbers to fade the palette.\r
+                               var cop_fadepalIndex = 0;\r
+                               var pfadepalIndex = 0;\r
+\r
+                               for (var nIndex = 0; nIndex < (768 / 16); nIndex++)\r
+                               {\r
+                                       for (var ccc = 0; ccc < 16; ccc++)\r
+                                       {\r
+                                               // var al = cop_fadepal_ReadByte(cop_fadepalIndex + (ccc * 2));\r
+                                               // al &= 0xFF;\r
+                                               // var ah = cop_fadepal_ReadByte(cop_fadepalIndex + (ccc * 2) + 1);\r
+                                               // ah &= 0xFF;\r
+                                               // [NK 17/1/2014] Read cop_fadepal as words, rather than bytes,\r
+                                               // [NK 17/1/2014] to avoid endian issues.\r
+                                               var ax = cop_fadepal_ReadWord(cop_fadepalIndex + (ccc * 2));\r
+                                               var al = ax & 0xFF;\r
+                                               var ah = (ax >> 8) & 0xFF;\r
+\r
+                                               var nOldValue = fadepal_ReadByte(pfadepalIndex + ccc + 768);\r
+                                               nOldValue &= 0xFF;\r
+\r
+                                               var t = fadepal_ReadByte(pfadepalIndex + ccc + 768);\r
+                                               t &= 0xFF;\r
+                                               t += al;\r
+                                               t &= 0xFF;\r
+                                               fadepal_WriteByte(pfadepalIndex + ccc + 768, t);\r
+\r
+                                               var nNewValue = fadepal_ReadByte(pfadepalIndex + ccc + 768);\r
+                                               nNewValue &= 0xFF;\r
+\r
+                                               var nCarry = 0;\r
+\r
+                                               if (nNewValue < nOldValue)\r
+                                               {\r
+                                                       nCarry = 1;\r
+                                               }\r
+\r
+                                               t = fadepal_ReadByte(pfadepalIndex + ccc);\r
+                                               t &= 0xFF;\r
+                                               t += ah + nCarry;\r
+                                               t &= 0xFF;\r
+                                               fadepal_WriteByte(pfadepalIndex + ccc, t);\r
+                                       }\r
+\r
+                                       cop_fadepalIndex += 32;\r
+                                       pfadepalIndex += 16;\r
+                               }\r
+                       }\r
+               }\r
+               else\r
+               {\r
+                       cop_drop = 0;\r
+               }\r
+       }\r
+}\r
+\r
+// [nk] just before retrace\r
+function copper1()\r
+{\r
+       // There is also assembly code to set the first pixel of\r
+       // display memory here, but it may not be necessary.\r
+\r
+       VGA_SetHorizontalScrollOffset(cop_scrl);\r
+}\r
+\r
+// [nk] in retrace\r
+function copper2()\r
+{\r
+       // [nk] Don't think this is used.\r
+       frame_count++;\r
+\r
+       if (do_pal != 0)\r
+       {\r
+               do_pal = 0;\r
+               // [NK 15/1/2014] cop_pal always points to fadepal, so just upload fadepal.\r
+               //VGA_UploadPalette(cop_pal);\r
+               VGA_UploadPalette(fadepal);\r
+       }\r
+\r
+       pompota();\r
+       moveplz();\r
+\r
+       if (cop_drop != 0)\r
+       {\r
+               do_drop();\r
+       }\r
+}\r
+\r
+\r
+//--------------------------------------------------------------------------------------\r
+// Plz\r
+\r
+function dis_exit()\r
+{\r
+       return false;\r
+}\r
+\r
+var s_nFrameCount = 0;\r
+function dis_getmframe()\r
+{\r
+       s_nFrameCount++;\r
+       return s_nFrameCount;\r
+}\r
+\r
+function init_plz()\r
+{\r
+       var a;\r
+\r
+       // [NK 8/1/2014] Instead of writing the tables as assembly files,\r
+       // [NK 8/1/2014] just use them directly in C++.\r
+       {\r
+               for(var a=0;a<1024*16;a++)\r
+               {\r
+                       if(a<1024*8)\r
+                       {\r
+                               lsini4_WriteWord(a, (Math.sin(a * DPII / 4096) * 55 + Math.sin(a * DPII / 4096 * 5) * 8 + Math.sin(a * DPII / 4096 * 15) * 2 + 64) * 8);\r
+                               lsini16_WriteWord(a, (Math.sin(a * DPII / 4096) * 55 + Math.sin(a * DPII / 4096 * 4) * 5 + Math.sin(a * DPII / 4096 * 17) * 3 + 64) * 16);\r
+                       }\r
+                       psini_WriteByte(a, Math.sin(a * DPII / 4096) * 55 + Math.sin(a * DPII / 4096 * 6) * 5 + Math.sin(a * DPII / 4096 * 21) * 4 + 64);\r
+               }\r
+\r
+               for(var a=1;a<=128;a++)\r
+               {\r
+                       ptau_WriteByte(a, Math.cos(a * DPII / 128 + 3.1415926535) * 31 + 32);\r
+               }\r
+       }\r
+\r
+       cop_start=96*(682-400);\r
+       set_plzstart(60);\r
+       init_copper();\r
+       for(var a=0;a<256;a++) tw_setrgbpalette(a,63,63,63);\r
+\r
+//     RGB\r
+       var nPalOffset = ((0 * 768) + 3) * 2;\r
+       for(a=1;a<64;a++)\r
+       {\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(a)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(0)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(0)); nPalOffset += 2;\r
+       }\r
+       for(a=0;a<64;a++)\r
+       {\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(63 - a)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(0)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(0)); nPalOffset += 2;\r
+       }\r
+       for(a=0;a<64;a++)\r
+       {\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(0)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(0)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(a)); nPalOffset += 2;\r
+       }\r
+       for(a=0;a<64;a++)\r
+       {\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(a)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(0)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(63 - a)); nPalOffset += 2;\r
+       }\r
+\r
+//     RB-black\r
+       nPalOffset = ((1 * 768) + 3) * 2;\r
+       for(a=1;a<64;a++)\r
+       {\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(a)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(0)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(0)); nPalOffset += 2;\r
+       }\r
+       for(a=0;a<64;a++)\r
+       {\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(63 - a)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(0)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(a)); nPalOffset += 2;\r
+       }\r
+       for(a=0;a<64;a++)\r
+       {\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(0)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(a)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(63 - a)); nPalOffset += 2;\r
+       }\r
+       for(a=0;a<64;a++)\r
+       {\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(a)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(63)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(a)); nPalOffset += 2;\r
+       }\r
+\r
+//     RB-white\r
+       nPalOffset = ((3 * 768) + 3) * 2;\r
+       for(a=1;a<64;a++)\r
+       {\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(a)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(0)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(0)); nPalOffset += 2;\r
+       }\r
+       for(a=0;a<64;a++)\r
+       {\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(63)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(a)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(a)); nPalOffset += 2;\r
+       }\r
+       for(a=0;a<64;a++)\r
+       {\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(63-a)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(63-a)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(63)); nPalOffset += 2;\r
+       }\r
+       for(a=0;a<64;a++)\r
+       {\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(0)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(0)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(63)); nPalOffset += 2;\r
+       }\r
+\r
+//     white\r
+       nPalOffset = ((2 * 768) + 3) * 2;\r
+       for(a=1;a<64;a++)\r
+       {\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(0)/2); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(0)/2); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(0)/2); nPalOffset += 2;\r
+       }\r
+       for(a=0;a<64;a++)\r
+       {\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(a)/2); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(a)/2); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(a)/2); nPalOffset += 2;\r
+       }\r
+       for(a=0;a<64;a++)\r
+       {\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(63-a)/2); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(63-a)/2); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(63-a)/2); nPalOffset += 2;\r
+       }\r
+       for(a=0;a<64;a++)\r
+       {\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(0)/2); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(0)/2); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(0)/2); nPalOffset += 2;\r
+       }\r
+\r
+\r
+//     white II\r
+       nPalOffset = ((4 * 768) + 3) * 2;\r
+       for(a=1;a<75;a++)\r
+       {\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(63-a*64/75)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(63-a*64/75)); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(63-a*64/75)); nPalOffset += 2;\r
+       }\r
+       for(a=0;a<106;a++)\r
+       {\r
+               pal_WriteWord(nPalOffset, 0); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, 0); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, 0); nPalOffset += 2;\r
+       }\r
+       for(a=0;a<75;a++)\r
+       {\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(a*64/75)*8/10); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(a*64/75)*9/10); nPalOffset += 2;\r
+               pal_WriteWord(nPalOffset, ptau_ReadByte(a*64/75)); nPalOffset += 2;\r
+       }\r
+\r
+       nPalOffset = 0;\r
+       for(var a=0;a<768;a++)\r
+       {\r
+               var n = pal_ReadWord(nPalOffset);\r
+               n -= 63;\r
+               n *= 2;\r
+               n &= 0xFFFF;\r
+               pal_WriteWord(nPalOffset, n);\r
+               nPalOffset += 2;\r
+       }\r
+\r
+       for(var a=768;a<768*5;a++)\r
+       {\r
+               var n = pal_ReadWord(nPalOffset);\r
+               n *= 8;\r
+               n &= 0xFFFF;\r
+               pal_WriteWord(nPalOffset, n);\r
+               nPalOffset += 2;\r
+       }\r
+}\r
+\r
+function plz()\r
+{\r
+       var y;\r
+\r
+       if(dis_getmframe()>timetable[ttptr])\r
+       {\r
+               fadepal_Clear();\r
+               cop_drop=1;\r
+               ttptr++;\r
+\r
+               if (ttptr == 4) {\r
+                       // [NK 18/1/2014] Loop back to the first plasma again.\r
+                       ttptr = 0;\r
+                       curpal = 0;\r
+                       s_nFrameCount = 0;\r
+                       fadepal_ClearToWhite();\r
+                       cop_drop = 1;\r
+               }\r
+\r
+               cop_fadepal_SetSelectedPaletteIndex(curpal++);\r
+\r
+               il1=inittable[ttptr][0];\r
+               il2=inittable[ttptr][1];\r
+               il3=inittable[ttptr][2];\r
+               il4=inittable[ttptr][3];\r
+               ik1=inittable[ttptr][4];\r
+               ik2=inittable[ttptr][5];\r
+               ik3=inittable[ttptr][6];\r
+               ik4=inittable[ttptr][7];\r
+       }\r
+//     if (curpal == 5 && cop_drop > 64) {\r
+//             return true;\r
+//     }\r
+\r
+       VGA_SelectBitPlanes02();\r
+\r
+       setplzparas(k1,k2,k3,k4);\r
+       for(y=0;y<MAXY;y+=2)\r
+               plzline(y,y*6);\r
+       setplzparas(l1,l2,l3,l4);\r
+       for(y=1;y<MAXY;y+=2)\r
+               plzline(y,y*6);\r
+\r
+       VGA_SelectBitPlanes13();\r
+\r
+       setplzparas(k1,k2,k3,k4);\r
+       for(y=1;y<MAXY;y+=2)\r
+               plzline(y,y*6);\r
+       setplzparas(l1,l2,l3,l4);\r
+       for(y=0;y<MAXY;y+=2)\r
+               plzline(y,y*6);\r
+\r
+       VGA_ShowFrameBuffer();\r
+\r
+       return false;\r
+//     cop_drop=0;\r
+//     set_plzstart(500);\r
+//     cop_plz=0;\r
+}\r
+\r
+\r
+//--------------------------------------------------------------------------------------\r
+// Main\r
+\r
+function tmain()\r
+{\r
+       // Create arrays.\r
+       inittable[0] = [1000,2000,3000,4000,3500,2300,3900,3670];\r
+       inittable[1] = [1000,2000,4000,4000,1500,2300,3900,1670];\r
+       inittable[2] = [3500,1000,3000,1000,3500,3300,2900,2670];\r
+       inittable[3] = [1000,2000,3000,4000,3500,2300,3900,3670];\r
+       inittable[4] = [1000,2000,3000,4000,3500,2300,3900,3670];\r
+       inittable[5] = [1000,2000,3000,4000,3500,2300,3900,3670];\r
+\r
+       init_copper();\r
+       init_plz();\r
+       cop_drop = 128;\r
+       cop_fadepal_SetSelectedPaletteIndex(curpal++);\r
+}\r
+\r
+\r
+//--------------------------------------------------------------------------------------\r
+// HTML5 specific code\r
+\r
+window.onload = function () {\r
+       document.getElementsByTagName("body")[0].className = "js";\r
+\r
+       start();\r
+};\r
+\r
+var canvas = null;\r
+var context = null;\r
+var fps = null;\r
+var tscale = 0.02;\r
+var lastTick = 0;\r
+var targetFps = 1;\r
+var image;\r
+var canvasId = "canvas";\r
+var fpsId = "fps";\r
+\r
+function init() {\r
+       canvas = canvasId ? document.getElementById(canvasId) : null;\r
+       fps = fpsId ? document.getElementById(fpsId) : null;\r
+\r
+       if (canvas && canvas.getContext) {\r
+               //              canvas.width = width = window.innerWidth;\r
+               //              canvas.height = height = window.innerHeight;\r
+               canvas.width = 320;\r
+               canvas.height = 400;\r
+\r
+               context = canvas.getContext("2d");\r
+\r
+               if (context.createImageData) {\r
+                       image = context.createImageData(canvas.width, canvas.height);\r
+               } else if (context.getImageData) {\r
+                       image = context.getImageData(0, 0, canvas.width, canvas.height);\r
+               } else {\r
+                       // it's Opera\r
+                       image = { 'width': canvas.width, 'height': canvas.height,\r
+                               'data': new Array(canvas.width * canvas.height * 4)\r
+                       }\r
+               }\r
+\r
+               for (i = 0; i < image.data.length; i++) {\r
+                       image.data[i] = 255;\r
+               }\r
+               return true;\r
+       } else {\r
+               return false;\r
+       }\r
+}\r
+\r
+function draw() {\r
+\r
+       // Clear to black.\r
+       length = 320 * 400;\r
+       var p = 0;\r
+       for (var i = 0; i < length; i++) {\r
+               image.data[p] = 0;\r
+               p++;\r
+               image.data[p] = 0;\r
+               p++;\r
+               image.data[p] = 0;\r
+               p++;\r
+               image.data[p] = 0xFF;\r
+               p++;\r
+       }\r
+\r
+       IsComplete = plz();\r
+\r
+       if (!image) {\r
+               return;\r
+       }\r
+\r
+       var x = 0;\r
+       var y = 0;\r
+//     var x = (window.innerWidth - 320) / 2;\r
+//     var y = (window.innerHeight - 400) / 2;\r
+\r
+       context.putImageData(image, x, y);\r
+}\r
+\r
+function tick() {\r
+       var start, elapsed, sleep, target;\r
+       start = new Date().getTime();\r
+\r
+       // check if the canvas has been resized\r
+//     if ((canvas.clientWidth / 8) != width ||\r
+//        (canvas.clientHeight / 8) != height) {\r
+//             init();\r
+//     }\r
+\r
+       if (!IsComplete) {\r
+               draw();\r
+       }\r
+\r
+       // calculate stable FPS \r
+       elapsed = new Date().getTime() - start;\r
+\r
+       target = 1000 / 60;\r
+\r
+       // calculate sleep and schedule next tick\r
+       sleep = target - elapsed;\r
+       if (sleep < 1) {\r
+               sleep = 1;\r
+       } else if (sleep > 1000) {\r
+               sleep = 1000;\r
+       }\r
+\r
+       lastTick = start;\r
+       setTimeout(tick, sleep);\r
+}\r
+\r
+function start() {\r
+       lastTick = new Date().getTime();\r
+\r
+       tmain();\r
+\r
+       if (init()) tick();\r
+}\r