Related
I want to pass a button name to tkinter as a variable. This method works for Text fields, but not for buttons in my code.
I am building a gui app and I want to have a generic clear function that zaps a text entry field and resets a button from NORMAL to DiSABLED.
There are multiple buttons and fields, hence the desire to make this generic.
For the code I have, the buttons are present with the exception of clear all.
I am setting the variable w_button to the specific name of the (existing) button based on what is passed to the function.
def switch_clear(elem_type):
if elem_type == 'scn':
w_button = 'b_clear_scn'
clear_field = 'scn_file_entry'
print ('scenario')
elif elem_type == 'sol2':
w_button = 'b_clear_sol2'
clear_field = 'sol2_file_entry'
print ('sol2')
elif elem_type == 'mdl':
w_button = 'b_clear_mdlList'
clear_field = 'mdlList_file_entry'
print ('mdl')
elif elem_type == 'all':
print ('clear all TBD')
return()
if w_button["state"] == NORMAL:
clear_field.delete(0, END)
w_button["state"] = DISABLED
return()
Here's what happens:
C:\utils>my_frame3.py
scenario
Traceback (most recent call last):
File "C:\utils\my_frame3.py", line 127, in <module>
b_clear_scn = Button(first_frame, text = "Clear scenario", command = switch_clear('scn'), height = 2, state=DISABLED)
File "C:\utils\my_frame3.py", line 100, in switch_clear
if w_button["state"] == NORMAL:
TypeError: string indices must be integers
C:\utils>
I realize I could duplicate and push the clear operations into the if/elif statements, and I may have to live with that but - is it possible to reference buttons as variables? How can I do this?
Complete code as requested below. The preview is a mess despite using the code widget, but in my file lines are correctly formatted (notepad++). Tx
import os, sys
from tkinter import *
from tkinter import messagebox
from tkinter import filedialog
root2 = Tk()
root2.title('Model Processing')
root2.geometry('{}x{}'.format(512, 400))
# colors
color1 = 'light cyan'
color2 = 'gold'
color3 = 'RosyBrown1'
color4 = 'lavender'
color5 = 'linen'
bg_color = 'azure'
# number of items to process; until >1 OK is disabled; if >1 OK is enabled TBD
l_to_do = [] # items to process; scn, sol2, modelList, installed models
# functions/commands
def callback():
print ('A button was clicked.')
return;
def my_exit():
result = messagebox.askquestion("Cancel Model Processing", "Are you sure?", icon='warning')
if result == 'yes':
root2.quit()
else: # user changed mind
pass
def choose_import_file(str_ftype):
which_field = ''
which_clear_btn = ''
ftype = str_ftype
mdl_opts = {}
if ftype == 'scn':
title_msg = 'Choose a scenario file'
mdl_opts['filetypes'] = [('Supported types', ('.scn')),
('scenario files',('.scn'))]
which_field = scn_file_entry
which_clear_btn = 'b_clear_scn'
elif ftype == 'sol2':
title_msg = 'Choose a SOL2 file'
mdl_opts['filetypes'] = [('Supported types', ('.txt')),
('sol2 files',('.txt'))]
which_field = sol2_file_entry
elif ftype == 'mdllist':
title_msg = 'Choose a ModelList file'
print ('TBD: ModelList file')
file_input = filedialog.askopenfilename(title = title_msg, **mdl_opts)
if file_input == '':
print ('error or cancelled by user')
return
else:
f_inp_file = os.path.basename(file_input)
f_inp_file_base = str(file_input.split('.')[0])
f_inp_file_ext = str.lower(str(file_input.split('.')[1]))
f_inp_d_name = os.path.dirname(file_input)
print('File chosen:', f_inp_file_base)
# populate scenario file field
which_field.insert(INSERT,file_input)
which_clear_btn["state"] = NORMAL
# define appropriate clear button active
# define_clear_btn.configure(state = ACTIVE)
return
def switch_clear(elem_type):
if elem_type == 'scn':
if b_clear_scn["state"] == NORMAL:
scn_file_entry.delete(0, END)
b_clear_scn["state"] = DISABLED
elif elem_type == 'sol2':
f b_clear_sol2["state"] == NORMAL:
clear_field = 'sol2_file_entry'
b_clear_sol2["state"] = DISABLED
elif elem_type == 'mdl':
if b_clear_mdlList["state"] == NORMAL:
clear_field = 'mdlList_file_entry'
b_clear_mdlList["state"] = DISABLED
elif elem_type == 'all':
print ('clear all TBD')
return()
return()
# create all of the main containers
first_frame = Frame(root2, bg=color5, width = 512, height=90, pady=10)
second_frame = Frame(root2, bg=color5, width = 512, height=90, pady=10)
third_frame = Frame(root2, bg=color5, width=512, height=90, pady=10)
fourth_frame = Frame(root2, bg=color5, width = 512, height = 90, pady=10)
# layout all of the main containers
root2.grid_rowconfigure(3, weight=1)
root2.grid_rowconfigure(2, weight=1)
root2.grid_rowconfigure(1, weight=1)
root2.grid_columnconfigure(0, weight=1)
first_frame.grid(row=0, sticky="ew")
second_frame.grid(row=1, sticky="ew")
third_frame.grid(row=2, sticky="ew")
fourth_frame.grid(row = 3, sticky="e")
# create the widgets for the first frame
#scn_label = Label(first_frame, text = 'Scenario file')
scn_file_entry = Entry(first_frame, background=bg_color, width = 50)
b_choose_scn = Button(first_frame, text = "Choose a scenario..", command = lambda: choose_import_file('scn'), height = 2)
b_clear_scn = Button(first_frame, text = "Clear scenario", command = switch_clear('scn'), height = 2, state=DISABLED)
# layout the widgets in the first frame
#scn_label.grid(row = 0, column = 0, padx = (10,50), pady=5)
scn_file_entry.grid(row = 0, column = 1, padx = (10,10))
b_choose_scn.grid(row=0, column=0, padx = (10,10), sticky=W)
b_clear_scn.grid(row=2, column=0, padx = (10,10), sticky=W)
# second frame
# sol2_label = Label(second_frame, text = 'Sol2 file')
sol2_file_entry = Entry(second_frame, background=bg_color, width = 50)
b_choose_sol2 = Button(second_frame, text = "Choose SOL2 file..", command = lambda: choose_import_file('sol2'), height = 2)
b_clear_sol2 = Button(second_frame, text = "Clear SOL2", command = switch_clear('sol2'), height = 2, state=DISABLED)
# layout the widgets in the second frame
# sol2_label.grid(row = 0, column = 0, padx = (10,50), pady=5)
sol2_file_entry.grid(row = 0, column = 1, padx = (10,10), sticky=EW)
b_choose_sol2.grid(row=0, column=0, padx = (10,10), sticky=W)
b_clear_sol2.grid(row=2, column=0, padx = (10,10), sticky=W)
# third frame
# mdlList_label = Label(third_frame, text = 'ModelList.txt file')
mdlList_file_entry = Entry(third_frame, background=bg_color, width = 50)
b_choose_mdlList = Button(third_frame, text = "Choose ModelList.txt file..", command = callback, height = 2)
b_clear_mdlList = Button(third_frame, text = "Clear ModelList", command = callback, height = 2, state=DISABLED)
# layout the widgets in the third frame
#mdlList_label.grid(row = 0, column = 0, padx = (10,10), pady=5, sticky = 'ns')
mdlList_file_entry.grid(row = 0, column = 1, padx = (10,10), sticky=EW)
b_choose_mdlList.grid(row=0, column=0, padx = (10,10), sticky=W)
b_clear_mdlList.grid(row=2, column=0, padx = (10,10), sticky=W)
#####################################################################
# create bottom widgets
#####################################################################
clear_all = Button(fourth_frame, text='Clear All', padx = '5', command = callback, height = 2, state=DISABLED)
ok_btn = Button(fourth_frame, text='OK', padx = '5', command = callback, height = 2, state=DISABLED)
cancel_btn = Button(fourth_frame, text='Cancel', height = 2, padx = '12', command = my_exit)
#####################################################################
# layout the bottom widgets
#####################################################################
clear_all.grid(row = 0, column = 2, sticky = 'e')
ok_btn.grid(row = 0, column = 3, sticky = 'e')
cancel_btn.grid(row = 0, column = 4, sticky = 'e')
# commands/bindings
root2.mainloop()
I believe this is what you are trying to do. The below is fully commented with explanations. switch_clear becomes entirely unnecessary with this method. The buttons directly clear their corresponding entry in their command, and Entry validation takes care of the corresponding button state.
Note: I wrote all of this before you posted your full code
import tkinter as tk
root = tk.Tk()
root.geometry('400x400')
#toggle the state of buttons based on entry text length
def toggle_button(name, text):
global btn_switch
btn_switch[name]['state'] = 'normal' if len(text) else 'disabled'
return True
#to hold the buttons so they are easy to position
#just for this example
buttons = tk.Frame(root)
buttons.pack(side='top', anchor='nw')
#create a tcl wrapper for the validate command
vcmd = tk.Widget.register(root, toggle_button)
#mock-up of your entries ~ validate on key press. send widget name and full text to vcmd
scn_file_entry = tk.Entry(root, width=20)
scn_file_entry.configure(validate="key", validatecommand=(vcmd, '%W', '%P'))
scn_file_entry.pack(side='left', anchor='nw')
sol2_file_entry = tk.Entry(root, width=20)
sol2_file_entry.configure(validate="key", validatecommand=(vcmd, '%W', '%P'))
sol2_file_entry.pack(side='left', anchor='nw')
mdlList_file_entry = tk.Entry(root, width=20)
mdlList_file_entry.configure(validate="key", validatecommand=(vcmd, '%W', '%P'))
mdlList_file_entry.pack(side='left', anchor='nw')
#mock-up of your buttons ~ delete the entry text in a lambda and let entry validation handle the button state
b_clear_scn = tk.Button(buttons, text="scn", state='disabled')
b_clear_scn.configure(command=lambda: scn_file_entry.delete(0, 'end'))
b_clear_scn.pack(side='left', anchor='nw')
b_clear_sol2 = tk.Button(buttons, text="sol2", state='disabled')
b_clear_sol2.configure(command=lambda: sol2_file_entry.delete(0, 'end'))
b_clear_sol2.pack(side='left', anchor='nw')
b_clear_mdlList = tk.Button(buttons, text="mdl", state='disabled')
b_clear_mdlList.configure(command=lambda: mdlList_file_entry.delete(0, 'end'))
b_clear_mdlList.pack(side='left', anchor='nw')
#create a dictionary of 'widget name':corresponding button, for toggle_button to reference
btn_switch = {
f'{scn_file_entry}':b_clear_scn,
f'{sol2_file_entry}':b_clear_sol2,
f'{mdlList_file_entry}':b_clear_mdlList,
}
root.mainloop()
I have a long chunk of code. I do not want to paste it all here, so let me explain what I am trying to accomplish here. Based on a number provided by the user I want to create that many text boxes and then get what is entered into that text box and insert that into the dictionary. I have tried this a few ways and just cannot get it to work correctly. The list is either empty or it only contains the last text box as the value for each key.
def multiple_choice():
def add():
top.destroy()
top = Tk()
top.title("Add Question")
w = 800
h = 800
ws = top.winfo_screenwidth()
hs = top.winfo_screenheight()
x = (ws/2) - (w/2)
y = (hs/2) - (h/2)
top.geometry('%dx%d+%d+%d' % (w, h, x, y))
question = Label(top, text="Question to be asked?", font = "Times 14 bold", fg = "blue")
question.grid(row = 2, column = 4)
questionText = Text(top, borderwidth = 5, width=50,height=5, wrap=WORD, background = 'grey')
questionText.grid(row = 3, column = 4)
numQuestions = Label(top, text = "Number of answer choices?", font = "Times 14 bold", fg = "blue")
numQuestions.grid(row = 4, column=4)
num = Entry(top, bd = 5)
num.grid(row=5, column = 4)
answerList = {}
def multiple():
def preview():
preview = Tk()
top.title("Question Preview")
w = 500
h = 500
ws = top.winfo_screenwidth()
hs = top.winfo_screenheight()
x = (ws/2) - (w/2)
y = (hs/2) - (h/2)
top.geometry('%dx%d+%d+%d' % (w, h, x, y))
title = Label(preview, text = "Short Answer Question Preview", font = "Times 18 bold", fg = "blue" )
title.grid(row = 0, column = 2)
qtext = "Question text will read: "
ques = Label(preview, text = qtext)
ques.grid(row=1, column = 2)
ques2 = Label( preview, text = questionText.get("1.0",END))
let = 'A'
i = 1
for word in answerList:
prev = let + ": " + word
ans = Label(preview, text = prev)
ans.grid(row=1+i, column = 2)
let = chr(ord(let) + 1)
answerCor = "The correct answer(s): "
a = Label(preview, text = answerCor)
a.grid(row=4, column = 2)
b = Label(preview, text = cor.get)
b.grid(row=5, column = 2)
if num.get().isdigit():
number = int(num.get())
AnswerChoices = Label(top, text = "Answer Choices?", font = "Times 14 bold", fg = "blue")
AnswerChoices.grid(row = 6, column=4)
i = 0
let = 'A'
while i < number:
letter = Label(top, text = let)
letter.grid(row = 8+(i*4), column = 3)
answer = Text(top, borderwidth = 5, width=50, height=3, wrap=WORD, background = 'grey')
answer.grid(row = 8+(i*4), column = 4)
answerList[let] = answer.get("1.0",END)
i = i+1
let = chr(ord(let) + 1)
print answerList
correct = Label(top, text = "Correct Answer(s) (seperated by commas)",
font = "Times 14 bold", fg = "blue")
correct.grid(row =99 , column=4)
cor = Text(top, borderwidth = 5, width=50, height=3, wrap=WORD, background = 'grey')
cor.grid(row=100, column = 4)
else:
error = Tk()
w = 500
h = 100
ws = top.winfo_screenwidth()
hs = top.winfo_screenheight()
x = (ws/2) - (w/2)
y = (hs/2) - (h/2)
error.geometry('%dx%d+%d+%d' % (w, h, x, y))
text = "ERROR: You must enter an integer number"
Label(error,text = text, fg = "red", font = "Times 16 bold").pack()
MyButton5 = Button(top, text="Preview Question", width=20, command = preview, anchor=S)
MyButton5.grid(row=102, column=5)
MyButton4 = Button(top, text="Finish and Add Question", width=20, command = add, anchor=S)
MyButton4.grid(row=102, column=2)
but = Button(top, text="Submit", width=10, command = multiple)
but.grid(row=6, column = 4)
top.mainloop()
def button():
MyButton21 = Button(quiz, text="Short Answer Question", width=20, command = short_answer)
MyButton21.grid(row=8, column=2)
MyButton22 = Button(quiz, text="True/False Question", width=20, command = true_false)
MyButton22.grid(row=8, column=4)
MyButton23 = Button(quiz, text="Multiple Choice Question", width=20, command = multiple_choice)
MyButton23.grid(row=9, column=2)
#MyButton24 = Button(quiz, text="Matching Question", width=20, command = matching)
#MyButton24.grid(row=9, column=4)
MyButton25 = Button(quiz, text="Ordering Question", width=20, command =order)
MyButton25.grid(row=10, column=2)
MyButton26 = Button(quiz, text="Fill in the Blank Question", width=20, command = fill_blank)
MyButton26.grid(row=10, column=4)
MyButton3 = Button(quiz, text="Finsh Quiz", width=10, command = quiz)
MyButton3.grid(row=12, column=3)
quiz = Tk()
w = 700
h = 300
ws = quiz.winfo_screenwidth()
hs = quiz.winfo_screenheight()
x = 0
y = 0
quiz.geometry('%dx%d+%d+%d' % (w, h, x, y))
quiz.title("eCampus Quiz Developer")
L1 = Label(quiz, text="Quiz Title?")
L1.grid(row=0, column=0)
E1 = Entry(quiz, bd = 5)
E1.grid(row=0, column=3)
name_file = E1.get()
name_file = name_file.replace(" ", "")
name_file = name_file + ".txt"
with open(name_file,"w") as data:
MyButton1 = Button(quiz, text="Submit", width=10, command = button)
MyButton1.grid(row=1, column=3)
quiz.mainloop()
I am trying to create the dictionary using this chunk of code:
i = 0
let = 'A'
while i < number:
letter = Label(top, text = let)
letter.grid(row = 8+(i*4), column = 3)
answer = Text(top, borderwidth = 5, width=50, height=3, wrap=WORD, background = 'grey')
answer.grid(row = 8+(i*4), column = 4)
answerList[let] = answer.get("1.0",END)
i = i+1
let = chr(ord(let) + 1)
I have even tried putting a loop in the preview function but that is when the last box was the only value contained in the dictionary. Any ideas would be appreciated
Please see my commeneted snippet below which demonstrates this:
from tkinter import *
class App:
def __init__(self, root):
self.root = root
self.entry = Entry(self.root) #entry to input number of entries later
self.button = Button(self.root, text="ok", command=self.command) #calls command to draw the entry boxes
self.frame = Frame(self.root)
self.entry.pack()
self.button.pack()
self.frame.pack()
def command(self):
self.frame.destroy() #destroys frame and contents
self.frame = Frame(self.root) #recreates frame
self.text = [] #empty array to store entry boxes
for i in range(int(self.entry.get())):
self.text.append(Entry(self.frame, text="Question "+str(i))) #creates entry boxes
self.text[i].pack()
self.done = Button(self.frame, text="Done", command=self.dict) #button to call dictionary entry and print
self.done.pack()
self.frame.pack()
def dict(self):
self.dict = {}
for i in range(len(self.text)):
self.dict.update({self.text[i].cget("text"): self.text[i].get()})
#the above line adds a new dict entry with the text value of the respective entry as the key and the value of the entry as the value
print(self.dict) #prints the dict
root = Tk()
App(root)
root.mainloop()
The above asks the user how many entry widgets they want to create, fills a frame with those entry widgets and then iterates through the list which contains them on the press of a button, adding a new dictionary entry for each entry widget, where the key of the dict is the attribute text for each entry and the value of the dict is the value of each entry.
I want to make a button in my widget that when I press it, it proceeds to the next lines of code, and closes the existing widget of where the button is.
from tkinter import *
root = Tk()
Label(root, text = "Childs First name").grid(row = 0, sticky = W)
Label(root, text = "Childs Surname").grid(row = 1, sticky = W)
Label(root, text = "Childs Year of Birth").grid(row = 2, sticky = W)
Label(root, text = "Childs Month of Birth").grid(row = 3, sticky = W)
Label(root, text = "Childs Day of Birth").grid(row = 4, sticky = W)
Fname = Entry(root)
Sname = Entry(root)
x = Entry(root)
y = Entry(root)
z = Entry(root)
Fname.grid(row = 0, column = 1)
Sname.grid(row = 1, column = 1)
x.grid(row = 3, column = 1)
y.grid(row = 2, column = 1)
z.grid(row = 4, column = 1)
button1 = Button(root, text = "Quit", command = root.quit, bg = "Grey", fg = "White", width = 12).grid(row = 5, column = 0, sticky = W)
def save():
Fname_value = Fname.get()
Sname_value = Sname.get()
x_value = x.get()
y_value = y.get()
z_value = z.get()
save()
mainloop()
Sorry for this late answer. To make a 'continue' button:
continue_button = tk.Button(frame,text='continue',command=func)
continue_button.config(width=width_continue_button)
# set the coordinates as you want. here 2,6 for the example
continue_button.grid(row=2,column=6,padx=width_continue_grid)
then you have to write the function 'func' to fulfill your needs.
hope this helps
from tkinter import *
window = Tk()
ia_answers= "trolol"
input_frame = LabelFrame(window, text="User :", borderwidth=4)
input_frame.pack(fill=BOTH, side=BOTTOM)
input_user = StringVar()
input_field = Entry(input_frame, text=input_user)
input_field.pack(fill=BOTH, side=BOTTOM)
ia_frame = LabelFrame(window, text="Discussion",borderwidth = 15, height = 100, width = 100)
ia_frame.pack(fill=BOTH, side=TOP)
user_says = StringVar()
user_text = Label(ia_frame, textvariable=user_says, anchor = NE, justify = RIGHT, bg="white")
user_text.pack(fill=BOTH, side=TOP)
ia_says = StringVar()
ia_text = Label(ia_frame, textvariable=ia_says, anchor = W, justify = LEFT, bg="white")
ia_text.pack(fill=BOTH, side=BOTTOM)
def Enter_pressed(event):
"""Took the current string in the Entry field."""
input_get = input_field.get()
input_user.set("")
user_says.set(input_get + "\n\n")
ia_says.set(ia_answers)
input_field.bind("<Return>", Enter_pressed)
window.mainloop()
Hi, i am trying to build a discussion Bot.
When I execute the code, the question in the input field and the answer get displayed correctly.
The problem is after entering the next sentence, the previous question/answer gets removed. Here is an example:
Hello Bot
Hello User
(then the text disappears)
How are you
Fine thank you
What i want :
Hello Bot
Hello User
(then the text stays in the frame)
How are you
Fine thank you
The issue occurs in line -
user_says.set(input_get + "\n\n")
ia_says.set(ia_answers)
You are replace users_says.set() and ia_says.set() resets the complete Labels , with the new value. Instead you should get the old value and append the new value to it and set it back, Example -
user_says.set(user_says.get() + input_get + "\n")
ia_says.set(ia_says.get() + ia_answers + "\n")
Or you can also create a new label for each new event and add it to the LabelFrame . Example -
from tkinter import *
window = Tk()
ia_answers= "trolol\n"
input_frame = LabelFrame(window, text="User :", borderwidth=4)
input_frame.pack(fill=BOTH, side=BOTTOM)
input_user = StringVar()
input_field = Entry(input_frame, text=input_user)
input_field.pack(fill=BOTH, side=BOTTOM)
ia_frame = LabelFrame(window, text="Discussion",borderwidth = 15, height = 100, width = 100)
ia_frame.pack(fill=BOTH, side=TOP)
user_says = StringVar()
user_text = Label(ia_frame, textvariable=user_says, anchor = NE, justify = RIGHT,
bg="white")
user_text.pack(fill=X)
ia_says = StringVar()
ia_text = Label(ia_frame, textvariable=ia_says, anchor = NW, justify = LEFT, bg="white")
ia_text.pack(fill=X)
user_texts = []
ia_texts = []
user_says_list = []
ia_says_list = []
def Enter_pressed(event):
"""Took the current string in the Entry field."""
input_get = input_field.get()
input_user.set("")
user_says1 = StringVar()
user_says1.set(input_get + "\n")
user_text1 = Label(ia_frame, textvariable=user_says1, anchor = NE, justify = RIGHT,
bg="white")
user_text1.pack(fill=X)
user_texts.append(user_text1)
user_says_list.append(user_says1)
ia_says1 = StringVar()
ia_says1.set(ia_answers)
ia_text1 = Label(ia_frame, textvariable=ia_says1, anchor = NW, justify = LEFT,
bg="white")
ia_text1.pack(fill=X)
ia_texts.append(ia_text1)
ia_says_list.append(ia_says1)
input_field.bind("<Return>", Enter_pressed)
window.mainloop()
I am trying to create a simple interface to access the name array with first, last, previous and next functionality. But the global variable I am using as a position tracker is not working. I have already referred to various question. Would really appreciate the help. Here is the code.
from tkinter import Tk, Label, Entry, Button, StringVar, IntVar
window = Tk()
name_array = [('a1','a2','a3'), ('b1','b2','b3'), ('c1','c2','c3'),('d1','d2','d3')]
global position_track
position_track = IntVar()
first_name = StringVar()
last_name = StringVar()
email = StringVar()
def return_value(pos):
first_name.set(name_array[pos][0])
last_name.set(name_array[pos][1])
email.set(name_array[pos][2])
def update_value(pos):
name_array[pos] = (first_name.get(), last_name.get(), email.get())
def first_value():
global position_track
return_value(0)
postion_track.set(0)
def last_value():
global position_track
return_value(-1)
postion_track.set(-1)
def next_value():
global position_track
if position_track.get() == len(name_array):
position_track.set(1)
temp = postion_track.get()
return_value(temp + 1)
postion_track.set(temp + 1)
def prev_value():
global position_track
if position_track.get() == -1:
position_track.set(len(name_array - 1))
temp = postion_track.get()
return_value(temp - 1)
postion_track.set(temp - 1)
label_first_name = Label(window, text = 'First Name:', justify = 'right', padx = 5)
entry_first_name = Entry(window, textvariable = first_name)
label_last_name = Label(window, text = 'Last Name:', justify = 'right', padx = 5)
entry_last_name = Entry(window, textvariable = last_name)
label_email = Label(window, text = 'Email Address:', justify = 'right', padx = 5)
entry_email = Entry(window, textvariable = email)
button_first = Button(window, text = 'First', command = first_value)
button_last = Button(window, text = 'Last', command = last_value)
button_prev = Button(window, text = 'Prev', command = prev_value)
button_next = Button(window, text = 'Next', command = next_value)
button_quit = Button(window, text = 'Quit')
button_quit.configure(command=window.destroy)
labels = [label_first_name, label_last_name, label_email]
entries = [entry_first_name, entry_last_name, entry_email]
buttons = [button_first, button_last, button_prev, button_next, button_last, button_quit]
for i in range(3):
labels[i].grid(row = i, column = 0, sticky = 'W')
entries[i].grid(row = i, column = 1, columnspan = 6)
for j in range(6):
buttons[j].grid(row = 3, column = j, sticky = 'E')
window.mainloop()
Too many typos. Plus, you don't need to declare a global in the outermost program space, just in the function defs. Corrected working code ->
from tkinter import Tk, Label, Entry, Button, StringVar, IntVar
window = Tk()
name_array = [('a1','a2','a3'), ('b1','b2','b3'), ('c1','c2','c3'),('d1','d2','d3')]
position_track = IntVar()
first_name = StringVar()
last_name = StringVar()
email = StringVar()
def return_value(pos):
first_name.set(name_array[pos][0])
last_name.set(name_array[pos][1])
email.set(name_array[pos][2])
def update_value(pos):
name_array[pos] = (first_name.get(), last_name.get(), email.get())
def first_value():
global position_track
return_value(0)
position_track.set(0)
def last_value():
global position_track
return_value(-1)
position_track.set(-1)
def next_value():
global position_track
if position_track.get() == len(name_array):
position_track.set(1)
temp = position_track.get()
return_value(temp + 1)
position_track.set(temp + 1)
def prev_value():
global position_track
if position_track.get() == -1:
position_track.set(len(name_array) - 1)
temp = position_track.get()
return_value(temp - 1)
position_track.set(temp - 1)
label_first_name = Label(window, text = 'First Name:', justify = 'right', padx = 5)
entry_first_name = Entry(window, textvariable = first_name)
label_last_name = Label(window, text = 'Last Name:', justify = 'right', padx = 5)
entry_last_name = Entry(window, textvariable = last_name)
label_email = Label(window, text = 'Email Address:', justify = 'right', padx = 5)
entry_email = Entry(window, textvariable = email)
button_first = Button(window, text = 'First', command = first_value)
button_last = Button(window, text = 'Last', command = last_value)
button_prev = Button(window, text = 'Prev', command = prev_value)
button_next = Button(window, text = 'Next', command = next_value)
button_quit = Button(window, text = 'Quit')
button_quit.configure(command=window.destroy)
labels = [label_first_name, label_last_name, label_email]
entries = [entry_first_name, entry_last_name, entry_email]
buttons = [button_first, button_last, button_prev, button_next, button_last, button_quit]
for i in range(3):
labels[i].grid(row = i, column = 0, sticky = 'W')
entries[i].grid(row = i, column = 1, columnspan = 6)
for j in range(6):
buttons[j].grid(row = 3, column = j, sticky = 'E')
window.mainloop()