简体   繁体   English

Tkinter GUI:在不改变行大小的情况下用 label 替换一行中的一个按钮。 哪怕是一毫米

[英]Tkinter GUI: Replacing one button in a row with a label WITHOUT changing the size of the row. Even by a millimetre

I made a game where you have a 10*10 grid of buttons.我做了一个游戏,你有一个 10*10 的按钮网格。 Ten of those are randomly selected to be "tanks".其中十个被随机选择为“坦克”。 If you click on a tank, the button is replaced with the label "Hit.", The problem I have is that once that happens.如果您单击坦克,则该按钮将替换为 label “命中。”,我遇到的问题是,一旦发生这种情况。 the row of that button is either a tiny amount longer or shorter than the other rows?该按钮的行比其他行长一点还是短一点? How do I stop this?我该如何阻止这个?

button[hit] = Label(text="Hit!", padx=5.5)

在此处输入图像描述 在此处输入图像描述

If I set "padx" to 5.4, then it is just a bit shorter than the other rows rather than just a bit longer.如果我将“padx”设置为 5.4,那么它只是比其他行短一点,而不是长一点。

在此处输入图像描述

I've tried numbers in between with several decimal points, but it just doesn't work.我试过中间有几个小数点的数字,但它不起作用。

from tkinter import *
import random

root = Tk()
button = [""] * 100
row = [""] * 10
tank = [""] * 10
showHit = Label(text="Hit!")
prevHits = []

for i in range(10):
    x = 3
    y = random.randint(0,9)
    tank[i] = "(" + str(x) + "," + str(y) + ")"
print(*tank)

def getPos(pos):
    global tank
    print(pos)
    for i in tank:
        if pos == i:
            print("Hit!")
            a = int(pos[1])
            b = int(pos[3])
            print(a, b)  
            hit = a*10# + b
            for i in range(10):
                button[hit].destroy()
                hit += 1
            hit = a*10
            for i in range(10):
                if hit != (a*10) + b and not hit in prevHits:
                    string = "(" + str(a) + "," + str(i) + ")"
                    button[hit] = Button(root, text=string, command=lambda pos=string: getPos(pos))
                    button[hit].pack(in_=row[a], side=LEFT)
                else:
                    button[hit] = Label(text="Hit!", padx=5.4)
                    button[hit].pack(in_=row[a], side=LEFT)
                    prevHits.append(hit)
                print(hit)
                hit += 1



for r in range(len(row)):
    row[r] = Frame(root)
    row[r].pack()
    print(row[r])


num = len(button)
for i in range(num):
    t = i
    t %= 10
    if t == 0:
        r +=1
    if r == 10:
        r = 0
    string = "(" + str(r) + "," + str(t) + ")"
    button[i] = Button(root, text=string, command=lambda pos=string: getPos(pos))
    r = i // 10
    button[i].pack(in_=row[r], side=LEFT)

mainloop()

I solved the issue by replacing pack() with grid(), consequently removing all frames, and instead putting 10 buttons into each row.我通过用 grid() 替换 pack() 解决了这个问题,因此删除了所有框架,而是将 10 个按钮放入每行。 I also managed to improve my code:我还设法改进了我的代码:

        for i in range(10):
                if not hit != (a*10) + b and not hit in prevHits:
                    button[hit] = Label(text="Hit!", padx=5.4)
                    button[hit].grid(row=a, column=b, sticky = W)
                    prevHits.append(hit)
                print(hit)
                hit += 1

Now I can target a button precisely and change it, rather than having to rewrite an entire row in a specific order.现在我可以精确定位按钮并更改它,而不必以特定顺序重写整行。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM