当前位置:   article > 正文

Python 围棋_围棋在python中一共几个方向

围棋在python中一共几个方向

效果图

python 围棋

完整代码

源码地址Python 围棋

# 使用Python内置GUI模块tkinter  
from tkinter import *  
# ttk覆盖tkinter部分对象,ttk对tkinter进行了优化  
from tkinter.ttk import *  
# 深拷贝时需要用到copy模块  
import copy  
import tkinter.messagebox  
  
# 默认9路  
MODE_NUM = 9  
NEW_APP = False  
  
  
# 围棋应用对象定义  
class Application(Tk):  
    # 初始化棋盘,默认九路棋盘  
    def __init__(self, my_mode_num=9):  
        Tk.__init__(self)  
        # 模式,九路棋:9,十三路棋:13,十九路棋:19  
        self.mode_num = my_mode_num  
        # 窗口尺寸设置,默认:1.8  
        self.size = 1.8  
        # 棋盘每格的边长  
        self.dd = 360 * self.size / (self.mode_num - 1)  
        # 相对九路棋盘的矫正比例  
        self.p = 1 if self.mode_num == 9 else (2 / 3 if self.mode_num == 13 else 4 / 9)  
        # 定义棋盘阵列,超过边界:-1,无子:0,黑棋:1,白棋:2  
        self.positions = [[0 for i in range(self.mode_num + 2)] for i in range(self.mode_num + 2)]  
        # 初始化棋盘,所有超过边界的值置-1  
        for m in range(self.mode_num + 2):  
            for n in range(self.mode_num + 2):  
                if m * n == 0 or m == self.mode_num + 1 or n == self.mode_num + 1:  
                    self.positions[m][n] = -1  
        # 拷贝三份棋盘“快照”,悔棋和判断“打劫”时需要作参考  
        self.last_3_positions = copy.deepcopy(self.positions)  
        self.last_2_positions = copy.deepcopy(self.positions)  
        self.last_1_positions = copy.deepcopy(self.positions)  
        # 记录鼠标经过的地方,用于显示shadow时  
        self.cross_last = None  
        # 当前轮到的玩家,黑:0,白:1,执黑先行  
        self.present = 0  
        # 设置先手  
        self.fm = -1  
        # 棋子阴影  
        self.cross = None  
  
        # 记录空位置  
        self.image_added = None  
        self.image_added_sign = None  
        # 初始停止运行,点击“开始游戏”运行游戏  
        self.stop = True  
        # 悔棋次数,次数大于0才可悔棋,初始置0(初始不能悔棋),悔棋后置0,下棋或弃手时恢复为1,以禁止连续悔棋  
        self.regret_chance = 0  
        # 图片资源,存放在当前目录下的/images/中  
        self.image_W = PhotoImage(file="./images/WD-9.png")  
        self.image_B = PhotoImage(file="./images/BD-9.png")  
        self.image_BD = PhotoImage(file="./images/" + "BD" + "-" + str(self.mode_num) + ".png")  
        self.image_WD = PhotoImage(file="./images/" + "WD" + "-" + str(self.mode_num) + ".png")  
        self.image_BU = PhotoImage(file="./images/" + "BU" + "-" + str(self.mode_num) + ".png")  
        self.image_WU = PhotoImage(file="./images/" + "WU" + "-" + str(self.mode_num) + ".png")  
        # 用于黑白棋子图片切换的列表  
        self.chequer_wbu_list = [self.image_BU, self.image_WU]  
        self.chequer_wbd_list = [self.image_BD, self.image_WD]  
        # 窗口大小  
        self.geometry(str(int(600 * self.size)) + 'x' + str(int(400 * self.size)))  
        # 画布控件,作为容器  
        self.canvas_bottom = Canvas(self, bg='#585858', bd=0, width=600 * self.size, height=400 * self.size)  
        self.canvas_bottom.place(x=0, y=0)  
        # 几个功能按钮  
        self.startButton = Button(self, text='开始游戏', command=self.start)  
        self.startButton.place(x=480 * self.size, y=200 * self.size)  
        self.giveUpButton = Button(self, text='弃一手', command=self.give_up)  
        self.giveUpButton.place(x=480 * self.size, y=225 * self.size)  
        self.regretButton = Button(self, text='悔棋', command=self.regret_chess)  
        self.regretButton.place(x=480 * self.size, y=250 * self.size)  
        # 初始悔棋按钮禁用  
        self.regretButton['state'] = DISABLED  
        self.replayButton = Button(self, text='重新开始', command=self.reload)  
        self.replayButton.place(x=480 * self.size, y=275 * self.size)  
        self.newGameButton1 = Button(self, text=('十三' if self.mode_num == 9 else '九') + '路棋', command=self.new_game_one)  
        self.newGameButton1.place(x=480 * self.size, y=300 * self.size)  
        self.newGameButton2 = Button(self, text=('十三' if self.mode_num == 19 else '十九') + '路棋',  
                                     command=self.new_game_second)  
        self.newGameButton2.place(x=480 * self.size, y=325 * self.size)  
        self.quitButton = Button(self, text='退出游戏', command=self.quit)  
        self.quitButton.place(x=480 * self.size, y=350 * self.size)  
        # 画棋盘,填充颜色  
        self.canvas_bottom.create_rectangle(0 * self.size, 0 * self.size, 400 * self.size, 400 * self.size, fill='#d0892e')  
        # 刻画棋盘线及九个点  
        # 先画外框粗线  
        self.canvas_bottom.create_rectangle(20 * self.size, 20 * self.size, 380 * self.size, 380 * self.size, width=3)  
        # 棋盘上的九个定位点,以中点为模型,移动位置,以作出其余八个点  
        for m in [-1, 0, 1]:  
            for n in [-1, 0, 1]:  
                self.original = self.canvas_bottom.create_oval(  
                    200 * self.size - self.size * 2,  
                    200 * self.size - self.size * 2,  
                    200 * self.size + self.size * 2,  
                    200 * self.size + self.size * 2, fill='#000')  
                self.canvas_bottom.move(  
                    self.original,  
                    m * self.dd * (2 if self.mode_num == 9 else (3 if self.mode_num == 13 else 6)),  
                    n * self.dd * (2 if self.mode_num == 9 else (3 if self.mode_num == 13 else 6)))  
        # 画中间的线条  
        for i in range(1, self.mode_num - 1):  
            self.canvas_bottom.create_line(20 * self.size, 20 * self.size + i * self.dd, 380 * self.size,  
                                           20 * self.size + i * self.dd, width=2)  
            self.canvas_bottom.create_line(20 * self.size + i * self.dd, 20 * self.size, 20 * self.size + i * self.dd,  
                                           380 * self.size, width=2)  
        # 放置右侧初始图片  
        self.pW = None  
        # 默认黑棋先手  
        self.pB = self.canvas_bottom.create_image(500 * self.size + 11, 65 * self.size, image=self.image_B)  
        # 每张图片都添加image标签,方便reload函数删除图片  
        self.canvas_bottom.addtag_withtag('image', self.pB)  
        self.bButton = Button(self, text='黑棋先手', command=self.first_b)  
        self.bButton.place(x=480 * self.size, y=100 * self.size)  
        self.wButton = Button(self, text='白棋先手', command=self.first_w)  
        self.wButton.place(x=480 * self.size, y=120 * self.size)  
        # 鼠标移动时,调用shadow函数,显示随鼠标移动的棋子  
        self.canvas_bottom.bind('<Motion>', self.shadow)  
        # 鼠标左键单击时,调用get_down函数,放下棋子  
        self.canvas_bottom.bind('<Button-1>', self.get_down)  
        # 设置退出快捷键<Ctrl>+<D>,快速退出游戏  
        self.bind('<Control-KeyPress-d>', self.keyboard_quit)  
  
    def first_b(self):  
        """  
        @summary: 黑棋先手  
        :return:  
        """        self.present = 0  
        self.create_pb()  
        self.del_pw()  
        if self.stop:  
            self.bButton['state'] = DISABLED  
            self.wButton['state'] = NORMAL  
        else:  
            self.bButton['state'] = DISABLED  
            self.wButton['state'] = DISABLED  
  
    def first_w(self):  
        """  
        @summary: 白棋先手  
        :return:  
        """        self.present = 1  
        self.create_pw()  
        self.del_pb()  
        if self.stop:  
            self.wButton['state'] = DISABLED  
            self.bButton['state'] = NORMAL  
        else:  
            self.bButton['state'] = DISABLED  
            self.wButton['state'] = DISABLED  
  
    # 开始游戏函数,点击“开始游戏”时调用  
    def start(self):  
        # 禁止选先手  
        self.bButton['state'] = DISABLED  
        self.wButton['state'] = DISABLED  
        # 利用右侧图案提示开始时谁先落子  
        if self.present == 0:  
            self.create_pb()  
            self.del_pw()  
        else:  
            self.create_pw()  
            self.del_pb()  
        # 开始标志,解除stop  
        self.stop = None  
  
    # 放弃一手函数,跳过落子环节  
    def give_up(self):  
        # 悔棋恢复  
        if not self.regret_chance == 1:  
            self.regret_chance += 1  
        else:  
            self.regretButton['state'] = NORMAL  
        # 拷贝棋盘状态,记录前三次棋局  
        self.last_3_positions = copy.deepcopy(self.last_2_positions)  
        self.last_2_positions = copy.deepcopy(self.last_1_positions)  
        self.last_1_positions = copy.deepcopy(self.positions)  
        self.canvas_bottom.delete('image_added_sign')  
        # 轮到下一玩家  
        if self.present == 0:  
            self.create_pw()  
            self.del_pb()  
            self.present = 1  
        else:  
            self.create_pb()  
            self.del_pw()  
            self.present = 0  
  
    # 悔棋函数,可悔棋一回合,下两回合不可悔棋  
    def regret_chess(self):  
        # 判定是否可以悔棋,以前第三盘棋局复原棋盘  
        if self.regret_chance == 1:  
            self.regret_chance = 0  
            self.regretButton['state'] = DISABLED  
            list_of_b = []  
            list_of_w = []  
            self.canvas_bottom.delete('image')  
            if self.present == 0:  
                self.create_pb()  
            else:  
                self.create_pw()  
            for m in range(1, self.mode_num + 1):  
                for n in range(1, self.mode_num + 1):  
                    self.positions[m][n] = 0  
            for m in range(len(self.last_3_positions)):  
                for n in range(len(self.last_3_positions[m])):  
                    if self.last_3_positions[m][n] == 1:  
                        list_of_b += [[n, m]]  
                    elif self.last_3_positions[m][n] == 2:  
                        list_of_w += [[n, m]]  
            self.recover(list_of_b, 0)  
            self.recover(list_of_w, 1)  
            self.last_1_positions = copy.deepcopy(self.last_3_positions)  
            for m in range(1, self.mode_num + 1):  
                for n in range(1, self.mode_num + 1):  
                    self.last_2_positions[m][n] = 0  
                    self.last_3_positions[m][n] = 0  
  
    # 重新加载函数,删除图片,序列归零,设置一些初始参数,点击“重新开始”时调用  
    def reload(self):  
        if self.stop == 1:  
            self.stop = 0  
        self.canvas_bottom.delete('image')  
        self.regret_chance = 0  
        self.present = 0  
        self.create_pb()  
        for m in range(1, self.mode_num + 1):  
            for n in range(1, self.mode_num + 1):  
                self.positions[m][n] = 0  
                self.last_3_positions[m][n] = 0  
                self.last_2_positions[m][n] = 0  
                self.last_1_positions[m][n] = 0  
  
    # 以下四个函数实现了右侧太极图的动态创建与删除  
    def create_pw(self):  
        """  
        @summary: 创建白棋  
        :return:  
        """        self.pW = self.canvas_bottom.create_image(500 * self.size + 11, 65 * self.size, image=self.image_W)  
        self.canvas_bottom.addtag_withtag('image', self.pW)  
  
    def create_pb(self):  
        """  
        @summary: 创建黑棋  
        :return:  
        """        self.pB = self.canvas_bottom.create_image(500 * self.size + 11, 65 * self.size, image=self.image_B)  
        self.canvas_bottom.addtag_withtag('image', self.pB)  
  
    def del_pw(self):  
        if self.pW:  
            self.canvas_bottom.delete(self.pW)  
  
    def del_pb(self):  
        if self.pB:  
            self.canvas_bottom.delete(self.pB)  
  
    # 显示鼠标移动下棋子的移动  
    def shadow(self, event):  
        if not self.stop:  
            # 找到最近格点,在当前位置靠近的格点出显示棋子图片,并删除上一位置的棋子图片  
            if (20 * self.size < event.x < 380 * self.size) and (20 * self.size < event.y < 380 * self.size):  
                dx = (event.x - 20 * self.size) % self.dd  
                dy = (event.y - 20 * self.size) % self.dd  
                self.cross = self.canvas_bottom.create_image(  
                    event.x - dx + round(dx / self.dd) * self.dd + 22 * self.p,  
                    event.y - dy + round(dy / self.dd) * self.dd - 27 * self.p,  
                    image=self.chequer_wbu_list[self.present])  
                self.canvas_bottom.addtag_withtag('image', self.cross)  
                if self.cross_last is not None:  
                    self.canvas_bottom.delete(self.cross_last)  
                self.cross_last = self.cross  
  
    # 落子,并驱动玩家的轮流下棋行为  
    def get_down(self, event):  
        if not self.stop:  
            # 先找到最近格点  
            if (20 * self.size - self.dd * 0.4 < event.x < self.dd * 0.4 + 380 * self.size) and \  
                    (20 * self.size - self.dd * 0.4 < event.y < self.dd * 0.4 + 380 * self.size):  
                dx = (event.x - 20 * self.size) % self.dd  
                dy = (event.y - 20 * self.size) % self.dd  
                x = int((event.x - 20 * self.size - dx) / self.dd + round(dx / self.dd) + 1)  
                y = int((event.y - 20 * self.size - dy) / self.dd + round(dy / self.dd) + 1)  
                # 判断位置是否已经被占据  
                if self.positions[y][x] == 0:  
                    # 未被占据,则尝试占据,获得占据后能杀死的棋子列表  
                    self.positions[y][x] = self.present + 1  
                    self.image_added = self.canvas_bottom.create_image(  
                        event.x - dx + round(dx / self.dd) * self.dd + 4 * self.p,  
                        event.y - dy + round(dy / self.dd) * self.dd - 5 * self.p,  
                        image=self.chequer_wbd_list[self.present])  
                    self.canvas_bottom.addtag_withtag('image', self.image_added)  
                    # 棋子与位置标签绑定,方便“杀死”  
                    self.canvas_bottom.addtag_withtag('position' + str(x) + str(y), self.image_added)  
                    dead_list = self.get_dead_list(x, y)  
                    self.kill(dead_list)  
                    # 判断是否重复棋局  
                    if not self.last_2_positions == self.positions:  
                        # 判断是否属于有气和杀死对方其中之一  
                        if len(dead_list) > 0 or self.if_dead([[x, y]], self.present + 1, [x, y]) == False:  
                            # 当不重复棋局,且属于有气和杀死对方其中之一时,落下棋子有效  
                            if not self.regret_chance == 1:  
                                self.regret_chance += 1  
                            else:  
                                self.regretButton['state'] = NORMAL  
                            self.last_3_positions = copy.deepcopy(self.last_2_positions)  
                            self.last_2_positions = copy.deepcopy(self.last_1_positions)  
                            self.last_1_positions = copy.deepcopy(self.positions)  
                            # 删除上次的标记,重新创建标记  
                            self.canvas_bottom.delete('image_added_sign')  
                            self.image_added_sign = self.canvas_bottom.create_oval(  
                                event.x - dx + round(dx / self.dd) * self.dd + 0.5 * self.dd,  
                                event.y - dy + round(dy / self.dd) * self.dd + 0.5 * self.dd,  
                                event.x - dx + round(dx / self.dd) * self.dd - 0.5 * self.dd,  
                                event.y - dy + round(dy / self.dd) * self.dd - 0.5 * self.dd, width=3, outline='#3ae')  
                            self.canvas_bottom.addtag_withtag('image', self.image_added_sign)  
                            self.canvas_bottom.addtag_withtag('image_added_sign', self.image_added_sign)  
                            if self.present == 0:  
                                self.create_pw()  
                                self.del_pb()  
                                self.present = 1  
                            else:  
                                self.create_pb()  
                                self.del_pw()  
                                self.present = 0  
                        else:  
                            # 不属于杀死对方或有气,则判断为无气,警告并弹出警告框  
                            self.positions[y][x] = 0  
                            self.canvas_bottom.delete('position' + str(x) + str(y))  
                            self.bell()  
                            self.show_warning_box('无气', "你被包围了!")  
                    else:  
                        # 重复棋局,警告打劫  
                        self.positions[y][x] = 0  
                        self.canvas_bottom.delete('position' + str(x) + str(y))  
                        self.recover(dead_list, (1 if self.present == 0 else 0))  
                        self.bell()  
                        self.show_warning_box("打劫", "此路不通!")  
                else:  
                    # 覆盖,声音警告  
                    self.bell()  
            else:  
                # 超出边界,声音警告  
                self.bell()  
  
    def if_dead(self, dead_list, your_chess, your_position):  
        """  
        判断棋子(种类为 your_chess,位置为 your_position)是否无气(死亡)。  
        如果棋子有气,则返回 False,表示棋子存活。  
        如果棋子无气,则返回包含所有无气棋子位置的列表。  
        参数:  
        - dead_list: 一个列表,初始时包含当前正在检查的棋子的位置。  
        - your_chess: 当前正在检查的棋子的种类。  
        - your_position: 当前正在检查的棋子的位置。  
  
        返回值:  
        - 如果棋子有气,返回 False。  
        - 如果棋子无气,返回包含所有无气棋子位置的列表。  
  
        函数逻辑:  
        1. 检查当前棋子周围是否有空位,如果有,则棋子有气,返回 False。  
        2. 如果周围没有空位,检查周围是否有同类棋子,如果有,则递归调用 if_dead 函数检查这些棋子是否有气。  
        3. 如果递归调用返回 False,表示至少有一个同类棋子有气,当前棋子也有气,返回 False。  
        4. 如果递归调用返回一个列表,表示所有检查的同类棋子都无气,将这些棋子的位置添加到 dead_list 中。  
        5. 如果所有周围的同类棋子都检查完毕且都无气,返回 dead_list,表示当前棋子无气。  
        """        # 检查上下左右四个方向是否有空位  
        for i in [-1, 1]:  
            # 检查上方和下方  
            if [your_position[0] + i, your_position[1]] not in dead_list:  
                if self.positions[your_position[1]][your_position[0] + i] == 0:  
                    return False  # 如果有空位,当前棋子有气  
            # 检查左侧和右侧  
            if [your_position[0], your_position[1] + i] not in dead_list:  
                if self.positions[your_position[1] + i][your_position[0]] == 0:  
                    return False  # 如果有空位,当前棋子有气  
  
        # 检查四个方向上是否有同类棋子,并递归检查这些棋子是否有气  
        # 上方的同类棋子  
        if ([your_position[0] + 1, your_position[1]] not in dead_list) and (  
                self.positions[your_position[1]][your_position[0] + 1] == your_chess):  
            mid = self.if_dead(dead_list + [[your_position[0] + 1, your_position[1]]], your_chess,  
                               [your_position[0] + 1, your_position[1]])  
            if not mid:  
                return False  # 如果上方同类棋子有气,则当前棋子也有气  
            else:  
                dead_list += copy.deepcopy(mid)  # 如果无气,将棋子位置添加到列表中  
        # 下方的同类棋子,逻辑同上  
        # ...  
        # 左侧的同类棋子,逻辑同上  
        # ...  
        # 右侧的同类棋子,逻辑同上  
        # ...  
  
        # 如果所有检查都完成,没有找到有气的同类棋子,则当前棋子无气,返回包含所有无气棋子位置的列表  
        return dead_list  
  
    # 警告消息框,接受标题和警告信息  
    def show_warning_box(self, title, message):  
        self.canvas_bottom.delete(self.cross)  
        tkinter.messagebox.showwarning(title, message)  
  
    # 落子后,依次判断四周是否有棋子被杀死,并返回死棋位置列表  
    def get_dead_list(self, x, y):  
        dead_list = []  
        for i in [-1, 1]:  
            if self.positions[y][x + i] == (2 if self.present == 0 else 1) and ([x + i, y] not in dead_list):  
                kill = self.if_dead([[x + i, y]], (2 if self.present == 0 else 1), [x + i, y])  
                if kill:  
                    dead_list += copy.deepcopy(kill)  
            if self.positions[y + i][x] == (2 if self.present == 0 else 1) and ([x, y + i] not in dead_list):  
                kill = self.if_dead([[x, y + i]], (2 if self.present == 0 else 1), [x, y + i])  
                if kill:  
                    dead_list += copy.deepcopy(kill)  
        return dead_list  
  
    # 恢复位置列表list_to_recover为b_or_w指定的棋子  
    def recover(self, list_to_recover, b_or_w):  
        if len(list_to_recover) > 0:  
            for i in range(len(list_to_recover)):  
                self.positions[list_to_recover[i][1]][list_to_recover[i][0]] = b_or_w + 1  
                self.image_added = self.canvas_bottom.create_image(  
                    20 * self.size + (list_to_recover[i][0] - 1) * self.dd + 4 * self.p,  
                    20 * self.size + (list_to_recover[i][1] - 1) * self.dd - 5 * self.p,  
                    image=self.chequer_wbd_list[b_or_w])  
                self.canvas_bottom.addtag_withtag('image', self.image_added)  
                self.canvas_bottom.addtag_withtag('position' + str(list_to_recover[i][0]) + str(list_to_recover[i][1]),  
                                                  self.image_added)  
  
    # 杀死位置列表killList中的棋子,即删除图片,位置值置0  
    def kill(self, kill_list):  
        if len(kill_list) > 0:  
            for i in range(len(kill_list)):  
                self.positions[kill_list[i][1]][kill_list[i][0]] = 0  
                self.canvas_bottom.delete('position' + str(kill_list[i][0]) + str(kill_list[i][1]))  
  
    # 键盘快捷键退出游戏  
    def keyboard_quit(self, event):  
        self.quit()  
  
    # 以下两个函数修改全局变量值,newApp使主函数循环,以建立不同参数的对象  
    def new_game_one(self):  
        global MODE_NUM, NEW_APP  
        MODE_NUM = (13 if self.mode_num == 9 else 9)  
        NEW_APP = True  
        self.quit()  
  
    def new_game_second(self):  
        global MODE_NUM, NEW_APP  
        MODE_NUM = (13 if self.mode_num == 19 else 19)  
        NEW_APP = True  
        self.quit()  
  
  
