Сохранять значения записей из предыдущего сеанса Tkinter в цикле - PullRequest
0 голосов
/ 28 февраля 2012

Я пытаюсь создать графический интерфейс Tkinter, который сохраняет все значения поля ввода в текстовом файле, затем считывает данные из этого текстового файла и отображает их по умолчанию при запуске следующего сеанса. Допустим, у меня есть текстовый файл со следующими данными:

one
two
three

Используя следующий код:

#!usr/bin/env python
from Tkinter import *

class Tracker(Tk):
    def __init__(self, var1, var2, var3):
        Tk.__init__(self)

        # Create label
        app_label = Label(self, text="Enter value")
        app_label.pack()

        self.entry1 = StringVar()
        self.entry1.set(var1)
        ent1 = Entry(self,textvariable=self.entry1)
        ent1.pack()
        self.entry2 = StringVar()
        self.entry2.set(var2)
        ent2 = Entry(self,textvariable=self.entry2)
        ent2.pack()
        self.entry3 = StringVar()
        self.entry3.set(var3)
        ent3 = Entry(self,textvariable=self.entry3)
        ent3.pack()

        # Track 'delete window' event
        self.protocol("WM_DELETE_WINDOW", self.handler)

    def handler(self):
        f = open("backup.txt", "w")
        f.write(self.entry1.get()+'\n'+self.entry2.get()+'\n'+self.entry3.get())
        f.close()
        self.destroy()

if __name__ == "__main__":

    t = open("backup.txt")
    var = t.readlines()
    Text1 = var[0]
    Text2 = var[1]
    Text3 = var[2]

    # Initialize GUI
    app = Tracker(Text1, Text2, Text3)  
    app.mainloop()

Я получаю следующее поле:

entry

Мой код должен считывать данные из текстового файла и отображать поля ввода с предопределенными значениями из текстового файла. Но это забавно. Это не сохраняет данные правильно

  1. Я хочу, чтобы этот графический интерфейс работал так, чтобы при редактировании данных в отображаемых выше полях ввода они сохранялись (при закрытии сеанса) и автоматически отображались при следующем запуске.

  2. Есть ли способ сделать это в цикле, чтобы я мог отображать любое количество полей ввода без необходимости жестко кодировать виджеты ввода?

Ответы [ 2 ]

0 голосов
/ 25 апреля 2014

Добавить каждую команду в список.Для этого вам, вероятно, потребуется привязать обработчик событий к виджету (ам) Entry.

В любом случае, что касается действий при запуске, в конце вашего конструктора вы можете сделать что-то подобное (используяСинтаксис Python 3.4, потому что это то, с чем я знаком).

from tkinter import *;
…
def __init__(self, etc.)
    self.commands=[];
    try:
        log=self.load_log();
        self.myTextWidget.replace("1.0", END, "\n".join(log)); #join here turns it into a string with list items separated by new lines.
    except IOError:
        self.save_log();
def load_log(self):
    #load and return the log file
def save_log(self):
    #save the log file; I recommend just pickling the list. Note: to save it, you'll want to load the list from the file and extend it with self.commands, and then save it again.
def on_entry(self, event):
    self.commands.append(the_entry.get());

Вызовите save_log при закрытии программы.

На вашем месте я бы просто сохранял журнал каждый развы вводите команду вместо того, чтобы просто закрывать программу (как она будет работать, даже если программа закрыта ненадлежащим образом), но, возможно, это будет проблемой производительности в вашем случае.

0 голосов
/ 28 февраля 2012

Вы можете легко создавать виджеты в цикле. Строго говоря, вам не нужно создавать StringVar s для каждого виджета, если вы действительно этого не хотите, потому что вы можете получить и установить значение виджета, используя методы для каждого объекта виджета.

Например:

import Tkinter as tk

class SampleApp(tk.Tk):
    def __init__(self, *args, **kwargs):
        tk.Tk.__init__(self, *args, **kwargs)
        button = tk.Button(text="Save", command=self.save)
        button.pack(side="top")
        self.widgets = []
        for line in ["one","two","three","four"]:
            widget = tk.Entry(self)
            widget.insert(0, line)
            widget.pack(side="top", fill="x")
            self.widgets.append(widget)

    def save(self):
        for widget in self.widgets:
            print widget.get()

if __name__ == "__main__":
    app = SampleApp()
    app.mainloop()
...