Search code examples
python-3.xtkinterpickletkinter-entryfiledialog

How can I get the data (DoubleVar) from multiple Tkinter Entry boxes and save them to a .dat file and retrieve them later to repopulate said boxes


First let me say brand new here and brand new to codeing

The whole idea I'm trying to get done is have a list of Parameters that can be saved by the user and used later with out having to change the code

I have a bigger program I am working on, but I have simplified this code to figure this out. I have the following code that will get and receive a single Entry box, if I try to add a second entry box to the "save" then it just adds to to the first Entry box like concatenation.

import tkinter
from tkinter import *
from tkinter import filedialog
from tkinter import ttk
import sqlite3
import pickle
#---------------------------------------------------------------



#---------------------------------------------------------------
root = Tk()
root.title("Cabinet Cut List Calculator")

frame = LabelFrame(root)
frame.pack()
#---------------------------------------------------------------

#---------------------------------------------------------------
toek = DoubleVar(value=3.5)
default_hgt = IntVar(value=42)
 
parms_list = [toek, default_hgt]



#---------------------------------------------------------------

#---------------------------------------------------------------
def SaveParms():
    parms_name = filedialog.asksaveasfilename(initialdir="/Users/Owner/Desktop/Python/cab databases/Parameters", title="Save Parameters", filetypes=(("Dat Files", "*.dat"),("All Files", "*.*")))

    if parms_name:
        if parms_name.endswith(".dat"):
            pass
        else:
            parms_name = f"{parms_name}.dat"

    parms_list = y.get()

    output_parms = open(parms_name, 'wb')

    pickle.dump(parms_list, output_parms)
        
def LoadParms():
    parms_name = filedialog.askopenfilename(initialdir="/Users/Owner/Desktop/Python/cab databases/Parameters", title="Load Parameters", filetypes=(("Dat Files", "*.dat"),("All Files", "*.*")))

    if parms_name:
            y.delete(0, END)

            input_parm = open(parms_name, "rb")

            load_item = pickle.load(input_parm)

            for i in load_item:
                y.insert(END, i)


def DelParms():
    y.delete(0,END)
    

#---------------------------------------------------------------

#---------------------------------------------------------------
the_menu = Menu(root)
root.config(menu = the_menu)
#^^^^^^^^^^
file_menu =  Menu(the_menu, tearoff=False)
the_menu.add_cascade(label="File", menu= file_menu)
#^^^^^^^^^^
file_menu.add_command(label="Save Parameters", command= SaveParms)
file_menu.add_command(label="Load Parameters", command= LoadParms)
file_menu.add_separator()
file_menu.add_command(label="Clear Parameters", command= DelParms)
#---------------------------------------------------------------

#---------------------------------------------------------------
y = Entry(frame, textvariable=toek)
y.pack(side=RIGHT)
yl= Label(frame, text = "1....")
yl.pack()

frame2 = LabelFrame(root)
frame2.pack()

x = Entry(frame2, textvariable= default_hgt)
x.pack(side=RIGHT)
xl= Label(frame2, text = "2....")
xl.pack()
#---------------------------------------------------------------




root.mainloop()

I know this is going to involve some sort of for loop but I cant figure it out. if I try

for i in parms_list:
    parms_list =+ i.get()

in the Save function I get

parms_list =+ i.get()
              ^^^^^
AttributeError: 'str' object has no attribute 'get'

PICKLE is beyond my limited scope of knowledge.

I know there is a simple solution here, I have tried other things but I am at a loss.

Thanks have a great day

EDIT: I have been working on this for a couple of days and this is what I have come up with for the "save" function

if parms_name:
    if parms_name.endswith(".dat"):
        pass
    else:
        parms_name = f"{parms_name}.dat"

new_list = []
for i in entry_list:
    entry_name = [key for key, value in globals().items()  if  value == i]
    new_list += [(entry_name[0] + ".get()")]

# print(new_list)
# new_list = [y.get(), x.get()]

output_parms = open(parms_name, 'wb')

pickle.dump(new_list, output_parms)

so I am getting closer but the "new_list" is just strings and i need it to run the .get() function on the variable, I'll keep working at it but if there is any help out there I would appreciate it, thanks.


Solution

  • So as most things in life there is more than one way to do things. I was using .dat files because that was what I was working with a tutorial. After banging my head against a wall and doing research in between I ended up using .ini (config file) and here is my working code.

    #---------------------------------------------------------------
    import tkinter
    from tkinter import *
    from tkinter import filedialog
    from tkinter import ttk
    import sqlite3
    from configparser import ConfigParser
    import os
    #---------------------------------------------------------------
    
    #---------------------------------------------------------------
    root = Tk()
    root.title("Cabinet Cut List Calculator")
    
    frame = LabelFrame(root)
    frame.pack()
    #---------------------------------------------------------------
    
    #---------------------------------------------------------------
    toek = DoubleVar(value=3.5)
    default_hgt = IntVar(value=42)
    #---------------------------------------------------------------
    
    #---------------------------------------------------------------
    def SaveParms():
        save_name = filedialog.asksaveasfilename(initialdir="/Users/Owner/Desktop/Python/cab databases/Parameters", title="Save Parameters", filetypes=(("ini Files", "*.ini"),("All Files", "*.*")))
    
        if save_name:
            if save_name.endswith(".ini"):
                pass
            else:
                save_name = f"{save_name}.ini"
    
        parser = ConfigParser()
        def write_file():
            if save_name:
                parser.write(open(save_name, 'w'))
    
        if not os.path.exists(save_name):
            parser['parameters'] = {'var1': y.get(), 'var2': x.get()}
    
            write_file()
            
    def LoadParms():
        load_name = filedialog.askopenfilename(initialdir="/Users/Owner/Desktop/Python//cab databases/Parameters", title="Load Parameters", filetypes=(("ini Files", "*.ini"),("All Files", "*.*")))
    
        if load_name:
            parser = ConfigParser()
            parser.read(load_name)
            saved_toek = parser.get('parameters', 'var1')
            saved_default_hgt = parser.get('parameters', 'var2')
            saved_toek = DoubleVar(value = saved_toek)
            saved_default_hgt = IntVar(value = saved_default_hgt)
    
            y.configure(textvariable=saved_toek)
            x.configure(textvariable=saved_default_hgt)
    
    def DelParms():
        y.delete(0,END)
        x.delete(0,END)
    
    #---------------------------------------------------------------
    
    #---------------------------------------------------------------
    the_menu = Menu(root)
    root.config(menu = the_menu)
    #^^^^^^^^^^
    file_menu =  Menu(the_menu, tearoff=False)
    the_menu.add_cascade(label="File", menu= file_menu)
    #^^^^^^^^^^
    file_menu.add_command(label="Save Parameters", command= SaveParms)
    file_menu.add_command(label="Load Parameters", command= LoadParms)
    file_menu.add_separator()
    file_menu.add_command(label="Clear Parameters", command= DelParms)
    #---------------------------------------------------------------
    
    #---------------------------------------------------------------
    y = Entry(frame, textvariable=toek)
    y.pack(side=RIGHT)
    yl= Label(frame, text = "1....")
    yl.pack()
    
    frame2 = LabelFrame(root)
    frame2.pack()
    
    x = Entry(frame2, textvariable= default_hgt)
    x.pack(side=RIGHT)
    xl= Label(frame2, text = "2....")
    xl.pack()
    #---------------------------------------------------------------
    
    root.mainloop()