Version : beta3
# NumWorks Python Game # Explore Escape 2.0 # Vincent ROBERT 12/01/2025 from kandinsky import * txt, rec = draw_string, fill_rect from random import randint as r from random import choice from time import sleep from math import sqrt from ion import keydown carte = [[0] * 32 for _ in range(20)] # 640 tiles to explore col = {"b":(248,248,248),"ui":(148, 113, 222), "p":(42, 142, 242), "h":(242, 160, 176), "w":(40, 200, 140), "l":(242,142,142)} p = {"x":1, "y":5, "vie":3, "level":False} #Player game = {"L":1, "R":6, "E":0} # Level Radar EMP w = {"x":0, "y":0, "e":0, "v":0} #win, bonus def wait(keys=(0,1,2,3,4,52)): # arrows, ok, exe while True: for k in keys: if keydown(k): while keydown(k): True return k def reset(): for y in range(0,20): # Blank card for x in range(0,32): carte[y][x] = 600 if x in (0, 31) or y in (0, 19) else 0 m=22 # 22 trap while m: y, x = r(2,18), r(2,29) if carte[y][x]!=600: carte[y][x]=600 m -= 1 n = 10*game["L"]- 30 # trap level while n>0: y, x = r(1,18), r(2,29) if carte[y][x]!=600 and count(y,x)>0: carte[y][x]=600 n -= 1 y , x = r(1,18), 1 # start position p["x"], p["y"], = 1, y carte[y][x]=0 x, y = r(10,42), choice((0,19)) # win condition if x >= 28: x, y = 31, r(3,17) carte[y][x]=300 w["x"], w["y"] = x, y bonus() def bonus(): w["e"], w["v"] = r(1,5-game["L"]//10), r(1,5-game["L"]//8) t,e,v = 0, w["e"], w["v"] while t<4242 and (e>0 or v>0): y, x = r(1,18), r(2,29) if e>0 and count(y,x)==0 and carte[y][x]==0: carte[y][x]=200 e-=1 elif v>0 and count(y,x)==0 and carte[y][x]==0: carte[y][x]=100 v-=1 t +=1 w["e"], w["v"] = w["e"]-e, w["v"]-v def count(y,x): """Number of trap in the neighborhood""" b = 0 for i in range(-1,2): for j in range(-1,2): if x+i<0 or x+i>31 or y+j<0 or y+j>19: b += 1 if 0<=x+i<=31 and 0<=y+j<=19 and carte[y+j][x+i]//100==6: b += 1 return b def ui(): rec(0, 200, 320, 22, col["ui"]) txt( "nsi.xyz/escape", 10, 202, col["b"], col["ui"]) stats() draw_heart(27,20.7) def stats(): t = ""+" "*(game["E"]<10) for k in game.keys(): t += k+str(game[k])+" " txt(t, 270-10*len(t), 202, col["b"], col["ui"]) txt(str(p["vie"])+" ", 285, 202, col["b"], col["ui"]) def draw_heart(x,y,c=col["h"]): """heart Pixel Art 10x10""" xi,yi = 0,0 for i, j in enumerate((1,2,3,2,3,3,1,4,1,39,2,8,3,6,5,4,7,2)): #heart while j>0: if i % 2 == 1 : rec(int(10*x)+(xi%10),int(10*y)+yi,1,1,c) xi,yi,j = xi+1, (xi+1)//10, j-1 def draw_emp(x,y): """Plus sign Pixel Art 10x10""" rec(int(x*10+4), int(y*10+2), 2, 6, col["w"] ) rec(int(x*10+2), int(y*10+4), 6, 2, col["w"] ) def draw_robot(x,y, c=col["p"]): """Robot head Pixel Art 10x10""" rec(x*10,y*10,10,10, c) rec(x*10+2, y*10+2, 2, 2, col["b"] ) rec(x*10+6, y*10+2, 2, 2, col["b"] ) rec(x*10+2, y*10+6, 6, 2, col["b"] ) rec(x*10+4, y*10+6, 2, 1, c ) def go(y,x): """Darken each square and move the player""" p["x"], p["y"] = x, y c = carte[y][x]//100 if x<0 or x>31 or y<0 or y>19: return restart() elif c == 6: carte[y][x] = 16 p["vie"] -= 1 for i in range(2): draw_heart(27,20.7,c=col["ui"]) sleep(0.21) draw_heart(27,20.7,c=col["h"]) sleep(0.21) stats() if p["vie"]==0: p["level"] = True stats() elif c == 3: return finish() elif c == 1: carte[y][x] = 16 p["vie"] += 1 elif c == 2: carte[y][x] = 16 game["E"] += 1 radar() darken(x,y) def darken(x,y): for x0 in range(32): for y0 in range(20): if distance(x,y,x0,y0) > game["R"]+0.50: c = carte[y0][x0] carte[y0][x0] = max(100*(c//100),c-1) if c != carte[y0][x0]: g = 16*(carte[y0][x0]%100) rec(x0*10, y0*10, 10, 10, (g,g,g)) def radar(d=1): x, y = p["x"], p["y"] for i in range(-d,d+1,1): for j in range(-d,d+1,1): if i == 0 and j == 0: draw_robot(x,y) elif distance(i,j) <= d+0.5 and 0<=y+j<20 and 0<=x+i<32: c = carte[y+j][x+i] carte[y+j][x+i]= 100*(c//100)+16-count(y+j,x+i) g = 16*(carte[y+j][x+i]%100-1) if c != carte[y+j][x+i] or i+j<1.1: rec((x+i)*10, (y+j)*10, 10, 10, (g,g,g)) if carte[y+j][x+i]//100==2: draw_emp(x+i,y+j) if carte[y+j][x+i]//100==1: draw_heart(x+i,y+j) out() def out(): "If the exit is within a reasonable distance from the player it is displayed" if distance(w["x"],w["y"],p["x"],p["y"]) <= game["R"]+1.9: rec(w["x"]*10, w["y"]*10, 10, 10, col["w"]) def restart(): p["vie"] -= 1 p["level"] = True def finish(): p["vie"] += 1 p["level"] = True game["L"] += 1 def emp(d=1): game["E"] -= 1 for x in range(-d,d+1,1): for y in range(-d,d+1,1): xe, ye = p["x"]+x, p["y"]+y if distance(x,y)<d+0.5 and 0<xe<31 and 0<ye<19 and carte[ye][xe]//100!=1: carte[ye][xe] = 0 radar(max(game["R"],d) +3) def init(): rec(0,0,320,200,(0,0,0)) game["R"] = max(2,5-game["L"]//8) game["E"] = max(game["E"], min(game["L"],9)) reset() ui() if game["L"]%2==1 and game["L"]<10 and p["vie"]>0: for y in range(0,20): for x in range(0,32): if carte[y][x]==600: rec(10*x,10*y,10,10,col["l"]) sleep(4.2-0.42*game["L"]) rec(0,0,320,200,(0,0,0)) radar(game["R"]) level() def distance(a,b,c=0,d=0): return sqrt((a-c)**2+(b-d)**2) def level(): n = game["L"] end = False if n>42 or p["vie"]<1: end = True ui,b = col["ui"], col["b"] rec(80,40,160,120,ui) txt( "EXPLORE ESCAPE", 90, 50, b, ui) txt( "lvl "+str(min(n,42)), 90+40*(not 9<n<31), 80, b, ui) if 9<n<31: txt( str(bin(w["x"]))[1:], 170, 80, b, ui) if not end: txt( str(w["e"])+" XMP Bonus", 90, 110, b, ui) txt( str(w["v"])+" life Bonus", 90, 130, b, ui) draw_heart(10.5,13.3) draw_emp(10.5,11.3) wait() rec(80,40,160,120,(0,0,0)) elif n==43: txt( "GAME COMPLETE", 90, 120, b, ui) q() else: txt( "GAME OVER", 110, 120, b, ui) q() def q(): wait() p["vie"]=-1 while p["vie"]>-1: p["level"] = False init() while not p["level"] and p["vie"]>0: k = wait() if k == 4 or k == 52: if game["E"]>0: emp(int(-0.00657*game["L"]**2+0.27619*game["L"]+2.1)) else: go(p["y"]-1*(k==1)+1*(k==2), p["x"]-1*(k==0)+1*(k==3)) radar(game["R"]) stats()