简易五子棋下篇-内部逻辑

目标:

接上篇,此篇完成五子棋的逻辑部分。

思路:

  • 分析:需要一个判断输赢的逻辑、一个将棋子落在目标位置的逻辑、标签和按钮对应的方法
  • 判断输赢:
    • 分别对落子位置的横纵轴位置和两个斜边位置的同色棋子进行计数
    • 如果任意一处同色棋子数量达到5或5以上,则判断赢家和游戏结束
    • 每次棋子落下,都要调用一次判断输赢的逻辑
  • 落子:
    • 每次坐标点击会捕获一个坐标位置,找出离这个坐标最近的棋位
    • 落子

实现:

# -*- coding: utf-8 -*-
"""
Created on Fri Feb  2 20:04:38 2018

@author: 23755
"""

import tkinter as tk

PIECE_SIZE = 10

click_x = 0
click_y = 0

pieces_x = [i for i in range(32, 523, 35)]
pieces_y = [i for i in range(38, 529, 35)]

coor_black = []
coor_white = []

person_flag = 1
piece_color = "black"

#右上方的棋子提示(工具)
def showChange(color):
    global piece_color
    piece_color = color
    side_canvas.delete("show_piece")
    side_canvas.create_oval(110 - PIECE_SIZE, 25 - PIECE_SIZE,
                        110 + PIECE_SIZE, 25 + PIECE_SIZE,
                        fill = piece_color, tags = ("show_piece"))

#输赢的提示、游戏结束的提示(工具)
def pushMessage():
    if person_flag == -1:
        var1.set("白棋赢")
    elif person_flag == 1:
        var1.set("黑棋赢")
    var2.set("游戏结束")

#棋子的计数(工具)
def piecesCount(coor, pieces_count, t1, t2):
    for i in range(1, 5):
        (x, y) = (click_x + t1 * 35 * i, click_y + t2 * 35 * i)
        if (x, y) in coor:
            pieces_count += 1
        else:
            break
    return pieces_count

#事件监听处理
def coorBack(event):  #return coordinates of cursor 返回光标坐标
    global click_x, click_y
    click_x = event.x
    click_y = event.y
    coorJudge()

#定义重置按钮的功能
def gameReset():
    global person_flag, coor_black, coor_white, piece_color
    person_flag = 1       #打开落子开关
    var.set("执黑棋")      #还原提示标签
    var1.set("")          #还原输赢提示标签
    var2.set("")          #还原游戏结束提示标签
    showChange("black")   #还原棋子提示图片
    canvas.delete("piece")#删除所有棋子
    coor_black = []       #清空黑棋坐标存储器
    coor_white = []       #清空白棋坐标存储器


'''判断输赢的逻辑'''
#preJudge调用realJudge0,realJudge0调用realJudge1和realJudge2;
#realJudge1负责横纵两轴的计数,realJudge2负责两斜线方向的计数
#realJudge0汇总指定颜色棋子结果,作出决策,判断是否游戏结束
#preJudge决定是判断黑棋还是判断白棋,对两种颜色的棋子判断进行导流
def preJudge(piece_color):
    if piece_color == "black":
        realJudge0(coor_black)
    elif piece_color == "white":
        realJudge0(coor_white)

def realJudge0(coor):
    global person_flag, person_label

    if realJudge1(coor) == 1 or realJudge2(coor) == 1:
        pushMessage()
        person_flag = 0

def realJudge1(coor):
    pieces_count = 0
    pieces_count = piecesCount(coor, pieces_count, 1, 0) #右边
    pieces_count = piecesCount(coor, pieces_count, -1, 0)#左边
    if pieces_count >= 4:
        return 1
    else:
        pieces_count = 0
        pieces_count = piecesCount(coor, pieces_count, 0, -1)#上边
        pieces_count = piecesCount(coor, pieces_count, 0, 1) #下边
        if pieces_count >= 4:
            return 1
        else:
            return 0

def realJudge2(coor):
    pieces_count = 0
    pieces_count = piecesCount(coor, pieces_count, 1, 1)  #右下角
    pieces_count = piecesCount(coor, pieces_count, -1, -1)#左上角
    if pieces_count >= 4:
        return 1
    else:
        pieces_count = 0
        pieces_count = piecesCount(coor, pieces_count, 1, -1) #右上角
        pieces_count = piecesCount(coor, pieces_count, -1, 1) #左下角
        if pieces_count >= 4:
            return 1
        else:
            return 0

'''落子的逻辑'''
#落子
def putPiece(piece_color):
    global coor_black, coor_white
    canvas.create_oval(click_x - PIECE_SIZE, click_y - PIECE_SIZE,
                       click_x + PIECE_SIZE, click_y + PIECE_SIZE, 
                       fill = piece_color, tags = ("piece"))
    if piece_color == "white":
        coor_white.append( (click_x, click_y) )
    elif piece_color == "black":
        coor_black.append( (click_x, click_y) )
    preJudge(piece_color)  #每放置一枚棋子就对该种颜色的棋子进行一次判断

#找出离鼠标点击位置最近的棋盘线交点,调用putPiece落子
def coorJudge():
    global click_x, click_y
    coor = coor_black + coor_white
    global person_flag, show_piece
    #print("x = %s, y = %s" % (click_x, click_y))
    item = canvas.find_closest(click_x, click_y)
    tags_tuple = canvas.gettags(item)
    if len(tags_tuple) > 1:
        tags_list = list(tags_tuple)
        coor_list = tags_list[:2]
        try:
            for i in range(len(coor_list)):
                coor_list[i] = int(coor_list[i])
        except ValueError:
            pass
        else:
            coor_tuple = tuple(coor_list)
            (click_x, click_y) = coor_tuple
            #print("tags = ", tags_tuple, "coors = ", coor_tuple)
            if ( (click_x, click_y) not in coor )and( click_x in pieces_x )and( click_y in pieces_y ):
                #print("True")
                if person_flag != 0:
                    if person_flag == 1:
                        putPiece("black")
                        showChange("white")
                        var.set("执白棋")
                    elif person_flag == -1:
                        putPiece("white")
                        showChange("black")
                        var.set("执黑棋")
                    person_flag *= -1
            #else:
                #print("False")


效果图:

五子棋下篇

延伸:

可以另写一个逻辑作为对手进行对弈。

参考代码
我的GitHub仓库

此为旧文,图片水印为我的CSDN账号,无妨

发表评论

电子邮件地址不会被公开。 必填项已用*标注