CS課程項目設計1:交互友好的井字棋游戲

最近突然想開設一個專欄了,專門為計算機專業的同行分享一些入門級的課程項目設計,旨在讓同學更好地了解CS項目的設計流程,同時給出代碼來介紹coding過程。


今天要分享的是第一個CS課程項目:交互友好的井字棋游戲。

1. 研究目的

井字棋(Tic-Tac-Toe)作為一款經典的雙人策略游戲,具有規則簡單、易于理解的特點,適合作為編程教育和人機交互研究的基礎案例。目前各類知識分享平臺上(如CSDN、知乎)的井字棋游戲雖然數量眾多,但部分存在功能單一、界面簡陋、交互體驗不佳等問題。本項目旨在開發一款具有現代 UI 設計和豐富交互功能的井字棋游戲,滿足用戶對游戲趣味性和易用性的需求。

本項目設計的井字棋游戲包含以下功能:

  1. 實現井字棋的基本游戲規則,包括輪流落子、勝負判定和平局檢測。
  2. 提供友好的用戶界面,支持玩家自定義名稱,增強游戲的個性化體驗。
  3. 開發附加功能,如悔棋、保存 / 加載游戲進度等,提升游戲的實用性。
  4. 引入音效和動畫效果,增強游戲的視覺和聽覺反饋,提高用戶體驗。

2. 技術方案

本項目采用 Python 語言結合 tkinter 庫實現,具體技術方案如下:

  1. 開發語言:Python 3.8
  2. GUI 庫:tkinter(Python 內置庫,無需額外安裝)
  3. 數據存儲:JSON 格式文件用于保存和加載游戲進度
  4. 多線程處理:使用 threading 模塊處理音效播放,避免阻塞 UI 線程
  5. 動畫效果:通過 tkinter 的 update () 方法和延時函數實現簡單動畫

系統架構采用面向對象設計,將游戲邏輯和界面交互分離,提高代碼的可維護性和可擴展性。主要類包括:

  • TicTacToe:游戲主類,負責管理游戲狀態、處理用戶輸入和更新界面
  • 界面組件:包括棋盤按鈕、狀態標簽、控制按鈕等,通過 tkinter 實現

3. 實現流程

明確游戲的基本功能和交互邏輯,設計數據結構和類的關系。確定需要實現的核心功能包括:棋盤顯示、玩家輪流落子、勝負判定、悔棋、保存 / 加載游戲等。

首先實現游戲的核心邏輯,包括:

  • 初始化棋盤和游戲狀態
  • 處理玩家點擊事件,更新棋盤狀態
  • 判斷勝負和平局條件
  • 實現玩家輪流機制

其中,處理玩家點擊事件,更新棋盤狀態的代碼如下所示:

def make_move(self, row, col):"""處理玩家移動"""if self.board[row][col] == ' ' and self.game_active:# 記錄當前移動到歷史self.move_history.append((row, col, self.current_player))self.undo_button.config(state=tk.NORMAL)  # 啟用悔棋按鈕# 播放放置音效self.play_sound('place')# 添加放置動畫self.animate_cell(row, col)# 更新棋盤數據self.board[row][col] = self.current_player# 更新按鈕顯示self.buttons[row][col].config(text=self.current_player)# 記錄上一步self.last_move = (row, col)self.last_move_label.config(text=f"上一步: {self.player_names[self.current_player]} 在位置 {row + 1},{col + 1}")# 檢查游戲狀態if self.check_winner(self.current_player):self.status_label.config(text=f"{self.player_names[self.current_player]} 獲勝!")self.game_active = Falseself.undo_button.config(state=tk.DISABLED)  # 禁用悔棋按鈕# 播放勝利音效和動畫self.play_sound('win')self.animate_winning_cells()messagebox.showinfo("游戲結束", f"{self.player_names[self.current_player]} 獲勝!")elif self.is_board_full():self.status_label.config(text="游戲平局!")self.game_active = Falseself.undo_button.config(state=tk.DISABLED)  # 禁用悔棋按鈕# 播放平局音效self.play_sound('draw')messagebox.showinfo("游戲結束", "游戲平局!")else:# 切換玩家self.current_player = 'O' if self.current_player == 'X' else 'X'self.status_label.config(text=f"當前玩家: {self.player_names[self.current_player]}")

