0

我有以下代码,我要求用户打开一个文本,该文本可以在一段数据中包含几行。

然后,我需要为每一行创建一个 OptionMenu。我的问题是我需要为每个选项菜单做不同的事情,并将其仅应用于“网格”中的特定行。我不能这样做,因为我正在以相同的名称创建它们并且不明白如何做不同的事情。

with askopenfile(filetypes=[(".txt files","*.txt")], title='Import', mode='r') as f: 
    data_dict=parse_file(f) 


info=data_dict['three'] 
i = 2
for row in info:
    # Create row in 'table' for each output
    no_1, code, value = row             # Obtain results
    def three( code ):
        c = { "1" : "1",
              "2" : "2",
              "3" : "3" }
        try:
            return c[code]
        except KeyError:
            return "None"


    variablelist = StringVar(self.frame_table)
    variablelist.set("Fixed")
    self.list1 = OptionMenu(self.frame_table, variablelist, "Fixed", "List", "Min", "Max", command=self.ChoiceBox)
    self.list1.grid(row=i, column=6, sticky="nsew", padx=1, pady=1)
    i = i + 1

例如,我想在第三行中的第二行旁边创建一个额外的框,但由于第三行是最后创建的,当我尝试获取网格信息时,我只能将它添加到第三行。

我这样做的原因是因为我并不总是知道行数,而且我不想创建很多代码行,每次都单独创建一个选项菜单(即使我确实知道行数)。

4

2 回答 2

0
self.variablelists=[]
self.lists=[]
for row in info:
    # Create row in 'table' for each output
    no_1, code, value = row             # Obtain results
    def three( code ):    #don't know what this is for, but if it's necessary later, this is more clean than your previous code.
        return c if c in "123" else "None"    

    variablelist = StringVar()
    variablelist.set("Fixed")
    self.variablelists.append(variablelist)
    list1 = OptionMenu(self.frame_table, variablelist, "Fixed", "List", "Min", "Max", command=self.ChoiceBox)
    list1.grid(row=i, column=6, sticky="nsew", padx=1, pady=1)
    self.lists.append(list1)
    i += 1

现在您可以处理每个选项菜单。

于 2012-07-10T14:30:06.060 回答
0

你的问题很不清楚,主要是因为你的例子没有任何意义。例如,为什么你three在每次迭代时都重新定义函数,但你从不使用它?

无论如何,也许下面的例子会对你有所帮助。它创建三个选项菜单,将一个变量与每个菜单关联,并在值更改时让它们中的每一个都调用相同的过程。默认情况下,此方法将被赋予选项菜单的新值;通过使用 lambda 函数,我们还可以将行号传递给函数。

import Tkinter as tk

# data for the example
info = (
    ("1.1","1.2","1.3"),
    ("2.1","2.2","2,3"),
    ("3.1","3.2","3.3"),
)

class SampleApp(tk.Tk):
    def __init__(self):
        tk.Tk.__init__(self)
        self.status = tk.Label(self, anchor="w")
        self.frame_table = tk.Frame(self, background="black")
        self.frame_table.grid_columnconfigure(1, weight=1)
        self.frame_table.grid_columnconfigure(2, weight=1)
        self.frame_table.grid_columnconfigure(3, weight=1)

        self.status.pack(side="bottom", fill="x")
        self.frame_table.pack(side="top", fill="x", padx=10, pady=10)

        for row_number, row_data in enumerate(info):
            no_1, code, value = row_data
            label = tk.Label(self.frame_table, text="row %d" % row_number, background="gray")
            col1  = tk.Label(self.frame_table, text=no_1)
            col2  = tk.Label(self.frame_table, text=code)
            col3  = tk.Label(self.frame_table, text=value)

            # N.B. 'value' is automatically passed to
            # the command by tkinter; we're adding
            # an extra parameter, 'row' 
            command=lambda value, row=row_number: self.ChoiceBox(value, row)
            stringvar = tk.StringVar(self.frame_table)
            stringvar.set("Fixed")
            option_menu = tk.OptionMenu(self.frame_table, stringvar, 
                                        "Fixed","List","Min","Max", 
                                        command=command)
            label.grid(row=row_number, column=0, sticky="nsew", padx=1, pady=1)
            col1.grid(row=row_number, column=1, sticky="nsew", padx=1, pady=1)
            col2.grid(row=row_number, column=2, sticky="nsew", padx=1, pady=1)
            col3.grid(row=row_number, column=3, sticky="nsew", padx=1, pady=1)
            option_menu.grid(row=row_number, column=6, sticky="nsew", 
                             padx=1, pady=1)

    def ChoiceBox(self, value, row_number):
        self.status.config(text="you set row %d to '%s'" % (row_number, value))

app = SampleApp()
app.mainloop()
于 2012-07-10T14:37:04.763 回答