• Python GUI案例之看图猜成语开发(第三篇)


    Python GUI案例之看图猜成语(第三篇)

    Python GUI案例之看图猜成语开发(第一篇)
    Python GUI案例之看图猜成语开发(第二篇)
    Python GUI案例之看图猜成语开发(完结篇)


    前言

    我们将要实现这些功能:

    • 一,游戏首页页面:在首页页面里需要实现绘制一个看图猜成语文字的标题,定义两个按钮功能(开始游戏,退出游戏),还有一个输入游戏昵称的功能并且要对昵称进行验证是否为空,才能开始游戏;
    • 二,游戏选择模式页面:在首页点击开始游戏后,进入游戏的选择模式页面,分为训练模式和闯关模式两种;
    • 三,游戏训练模式页面:将成语图片加载后,只实现猜成语功能(一张图片,一个输入框,一个按钮)和回答的准确率;
    • 四,游戏闯关模式页面:将实现自定义有多少个关卡数,16个汉字提示(12个随机生成的干扰汉字),游戏通关记录所用的时间。

    (素材提取:https://download.csdn.net/download/qq_59142194/85827790


    看图猜成语小程序开发(第三篇)

    终于来到第三篇了!!!


    游戏闯关模式页面

    在这里我们将实现自定义有多少个关卡数,16个汉字提示(12个随机生成的干扰汉字),游戏通关记录所用的时间,主要要注意下面3个的实现功能。

    在这里插入图片描述

    自定义关卡数
    在自定义关卡数时(默认10关),我们需要在游戏选择模式页面中点击闯关模式后添加ttkbootstrap里面的一个查询框Querybox,然后根据提示输入关卡数后则将进入游戏闯关模式页面。

        def game_chuangguan_mode(self,event):
            # 默认10个关卡(initialvalue=10)
            number = Querybox.get_integer(prompt="请设置关卡数量:",title="自定义关卡数量 ",initialvalue=10,minvalue=0,maxvalue=50)
            if number:
                self.frame.destroy()
                game_chuangguan_page(self.nickname,number)
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6

    ① 创建四个用于显示选择结果的标签,在这里还要定义一个self.answer_list 列表来装下生成的标签对象,以便后面在标签上配置文字configure()。

    # 创建四个用于选择结果的标签
        def create_selection_result_label(self):
            self.answer_list = []
            for i in range(4):
                label = ttk.Label(self.canvas, text='', font=("微软雅黑", 35), background='', width=2, cursor='hand2')
                label.place(x=130 + i * 100, y=450)
                self.answer_list.append(label)
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7

    重选按钮,点击执行后就会将self.answer_list 列表里面的标签对象全部摧毁后重新创建。

     # 重选
        def update_label(self):
            self.CLICKTIMES = 0
            self.TRUEANSWER = ''
            for i in self.answer_list:i.destroy()
            self.create_selection_result_label()
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6

    ② 创建用于选择文字内容的16个标签(4 x 4),其中将有12个干扰文字,并且在创建标签时还要为每一个标签对象绑定一个鼠标点击事件click_label(event)。

    # 创建用于选择文字内容的标签
        def create_option_text_label(self):
            def click_label(event):
                if self.CLICKTIMES < 4:
                    self.CLICKTIMES += 1
                    label_text = event.widget["text"]  # 得到标签上的文本
                    self.answer(label_text)
            self.label_oop_list = []
            # 设置4行4列的标签
            for i in range(4):
                for j in range(4):
                    label = ttk.Label(self.canvas, text='', font=("微软雅黑", 35), background='#FFFAE3', width=2,cursor='hand2')
                    label.place(x=510 + j * 100, y=90 + i * 95)
                    label.bind("<Button-1>", click_label)
                    self.label_oop_list.append(label)
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15

    这里也比较重要的部分,变量IDX记录第几关,loading_idiom_img()方法里面的for循环则是为前面创建的16个文字标签配置文字(包括
    正确的4个文字([i for i in self.idiom])和
    12个干扰文字(disturb_text_list ))

        IDX = 1  # 第几关,默认第1关
        # 加载成语图片
        def loading_idiom_img(self,):
            self.idiom = self.idiom_list[self.IDX - 1].split('.')[0]
            print('答案:', self.idiom)
            disturb_text_list = [self.GBK2312() for i in range(12)]  # 随机生成12个干扰汉字
            disturb_text_list.extend([i for i in self.idiom])
            for label_oop in self.label_oop_list:
                text = random.choice(disturb_text_list)
                disturb_text_list.remove(text)
                label_oop.configure(text=text)
            self.guanqia_lable.config(text=f'第 {self.IDX} / {len(self.idiom_list)}关')
            self.idiom_img = ttk.PhotoImage(file=f'../看图猜成语/{self.idiom}.png')
            self.lm.configure(image=self.idiom_img)
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14

    随机生成干扰文字

     # 随机生成一个汉字
        def GBK2312(self, ):
            head = random.randint(0xb0, 0xf7)
            body = random.randint(0xa1, 0xfe)
            val = f'{head:x}{body:x}'
            str = bytes.fromhex(val).decode('gb2312')
            return str
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7

    ③ 记录时间,这里的写法与前面的动态移动原理都一样,都是由after()实现,间隔1秒刷新标签(time_label )一次。self.flag = True 为定义一个信号量,用于当我们完成游戏通过时,run()结束循环

    # 记录通关所耗时
        def recording_time(self):
            self.flag = True  # 定义一个信号量,用于当我们完成游戏通过时,run()结束循环
            time_label = ttk.Label(self.canvas,text='时长:00:00:00', font=("华文行楷", 15), background='#DAEFE6',bootstyle=DANGER)
            time_label.place(x=730,y=50)
            start_time = datetime.datetime.now()
            def run():
                if self.flag:
                    time_label.after(1000, run)
                    update_time = datetime.datetime.now() - start_time
                    self.time_ =f'时长:{update_time}'.split('.')[0]
                    time_label.configure(text=self.time_) # 不显示时长的毫秒值
            run()
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13

    提示回答是否正确,这里用了一点线程的知识,回答正确线程启动提示“回答正确”标签,3秒后将自动消失;回答错误,同理。

    在这里插入图片描述

      t = threading.Thread(target=self.dispaly_answer_result, args=('回\n答\n错\n误',))
                    t.setDaemon(True)
                    t.start()
        # 显示回答结果是否正确
        def dispaly_answer_result(self,text):
            self.result_label.configure(text=text)
            time.sleep(3)
            try: self.result_label.configure(text='')
            except Exception as e: print(e)
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9

    第三篇也就到这里吧!
  • 相关阅读:
    网站接公网+配置域名访问宝宝级教程
    1. 开篇:SpringBoot与SpringCloud的那些事
    Arm架构下麒麟操作系统安装配置Mariadb数据库
    Windows-docker集成SRS服务器的部署和使用
    基于Spring、SpringMVC、Mybatis的超市管理系统
    Nodejs系列之系统模块path
    STM32-NUCLEO-F411RE—输出PWM及修改PWM频率与占空比
    Java MVC 架构初学者指南
    随笔记:重新认识 else if
    Java牛客网社区项目——知识点&面试题
  • 原文地址:https://blog.csdn.net/qq_59142194/article/details/125537922