Python Forum
Tkinter number guessing game
Thread Rating:
  • 0 Vote(s) - 0 Average
  • 1
  • 2
  • 3
  • 4
  • 5
Tkinter number guessing game
#1
Another number guessing game

import tkinter as tk
from random import randint

'''
Define some global variables
start is the low number end is the high number
e.g. guess a number between 1 and 20
count is the number of tries
'''
start, end = 1, 20
count = 5


class Window:
    '''
    Define the class window. Set some variables for our game.
    Setup the layout with tkinter
    self.number is a random generated number
    self.count is the number of tries to guess the number
    '''
    def __init__(self, parent):
        self.number = self.random_number()
        self.counter = count

        parent.columnconfigure(0, weight=1)
        parent.rowconfigure(0, weight=1)

        container = tk.Frame(parent)
        container.grid(column=0, row=0, sticky='new')
        container.grid_columnconfigure(0, weight=3)

        header = tk.Label(parent, text='Number Guessing Game')
        header['font'] = ('times 16 bold')
        header['relief'] = 'groove'
        header.grid(column=0, row=0, sticky='new', pady=4, ipady=4)

        instructions = tk.Label(parent)
        instructions['text'] = f'Choose a number between {start} and {end}'
        instructions['bg'] = 'lightyellow'
        instructions['relief'] = 'groove'
        instructions.grid(column=0, row=1, sticky='new', pady=4)

        self.msgbox = tk.Label(parent, anchor='w')
        self.msgbox['relief'] = 'groove'
        self.msgbox['text'] = f'Tries Left: {self.counter}'
        self.msgbox.grid(column=0, row=2, sticky='new', pady=8)

        self.entry = tk.Entry(parent)
        self.entry.grid(column=0, row=3, sticky='new', pady=8)

        btn_frame = tk.Frame(parent)
        btn_frame.grid(column=0, row=4, sticky='new')
        for i in range(2):
            btn_frame.grid_columnconfigure(i, weight=3, uniform='btns')

        self.btn = tk.Button(btn_frame)
        self.btn['text'] = 'Submit'
        self.btn['command'] = lambda: self.check(self.entry.get())
        self.btn.grid(column=0, row=0, sticky='new')

        self.reset_btn = tk.Button(btn_frame)
        self.reset_btn['text'] = 'Reset'
        self.reset_btn['state'] = 'disabled'
        self.reset_btn.grid(column=1, row=0, sticky='new')

        msg_container = tk.Frame(parent)
        msg_container['relief'] = 'groove'
        msg_container['highlightbackground'] = 'lightgray'
        msg_container['highlightcolor'] = 'lightgray'
        msg_container['highlightthickness'] = 1
        msg_container.grid(column=0, row=5, sticky='new', pady=4)
        msg_container.grid_columnconfigure(0, weight=0)
        msg_container.grid_columnconfigure(1, weight=3)

        self.label = tk.Label(msg_container, text='MSG:', anchor='w')
        self.label.grid(column=0, row=0, sticky='new')

        self.msg_label = tk.Label(msg_container, anchor='w')
        self.msg_label.grid(column=1, row=0, sticky='new')
        self.entry.focus()
        self.entry.bind('<Return>', lambda num: self.check(self.entry.get()))


    def random_number(self):
        '''
        random_number is a function for generating a random number
        between the start and ending numbers defined above
        '''
        number = randint(start, end)
        return number

    def check(self, guess):
        '''
        Check does several things
        With a try statement we check to make sure only whole numbers are entered.
        If not display an error message
        '''
        try:
            guess = int(guess) # Convert gues to int
            self.counter = self.counter - 1 # Subtract 1 from the counter
            self.msgbox['text'] = f'Tries Left: {self.counter}'

            self.entry.delete(0, tk.END) # Clear the entry
            if guess > end or guess < start: # Check if the guess is within bounds
                if self.counter > count: # If the counter > than tries, set to default tries
                    self.counter = count
                else: # Counter is below default. Add 1 back due to incorrect input
                    self.counter = self.counter + 1
                # Display error
                self.msg_label['text'] = f'Please choose a number between {start} and {end}'
                self.msg_label['fg'] = 'red'
                self.msgbox['text'] = f'Tries Left: {self.counter}'

            elif guess > self.number: # Display message that the guess was too high
                self.msg_label['text'] = f'{guess} is too high.'
                self.msg_label['fg'] = 'red'
            elif guess < self.number: # Display message that guess was too low
                self.msg_label['text'] = f'{guess} is too low.'
                self.msg_label['fg'] = 'darkorange'
            else: # Display message that guess was correct
                self.msg_label['text'] = f'You win! {guess} is correct.'
                self.msg_label['fg'] = 'green'
                self.btn['state'] = 'disabled'
                self.reset_btn['state'] = 'normal'
                self.reset_btn['command'] = self.reset

            if self.counter == 0: # Number of tries has been reached. Disable submit button and enable reset
                self.msg_label['text'] = 'You have no tries left.'
                self.msg_label['fg'] = 'tomato'
                self.btn['state'] = 'disabled'
                self.reset_btn['state'] = 'normal'
                self.reset_btn['command'] = lambda: self.reset()

        except ValueError: # Display error - input is not correct
            self.msg_label['text'] = 'Error! Please enter only whole numbers.'
            self.msg_label['fg'] = 'red'
            self.entry.delete(0, tk.END)


    def reset(self):
        '''
        Resets all the default values and generates a new random number
        '''
        self.counter = count
        self.btn['state'] = 'normal'
        self.reset_btn['state'] = 'disabled'
        self.msg_label['text'] = ''
        self.msg_label['fg'] = 'black'
        self.msgbox['text'] = f'Tries Left: {count}'
        self.number = self.random_number()

def main():
    root = tk.Tk()
    root['padx'] = 8
    root['pady'] = 5
    root.geometry('400x210+250+250')
    root.resizable(False, False)
    Window(root)
    root.mainloop()

if __name__ == '__main__':
    main()
BashBedlam likes this post
I welcome all feedback.
The only dumb question, is one that doesn't get asked.
My Github
How to post code using bbtags


Reply


Messages In This Thread
Tkinter number guessing game - by menator01 - Mar-21-2022, 07:35 PM
RE: Tkinter number guessing game - by BashBedlam - Mar-21-2022, 08:47 PM
RE: Tkinter number guessing game - by menator01 - Mar-24-2022, 07:13 PM

Possibly Related Threads…
Thread Author Replies Views Last Post
  Guessing games pyzyx3qwerty 0 2,034 Apr-16-2020, 11:59 AM
Last Post: pyzyx3qwerty
  guess my number GAME ronblue77 2 2,820 Nov-24-2019, 04:23 PM
Last Post: CodingStranger

Forum Jump:

User Panel Messages

Announcements
Announcement #1 8/1/2020
Announcement #2 8/2/2020
Announcement #3 8/6/2020