當前玩家可以看到上一位玩家的下子坐標位置,可視化界面如下所示:

判斷勝負和平局條件的代碼如下所示:

def check_winner(self, player):"""檢查玩家是否獲勝,并記錄獲勝的格子"""# 檢查行for row in range(3):if all([self.board[row][col] == player for col in range(3)]):self.winning_cells = [(row, col) for col in range(3)]return True# 檢查列for col in range(3):if all([self.board[row][col] == player for row in range(3)]):self.winning_cells = [(row, col) for row in range(3)]return True# 檢查對角線if all([self.board[i][i] == player for i in range(3)]):self.winning_cells = [(i, i) for i in range(3)]return Trueif all([self.board[i][2 - i] == player for i in range(3)]):self.winning_cells = [(i, 2 - i) for i in range(3)]return Truereturn False

此外,該項目使用 tkinter 創建用戶界面,包括:

  • 設計棋盤布局和樣式
  • 添加狀態顯示區域,顯示當前玩家和游戲狀態
  • 實現控制按鈕(悔棋、重新開始等)
  • 支持玩家自定義名稱

其中,支持玩家自定義名稱的代碼如下所示:

def set_player_names(self):"""設置玩家名稱"""# 詢問玩家X的名稱name = simpledialog.askstring("玩家名稱", "請輸入玩家X的名稱:", parent=self.root)if name:self.player_names['X'] = name# 詢問玩家O的名稱name = simpledialog.askstring("玩家名稱", "請輸入玩家O的名稱:", parent=self.root)if name:self.player_names['O'] = name# 更新玩家標簽self.player_x_label.config(text=f"{self.player_names['X']} (X)")self.player_o_label.config(text=f"{self.player_names['O']} (O)")self.status_label.config(text=f"當前玩家: {self.player_names[self.current_player]}")# 啟用保存按鈕self.save_button.config(state=tk.NORMAL)

支持玩家自定義名稱的可視化界面如下所示:

?我們逐步添加附加功能:

  • 悔棋功能:記錄歷史操作,支持撤銷上一步
  • 保存 / 加載功能:使用 JSON 格式保存游戲狀態到文件
  • 音效系統:使用 playsound 庫播放操作音效
  • 動畫效果:為棋子放置和獲勝狀態添加視覺動畫

其中,悔棋功能的代碼如下所示:

def undo_move(self):"""悔棋功能"""if not self.move_history:return  # 沒有歷史記錄# 播放悔棋音效self.play_sound('undo')# 恢復上一步row, col, player = self.move_history.pop()self.board[row][col] = ' 'self.buttons[row][col].config(text='', bg='SystemButtonFace')  # 恢復默認背景# 清除獲勝高亮if self.winning_cells:for r, c in self.winning_cells:self.buttons[r][c].config(bg='SystemButtonFace')self.winning_cells = []# 更新上一步信息if self.move_history:last_row, last_col, last_player = self.move_history[-1]self.last_move = (last_row, last_col)self.last_move_label.config(text=f"上一步: {self.player_names[last_player]} 在位置 {last_row + 1},{last_col + 1}")else:self.last_move = Noneself.last_move_label.config(text="上一步: 無")# 切換回上一個玩家self.current_player = playerself.status_label.config(text=f"當前玩家: {self.player_names[self.current_player]}")# 重新激活游戲(如果之前結束了)self.game_active = True# 如果沒有歷史記錄了,禁用悔棋按鈕if not self.move_history:self.undo_button.config(state=tk.DISABLED)

悔棋功能的可視化界面如下所示:

因此,該游戲的主要流程如下所示:

  1. 初始化 3x3 空棋盤
  2. 玩家 X 先開始游戲
  3. 輪流輸入位置(行和列,范圍 1-3)
  4. 程序會驗證輸入有效性并更新棋盤
  5. 每次移動后檢查是否有玩家獲勝或平局
  6. 游戲結束時顯示結果

4. 項目展示

前面說太多了,最后還是上傳個該項目的簡要演示視頻,供大家了解。

IMG_4950

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/web/88724.shtml
繁體地址,請注明出處:http://hk.pswp.cn/web/88724.shtml
英文地址,請注明出處:http://en.pswp.cn/web/88724.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

