My application is written using the latest versions of Python 3.7, PyQt5 and python-chess. I have an SVG chessboard, produced by python-chess itself. My application handles mouse clicks on the chessboard which highlight the clicked square. I have a problem with precision. Sometimes the adjacent square is highlighted. I also have the chessboard coordinates on the left and on the top of the chessboard which are the root cause of my bug. Without the chessboard coordinates it works perfectly.
If anyone is interested in helping me, here's the code.
import chess
import chess.svg
from PyQt5.QtCore import pyqtSlot
from PyQt5.QtSvg import QSvgWidget
COORDINATES = True
FLIPPED = False
class Chessboard(QSvgWidget):
def __init__(self):
super().__init__()
self.clicked_square = -20
self.move_from_square = -20
self.move_to_square = -20
self.piece_to_move = [None, None]
viewbox_size = 400
self.margin = chess.svg.MARGIN * 800 / viewbox_size if COORDINATES else 0
self.file_size = chess.svg.SQUARE_SIZE * 800 / viewbox_size
self.rank_size = chess.svg.SQUARE_SIZE * 800 / viewbox_size
self.chessboard = chess.Board()
self.draw_chessboard()
@pyqtSlot(QSvgWidget)
def mousePressEvent(self, event):
x_coordinate = event.x()
y_coordinate = event.y()
file = int(x_coordinate / 800 * 8)
rank = 7 - int(y_coordinate / 800 * 8)
if file < 0:
file = 0
if rank < 0:
rank = 0
if file > 7:
file = 7
if rank > 7:
rank = 7
self.clicked_square = chess.square(file, rank)
piece = self.chessboard.piece_at(self.clicked_square)
file_character = chr(file + 97)
rank_number = str(rank + 1)
ply = f"{file_character}{rank_number}"
if self.piece_to_move[0]:
move = chess.Move.from_uci(f"{self.piece_to_move[1]}{ply}")
if move in self.chessboard.legal_moves:
self.chessboard.push(move)
self.move_from_square = move.from_square
self.move_to_square = move.to_square
piece = None
ply = None
self.piece_to_move = [piece, ply]
self.draw_chessboard()
def draw_chessboard(self):
is_it_check = self.chessboard.king(self.chessboard.turn) \
if self.chessboard.is_check() \
else None
self.svg_chessboard = chess.svg.board(board=self.chessboard,
lastmove=chess.Move(from_square=self.move_from_square,
to_square=self.move_to_square),
arrows=[(self.clicked_square, self.clicked_square),
(self.move_from_square, self.move_to_square)],
check=is_it_check,
flipped=FLIPPED,
coordinates=COORDINATES,
size=800)
self.svg_chessboard_encoded = self.svg_chessboard.encode("utf-8")
self.load(self.svg_chessboard_encoded)