I am writing a files manager in python. One of the functions is to rename a file. Instead of entering the filename in the terminal with the 'input()' function, I want an input box to pop up so the user can enter the filename in there.
This is the function that renames the file.
import os
import tkinter
from tkinter import filedialog
from tkinter import messagebox
def rename_file():
messagebox.showinfo(title="Rename File", message="Select the file you want to rename!")
renameFileSource = filedialog.askopenfilename()
if renameFileSource == "":
messagebox.showinfo(title="File Select Canceled", message="You have canceled the file selection!")
else:
try:
namePath = os.path.dirname(renameFileSource)
renameFileDestination = os.path.splitext(namePath)[1]
messagebox.showinfo(title="Rename File", message="Enter the new file name!")
entry_box()
if renameFileInput == "":
messagebox.showinfo(title="No input", message="You have not entered anything!")
else:
newPath = os.path.join(namePath, renameFileInput renameFileDestination)
os.rename(renameFileSource, newPath)
messagebox.showinfo(title="File Renamed", message="The file has succesfully been renamed!")
except OSError as renameFileError:
messagebox.showerror(title="File Error", message="The following error has occured:\n\n" str(renameFileError) "\n\nPlease try again!")
This is the function that has the input box I made with tkinter. I want this function to pass the input to the variable 'renameFileInput' in the 'rename_file()' function
def entry_box():
entryBox = tkinter.Tk()
def rename_input():
renameFileInput = entryInput.get()
entryBox.destroy()
tkinter.Label(entryBox, text="Enter data here: ").pack()
entryInput = tkinter.Entry(entryBox)
entryInput.pack()
button = tkinter.Button(entryBox, text="GO!", width=3, height=1, command=rename_input)
button.pack()
entryBox.mainloop()
This is the function that has my main GUI.
def gui_window():
guiWindow = tkinter.Tk()
tkinter.Label(guiWindow, text="Lucas' Files Manager\n", fg="green", font=("", 40, "normal", "underline")).pack()
tkinter.Button(guiWindow, text="Rename File", width=25, height=1, bg="blue", fg="red", font=("", "20", "bold"), command=rename_file).pack()
tkinter.Button(guiWindow, text="Exit Program", width=25, height=1, bg="blue", fg="red", font=("", "20", "bold"), command=guiWindow.destroy).pack()
guiWindow.mainloop()
gui_window()
When I run the code as shown above, I get the following error: NameError: name 'renameFileInput' is not defined.
I have uploaded the code to my entire files manager to github: https://github.com/GierLucas/File-Manager
CodePudding user response:
What is happening is that your program is trying to acces the variable renameFileInput
before it creates it, so a NameError
exception is raised. From the code you linked (here), you define that variable in the function rename_input
(which is inside of entry_box
) and try to use it in the function rename_file
.
The problem is that the variable created in rename_input
is destroyed when the function ends, that is when its scope ends. To get the rest of the code know that value you have a few options. The recommended is to return
that value, so you can transfer it to the scope where that function was called. The other option is to make that variable a global
variable. This means that variable can be accessed in every part of your code.
To globalize a variable in a scope, type global <variable>
at the start of the function, in your case:
def entry_box():
entryBox = tkinter.Tk()
def callback():
global renameFileInput
renameFileInput = entryInput.get()
print(renameFileInput)
entryBox.destroy()
tkinter.Label(entryBox, text="Enter data here: ").pack()
entryInput = tkinter.Entry(entryBox)
entryInput.pack()
btn = tkinter.Button(entryBox, text="GO!", width=3, height=1, command=callback)
btn.pack()
entryBox.mainloop()
This should solve the problem you state, although your code has more errors, starting from that mainloop
you have in that method. It will not let you keep the application as you would expect.
Further information
To create popup windows better use TopLevel
class. See here a related question.
About scopes
About return in functions, see here