import random
import os
import keyboard
import copy
import sys
class Game_2048:
randomNum = [2, 4]
probability = [0.65, 0.35]
mainList = []
lastMainList = []
theNewNum = []
length = 0
grade = 0
bestGrade = 0
# emptyPosition [] # 用于记录空位置
# 初始化4*4方格
def __init__(self, length = 4, count = 2):
'''
length : 表示初始化网格大小
count : 表示初始化几个元素
'''
self.mainList = []
self.length = length
for i in range(length):
sonList = []
for j in range(length):
sonList.append(0)
self.mainList.append(sonList)
self.writeNum(count)
self.getUserdata()
self.printMap()
print("The map has already init...", end = "\r")
# 判断该处是否为空
def isEmpty(self, i, j):
if self.mainList[i][j] == 0:
return True
else:
return False
# 按给定的概率生成数字
def getCertainProbability(self):
x = random.uniform(0, 1)
cumulativeProbability = 0.0
for item, itemProbability in zip(self.randomNum, self.probability):
cumulativeProbability += itemProbability
if x < cumulativeProbability:
break
return item
# 随机写入数字
def writeNum(self, count):
while count:
xAxis = random.randint(0, self.length-1)
yAxis = random.randint(0, self.length-1)
if self.isEmpty(xAxis, yAxis):
self.mainList[xAxis][yAxis] = self.getCertainProbability()
count -= 1
# 键盘事件对应操作
def pressKey(self, anyKey):
flag = 0
anyKey = str(anyKey)
self.lastMainList = copy.deepcopy(self.mainList)
if "w up" in anyKey or "W up" in anyKey:
self.pressW()
flag = 1
elif "a up" in anyKey or "A up" in anyKey:
self.pressA()
flag = 1
elif "s up" in anyKey or "S up" in anyKey:
self.pressS()
flag = 1
elif "d up" in anyKey or "D up" in anyKey:
self.pressD()
flag = 1
else:
if "a down" not in anyKey and "w down" not in anyKey and "s down" not in anyKey and "d down" not in anyKey\
and "A down" not in anyKey and "W down" not in anyKey and "S down" not in anyKey and "D down" not in anyKey:
print('''Please press one of the "wasd" in the keyboard !''', end = "\r")
else:
pass
if flag == 1:
if self.isFall():
print("You fall...")
input("\b"*100 + "please any key for exit...")
exit()
self.theNewNum = []
def pressW(self):
listTemp = []
for c in range(self.length):
for r in range(self.length):
listTemp.append(self.mainList[r][c])
listTemp = self.addNum(listTemp)
for r in range(self.length):
self.mainList[r][c] = listTemp[r]
listTemp = []
if self.lastMainList != self.mainList:
if self.isWin() == 1024:
self.writeNum(1)
self.grade += self.getGrade()
self.printMap()
print("You win...")
input("\b"*100, "please any key to exit...")
exit()
else:
self.writeNum(1)
self.grade += self.getGrade()
self.printMap()
print("You press W...", end = "\r")
def pressA(self):
listTemp = []
for i in range(self.length):
listTemp = self.mainList[i]
listTemp = self.addNum(listTemp)
self.mainList[i] = listTemp
if self.lastMainList != self.mainList:
if self.isWin() == 1024:
self.writeNum(1)
self.grade += self.getGrade()
self.printMap()
print("You win...")
input("\b"*100, "please any key to exit...")
exit()
else:
self.writeNum(1)
self.grade += self.getGrade()
self.printMap()
print("You press A...", end = "\r")
def pressD(self):
listTemp = []
for i in range(self.length):
listTemp = list(reversed(self.mainList[i]))
listTemp = self.addNum(listTemp)
self.mainList[i] = list(reversed(listTemp))
if self.lastMainList != self.mainList:
if self.isWin() == 1024:
self.writeNum(1)
self.grade += self.getGrade()
self.printMap()
print("You win...")
input("\b"*100, "please any key to exit...")
exit()
else:
self.writeNum(1)
self.grade += self.getGrade()
self.printMap()
print("You press D...", end = "\r")
def pressS(self):
listTemp = []
for c in range(self.length):
for r in range(self.length):
listTemp.insert(0, self.mainList[r][c])
listTemp = self.addNum(listTemp)
for r in range(self.length):
self.mainList[r][c] = listTemp[self.length-r-1]
listTemp = []
if self.lastMainList != self.mainList:
if self.isWin() == 1024:
self.writeNum(1)
self.grade += self.getGrade()
self.printMap()
print("You win...")
input("\b"*100, "please any key to exit...")
exit()
else:
self.writeNum(1)
self.grade += self.getGrade()
self.printMap()
print("You press S...", end = "\r")
# 数字变换逻辑
def addNum(self, listNum):
temp = 0
count = 0
for each in listNum:
if each != 0 and temp == 0:
temp = each
elif each != 0:
if each == temp:
temp = temp*2
self.theNewNum.append(temp)
listNum[count] = temp
count += 1
temp = 0
else:
listNum[count] = temp
count += 1
temp = each
elif each == 0:
continue
if temp != 0:
listNum[count] = temp
count += 1
temp = each
for i in range(count, len(listNum)):
listNum[i] = 0
return listNum
# 打印游戏界面
def printMap(self):
os.system("cls") # 清空命令行
if self.grade > self.bestGrade:
self.bestGrade = self.grade
self.writeUserdata()
print("The current grade is %d, the best grade is %d" % (self.grade, self.bestGrade))
print("-" * int(6.1*self.length))
for sonList in self.mainList:
print("|", end = "")
for elem in sonList:
if elem != 0:
if elem == 2:
print(str(elem).ljust(5) +"|", end = "")
elif elem == 4 or elem == 1024:
print('\033[;32;41m'+str(elem).ljust(5) + '\033[0m' +"|", end = "")
elif elem == 8 or elem == 2048:
print('\033[1;33;42m'+str(elem).ljust(5) + '\033[0m' +"|", end = "")
elif elem == 16:
print('\033[1;34;43m'+str(elem).ljust(5) + '\033[0m' +"|", end = "")
elif elem == 32:
print('\033[1;36;44m'+str(elem).ljust(5) + '\033[0m' +"|", end = "")
elif elem == 64:
print('\033[1;36;45m'+str(elem).ljust(5) + '\033[0m' +"|", end = "")
elif elem == 128:
print('\033[1;37;46m'+str(elem).ljust(5) + '\033[0m' +"|", end = "")
else:
print('\033[1;30;47m'+str(elem).ljust(5) + '\033[0m' +"|", end = "")
else:
print(" ".ljust(5) + "|", end = "")
print("\n" , end = "")
print("-" * int(6.1*self.length))
def getGrade(self):
'''合成多少加多少分'''
return sum(self.theNewNum)
# 读取用户数据
def getUserdata(self):
if not os.path.exists("C:\\UserData"):
os.makedirs("C:\\UserData")
if not os.path.exists("C:\\UserData\\init.dta"):
with open("C:\\UserData\\init.dta", "w") as f:
f.write("theBestGrade:0")
with open("C:\\UserData\\init.dta", "r") as f:
self.bestGrade = int(list(f)[0].split(":")[-1])
def writeUserdata(self):
with open("C:\\UserData\\init.dta", "w") as f:
f.write("theBestGrade:%d" % self.bestGrade)
# 出现1024即为成功
def isWin(self):
for i in self.mainList:
for j in i:
if j == 2048:
return 1024
return -1
# 判断是否失败
def isFall(self):
count = 0
for eachList in self.mainList:
for eachElem in eachList:
if eachElem == 0:
return False
if self.getCommon(eachElem, count):
# print(count)
return False
count += 1
return True
# 检测一个元素周围是否有相同的元素
def getCommon(self, elem, now):
right = (now+1) - int(now/self.length)*self.length
down = int((now+self.length)/self.length)
row = int(now / self.length)
column = now % self.length
if right < self.length and elem == self.mainList[row][right]:
return True
if down < self.length and elem == self.mainList[down][column]:
return True
return False
# 程序入口
def main():
mainGame = Game_2048()
keyboard.hook(mainGame.pressKey)
keyboard.wait()
if __name__ == "__main__":
main()