1

I have built a Python tkinter GUI application which is an application for running different tasks. The application window is divided into 2 halves horizontally, first half shows the options the user can choose for the selected menu option and second half shows the progress of the task by showing the log messages. Each task has a separate menu option, the user selects the menu option and first half is refreshed with user option along with a Submit button.

The GUI is built using the object oriented method where each task in the menu option is an class method of the GUI object. I now have about 5-6 menu options and working fine but the code size is becoming huge and it is becoming hard to debug any issue or add new features.

Is there any way to write the method of a class in separate file which can be called from within the main class. The logging of messages in the GUI is written in the main class so if the method is written in a separate file the how will the log messages written in the other file appear in the main window.

Please suggest alternatives.

neo
  • 55
  • 12
  • you should use standard `import` to load code from other files. All Python programs work this way. Even `tkinter` works this way. As for logging - you didn't show code so we can't say how to fix it. Maybe you should put it in separated file and import to all other files, or maybe you should send it to other files/classes as parameter. – furas May 01 '21 at 06:13

1 Answers1

0

This might not help you completely, but this is what I use. I divide my tkinter code into 2 files. First gui.py contains the GUI components (widgets) and the second methods.py contains the methods. Both the files should be in same directory.

Here is an example of a simple app that changes the label on a button click. The method change() is stored in a different file.

gui.py

from tkinter import *
from tkinter import ttk
from methods import change   #Using absolute import instead of wildcard imports

class ClassNameGoesHere:
    
  def __init__(self,app):

    self.testbtn = ttk.Button(app,text="Test",command = lambda: change(self))
     #calling the change method.
    self.testbtn.grid(row=0,column=0,padx=10,pady=10)

    self.testlabel = ttk.Label(app,text="Before Button Click")
    self.testlabel.grid(row=1,column=0,padx=10,pady=10)

def main():
  root = Tk()
  root.title("Title Goes Here")
  obj = ClassNameGoesHere(root)
  root.mainloop()
  
if __name__ == "__main__":
  main()

methods.py

from tkinter import *
from tkinter import ttk

def change(self):
    self.testlabel.config(text="After Button Click")
Aaditya Joshi
  • 122
  • 10
  • If you do it this way, there can be easily conflicts with names. – Thingamabobs May 01 '21 at 06:55
  • @Atlas435 Can you please elaborate? It would help me in writing better code. – Aaditya Joshi May 01 '21 at 08:04
  • espacilly in this case, the name *change* is now taken. Lets say you do exactly the same with a different file like *methods4object2.py* and have another function that is named *change*. In this case the function *change* becomes the last one it is bounded to. So wildcard imports arent ideal and its better to use [absolute imports](https://realpython.com/absolute-vs-relative-python-imports/#pros-and-cons-of-absolute-imports). Another [good answers](https://stackoverflow.com/a/3615206/13629335) – Thingamabobs May 01 '21 at 08:13
  • @Atlas435 Thank you. I will keep this in mind. – Aaditya Joshi May 01 '21 at 11:42