从wxPython事件指针中调用函数

2024-10-01 07:19:40 发布

您现在位置:Python中文网/ 问答频道 /正文

我正在努力寻找从wxPython事件处理程序函数中使用函数的方法。假设我有一个按钮,当单击它时,它使用事件处理程序运行一个名为OnRun的函数。但是,用户忘记在OnRun按钮之前单击一个radion按钮,我想弹出一个消息对话框,告诉他们他们忘记了一个步骤。我将多次重用这个MessageDialog,因此我不想复制/粘贴相同的代码,我只希望在函数中包含这个MessageDialog,如果用户忘记检查一个RadioButton,就调用这个MessageDialog函数。在

如果这不是一个在事件处理程序中使用的函数,我知道我可以简单地将函数作为一个参数,但是我看不到用这些函数来实现这个目的的方法。如有任何帮助,我们将不胜感激。在


Tags: 方法函数用户程序运行消息处理程序粘贴wxpython
3条回答

即使我也会直截了当地回答。我会在封闭的框架中设置一个属性来标记单选按钮是否被点击。然后当调用OnRun时,请检查该属性。如果它处于错误的状态,请调用MessageDialog并中止/暂停/修改OnRun。在

编辑这是我的意思,一个有两个按钮的简单示例,除非单击用户协议,否则这两个按钮都不会导致进一步的操作。在

import wx

class ButtonFrame(wx.Frame):
    def __init__(self):
        wx.Frame.__init__(self, None, -1, 'Button Example', 
                          size=(300, 100))
        panel = wx.Panel(self, -1)
        self.radio = wx.RadioButton(panel, -1, "Accept user agreement", pos=(50, 10))
        self.button = wx.Button(panel, -1, "Run", pos=(50, 30))
        self.Bind(wx.EVT_BUTTON, self.OnRun, self.button)
        self.button.SetDefault()
        self.btn2 = wx.Button(panel, -1, "Walk", pos=(150, 30))
        self.Bind(wx.EVT_BUTTON, self.OnWalk, self.btn2)

    def OnRun(self, event):
        if not self.CheckRadio():
            return
        self.button.SetLabel("Running")

    def OnWalk(self, event):
        if not self.CheckRadio():
            return
        self.btn2.SetLabel("Walking")

    def CheckRadio(self):
        accepted = self.radio.GetValue()
        if not accepted:
            dlg = wx.MessageDialog(None, 'First accept the user agreement',
                                  'MessageDialog', wx.OK | wx.ICON_QUESTION)
            result = dlg.ShowModal() # result not used in this demo
            dlg.Destroy()
            return False
        else:
            return True

if __name__ == '__main__':
    app = wx.PySimpleApp()
    frame = ButtonFrame()
    frame.Show()
    app.MainLoop()

代码改编自wxPython in Action的清单7.11。如果你在过去的时间里还没有解决这个问题,我希望这能有所帮助。在

下面的代码演示如何创建一个小方法,您可以重用它来显示自定义对话框,并告诉用户他们需要接受协议。当然,你可以改变条件来做任何你想做的事。你可以改变“showMsg”方法,这样图标也会改变,只需稍作调整。在

import wx

########################################################################
class TestFrame(wx.Frame):
    """"""

    #                                   
    def __init__(self):
        """Constructor"""
        wx.Frame.__init__(self, None, title="Test")

        panel = wx.Panel(self)
        self.radios = wx.RadioBox(panel, label="Choices",
                                  choices = ["None", "Accept", "Reject"])

        button = wx.Button(panel, label="Run")
        button.Bind(wx.EVT_BUTTON, self.onBtn)

        sizer = wx.BoxSizer(wx.VERTICAL)
        sizer.Add(self.radios, 0, wx.ALL, 5)
        sizer.Add(button, 0, wx.ALL, 5)
        panel.SetSizer(sizer)

    #                                   
    def onBtn(self, event):
        """"""
        btn = event.GetEventObject()
        btn.SetLabel("Running")
        radio_value = self.radios.GetStringSelection()
        if radio_value == "None":
            self.showMsg("Error", "Please Choose 'Accept' or 'Reject'!")
        elif radio_value == "Accept":
            self.showMsg("Message", "Thank you for accepting!")
        else:
            self.showMsg("Message", "We're sorry, but you cannot continue the install")

    #                                   
    def showMsg(self, title, msg):
        """"""
        dlg = wx.MessageDialog(None, msg, title, wx.OK | wx.ICON_QUESTION)
        dlg.ShowModal()
        dlg.Destroy()



if __name__ == "__main__":
    app = wx.App(False)
    frame = TestFrame()
    frame.Show()
    app.MainLoop()

您可以创建自己的MessageDialog(继承),也可以使用functools.partial/lambda将附加参数传递给事件处理程序:

self.Bind(wx.MY_EVENT, lambda evt: self.OnEventX(evt, handler=foo), id=12)

相关问题 更多 >