From cbe2ee20f5af4ff4cf702e018b9a81485feb788a Mon Sep 17 00:00:00 2001 From: Artur Savitskiy Date: Tue, 7 May 2024 10:24:05 +0200 Subject: [PATCH] Lesson results commit --- HNS/MB/ShipField.py | 33 +++++-------- HNS/MB/main.py | 116 +++++++++++++++++++++++++++++++------------- 2 files changed, 92 insertions(+), 57 deletions(-) diff --git a/HNS/MB/ShipField.py b/HNS/MB/ShipField.py index 6ecd42f..04fd698 100644 --- a/HNS/MB/ShipField.py +++ b/HNS/MB/ShipField.py @@ -1,8 +1,7 @@ import copy - from ShootResult import ShootResult -from ShipDirection import ShipDirection from ShipMode import ShipMode +from ShipDirection import ShipDirection class ShipField: @@ -120,7 +119,7 @@ class ShipField: ship_size = 1 ship_direction = ShipDirection.UNKNOWN - # Проверим вертикаль + # check vertical for r in range(row + 1, self.field_size): if self.check_ship(r, col): ship_size += 1 @@ -138,7 +137,7 @@ class ShipField: break if ship_direction == ShipDirection.UNKNOWN: - # Проверим горизонталь + # check horizontal for c in range(col + 1, self.field_size): if self.check_ship(row, c): ship_size += 1 @@ -147,7 +146,7 @@ class ShipField: else: break - for c in range(col - 1, -1, -1): + for c in range(col - 1, - 1, -1): if self.check_ship(row, c): ship_size += 1 ship_direction = ShipDirection.HORIZONTAL @@ -176,17 +175,11 @@ class ShipField: return ShootResult.UNDEFINED def check_ship(self, row, col): - # Функция должна возвращать True, если в заданной клетке есть корабль, - # в противном случае - False return self.field[row * self.field_size + col].strip() == '1' def check_possible(self, row, col): - # Функция должна возвращать True, если можно поставить сюда корабль, - # в противном случае - False if self.ship_direction == ShipDirection.VERTICAL: - # Здесь мы знаем, что корабль помещается на поле. if self.field_size - row >= self.ship_size: - # Теперь нужно проверить, не заблокировано ли какое-то из полей, for r in range(row, row + self.ship_size): if not self.check_blocked(r, col): return False @@ -202,8 +195,6 @@ class ShipField: return False def check_blocked(self, row, col): - # Функция возвращает True, если все клетки вокруг клетки с координатами row, col - # либо находятся за пределами поля, либо в них нет корабля/они пустые for r in range(row - 1, row + 2): for c in range(col - 1, col + 2): if 0 <= r < self.field_size and 0 <= c < self.field_size: @@ -233,10 +224,11 @@ class ShipField: self.ship_direction = value def toggle_ship_direction(self): - if self.ship_direction == ShipDirection.VERTICAL: - self.ship_direction = ShipDirection.HORIZONTAL - else: - self.ship_direction = ShipDirection.VERTICAL + if self.field_mode == ShipMode.PUT: + if self.ship_direction == ShipDirection.VERTICAL: + self.ship_direction = ShipDirection.HORIZONTAL + else: + self.ship_direction = ShipDirection.VERTICAL def toggle_field_mode(self): if self.field_mode == ShipMode.PUT: @@ -245,15 +237,13 @@ class ShipField: self.field_mode = ShipMode.PUT def print_field(self): - print(self.ships) for r in range(0, self.field_size): blocked_string = "" ship_string = "" for c in range(0, self.field_size): blocked_string += str(self.check_blocked(r, c))[0] + ", " ship_string += self.field[r * self.field_size + c] + ', ' - print(ship_string[:-2]) - # print(blocked_string[:-2] + ' ' + ship_string[:-2]) + print(blocked_string[:-2] + ' ' + ship_string[:-2]) print("********************************************************************") @staticmethod @@ -262,5 +252,4 @@ class ShipField: result = copy.copy(obj.__dict__) result['field_mode'] = obj.field_mode.value result['ship_direction'] = obj.ship_direction.value - return result - + return result \ No newline at end of file diff --git a/HNS/MB/main.py b/HNS/MB/main.py index 90720e7..24f530c 100644 --- a/HNS/MB/main.py +++ b/HNS/MB/main.py @@ -1,22 +1,23 @@ import json import os -from tkinter import * +import time from tkinter import filedialog - +from tkinter import * from ShipField import ShipField my_field = ShipField() enemy_field = ShipField() active_field = my_field +active_text = {} -def draw_field(window, field, col_offset): +def draw_field(window, field, col_offset=0, row_offset=0): buttons = [] for r in range(0, field.field_size): for c in range(0, field.field_size): btn = Button(window, text='', width=5, height=2) - btn.grid(column=c + col_offset, row=r) + btn.grid(column=c + col_offset, row=r + row_offset) btn.bind('', lambda e, x=r, y=c: left_button_click(buttons, x, y)) btn.bind('', right_button_click) btn.bind('', lambda e, x=r, y=c: button_enter(buttons, x, y)) @@ -26,27 +27,27 @@ def draw_field(window, field, col_offset): def colorize(field, buttons): - for i in range(len(buttons)): + for i in range(len(field.field)): bg = "white" - if field[i] == "1": + if field.field[i] == "1": bg = 'pink' - if field[i] == "\\": - bg = 'red' - if field[i] == "0": + if field.field[i] == "\\": + bg = 'grey' + if field.field[i] == "0": bg = 'black' - if field[i] == "p": + if field.field[i] == "p": bg = 'blue' - if "+" in field[i]: - bg = 'orange' - if "r" in field[i]: + if field.field[i] == "r": bg = 'red' + if "+" in field.field[i]: + bg = 'orange' buttons[i].configure(bg=bg) def keypress_handler(e): global active_field if e.keysym.isnumeric(): - active_field.set_ship_size(e.keysym) + active_field.set_ship_size(int(e.keysym)) else: if e.keysym == 'm': active_field.toggle_field_mode() @@ -54,27 +55,32 @@ def keypress_handler(e): def left_button_click(buttons, row, col): global active_field + global active_text active_field.action(row, col) colorize(active_field, buttons) + refresh_remaining_ships_label(active_field, active_text) -def right_button_click(unused): + +def right_button_click(d): global active_field - active_field.toggle_ship_direction() def button_enter(buttons, row, col): global active_field + global active_text if buttons == my_buttons: active_field = my_field + active_text = my_remainingShipsText enemy_field.clear_marker() my_field.target(row, col) elif buttons == enemy_buttons: active_field = enemy_field + active_text = enemy_remainingShipsText my_field.clear_marker() enemy_field.target(row, col) @@ -82,44 +88,84 @@ def button_enter(buttons, row, col): colorize(enemy_field, enemy_buttons) -def savebutton_click(event): +def savebutton_click(field): file_path = filedialog.asksaveasfilename(filetypes=[("JSON files", "*.json")]) if file_path: with open(file_path, 'w') as f: - json.dump({'my_field': my_field}, f, default=ShipField.convert_to_json) + json.dump({'shipField': field}, f, default=ShipField.convert_to_json) -def loadbutton_click(event): - global my_field - +def loadbutton_click(field, buttons): file_path = filedialog.askopenfilename(filetypes=[("JSON files", "*.json")]) if os.path.isfile(file_path): with open(file_path) as lines: - my_field.from_json(json.load(lines)["my_field"]) + field.from_json(json.load(lines)["shipField"]) - colorize(my_field, my_buttons) + colorize(field, buttons) + + +def refresh_remaining_ships_label(field, stringvar): + text = '' + for i in range(1, 5): + count = field.ships.count(i) + if count > 0: + text += f'{"[]" * i}: {count}, ' + + stringvar.set(text[:-2]) window = Tk() window.title("Ship Craft!") -window.geometry('940x510') +window.geometry('1020x540') window.bind_all('', keypress_handler) -my_buttons = draw_field(window, my_field, 0) -enemy_buttons = draw_field(window, enemy_field, 11) +my_remainingShipsText = StringVar() +enemy_remainingShipsText = StringVar() -lbl = Label(window, text='', width=5, height=2) -lbl.grid(column=10, row=0) +start_column_my_field = 1 +start_row_my_field = 1 -savebutton = Button(window, text='Save', width=20, height=2) -savebutton.bind('', savebutton_click) -savebutton.grid(column=0, row=11, columnspan=4) +start_column_enemy_field = start_column_my_field + my_field.field_size + 1 +start_row_enemy_field = start_row_my_field + +col_vertical_separator = start_column_my_field + my_field.field_size +row_horizontal_separator = start_row_my_field + my_field.field_size + +load_button_row = start_row_my_field + my_field.field_size + 1 + +my_buttons = draw_field(window, my_field, start_column_my_field, start_row_my_field) +enemy_buttons = draw_field(window, enemy_field, start_column_enemy_field, start_row_enemy_field) + +if start_column_my_field > 0: + lbl_left_vertical = Label(window, text='', width=5, height=2) + lbl_left_vertical.grid(column=start_column_my_field - 1, row=start_row_my_field) + +lbl_center_vertical = Label(window, text='', width=5, height=2) +lbl_center_vertical.grid(column=col_vertical_separator, row=start_row_my_field) + +if start_row_my_field > 0: + lbl_upper_horizontal = Label(window, text='', width=5, height=2) + lbl_upper_horizontal.grid(column=start_column_my_field, row=start_row_my_field - 1) + +lbl_lower_horizontal = Label(window, text='', width=50, height=2, textvariable=my_remainingShipsText) +lbl_lower_horizontal.grid(column=start_column_my_field, row=row_horizontal_separator, columnspan=10) + +lbl_lower_enemy_horizontal = Label(window, text='', width=50, height=2, textvariable=enemy_remainingShipsText) +lbl_lower_enemy_horizontal.grid(column=start_column_enemy_field, row=row_horizontal_separator, columnspan=10) + +savebutton = Button(window, text='Save', width=20, height=2, command=lambda: savebutton_click(my_field)) +savebutton.grid(column=start_column_my_field, row=load_button_row, columnspan=4) + +loadbutton = Button(window, text='Load', width=20, height=2, command=lambda: loadbutton_click(my_field, my_buttons)) +loadbutton.grid(column=start_column_my_field + 6, row=load_button_row, columnspan=4) + +savebutton_enemy = Button(window, text='Save', width=20, height=2, command=lambda: savebutton_click(enemy_field)) +savebutton_enemy.grid(column=start_column_enemy_field, row=load_button_row, columnspan=4) + +loadbutton_enemy = Button(window, text='Load', width=20, height=2, command=lambda: loadbutton_click(enemy_field, enemy_buttons)) +loadbutton_enemy.grid(column=start_column_enemy_field + 6, row=load_button_row, columnspan=4) -loadbutton = Button(window, text='Load', width=20, height=2) -loadbutton.bind('', loadbutton_click) -loadbutton.grid(column=5, row=11, columnspan=4) window.mainloop() -