Как вернуть значение записи из другого класса? - PullRequest
0 голосов
/ 27 сентября 2019

Я пытаюсь вернуть значение из виджета Entry из другого класса.

Моя идея заключается в том, что, когда пользователь успешно вошел в систему, на экране приветствия отобразится имя пользователя, который только что вошел в систему.

Я пытался использовать это:

    self.userLogged = Label(main, text = self.entry_username.get())
    self.userLogged.pack()

Я пытался связать> self.entry.entry_username.get() из класса login.Но вот код ошибки:

AttributeError: 'App' object has no attribute 'entry_username'

Где я ошибаюсь?

Вот полный код:

from tkinter import *
import tkinter.ttk as ttk


class App():
    def __init__(self,master):


        notebook = ttk.Notebook(master)
        notebook.pack(expand = 1, fill = "both")

        #Frames
        main = ttk.Frame(notebook)


        notebook.add(main, text='Welcome Screen')




        self.userLogged = Label(main, text = self.entry_username.get())
        self.userLogged.pack()





###################################################################################################################################
                                                        ##USERS##
###################################################################################################################################
class login(Frame):
    def __init__(self, master):
        super().__init__(master)

        self.label_username = Label(self, text="Username: ",font=("bold",16))
        self.label_password = Label(self, text="Password: ",font=("bold",16))

        self.entry_username = Entry(self, font = ("bold", 14))
        self.entry_password = Entry(self, show="*", font = ("bold", 14))



        self.label_username.grid(row=0, sticky=E)
        self.label_password.grid(row=1, sticky=E)
        self.entry_username.grid(row=0, column=1)
        self.entry_password.grid(row=1, column=1)

        self.logbtn = Button(self, text="Login", font = ("bold", 10), command=self._login_btn_clicked)
        self.logbtn.grid(columnspan=2)

        self.pack()


    def _login_btn_clicked(self):
        # print("Clicked")
        username = self.entry_username.get()
        password = self.entry_password.get()

        # print(username, password)
        account_list = [line.split(":", maxsplit=1) for line in open("passwords.txt")]
        # list of 2-tuples. Usersnames with colons inside not supported.
        accounts = {key: value.rstrip() for key, value in account_list}
        # Convert to dict[username] = password, and slices off the line ending.
        # Does not support passwords ending in whitespace.

        if accounts[username] == password:
            self.label_username.grid_forget()
            self.label_password.grid_forget()
            self.entry_username.grid_forget()
            self.entry_password.grid_forget()
            self.logbtn.grid_forget()
            self.pack_forget()
            app = App(root)
        else:
            print("error")





root = Tk()
root.minsize(950, 450)
root.title("test")

lf = login(root)
root.mainloop()

Ответы [ 2 ]

0 голосов
/ 27 сентября 2019

При работе с несколькими классами в tkinter часто хорошей идеей является использование непереносимости классов для основного окна и фреймов.Это позволяет нам использовать self.master для взаимодействия между классами.

Тем не менее, у вас есть несколько вещей, которые нужно изменить.Вы используете self там, где это не нужно, и вы должны делать import tkinter as tk, чтобы предотвратить перезапись методов.

Я добавил класс в ваш код, поэтому мы используем один класс для корневого окна.Затем используйте один класс для экрана входа в систему и затем используйте один класс для фрейма после входа в систему.

import tkinter as tk
import tkinter.ttk as ttk


class NotebookFrame(tk.Frame):
    def __init__(self, username):
        super().__init__()
        notebook = ttk.Notebook(self)
        notebook.pack(expand=1, fill="both")
        main = ttk.Frame(notebook)
        notebook.add(main, text='Welcome Screen')
        tk.Label(main, text=username).pack()


class Login(tk.Frame):
    def __init__(self):
        super().__init__()
        tk.Label(self, text="Username: ", font=("bold", 16)).grid(row=0, sticky='e')
        tk.Label(self, text="Password: ", font=("bold", 16)).grid(row=1, sticky='e')
        self.entry_username = tk.Entry(self, font=("bold", 14))
        self.entry_password = tk.Entry(self, show="*", font=("bold", 14))
        self.entry_username.grid(row=0, column=1)
        self.entry_password.grid(row=1, column=1)
        tk.Button(self, text="Login", font=("bold", 10), command=self.master._login_btn_clicked).grid(columnspan=2)


class App(tk.Tk):
    def __init__(self):
        super().__init__()
        self.title("test")
        self.minsize(950, 450)
        self.login_frame = Login()
        self.login_frame.pack()

    def _login_btn_clicked(self):
        username = self.login_frame.entry_username.get()
        password = self.login_frame.entry_password.get()
        account_list = [line.split(":", maxsplit=1) for line in open("passwords.txt")]
        accounts = {key: value.rstrip() for key, value in account_list}
        if accounts[username] == password:
            self.login_frame.destroy()
            NoteFrame = NotebookFrame(username)
            NoteFrame.pack()
        else:
            print("error")


if __name__ == "__main__":
    App().mainloop()
0 голосов
/ 27 сентября 2019

Во-первых, вы должны изменить имя класса с class login(Frame) на class Login(Frame).

Перед тем, как его исправить, вы вызвали функцию входа из App, но вам нужно вызвать класс Login и использовать его.

class App:
    def __init__(self, master):
        notebook = ttk.Notebook(master)
        notebook.pack(expand=1, fill="both")

        # Frames
        main = ttk.Frame(notebook)

        notebook.add(main, text='Welcome Screen')

        # `entry_username.get()` method is owned by the Login class,
        # so you need to call from not `self(App class)` but `login(Login class)`.
        login = Login(master)  # Call Login class
        self.userLogged = Label(main, text=login.entry_username.get())  
        self.userLogged.pack()

С этим исправлением я могу вызвать экран приветствия.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...