首個自動駕駛VLA綜述介紹

當視覺(Vision)、語言(Language)和行動(Action)三大能力在一個模型中融合,自動駕駛的未來將走向何方? 近日,來自麥吉爾大學、清華大學、小米公司和威斯康辛麥迪遜的研究團隊聯合發布了全球首篇針對自動駕駛領域的視覺-語言-行動(Vision-Language-Action, VLA)模型的…

C# 接口(接口可以繼承接口)

接口可以繼承接口 之前我們已經知道接口實現可以從基類被繼承,而接口本身也可以從一個或多個接口繼承而來。要指定某個接口繼承其他的接口,應在接口聲明中把基接口名稱以逗號分隔的列表形式 放在接口名稱后面的冒號之后,如下所示。類在基類列…

linux----------------------線程同步與互斥(上)

1.線程互斥 1-1 進程線程間的互斥相關背景概念 臨界資源:多線程執行流共享的資源就叫做臨界資源 臨界區:每個線程內部訪問臨界資源的代碼就叫做臨界區 互斥:任何時刻,互斥保證只有一個執行進入臨界區,對臨界資源起…

百度AI的開放新篇章:文心4.5本地化部署指南與未來生態戰略展望

百度AI的開放新篇章:文心4.5本地化部署指南與未來生態戰略展望 一起來玩轉文心大模型吧👉文心大模型免費下載地址:https://ai.gitcode.com/theme/1939325484087291906 🌟 嗨,我是IRpickstars! &#x1f30…

筆記/sklearn中的數據劃分方法

文章目錄一、前言二、數據劃分方法1. 留出法(Hold-out)2. K折交叉驗證(K-Fold)3. 留一法(Leave-One-Out)三、總結一、前言 簡要介紹數據劃分在機器學習中的作用。 二、數據劃分方法 1. 留出法&#xff0…

Android14 開屏頁SplashScreen設置icon圓角的原理

簡介 我們在看到一個應用在啟動的時候會看到一個啟動的icon,這個圖標是應用的icon當然也是可以應用自己去控制的如 <item name="android:windowSplashScreenAnimatedIcon">@drawable/adas_icon</item> 圖上的效果明顯不理想,圖標是自帶圓角,而且還是…

flutter redux狀態管理

&#x1f4da; Flutter 狀態管理系列文章目錄 Flutter 狀態管理(setState、InheritedWidget、 Provider 、Riverpod、 BLoC / Cubit、 GetX 、MobX 、Redux) setState() 使用詳解&#xff1a;原理及注意事項 InheritedWidget 組件使用及原理 Flutter 中 Provider 的使用、注…

AMIS全棧低代碼開發

amis是百度開源的前端低代碼框架&#xff0c;它通過JSON配置來生成各種后臺頁面&#xff0c;旨在簡化前端開發過程&#xff0c;提高開發效率&#xff0c;降低開發門檻。以下是詳細介紹&#xff1a; 核心特點&#xff1a; 可視化開發&#xff1a;允許開發者通過可視化方式構建頁…

【Python基礎】變量、運算與內存管理全解析

一、刪除變量與垃圾回收&#xff1a;內存管理的底層邏輯 在Python中&#xff0c;變量是對象的引用&#xff0c;而不是對象本身。當我們不再需要某個變量時&#xff0c;可以用del語句刪除它的引用&#xff0c;讓垃圾回收機制&#xff08;GC&#xff09;自動清理無引用的對象。 1…

Spring Boot + Javacv-platform:解鎖音視頻處理的多元場景

Spring Boot Javacv-platform&#xff1a;解鎖音視頻處理的多元場景 一、引言 在當今數字化時代&#xff0c;音視頻處理已成為眾多應用場景中不可或缺的一部分&#xff0c;從在線教育、視頻會議到短視頻平臺、智能安防等&#xff0c;音視頻數據的處理與分析需求日益增長。Java…

k8s 的基本原理、架構圖、使用步驟和注意事項

