萬能的窗口,實作視窗都可以進行簡單的修改進行使用:
from tkinter import * root = Tk() #窗口名称 root.title("憨憨制作的三子棋") f1=Frame(root) f1.pack() w1 = Canvas(f1, width=580,height=580,background='lightcyan')#创建一个画布,设置大小和背景颜色 w1.pack() root.mainloop()
畫出棋盤
#画出棋盘 for i in range(0, 4): w1.create_line(i * 180 + 20, 20, i * 180 + 20, 560) w1.create_line(20, i * 180 + 20, 560, i * 180 + 20)
分別畫橫豎線,四條橫線四條豎線,生成九個格子。也可以畫出兩橫兩豎,更貼近井字形狀。少畫幾條線就好,例如:
for i in range(1, 3): w1.create_line(i * 180 + 20, 20, i * 180 + 20, 560) w1.create_line(20, i * 180 + 20, 560, i * 180 + 20)
num = 0 #记录点击的次数,用来决定点击后该画哪种图形 A = np.full((3, 3), 0) #记录每个位置的图形
每次點擊以後我們都要畫圖、判斷是否達到獲勝的條件。
設定函數
def dawn(event): global w1 global num, A for i in range(0, 3): for j in range(0, 3): if 20 + j * 180 < event.y and event.y <= 20 + (j+1) * 180: break if 20 + i * 180 <= event.x and event.x <= 20 + (i+1) * 180: break if num % 2 == 0 and A[i][j] == 0: A[i][j] = 1 w1.create_line(110 + 180 * i - 45 * math.sqrt(2), 110 + 180 * j - 45 * math.sqrt(2), 110 + 180 * i + 45 * math.sqrt(2), 110 + 180 * j + 45 * math.sqrt(2)) w1.create_line(110 + 180 * i + 45 * math.sqrt(2), 110 + 180 * j - 45 * math.sqrt(2), 110 + 180 * i - 45 * math.sqrt(2), 110 + 180 * j + 45 * math.sqrt(2)) num += 1 if num % 2 != 0 and A[i][j] == 0: A[i][j] = 2 w1.create_oval(20 + 180 * i, 20 + 180 * j, 20 + 180 * (i + 1), 20 + 180 * (j + 1)) num += 1 if A[0][0] == A[0][1] == A[0][2] == 2 or A[1][0] == A[1][1] == A[1][2] == 2 or A[2][0] == A[2][1] == A[2][ 2] == 2 or \ A[0][0] == A[1][0] == A[2][0] == 2 or A[0][1] == A[1][1] == A[2][1] == 2 or A[0][2] == A[1][2] == \ A[2][ 2] == 2 or \ A[0][0] == A[1][1] == A[2][2] == 2 or A[2][0] == A[1][1] == A[0][2] == 2: tkinter.messagebox.showinfo('消息提示', '圆圈获胜') elif A[0][0] == A[0][1] == A[0][2] == 1 or A[1][0] == A[1][1] == A[1][2] == 1 or A[2][0] == A[2][1] == A[2][ 2] == 1 or \ A[0][0] == A[1][0] == A[2][0] == 1 or A[0][1] == A[1][1] == A[2][1] == 1 or A[0][2] == A[1][2] == \ A[2][ 2] == 1 or \ A[0][0] == A[1][1] == A[2][2] == 1 or A[2][0] == A[1][1] == A[0][2] == 1: tkinter.messagebox.showinfo('消息提示', '叉号获胜') w1.bind("<Button -1>", dawn)
我們拆開進行分析:
首先是:點擊位置的確定,得到我們的點擊單元格,開始時我是用的是判斷是否在方格的內切圓範圍內,發現點擊到方格的剩餘部分會導致化的圖形錯位,透過進一步的分析發現,可以透過分別定位點擊位置的橫縱座標,確定點擊的方格。
for i in range(0, 3): for j in range(0, 3): if 20 + j * 180 < event.y and event.y <= 20 + (j+1) * 180: break if 20 + i * 180 <= event.x and event.x <= 20 + (i+1) * 180: break
接著,確定了位置以後我們就開始判斷當前位置是否能畫圖形,應該畫什麼圖形,畫❌是比較麻煩的需要進行複雜的計算,畫⚪就比較簡單。
if num % 2 == 0 and A[i][j] == 0: #若为偶数就画叉号 A[i][j] = 1 w1.create_line(110 + 180 * i - 45 * math.sqrt(2), 110 + 180 * j - 45 * math.sqrt(2), 110 + 180 * i + 45 * math.sqrt(2), 110 + 180 * j + 45 * math.sqrt(2)) w1.create_line(110 + 180 * i + 45 * math.sqrt(2), 110 + 180 * j - 45 * math.sqrt(2), 110 + 180 * i - 45 * math.sqrt(2), 110 + 180 * j + 45 * math.sqrt(2)) num += 1 if num % 2 != 0 and A[i][j] == 0: #若为奇数就画圆圈 A[i][j] = 2 w1.create_oval(20 + 180 * i, 20 + 180 * j, 20 + 180 * (i + 1), 20 + 180 * (j + 1)) num += 1
畫完以後我們要判斷是否達到獲勝的條件,這裡我沒想到簡便的方法,但是好在獲勝的情況屈指可數,只有八種(橫3,豎3,兩個斜方向的)於是將八種情況列出進行判斷是否達到獲勝條件,而且兩種圖形都需要列出。
if A[0][0] == A[0][1] == A[0][2] == 2 or A[1][0] == A[1][1] == A[1][2] == 2 or A[2][0] == A[2][1] == A[2][ 2] == 2 or \ A[0][0] == A[1][0] == A[2][0] == 2 or A[0][1] == A[1][1] == A[2][1] == 2 or A[0][2] == A[1][2] == \ A[2][ 2] == 2 or \ A[0][0] == A[1][1] == A[2][2] == 2 or A[2][0] == A[1][1] == A[0][2] == 2: tkinter.messagebox.showinfo('消息提示', '圆圈获胜') elif A[0][0] == A[0][1] == A[0][2] == 1 or A[1][0] == A[1][1] == A[1][2] == 1 or A[2][0] == A[2][1] == A[2][ 2] == 1 or \ A[0][0] == A[1][0] == A[2][0] == 1 or A[0][1] == A[1][1] == A[2][1] == 1 or A[0][2] == A[1][2] == \ A[2][ 2] == 1 or \ A[0][0] == A[1][1] == A[2][2] == 1 or A[2][0] == A[1][1] == A[0][2] == 1: tkinter.messagebox.showinfo('消息提示', '叉号获胜')
最後設定點擊時間的取得以及退出按鈕的設定。
w1.bind("<Button -1>", dawn) def quit(): root.quit() button1 = Button(root, text="退出", font=('楷体', 20), command=quit) button1.pack()
到這裡遊戲的每個程式碼都講解完了。
附完整程式碼:
from tkinter import * import numpy as np import math import tkinter.messagebox root = Tk() #窗口名称 root.title("憨憨制作的三子棋") f1=Frame(root) f1.pack() w1 = Canvas(f1, width=580,height=580,background='lightcyan') w1.pack() #棋盘 for i in range(0, 4): w1.create_line(i * 180 + 20, 20, i * 180 + 20, 560) w1.create_line(20, i * 180 + 20, 560, i * 180 + 20) num = 0 A = np.full((3, 3), 0) def dawn(event): global w1 global num, A for i in range(0, 3): for j in range(0, 3): if 20 + j * 180 < event.y and event.y <= 20 + (j+1) * 180: break if 20 + i * 180 <= event.x and event.x <= 20 + (i+1) * 180: break if num % 2 == 0 and A[i][j] == 0: A[i][j] = 1 w1.create_line(110 + 180 * i - 45 * math.sqrt(2), 110 + 180 * j - 45 * math.sqrt(2), 110 + 180 * i + 45 * math.sqrt(2), 110 + 180 * j + 45 * math.sqrt(2)) w1.create_line(110 + 180 * i + 45 * math.sqrt(2), 110 + 180 * j - 45 * math.sqrt(2), 110 + 180 * i - 45 * math.sqrt(2), 110 + 180 * j + 45 * math.sqrt(2)) num += 1 if num % 2 != 0 and A[i][j] == 0: A[i][j] = 2 w1.create_oval(20 + 180 * i, 20 + 180 * j, 20 + 180 * (i + 1), 20 + 180 * (j + 1)) num += 1 if A[0][0] == A[0][1] == A[0][2] == 2 or A[1][0] == A[1][1] == A[1][2] == 2 or A[2][0] == A[2][1] == A[2][ 2] == 2 or \ A[0][0] == A[1][0] == A[2][0] == 2 or A[0][1] == A[1][1] == A[2][1] == 2 or A[0][2] == A[1][2] == \ A[2][ 2] == 2 or \ A[0][0] == A[1][1] == A[2][2] == 2 or A[2][0] == A[1][1] == A[0][2] == 2: tkinter.messagebox.showinfo('消息提示', '圆圈获胜') elif A[0][0] == A[0][1] == A[0][2] == 1 or A[1][0] == A[1][1] == A[1][2] == 1 or A[2][0] == A[2][1] == A[2][ 2] == 1 or \ A[0][0] == A[1][0] == A[2][0] == 1 or A[0][1] == A[1][1] == A[2][1] == 1 or A[0][2] == A[1][2] == \ A[2][ 2] == 1 or \ A[0][0] == A[1][1] == A[2][2] == 1 or A[2][0] == A[1][1] == A[0][2] == 1: tkinter.messagebox.showinfo('消息提示', '叉号获胜') w1.bind("<Button -1>", dawn) def quit(): root.quit() button1 = Button(root, text="退出", font=('楷体', 20), command=quit) button1.pack() root.mainloop()
以上是如何用Python寫一個簡單的井字棋小遊戲?的詳細內容。更多資訊請關注PHP中文網其他相關文章!