I'm pretty new to python, but I'm trying to create a simplistic version of Mineweeper. I have developed functions that randomly place mines in a 9x9 matrix (nested lists) and then I have functions that assign values to every cell that doesn't contain a mine corresponding to the number of mines a given cell touches. This should make sense to anyone familiar with the game.

Anyway, I've started creating the GUI using Tkinter, which I am completely new to, and have run into a problem. As you can see, I have two nested for loops that create 81 buttons in Tkinter, these make up the grid that the user will interact with to "mine sweep". I've assigned them all to a list and, on mouse click, I have it call a function called "swept" which is where I will place all of the logic for determining if the user has clicked on a mine, etc. The problem is that I don't know how to figure out just which button has been clicked from inside the "swept" function. Any thoughts?

I'm sure there's a much more elegant way to create this game, but I'd like to keep going with the way I have come up with so far. Below I've added the code that I have written for the GUI.

from Tkinter import *

class App:
    
    def __init__(self,master):

        global rows
        global grid
        frame = Frame(master)
        frame.grid()
        r1 = []; r2 = []; r3 = []; r4 = []; r5 = []; r6 = []; r7 = []; r8 = []; r9 = [];
        grid = [r1,r2,r3,r4,r5,r6,r7,r8,r9]
        
        for x in range(0,9):
            for y in range(0,9):
                grid[x].append(Button(frame, text=" ", command = self.swept, height = 1,width = 2))
                grid[x][y].grid(row=x, column=y)
##        for x in range(0,9):
##                print rows[x]

    def swept(self):
        ## Don't know how to determine which button has been pressed from inside this function.
        print self
        
root = Tk()

app = App(root)
root.mainloop()

hi,
I recently created a fully working version of Minesweeper using Tkinter and I'll try to help you because it was rather hard to figure out the logic :) Here's my idea for all the buttons for the game:

Note: I am assuming that you know about dictionaries :) if not it gets more complicated :)

have a dictionary with the button instances as keys and a value that represents the button number 0 - 80 in your case. Here's what I mean:

from Tkinter import *

root = Tk(); root.geometry( "225x300+530+180" )
buttons = {}

def makeChoice( event ):
    global buttons
    print buttons[ event.widget ]
    
def createBoard():
    global buttons
    buttonNum = 0
    x = -225
    y = 65
    for b in range( 9 ):
        for b2 in range( 9 ):
            button = Button( root, text = " ", font = "Courier 9", width = 2, bd = 3 ); button.place( relx = 1, x = x, y = y )
            buttons[ button ] = buttonNum
            buttonNum += 1
            button.bind( "<Button-1>", makeChoice )
            x += 25
        x = -225
        y += 26

createBoard()
mainloop()

when you press a button, it calls the makeChoice function which then selects the value of the widget from the dictionary.

hope this gives you some ideas :) note that this is my approach, there are probably easier ways :)

Comments
Helpful and to the point.

hi,
I recently created a fully working version of Minesweeper using Tkinter and I'll try to help you because it was rather hard to figure out the logic :) Here's my idea for all the buttons for the game:

Note: I am assuming that you know about dictionaries :) if not it gets more complicated :)

have a dictionary with the button instances as keys and a value that represents the button number 0 - 80 in your case. Here's what I mean:

from Tkinter import *

root = Tk(); root.geometry( "225x300+530+180" )
buttons = {}

def makeChoice( event ):
    global buttons
    print buttons[ event.widget ]
    
def createBoard():
    global buttons
    buttonNum = 0
    x = -225
    y = 65
    for b in range( 9 ):
        for b2 in range( 9 ):
            button = Button( root, text = " ", font = "Courier 9", width = 2, bd = 3 ); button.place( relx = 1, x = x, y = y )
            buttons[ button ] = buttonNum
            buttonNum += 1
            button.bind( "<Button-1>", makeChoice )
            x += 25
        x = -225
        y += 26

createBoard()
mainloop()

when you press a button, it calls the makeChoice function which then selects the value of the widget from the dictionary.

hope this gives you some ideas :) note that this is my approach, there are probably easier ways :)

Thanks! Problem solved! Excellent advice.

This article has been dead for over six months. Start a new discussion instead.