Advertisement
T3RRYT3RR0R

Tetris [Batch]

Nov 4th, 2020 (edited)
1,592
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Batch 13.42 KB | None | 0 0
  1. @Echo off & CD "%~dp0"
  2. ======================================================================================
  3. ::: Last Updated: 07/12/2020
  4. ::: getkey.exe and sleep.bat required for enhanced controls and gameplay timing
  5. ::: Download from:
  6. ======================================================================================
  7. ::: https://drive.google.com/file/d/18M21SoDpC4FyFBcsiYnqUAGOaciHIQMD/view?usp=sharing
  8. ::: Download contains:
  9. ::::::::::::::::::::::::::::::::::::::::::::::::::
  10. ::: Getkey.Exe by Antonio {https://stackoverflow.com/users/778560/aacini} for Extended key controls.
  11. ::: Tetris.Bat by T3RRY {https://stackoverflow.com/users/12343998/t3rr0r}
  12. ::: Sleep.bat by Dave Benham {https://www.dostips.com/forum/memberlist.php?mode=viewprofile&u=2258}
  13. ======================================================================================
  14.  :newgame
  15.  CHCP 65001 > nul
  16.  Setlocal EnableExtensions DISABLEdelayedexpansion
  17.  wmic OS get OSArchitecture,caption | FIND "10" >nul || (ECHO/Windows 10 required for ascii escape codes & Endlocal & Exit /B)
  18. :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  19.  Title Tetris by T3RRY & rem commenced 30/10/2020
  20. rem ::: 30/10/2020 Piece creation, basic collision detection, piece movement implemented.
  21. rem ::: 31/10/2020 New piece and Game over trigger tests added.
  22. rem ::: 31/10/2020 Color, Piece rotation added
  23. rem ::: 01/11/2020 Function to test for a completed line added.
  24. rem ::: 01/11/2020 Scoring system added
  25. rem ::: 02/11/2020 Replaced choice controller with getkeys.exe
  26. rem ::: 02/11/2020 Implemented game levels and pace control
  27. rem ::: 02/11/2020 Augmented Graphics engine. New:
  28. rem :::             the x coords for piece drop site shown at screen base.
  29. rem :::             show inverted line on match
  30. rem :::             Unicode character ( active piece ) and Ascii character ( Locked piece )
  31. rem ::: 07/11/2020 Added Next Piece display
  32. rem ::: 13/11/2020 Corrected rotation X axis shift so pieces now maintain current Min X axis.
  33. rem ::: 16/11/2020 Replaced delay timing method to use Dave Benhams Sleep.bat for finer control of delay increments
  34. rem ------/* Getkeys controller. allows variable delay for speed increase based on score */
  35.  For /F "Delims=" %%C in ('dir "%~dp0*GetKey.exe" /B /S') Do If not defined GetKey Set "GetKey="%%C" /n"
  36. :::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  37. rem ---------------------------------------------------- /* ASCII escape code definition */
  38.  for /F "delims=#" %%a in ('"prompt #$E# & for %%a in (1) do rem"') do set "\E=%%a"
  39. rem ------------------------------------------------ /* ensure } reference var undefined */
  40.  (For /F "Tokens=1,2 Delims==" %%G in ('Set "}"')Do Set "%%G=") 2> nul
  41. rem ------------------------------------------------------------------ /* define macro's */
  42.  Set "nPiece[1]=Set /A "x1=5,y1=1,x2=6,y2=1,x3=7,y3=1,x4=8,y4=1""
  43.  Set "nPiece[2]=Set /A "x1=6,y1=1,x2=7,y2=1,x3=6,y3=2,x4=7,y4=2""
  44.  Set "nPiece[3]=Set /A "x1=7,y1=1,x2=6,y2=1,x3=5,y3=2,x4=5,y4=1""
  45.  Set "nPiece[4]=Set /A "x1=5,y1=1,x2=6,y2=1,x3=7,y3=1,x4=7,y4=2""
  46.  Set "nPiece[5]=Set /A "x1=5,y1=2,x2=6,y2=2,x3=6,y3=1,x4=7,y4=1""
  47.  Set "nPiece[6]=Set /A "x1=5,y1=1,x2=6,y2=1,x3=6,y3=2,x4=7,y4=2""
  48.  Set "nPiece[7]=Set /A "x1=5,y1=1,x2=6,y2=1,x3=6,y3=2,x4=7,y4=1""
  49.  Set "iPiece[1]=Set /A "ix1=20,iy1=16,ix2=21,iy2=16,ix3=22,iy3=16,ix4=23,iy4=16""
  50.  Set "iPiece[2]=Set /A "ix1=21,iy1=16,ix2=22,iy2=16,ix3=21,iy3=17,ix4=22,iy4=17""
  51.  Set "iPiece[3]=Set /A "ix1=20,iy1=16,ix2=21,iy2=16,ix3=22,iy3=16,ix4=20,iy4=17""
  52.  Set "iPiece[4]=Set /A "ix1=20,iy1=16,ix2=21,iy2=16,ix3=22,iy3=16,ix4=22,iy4=17""
  53.  Set "iPiece[5]=Set /A "ix1=20,iy1=17,ix2=21,iy2=17,ix3=21,iy3=16,ix4=22,iy4=16""
  54.  Set "iPiece[6]=Set /A "ix1=20,iy1=16,ix2=21,iy2=16,ix3=21,iy3=17,ix4=22,iy4=17""
  55.  Set "iPiece[7]=Set /A "ix1=20,iy1=16,ix2=21,iy2=16,ix3=21,iy3=17,ix4=22,iy4=16""
  56.  Set "tetra1=▓"
  57.  Set "tetra2=X"
  58.  Set /A iPce=%random% %%7 + 1
  59.  Set "DropMarker=For %%n in (1 2)Do if %%n==2 (For /F "Tokens=1,2 Delims={}" %%G in ("!Marker!")Do ( <nul Set /P "=%\E%[%%~Gm%\E%[23;!#x1!H%%~H%\E%[23;!#x2!H%%~H%\E%[23;!#x3!H%%~H%\E%[23;!#x4!H%%~H%\E%[0m" ))Else Set marker="
  60.  Set "MoveLeft=Set "valid=0"&Set /A "_x1=!x1!-1,_x2=!x2!-1,_x3=!x3!-1,_x4=!x4!-1" & (For %%v in ("!y1!;!_x1!" "!y2!;!_x2!" "!y3!;!_x3!" "!y4!;!_x4!")Do (IF "!}%%~v!" == "" (Set /A "Valid=!Valid! + 1"))) & If "!Valid!" == "4" (Set /A "x1-=1,x2-=1,x3-=1,x4-=1")"
  61.  Set "MoveRight=Set "valid=0"&Set /A "_x1=!x1!+1,_x2=!x2!+1,_x3=!x3!+1,_x4=!x4!+1" & (For %%v in ("!y1!;!_x1!" "!y2!;!_x2!" "!y3!;!_x3!" "!y4!;!_x4!")Do (IF "!}%%~v!" == "" (Set /A "Valid=!Valid! + 1"))) & If "!Valid!" == "4" (Set /A "x1+=1,x2+=1,x3+=1,x4+=1")"
  62.  Set "MoveDown=Set "valid=0"&Set /A "_y1=!y1!+1,_y2=!y2!+1,_y3=!y3!+1,_y4=!y4!+1" & (For %%v in ("!_y1!;!x1!" "!_y2!;!x2!" "!_y3!;!x3!" "!_y4!;!x4!")Do (IF "!}%%~v!" == "" (Set /A "Valid=!Valid! + 1"))) & (If "!Valid!" == "4" (Set /A "y1+=1,y2+=1,y3+=1,y4+=1")Else (Set /A "Score+=25"&Set "}!y1!;!x1!=%\E%[!y1!;!x1!H%\E%[3!pce!m!tetra2!%\E%[0m"& Set "}!y2!;!x2!=%\E%[!y2!;!x2!H%\E%[3!pce!m!tetra2!%\E%[0m"& Set "}!y3!;!x3!=%\E%[!y3!;!x3!H%\E%[3!pce!m!tetra2!%\E%[0m"& Set "}!y4!;!x4!=%\E%[!y4!;!x4!H%\E%[3!pce!m!tetra2!%\E%[0m"& >"%TEMP%\tetris.~tmp" (For /F "Tokens=2* Delims==" %%G in ('Set }')Do Echo/%%G) & (For %%. in (!y1! !y2! !y3! !y4!)Do if %%. EQU 2 (Goto :GameOver)) & ( Call :isMatch & Goto :newpiece )))"
  63.  Set "ShowPiece=<Nul Set /P "=%\E%[3!pce!m%\E%[!y1!;!x1!H!tetra1!%\E%[!y2!;!x2!H!tetra1!%\E%[!y3!;!x3!H!tetra1!%\E%[!y4!;!x4!H!tetra1!%\E%[0m""
  64.  Set "HideLast=<Nul Set /P "=%\E%[!ly1!;!lx1!H %\E%[!ly2!;!lx2!H %\E%[!ly3!;!lx3!H %\E%[!ly4!;!lx4!H %\E%[0m""
  65. rem ---------------------------------------------------------- /* Define Control Display */
  66.  Set "Score=0"
  67.  Set /A "level=1,MaxSpeed=5"
  68.  Set "}1;20=%\E%[1;20H%\E%[90mScore: %\E%[91m!score!"
  69.  Set "}3;20=%\E%[3;20H%\E%[33mControls:"
  70.  Set "}4;20=%\E%[4;20H  ◄    - Left"
  71.  Set "}5;20=%\E%[5;20H  ▼    - Down"
  72.  Set "}6;20=%\E%[6;20H  ►    - Right"
  73.  Set "}7;20=%\E%[7;20HSpace  - Rotate"
  74.  Set "}8;20=%\E%[8;20HPage▼  - Drop Piece"
  75.  Set "}9;20=%\E%[9;20HEnter  - Pause"
  76.  Set "}10;20=%\E%[10;20H%\E%[32mEscape - Exit%\E%[0m"
  77.  Set "}12;20=%\E%[12;20H%\E%[90mLevel: %\E%[36m%\E%[7m!level!%\E%[0m"
  78.  Set "}13;20=%\E%[13;20H%\E%[90mSpeed: %\E%[33m%\E%[7m!MaxSpeed!%%%\E%[0m"
  79.  Set "}15;20=%\E%[14;20H%\E%[90mNext Tetramino:%\E%[0m"
  80.  Set "BEL=( Echo/| CHOICE /N > nul 2> nul )"
  81. rem -------------------- /* Establish environment for macro usage and code block actions */
  82.  Setlocal EnableDelayedExpansion
  83. ::: { Define Variables For mapping errorlevel to Key.
  84. :::  ** Numbers within the below ranges must not be assigned as other variables: k# **
  85.     Set "k-82=Insert"
  86.     Set "k-80=Down"
  87.     Set "k-75=Left"
  88.     Set "k-81=PageDown"
  89.     Set "k-77=Right"
  90.     Set "k32=space"
  91.     Set "k13=enter"
  92.     Set "k27=ESC"
  93. ::: }
  94.  mode 54,24
  95. rem ----------------------------------------------------------------- /* hide the cursor */
  96.  <nul Set /P "=%\E%[?25l"
  97. rem --------------------------------------------------------------- /* define the border */
  98.  For %%s in (1 12)Do For /L %%n in (1 1 23) Do (
  99.   Set "}%%n;%%s=%\E%[%%n;%%sH%\E%[90m.%\E%[0m"
  100.   If %%n LSS 3 Set "}%%n;%%s=%\E%[%%n;%%sH%\E%!!%\E%[0m"
  101.   If %%n==23 For /L %%b in (2 1 11)Do (
  102.    Set "}%%n;%%b=%\E%[%%n;%%bH%\E%[90m.%\E%[0m"
  103.   )
  104.  )
  105.  >"%TEMP%\tetris.~tmp" (For /F "Tokens=2* Delims==" %%G in ('Set "}"')Do Echo/%%G)
  106. :newpiece
  107. rem -------------- /* level is Score based and is used to control the speed of the game */
  108.  For /L %%l in (2 1 20)Do For /F "Delims=" %%G in ('Set /A "tst=(%%l-1)*10000"')Do if !Score! GTR %%G Set "level=%%l"
  109.  Set /A "MaxSpeed=!level! * 5"
  110.  CLS
  111.  Type "%TEMP%\tetris.~tmp"
  112.  Set "pce=%iPce%"
  113.  Set /A iPce=%random% %%7 + 1
  114.  !iPiece[%iPce%]!
  115.  !nPiece[%pce%]!
  116.  %ShowPiece%
  117.  %Dropmarker:#x=x%{3!Pce!}{▄}
  118. :loop
  119. rem ----------------------------- /* get pieces last y;x vals to blank out with hidelast */
  120.  For %%c in (y x)Do For %%i in (1 2 3 4)Do Set "l%%c%%i=!%%c%%i!"
  121.  %Dropmarker:#x=x%{3!Pce!}{▄}
  122.  <nul Set /P "=%\E%[!iy1!;!ix1!H%\E%[3!iPce!m%Tetra1%%\E%[0m%\E%[!iy2!;!ix2!H%\E%[3!iPce!m%Tetra1%%\E%[0m%\E%[!iy3!;!ix3!H%\E%[3!iPce!m%Tetra1%%\E%[0m%\E%[!iy4!;!ix4!H%\E%[3!iPce!m%Tetra1%%\E%[0m"
  123. rem ----------------------------------------------------------------------- /* game pace */
  124.  Set /A Delay=400 / level
  125.  
  126.   Call Sleep.bat %Delay% !Time!
  127.   Set Key=
  128.   %GetKey%
  129.   For %%E in (!Errorlevel!) Do Set "Key=!k%%E!"
  130.   If Not "!Key!" == "" (
  131.    Goto :Move
  132.   )
  133.  %MoveDown%
  134.  %HideLast%
  135.  %Dropmarker:#x=lx%{90}{.}
  136.  %ShowPiece%
  137. Goto :loop
  138. rem ----------------------------------------------------------------- /* game controller */
  139. :Move
  140.  For %%G in (!Key!) Do (
  141.   If /I "%%G" == "esc" ( %BEL% & TITLE Quit Y\N?&For /F "Delims=" %%C in ('Choice /N /C:YN')Do if %%C==Y (Title & Goto :quit)Else (Title Tetris by T3RRY))
  142.   If /I "%%G" == "enter" ( Title Paused & Pause > nul & Title Tetris by T3RRY )
  143.   If /I "%%G" == "pagedown" For /L %%s in (1 1 21)Do %MoveDown%
  144.   If /I "%%G" == "left" (
  145.    %Moveleft%
  146.    %Dropmarker:#x=lx%{90}{.}
  147.   )
  148.   If /I "%%G" == "right" (
  149.    %Moveright%
  150.    %Dropmarker:#x=lx%{90}{.}
  151.   )
  152.   If /I "%%G" == "down" %Movedown%
  153. rem ------------------------------------------------------------ /* start rotation logic */
  154. rem --- [ Horizontal flip followed by mirror to simulate 90 degree rotation. ]
  155.   If /I "%%G" == "space" (
  156. rem ----------------------------------------------------------------- /* flip horizontal */
  157.    Set /A midX=500,midY=500
  158.    For %%A in ("!y1!;!x1!" "!y2!;!x2!" "!y3!;!x3!" "!y4!;!x4!") Do (
  159.     For /F "Tokens=1,2 Delims=;" %%X in ("%%~A") Do (
  160.      Set /A "oY=%%~X"
  161.      Set /A "oX=%%~Y"
  162.     )
  163.     If !oY! LSS !midY! Set /A "midY=!oY!"
  164.     If !oX! LSS !midX! Set /A "midX=!oX!"
  165.    )
  166.    Set "pixel=0"
  167.    For %%B in ("!y1!;!x1!" "!y2!;!x2!" "!y3!;!x3!" "!y4!;!x4!") Do (
  168.     Set /A pixel+=1
  169.     For /F "Tokens=1,2 Delims=;" %%r in ("%%~B") Do (
  170.      Set /A "ny!pixel!=(%%~s-midX)+!midY!,nx!pixel!=(%%~r-!midY!)+!midX!"
  171.    ))
  172. rem --------------- /* mirror, correcting piece centre X axis by piece type / orientation */
  173.   Set "pixel=0"
  174.   Set /A lmidX=500,umidX=0
  175.   For %%C in (!nx1! !nx2! !nx3! !nx4!) Do (
  176.    If %%C LSS !lmidX! (Set /A "lmidX=%%C")
  177.    If %%C GTR !umidX! (Set /A "umidX=%%C")
  178.   )
  179.   If !Centre!==0 (
  180.    Set "Centre=1"
  181.   ) Else Set Centre=0"
  182.   Set /A PceWidth=umidX-lmidX
  183.   If !PceWidth!==2 Set "Centre=1"
  184.   If !Pce!==2 Set "Centre=1"
  185.   If !Pce!==1 (
  186.    If !PceWidth!==1 Set "Centre=0"
  187.    If !PceWidth!==3 Set "Centre=1"
  188.   )
  189.   Set /A "Mid.X=( !lmidX! + !umidX! ) / 2"
  190.   For %%X in (!nx1! !nx2! !nx3! !nx4!) Do (
  191.    Set /A "pixel=!pixel! + 1"
  192.    Set /A "nx!pixel!=%%X + !centre!"
  193.    IF %%X LSS !Mid.X! (Set /A "nx!pixel!= %%X + ((!Mid.X!-%%X) * 2) + !centre!")
  194.    IF %%X GTR !Mid.X! (Set /A "nx!pixel!= %%X - ((%%X-!Mid.X!) * 2) + !centre!")
  195.   )
  196. rem ------------------------------------------- /* collision detection for rotated coords */
  197.    Set "valid=0"
  198.    For /L %%i in (1 1 4)Do (
  199.     for %%c in ("!ny%%i!;!nx%%i!")Do If "!}%%~c!" == "" (
  200.      Set /A "valid=!valid!+1"
  201.   ))
  202.    If "!valid!" == "4" (
  203.     For %%v in (x y)Do For /L %%i in (1 1 4)Do (
  204.       Set "%%v%%i=!n%%v%%i!"
  205.     )
  206.     %Dropmarker:#x=lx%{90}{.}
  207.   ))
  208. rem --------------------------------------------------------------- /* end rotation logic */
  209. rem ------------------------------------------------------------ /* display current state */
  210.   TYPE "%TEMP%\tetris.~tmp"
  211.   %HideLast%
  212.   %ShowPiece%
  213.   %Dropmarker:#x=x%{3!Pce!}{▄}
  214.  )
  215. Goto :loop
  216. rem ----------------------------- /* test for completed line when a piece is set in place */
  217. :isMatch
  218.  %HideLast%
  219.  %ShowPiece%
  220.  Set "match=0"
  221.  Set "ymin=24"
  222.  Set "ymax=0"
  223.  For %%n in (!y1! !y2! !y3! !y4!)Do (
  224.   if %%n gtr !ymax! Set "ymax=%%n"
  225.   if %%n lss !ymin! Set "ymin=%%n"
  226.  )
  227. rem ------------- /* test completion of line for each y coord for last piece set in place */
  228.  For /L %%i in (!ymin! 1 !ymax!)Do (
  229.   Set "#of10=0"
  230.   For /L %%c in (2 1 11)Do If Not "!}%%i;%%c!" == "" Set /A "#of10=!#of10!+1"
  231.   If "!#of10!" == "10" (
  232.    <nul Set /P "=%\E%[7m!}%%i;2!%\E%[7m!}%%i;3!%\E%[7m!}%%i;4!%\E%[7m!}%%i;5!%\E%[7m!}%%i;6!%\E%[7m!}%%i;7!%\E%[7m!}%%i;8!%\E%[7m!}%%i;9!%\E%[7m!}%%i;10!%\E%[7m!}%%i;11!"
  233.    Call Sleep.bat 200 !Time!
  234.    Set /A "match=!match!+1"
  235.    Set /A "Score+=250 * ( !match! + ( !level! / 3 ) )"
  236.    Set /A "lineabove=%%i-1"
  237.    For /L %%n in (0 1 !lineabove!) Do (
  238.     Set /A "offset=%%n+1"
  239. rem -------------------------- /* transfer updated coord values after iteration complete */
  240.     For %%o in (!offset!)Do For /L %%x in (2 1 11) Do If not "!}%%n;%%x!" == "" (
  241.      Set "n}%%o;%%x=!}%%n;%%x:[%%n;=[%%o;!"
  242.     ) Else (
  243.      Set "n}%%o;%%x="
  244.    ))
  245.    For /L %%Y in (1 1 %%i) Do For /L %%X in (2 1 11) Do Set "}%%Y;%%X=!n}%%Y;%%X!"
  246.  ))
  247. rem ----------------------------- /* Update display values for each cell to display file */
  248.  >"%TEMP%\tetris.~tmp" (For /F "Tokens=2* Delims==" %%G in ('Set "}"')Do Echo/%%G)
  249. Exit /B 0
  250. :Delay
  251. exit /B 0
  252. :gameover
  253.   %HideLast%
  254.   %ShowPiece%
  255.  %BEL%
  256.  Echo/%\E%[2;20H%\E%[31mGame Over.%\E%[0m
  257.  Timeout /T 2 /NoBreak > nul
  258.  Pause > nul
  259.  CLS
  260.  Echo(%\E%[12;18H%\E%[33mPlay Again %\E%[32mY%\E%[33m\%\E%[31mN%\E%[33m ?%\E%[0m
  261.  For /F "Delims=" %%C in ('Choice /N') Do if "%%C" == "Y" (
  262.   Endlocal
  263.   Endlocal
  264.   Goto :newgame
  265.  )
  266. :quit
  267. rem -------------------------------------- /* restore the cursor ; End of script cleanup */
  268.  <nul Set /P "=%\E%[?25h"
  269.  Del /Q "%TEMP%\tetris.~tmp" 2> nul
  270.  Endlocal
  271.  Endlocal
  272.  cls
  273.  (Title )
  274. Goto :Eof
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement