简体   繁体   English

AttributeError: 'str' object 没有属性 'tk', Python Tkinter

[英]AttributeError: 'str' object has no attribute 'tk', Python Tkinter

I'm trying to make a GUI rock, paper, scissors game.我正在尝试制作一个 GUI 摇滚、纸、剪刀游戏。 Here's the CLI version:这是 CLI 版本:

import random

print("Welcome to Rock, Paper, Scissors!")

rps = ["rock", "paper", "scissors"]
random_move = random.choice(rps)
print(random_move)

while True:
    attempt = input("Enter your attempt: ")
    if (attempt == random_move):
        print("We have a tie!")
        continue
    elif (attempt == "rock"):
        if (random_move == "scissors"):
            print("You smashed the computer's scissors with a rock!")
            break
        elif(random_move == "paper"):
            print("The computer wrapped your rock up in paper!")
            break
    elif (attempt == "paper"):
        if (random_move == "scissors"):
            print("The computer cut your paper in half with its scissors!")
            break
        elif (random_move == "rock"):
            print("You wrapped the computer's rock up in paper!")
            break
    elif(attempt == "scissors"):
        if (random_move == "paper"):
            print("You cut the computer's paper in half with your scissors!")
            break
        elif (random_move == "rock"):
            print("The computer smashed your scissors with its rock!")
            break

However, when implementing this in a GUI, I have decided to get rid of the loop to make things easier, and to only give the user one guess.然而,当在 GUI 中实现这一点时,我决定摆脱循环以使事情变得更容易,并且只给用户一个猜测。 It doesn't work, and nothing on Google gives me any clue as to how I can fix it.它不起作用,而且谷歌上没有任何东西给我任何关于如何修复它的线索。 Please help.请帮忙。

import tkinter as tk
import tkinter as ttk
import random

root = tk.Tk()
root.title("Rock, Paper, Scissors")

window_width = 300
window_height = 200

screen_width = root.winfo_screenwidth()
screen_height = root.winfo_screenheight()

center_x = int(screen_width/2 - window_width / 2)
center_y = int(screen_height/2 - window_height / 2)

root.geometry(f'{window_width}x{window_height}+{center_x}+{center_y}')

basic_label = tk.Label(root, text="Rock, Paper, Scissors")
basic_label.pack()

guess = ttk.Entry(root, textvariable="guess")
guess.pack()

def callback():
    rps = ["rock", "paper", "scissors"]
    random_move = random.choice(rps)
    userguess = guess.get()
    #Uncomment the following two lines of code for easy mode.
    #print_move = ttk.Label(random_move)
    #print_move.pack()
    if (userguess == random_move):
        tie = ttk.Label(root, text="We have a tie!")
        tie.pack()
    elif (userguess == "rock"):
        if (random_move == "scissors"):
            smash = ttk.Label(root, text="You smashed the computer's scissors with a rock!")
            smash.pack()
        elif (random_move == "paper"):
            wrap = ttk.Label(root, text="The computer wrapped your rock up in paper!")
            wrap.pack()
    elif (userguess == "paper"):
        if (random_move == "scissors"):
            cut = ttk.Label(root, text="The computer cut your paper in half with its scissors!")
            cut.pack()
        elif (random_move == "rock"):
            wrap1 = ttk.Label(root, text="You wrapped the computer's rock up in paper")
            wrap1.pack()
    elif (userguess == "scissors"):
        if (random_move == "paper"):
            cut1 = ttk.Label(root, text="You cut the computer's paper in half with your scissors!")
            cut1.pack()
        elif (random_move == "rock"):
            smash1 = ttk.Label(root, text="The computer smashed your scissors with its rock!")
            smash1.pack()

button = ttk.Button(root, text="Guess!", command=callback)
button.pack()

root.mainloop()

first of all, I would advise you to simplify your code.首先,我建议您简化代码。 You should never have more than one elif.你永远不应该拥有超过一个 elif。

Also, you have a lot of repetition, try to find all the repetitions and factor them all together, Here is an example on how I would have done it:此外,您有很多重复,尝试找到所有重复并将它们全部分解,这是我如何做到的示例:

def check_winner(user_move, random_move):
    beating_table = {
        'rock': 'scissors',
        'paper': 'rock',
        'scissors': 'paper'
    }
    action = {
        'rock': ['smashed', 'scissors with a rock!'],
        'paper':['wrapped', 'rock up in paper!'] ,
        'scissors':['cut', 'paper in half with scissors!' ] 
    }
    # We use an associative array to know the winner of each
    # combination, and to generate the winner string.
    if (user_move == random_move):
        return 'We have a tie!'
    elif (beating_table[user_move] == random_move):
        act = action[user_move]
        return f'You {act[0]} the computer\'s {act[1]}'
    # If it is not a tie, and you're not the winner, then
    # The computer wins.
    act = action[random_move]
    return f'The computer {act[0]} your {act[1]}'


def callback():
    rps = ["rock", "paper", "scissors"]
    random_move = random.choice(rps)
    userguess = guess.get()
    label = ttk.Label(root, text=check_winner(userguess, random_move))
    label.pack()

Concerning your error in particular, it would help to have the original error message, complete, with the stack-trace.特别是关于您的错误,使用堆栈跟踪获得完整的原始错误消息会有所帮助。 Also try to rename your tk object ( root ) differently, I seems this already caused issues in the passed if you use the same name (root) somewhere else in your code.还尝试以不同的方式重命名您的 tk object ( root ),如果您在代码中的其他位置使用相同的名称 (root),我似乎已经在传递中引起了问题。

Another odd thing in your code which may cause problems, is you're importing the same module twice with different alias and you use both:代码中可能导致问题的另一件奇怪的事情是,您使用不同的别名导入了两次相同的模块,并且您同时使用了两者:

import tkinter as tk
import tkinter as ttk

Does it help?它有帮助吗?

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

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