# 声明全局变量,用于新建Application对象时切换成不同模式的游戏  
  
if __name__ == '__main__':  
    # 循环,直到不切换游戏模式  
    while True:  
        NEW_APP = False  
        app = Application(MODE_NUM)  
        app.title('围棋')  
        app.mainloop()  
        if NEW_APP:  
            app.destroy()  
        else:  
            break
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
  • 79
  • 80
  • 81
  • 82
  • 83
  • 84
  • 85
  • 86
  • 87
  • 88
  • 89
  • 90
  • 91
  • 92
  • 93
  • 94
  • 95
  • 96
  • 97
  • 98
  • 99
  • 100
  • 101
  • 102
  • 103
  • 104
  • 105
  • 106
  • 107
  • 108
  • 109
  • 110
  • 111
  • 112
  • 113
  • 114
  • 115
  • 116
  • 117
  • 118
  • 119
  • 120
  • 121
  • 122
  • 123
  • 124
  • 125
  • 126
  • 127
  • 128
  • 129
  • 130
  • 131
  • 132
  • 133
  • 134
  • 135
  • 136
  • 137
  • 138
  • 139
  • 140
  • 141
  • 142
  • 143
  • 144
  • 145
  • 146
  • 147
  • 148
  • 149
  • 150
  • 151
  • 152
  • 153
  • 154
  • 155
  • 156
  • 157
  • 158
  • 159
  • 160
  • 161
  • 162
  • 163
  • 164
  • 165
  • 166
  • 167
  • 168
  • 169
  • 170
  • 171
  • 172
  • 173
  • 174
  • 175
  • 176
  • 177
  • 178
  • 179
  • 180
  • 181
  • 182
  • 183
  • 184
  • 185
  • 186
  • 187
  • 188
  • 189
  • 190
  • 191
  • 192
  • 193
  • 194
  • 195
  • 196
  • 197
  • 198
  • 199
  • 200
  • 201
  • 202
  • 203
  • 204
  • 205
  • 206
  • 207
  • 208
  • 209
  • 210
  • 211
  • 212
  • 213
  • 214
  • 215
  • 216
  • 217
  • 218
  • 219
  • 220
  • 221
  • 222
  • 223
  • 224
  • 225
  • 226
  • 227
  • 228
  • 229
  • 230
  • 231
  • 232
  • 233
  • 234
  • 235
  • 236
  • 237
  • 238
  • 239
  • 240
  • 241
  • 242
  • 243
  • 244
  • 245
  • 246
  • 247
  • 248
  • 249
  • 250
  • 251
  • 252
  • 253
  • 254
  • 255
  • 256
  • 257
  • 258
  • 259
  • 260
  • 261
  • 262
  • 263
  • 264
  • 265
  • 266
  • 267
  • 268
  • 269
  • 270
  • 271
  • 272
  • 273
  • 274
  • 275
  • 276
  • 277
  • 278
  • 279
  • 280
  • 281
  • 282
  • 283
  • 284
  • 285
  • 286
  • 287
  • 288
  • 289
  • 290
  • 291
  • 292
  • 293
  • 294
  • 295
  • 296
  • 297
  • 298
  • 299
  • 300
  • 301
  • 302
  • 303
  • 304
  • 305
  • 306
  • 307
  • 308
  • 309
  • 310
  • 311
  • 312
  • 313
  • 314
  • 315
  • 316
  • 317
  • 318
  • 319
  • 320
  • 321
  • 322
  • 323
  • 324
  • 325
  • 326
  • 327
  • 328
  • 329
  • 330
  • 331
  • 332
  • 333
  • 334
  • 335
  • 336
  • 337
  • 338
  • 339
  • 340
  • 341
  • 342
  • 343
  • 344
  • 345
  • 346
  • 347
  • 348
  • 349
  • 350
  • 351
  • 352
  • 353
  • 354
  • 355
  • 356
  • 357
  • 358
  • 359
  • 360
  • 361
  • 362
  • 363
  • 364
  • 365
  • 366
  • 367
  • 368
  • 369
  • 370
  • 371
  • 372
  • 373
  • 374
  • 375
  • 376
  • 377
  • 378
  • 379
  • 380
  • 381
  • 382
  • 383
  • 384
  • 385
  • 386
  • 387
  • 388
  • 389
  • 390
  • 391
  • 392
  • 393
  • 394
  • 395
  • 396
  • 397
  • 398
  • 399
  • 400
  • 401
  • 402
  • 403
  • 404
  • 405
  • 406
  • 407
  • 408
  • 409
  • 410
  • 411
  • 412
  • 413
  • 414
  • 415
  • 416
  • 417
  • 418
  • 419
  • 420
  • 421
  • 422
  • 423
  • 424
  • 425
  • 426
  • 427
  • 428
  • 429
  • 430
  • 431
  • 432
  • 433
  • 434
  • 435
  • 436
  • 437
  • 438
  • 439
  • 440
  • 441
  • 442
  • 443
  • 444
  • 445
  • 446
  • 447
  • 448
  • 449
  • 450
  • 451
  • 452
  • 453
  • 454
  • 455
  • 456
  • 457
  • 458
  • 459
  • 460
  • 461
  • 462
  • 463
  • 464
  • 465
  • 466
  • 467
  • 468

源码地址Python 围棋

在这里插入图片描述

实现思路

这段 Python 代码实现了一个基于 tkinter 的围棋游戏 GUI。以下是实现的主要思路:

  1. 初始化界面:创建一个 Tk 窗口,设置窗口大小,并加载所需的图片资源。

  2. 棋盘和棋子初始化一个二维数组来表示棋盘,数组中的元素表示棋盘上的位置状态(空、黑棋、白棋)。使用 Canvas 控件绘制棋盘和棋子。

  3. 棋子下法:通过鼠标点击画布来放置棋子。棋子的放置逻辑包括判断位置是否有效、是否被占据,以及放置后是否形成打劫(即重复之前的局面)。

  4. 悔棋功能:允许玩家悔棋,即撤销上一步操作。悔棋后棋盘状态回退到前一次的状态。

  5. 重新开始游戏:允许玩家重新开始游戏,重置棋盘状态和界面元素。

  6. 切换棋盘大小:支持 9 路、13 路和 19 路棋盘,玩家可以通过按钮切换棋盘大小。

  7. 玩家交替落子:通过变量 present 来记录当前轮到哪个玩家落子,0 表示黑棋,1 表示白棋。

  8. 判断死活:实现了一个递归函数 if_dead 来判断棋子是否被完全包围(即无气),如果是,则认为该棋子死亡。

  9. 界面交互:包括开始游戏、弃一手(跳过当前回合)、悔棋、重新开始、切换棋盘大小和退出游戏等按钮。

  10. 图形用户界面元素:使用 tkinter 的 ButtonCanvas 等组件来构建用户界面。

  11. 事件绑定:通过绑定鼠标事件和键盘事件来响应用户的交互操作。

  12. 辅助功能:包括显示警告框、声音提示等,以增强用户体验。

整体上,这段代码通过 tkinter 模块实现了一个基本的围棋游戏,包括棋盘的绘制、棋子的下法、悔棋功能以及基本的用户交互。代码结构清晰,功能模块化,易于理解和扩展。

源码地址Python 围棋

Python 爱心代码:https://stormsha.blog.csdn.net/article/details/138199890
Python 植物大战僵尸:https://stormsha.blog.csdn.net/article/details/138405944
Python 开心消消乐:https://stormsha.blog.csdn.net/article/details/139220748

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/在线问答5/article/detail/882472
推荐阅读
相关标签
  

闽ICP备14008679号