Kubernetes&#xff08;k8s&#xff09;是一個開源的容器編排平臺&#xff0c;用于自動化部署、擴展和管理容器化應用。以下是其基本原理、使用步驟和注意事項的總結&#xff1a;一、k8s 基本原理核心架構 Master 節點&#xff1a;控制集群的核心組件&#xff0c;包括&#xff…

Qt 多線程編程:單例任務隊列的設計與實現

引言&#xff1a; 在現代應用程序開發中&#xff0c;多線程編程已成為處理異步任務的標配。對于 GUI 應用而言&#xff0c;保持主線程的響應性尤為重要。本文將詳細介紹一個基于 Qt 的單例任務隊列實現方案&#xff0c;它通過線程池和單例模式&#xff0c;優雅地解決了后臺任務…

OpenEuler操作系統中檢測插入的USB設備并自動掛載

OpenEuler操作系統中檢測插入的USB設備并自動掛載 項目需求&#xff1a;工控機上openeuler操作系統是無界面版本的&#xff0c;在工控機上連接了激光雷達&#xff0c;當激光雷達采集完數據&#xff0c;我們要將采集數據導入u盤&#xff0c;故需要在工控機上插入u盤&#xff0c;…

《Spring 中上下文傳遞的那些事兒》Part 11:上下文傳遞最佳實踐總結與架構演進方向

&#x1f4dd; Part 11&#xff1a;上下文傳遞最佳實踐總結與架構演進方向 經過前面幾篇文章的深入探討&#xff0c;我們已經系統性地學習了 Spring 應用中上下文傳遞的各種技術原理、常見問題以及解決方案。從 Web 請求上下文到異步任務、從多租戶隔離到日志脫敏&#xff0c;…

使用云虛擬機搭建hadoop集群環境

使用云虛擬機搭建hadoop集群環境 安裝jdk17 配置docker網絡 docker network create --subnet172.18.0.0/16 hadoop 172.18.0.0&#xff1a;這是子網的網絡地址&#xff0c;也就是這個網絡的起始地址。/16&#xff1a;這是子網掩碼&#xff08;Network Mask&#xff09;&#x…

【機器學習】吳恩達機器學習課程代碼作業-Python版本

吳恩達老師的機器學習課程作業是MATLAB版本&#xff08;Octave&#xff09;的&#xff0c;現在有點過時了&#xff0c;我參考了幾位大牛的代碼&#xff0c;將作業改成了Python3.6版本&#xff0c;并做了中文注釋&#xff0c;推薦使用Jupyter notebook。Python作業使用了原版數據…

2025年人工智能、虛擬現實與交互設計國際學術會議

重要信息 官網&#xff1a;www.aivrid.com 時間&#xff1a;2025年10月17-19日 地點&#xff1a;中國-東莞 部分介紹 征稿主題 包括但不限于&#xff1a; 生物特征 模式識別 機器視覺 專家系統 深度學習 智能搜索 自動編程 智能控制 智能機器…

SHA-256算法流程分析與詳解——Github工程結合示例和動畫演示

近日筆者在學習區塊鏈的相關知識&#xff0c;接觸到SHA-256算法&#xff0c;這里做一個知識梳理和總結。 強烈推薦大家自行去學習下面鏈接github上的工程&#xff0c;作者的動畫演示和解釋做的非常出色&#xff0c;邏輯非常清晰&#xff0c;B站搬運的對應的油管的講解視頻也放…

CSPNet: A New Backbone that can Enhance Learning Capability of CNN (CSP模塊)

3. Method 方法 3.1 Cross Stage Partial Network 跨階段局部網絡 3.1.1 Cross Stage Partial Network 跨階段局部網絡 3.1.1.1 ResNet 和 DenseNet 的優缺點主流的卷積神經網絡&#xff08;CNN&#xff09;架構&#xff0c;如ResNet [8]、ResNeXt [37]、DenseNet [11]&#x…

前端學習4:小白入門注冊表單的制作(包括詳細思考CSS、JS實現過程)

這篇我們來做一個簡單表單&#xff0c;即常見的注冊頁面吧~學習完這篇我們將學習到Input、label、CSS偽類、CSS入門、更多的JS操作等。。一、首先明確需求&#xff1a;直接模仿常見的注冊頁面&#xff0c;包括&#xff1a;用戶名、Email、性別&#xff08;單選按鈕男/女&#x…