2

大家好,提前感谢!

我已经在谷歌周围搜索并阅读了我得到的几乎所有结果,但我仍然无法弄清楚
,所以请至少给我指出一些方向!
我阅读了有关 pmw 的信息,但我想先看看是否有任何方法可以使用 tkinter。

我正在为 DnD 掷骰子编写一个足够简单的程序,并且我有一个 OptionMenu
,其中包含有人需要玩的一些骰子。我还有一个用于输入
默认选项中未包含的骰子的输入字段。我的问题是,即使新
选项添加​​成功,选项也没有排序。

我在某个时候通过在添加新选项时销毁 OptionMenu、
排序我的列表然后从头开始重建 OptionMenu 解决了这个问题,但当时我使用的是
place manager 方法,后来我不得不重写程序,因为我有
一些分辨率问题。我现在正在使用包管理器,
除非我想“重新”打包我所有的小部件或为它们制作专属标签,否则销毁/重建不是一种选择!

这是我的代码的工作示例:

from tkinter import *

class DropdownExample(Frame):
    def __init__(self, master = None):
        Frame.__init__(self, master)
        self.pack(fill = 'both', expand = True)

        # Add Option Button
        self.addOptBtn = Button(self, text = "Add Option", command = self.add_option)

        # Option Input Field
        self.newOpt = IntVar()
        self.newOpt.set("Type a number")

        self.optIn = Entry(self)
        self.optIn['textvariable'] = self.newOpt

        # Dropdown Menu
        self.myOptions = [0, 1, 2]

        self.selOpt = IntVar()
        self.selOpt.set("Options")

        self.optMenu = OptionMenu(self, self.selOpt, *self.myOptions)

        # Positioning
        self.addOptBtn.pack(side = 'left', padx = 5)
        self.optIn.pack(side = 'left', padx = 5)
        self.optMenu.pack(side = 'left', padx = 5)


    def add_option(self):
        self.numToAdd = ""
        self.counter = 0

        try:
            self.numToAdd = int(self.optIn.get())                                           # Integer validation

            while self.counter < len(self.myOptions):                                       # Comparison loop & error handling
                if self.numToAdd == self.myOptions[self.counter]:
                    print("Already exists!")                    
                    break;

                elif self.numToAdd < 0:
                    print("No less than 0!")
                    break;

                elif self.counter < len(self.myOptions)-1:
                    self.counter += 1

                else:                                                                       # Dropdown menu option addition
                    self.myOptions.append(self.numToAdd)
                    self.myOptions.sort()

                    self.optMenu['menu'].add_command(label = self.numToAdd)

                    self.selOpt.set(self.numToAdd)

                    print("Added succesfully!")

                    self.counter += 2

        except ValueError:
            print("Type ONLY numbers!")


def runme():
    app = DropdownExample()
    app.master.title("Dropdown Menu Example")
    app.master.resizable(0, 0)
    app.mainloop()

runme()

我在 Windows 7 上使用 Python 3.3

4

3 回答 3

1

中有一组insert_something() 方法Menu。您必须使用每个插入(bisect模块)对列表进行排序。

from tkinter import *
import bisect

...
                else:                                                                       # Dropdown menu option addition
                    index = bisect.bisect(self.myOptions, self.numToAdd)
                    self.myOptions.insert(index, self.numToAdd)
                    self.optMenu['menu'].insert_command(index, label=self.numToAdd)
                    self.selOpt.set(self.numToAdd)
                    print("Added succesfully!", self.myOptions)
                    self.counter += 2
于 2013-05-10T05:43:55.223 回答
0

换行:

self.optMenu['menu'].add_command(label = self.numToAdd)

和:

for dit in self.myOptions:
    self.optMenu['menu'].delete(0)
for dat in self.myOptions:
    self.optMenu['menu'].add_command(label = dat)

问题是“add_command”将项目添加到菜单中,而“delete”则获取项目的索引。

于 2013-05-10T21:25:57.950 回答
0

似乎无论我选择采用哪种方式,这一切都归结为更新
小部件。
如果需要,更新帧通常会重绘一部分或整个帧。
所以我回到了第一方。我销毁了小部件,更新了列表,然后再次创建了它。
至于位置,我只使用标签作为选项菜单的背景。
这样,我可以随意删除/替换我的 OptionMenu,而无需移动任何小部件,只要它留在标签内并且它是其中唯一的一个,当然只要我不移动任何标签。

这可能是一种解决方法,而不是解决方案,但它完成了工作,并且经过一些
优化,它可以用于任何其他具有相同问题的小部件。

from tkinter import *

class DropdownExample(Frame):
    def __init__(self, master = None):
        Frame.__init__(self, master)
        self.pack(fill = 'both', expand = True)

        # Add Option Button
        self.addOptBtn = Button(self, text = "Add Option", command = self.add_option)

        # Option Input Field
        self.newOpt = IntVar()
        self.newOpt.set("Type a number")

        self.optIn = Entry(self)
        self.optIn['textvariable'] = self.newOpt

        # Dropdown Menu
        # menu's label
        self.optMenuLabel = Label(self)

        # option menu
        self.myOptions = [0, 1, 2]

        self.selOpt = IntVar()
        self.selOpt.set("Options")

        self.optMenu = OptionMenu(self.optMenuLabel, self.selOpt, *self.myOptions)

        # Positioning
        self.addOptBtn.pack(side = 'left', padx = 5)
        self.optIn.pack(side = 'left', padx = 5)
        self.optMenuLabel.pack(side = 'left', padx = 5)
        self.optMenu.pack(side = 'left', padx = 5)


    def add_option(self):
        self.numToAdd = ""
        self.counter = 0

        try:
            self.numToAdd = int(self.optIn.get())                                           # Integer validation

            while self.counter < len(self.myOptions):                                       # Comparison loop & error handling
                if self.numToAdd == self.myOptions[self.counter]:
                    print("Already exists!")                    
                    break;

                elif self.numToAdd < 0:
                    print("No less than 0!")
                    break;

                elif self.counter < len(self.myOptions)-1:
                    self.counter += 1

                else:                                                                       # Dropdown menu option addition
                    self.myOptions.append(self.numToAdd)
                    self.myOptions.sort()

                    self.selOpt.set(self.numToAdd)

                    self.optMenu.destroy()
                    self.optMenu = OptionMenu(self.optMenuLabel, self.selOpt, *self.myOptions)
                    self.optMenu.pack(side = 'left', padx = 5)

                    print("Added succesfully!", self.myOptions)
                    break;

        except ValueError:
            print("Type ONLY numbers!")


def runme():
    app = DropdownExample()
    app.master.title("Dropdown Menu Example")
    app.master.resizable(0, 0)
    app.mainloop()

runme()
于 2013-05-11T17:42:56.073 回答