from random import choice,randint, randrange from math import* from kandinsky import fill_rect as rect, draw_string as txt from ion import * # Sudoku 1.0 NumWorks, 27.04.2023 # Par Ilana R. & Vincent ROBERT # https://nsi.xyz/sudoku def reset(): return[[0 for i in range(9)] for j in range(9)] def ligne(x): return [i for i in range(1,10) if i in board[x]] def colonne(y): return [board[i][y] for i in range(9) if board[i][y] != 0] def bloc(x, y): nums = [] for i in range(x//3*3, x//3*3+3): for j in range(y//3*3, y//3*3+3): if board[i][j] != 0: nums.append(board[i][j]) return nums def possible(x, y): return [i for i in range(1,10) if i not in ligne(x)+colonne(y)+bloc(x,y)] def check(): return board == solution def genere_board(): global board board = reset() x = y = essai = 0 while x!=9: essai += 1 if essai ==42: x = essai =0 board = reset() y = 0 while y!=9: if possible(x,y)==[]: board[x] = [0 for i in range(9)] y = 8 x = x-1 else: board[x][y] = choice(possible(x,y)) y +=1 x +=1 return board def couleur(x,y,p=0): if (x//3 + y//3) %2 == 1: return (180-42*p,140-35*p,225) else: return (255,200-30*p,125-85*p) def grille(): for x in range(9): for y in range(9): rect(2+x*(22), 2+y*(22), 20, 20, couleur(x,y,0)) def dessine_nb(x,y,nb,mode): if board[x][y]>9: txt(str(0),x*22+7,y*22+3,"black",couleur(x,y,mode)) else: txt(str(nb),x*22+7,y*22+3,"black",couleur(x,y,mode)) def is_valid(x,y,nb): global vie if not pen: if board[x][y]==1*10**10: if nb == solution[x][y]: board[x][y]=nb dessine_nb(x,y,nb,2) else: vie-=1 perdre_vie() else: if len(str(board[x][y]))!=1: board[x][y]+=-1*(10**(10-nb))*(str(board[x][y])[nb]=="1")+1*(10**(10-nb))*(str(board[x][y])[nb]=="0") aff_draft() def suppr(nb): for i in range(nb): x, y = randint(0,8), randint(0,8) while board[x][y] == 1*10**10 : x, y = randint(0,8), randint(0,8) board[x][y] = 1*10**10 def aide(x,y): rect(200,140,200,20,(255,)*3) nbs = possible(x, y) if len(str(board[x][y]))!=1: for i in range(len(nbs)): txt(str(nbs[i]), 265 + i * 20- len(nbs) *10, 140) if nbs[i]!=nbs[-1]: txt(",", 275+ i * 20 - len(nbs) *10, 140) else: txt("Full", 240,140) def coeur (x,y): col=(255,80 ,0) rect(x+3,y+0,3,3, col) rect(x+15,y+0,3,3,col) rect(x+0,y+3,9,3,col) rect(x+12,y+3,9,3,col) rect(x+0,y+6,21,3,col) rect(x+3,y+9,15,3,col) rect(x+6,y+12,9,3,col) rect(x+9,y+15,3,3,col) def perdre_vie(): rect(272 - vie *25, 5, 21, 21, (255,) * 3) def affichage_nb(): for x in range (9): for y in range (9): if board[x][y] <10: dessine_nb(x,y,board[x][y],0) def surbrillance(x, y, mode): for i in range(9): rect(2+i*(22), 2+y*(22), 20, 20, couleur(i, y, mode)) rect(2+x*(22), 2+i*(22), 20, 20, couleur(x, i, mode)) if board[i][y]<10: dessine_nb(i, y, board[i][y], mode) if board[x][i]<10: dessine_nb(x, i, board[x][i], mode) for i in range(x//3*3, x//3*3+3): for j in range(y//3*3, y//3*3+3): rect(2+i*(22), 2+j*(22), 20, 20, couleur(i, j, mode)) if board[i][j]<10: dessine_nb(i, j, board[i][j], mode) def aff_draft(): x,y=pos[0],pos[1] if len(str(board[x][y]))!=1: nbs =[j for j in range (1,10) if str(board[x][y])[j]=="1"] rect(210,180,200,20,(255,)*3) for i in range(len( nbs)): txt(str(nbs[i]), 265 + i * 20- len(nbs) *10 -10*(len(nbs)>6), 180,) if nbs[i]!=nbs[-1]: txt(",", 275+ i * 20 - len(nbs) *10, 180) else: rect(210,180,200,20,(255,)*3) def is_pen(): global pen pen=not(pen) if pen: txt("pen: ON ", 237, 160) rect(210,180,200,20,(255,)*3) else: txt("pen: OFF", 237, 160) rect(210,180,200,20,(255,)*3) def draw_level(s=0): txt("< "*s+ " "*(s==0)+ " "+ str(lvl)+ " >"*s + " "*(s==0), 205, 30,(42,)*3) txt("Find:", 222,30,(42+106*s,42+71*s,42+180*s)) def draw_help(s=0): txt("< "*s+" "*(s==0)+ " "+str(s_help)+ ">"*s + " "*(s==0), 202,70,(42,)*3) txt("Help:", 217,70,(42+106*s,42+71*s,42+180*s)) def wait(buttons=(0,1,2,3,4,52,30,31,32,36,37,38,42,43,44)): while True: for i in buttons: if keydown(i): while keydown(i): True return i vie = 3 rect(0, 200, 320, 22, (148, 113, 222)) txt( " chargement en cours... ", 50, 202, (242,)*3, (148, 113,222)) genere_board() grille() txt( "Code by nsi.xyz/sudoku ", 50, 202, (242,)*3, (148, 113,222)) coeur(222,5), coeur(247,5), coeur(272,5) txt("pen:", 237, 160) lvl,s_help=32,"Off" draw_level(1) draw_help(0) pen=False keydraft= reset() options = [32, 42, 52, 62] diff = None pos = 0 def select_diff(): txt(str(options[pos]), 275, 30,(42,)*3) while diff is None: key_pressed= wait() if key_pressed == 3: pos = (pos + 1) % len(options) select_diff() elif key_pressed == 0: pos = (pos - 1) % len(options) select_diff() elif key_pressed in (4,52): lvl= options[pos] break draw_level(0) draw_help(1) options = ['Off', 'On '] help = None pos = 0 def select_help(): txt(options[pos], 273, 70,(42,)*3) while help is None: key_pressed = wait() if key_pressed == 3: pos = (pos + 1) % len(options) select_help() elif key_pressed == 0: pos = (pos - 1) % len(options) select_help() elif key_pressed in (4,52): s_help = options[pos] break draw_help(0) if s_help=="On ": txt("Valid",230, 110,(42,)*3) txt("numbers",225, 125,(42,)*3) solution = [row.copy() for row in board] suppr(lvl) affichage_nb() draw_level(0) pos = [4,4] pmax = (9,9) def deplacement(): x, y = pos_old surbrillance(x,y,0) x, y = pos surbrillance(x,y,1) rect(2+x*(20+2), 2+y*(20+2), 20, 20,couleur(x,y,2)) if board[x][y]<10: dessine_nb(x,y,board[x][y],2) while True: if vie==0: txt("Perdu!",230,5,(42,)*3,(255,)*3) break if check()==True : txt(" Gagné! ",210,5,(42,)*3,(255,)*3) break key_pressed = wait() pos_old = list(pos) if key_pressed in (4,52): is_pen() elif key_pressed == 1: pos[1] = (pos[1]-1) % pmax[1] aff_draft() if s_help=="On ": aide(pos[0],pos[1]) elif key_pressed == 2: pos[1] = (pos[1]+1) % pmax[1] aff_draft() if s_help=="On ": aide(pos[0],pos[1]) elif key_pressed == 3: pos[0] = (pos[0]+1) % pmax[0] aff_draft() if s_help=="On ": aide(pos[0],pos[1]) elif key_pressed == 0: pos[0] = (pos[0]-1) % pmax[0] aff_draft() if s_help=="On ": aide(pos[0],pos[1]) elif key_pressed == 42: is_valid(pos[0],pos[1],1) elif key_pressed == 43: is_valid(pos[0],pos[1],2) elif key_pressed == 44: is_valid(pos[0],pos[1],3) elif key_pressed == 36: is_valid(pos[0],pos[1],4) elif key_pressed == 37: is_valid(pos[0],pos[1],5) elif key_pressed == 38: is_valid(pos[0],pos[1],6) elif key_pressed == 30: is_valid(pos[0],pos[1],7) elif key_pressed == 31: is_valid(pos[0],pos[1],8) elif key_pressed == 32: is_valid(pos[0],pos[1],9) if key_pressed not in (42, 43 ,44 ,36 ,37 ,38 ,30 ,31, 32) : deplacement()