Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/google-sheets/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
如何使菜单选项在WxPython中执行不同的操作?_Python_Menu_Wxpython - Fatal编程技术网

如何使菜单选项在WxPython中执行不同的操作?

如何使菜单选项在WxPython中执行不同的操作?,python,menu,wxpython,Python,Menu,Wxpython,我的WxPython菜单有问题!在文件头中,我有“文件”和两个选项,“保存”和“关闭”…当我单击“保存”时,我希望它打印“已保存”,当我时钟退出时,应用程序应打印“已关闭”并关闭…但如果我甚至单击“保存”,它将关闭!你能帮我吗。以下是我代码的一部分: menubar=wx.menubar() fileMenu=wx.Menu() menubar.Append(文件菜单“&File”) m1=fileMenu.Append(wx.ID_退出“保存”) self.Bind(wx.EVT_菜单,sel

我的WxPython菜单有问题!在文件头中,我有“文件”和两个选项,“保存”和“关闭”…当我单击“保存”时,我希望它打印“已保存”,当我时钟退出时,应用程序应打印“已关闭”并关闭…但如果我甚至单击“保存”,它将关闭!你能帮我吗。以下是我代码的一部分:

menubar=wx.menubar()
fileMenu=wx.Menu()
menubar.Append(文件菜单“&File”)
m1=fileMenu.Append(wx.ID_退出“保存”)
self.Bind(wx.EVT_菜单,self.OnSave,m1)
m2=fileMenu.Append(wx.ID\u退出“退出”)
self.Bind(wx.EVT_菜单,self.OnQuit,m2)
self.SetMenuBar(menubar)
以及功能:

def OnSave(自我,事件):
text=self.text\u ctrl.GetValue()
文件写入(文本)
打印(“保存的文件”)
def OnQuit(自我,事件):
打印(“已关闭”)
self.Close()

fileMenu.Append的第一个参数很重要。它用于区分一个菜单项和另一个菜单项,但您对这两个菜单项使用了相同的值

    m1 = fileMenu.Append(wx.ID_SAVE, 'Save')
    self.Bind(wx.EVT_MENU, self.OnSave, m1)
    
    m2 = fileMenu.Append(wx.ID_EXIT, 'Quit')
    self.Bind(wx.EVT_MENU, self.OnQuit, m2)
在我的程序中,我更喜欢使用wx.NewId()从系统中获取免费id。如果您有这些“库存”菜单项,则ID_SAVE和ID_EXIT非常有意义,但如果您有自己的条目,则可以执行以下操作:

    m3 = fileMenu.Append(wx.NewId(), 'My own menu item')
    self.Bind(wx.EVT_MENU, self.OnMyOwnFunction, m3)
    m4 = fileMenu.Append (wx.NewId(), 'Another menu item')
    self.Bind(wx.EVT_MENU, self.OnAnotherFunction, m4)

fileMenu.Append的第一个参数很重要。它用于区分一个菜单项和另一个菜单项,但您对这两个菜单项使用了相同的值

    m1 = fileMenu.Append(wx.ID_SAVE, 'Save')
    self.Bind(wx.EVT_MENU, self.OnSave, m1)
    
    m2 = fileMenu.Append(wx.ID_EXIT, 'Quit')
    self.Bind(wx.EVT_MENU, self.OnQuit, m2)
在我的程序中,我更喜欢使用wx.NewId()从系统中获取免费id。如果您有这些“库存”菜单项,则ID_SAVE和ID_EXIT非常有意义,但如果您有自己的条目,则可以执行以下操作:

    m3 = fileMenu.Append(wx.NewId(), 'My own menu item')
    self.Bind(wx.EVT_MENU, self.OnMyOwnFunction, m3)
    m4 = fileMenu.Append (wx.NewId(), 'Another menu item')
    self.Bind(wx.EVT_MENU, self.OnAnotherFunction, m4)

您对两个菜单项使用相同的
Id
,即
wx.Id\u EXIT
,正如@Petr Blahos所指出的,这会导致您的问题。
然而,Petr的回答存在一个问题,尽管在技术上是正确的,
wx.NewId
现在已被弃用
,尽管它仍然有效,但已被
wx.NewIdRef
取代

wx.NewId()
Generates an integer identifier unique to this run of the program.

Return type
int

Deprecated IDs generated by this function can possibly conflict with IDs used elsewhere in the application code. It is recommended to instead use the wx.ID_ANY ID to assign generated IDs for the controls, menu items and etc. that you create in the application. These IDs are guaranteed to not conflict with the other IDs that are in use in the application. For those cases where you need to create an ID that can be used more than once then please see wx.NewIdRef.

wx.NewIdRef(count=1)
Reserves a new Window ID (or range of WindowIDs) and returns a wx.WindowIDRef object (or list of them) that will help manage the reservation of that ID.

This function is intended to be a drop-in replacement of the old and deprecated wx.NewId function, with the added benefit that the ID should never conflict with an in-use ID or other IDs generated by this function.
wx.NewIdRef
还具有一个
count
功能,因此它可用于
获取所需的一组id。i、 e

>>> myIds = wx.NewIdRef(count=6)
>>> myIds
[WindowIDRef: -31973, WindowIDRef: -31972, WindowIDRef: -31971, WindowIDRef: -31970, WindowIDRef: -31969, WindowIDRef: -31968]
>>> useId = myIds[3].Id
>>> useId
-31970
请注意,
wx.NewIdRef
wx.ID\u ANY
-1
都可以在此菜单上下文中使用。请参见以下简单示例:

import wx

class Test(wx.Frame):

    def __init__(self,parent):
        wx.Frame.__init__(self,parent,title="Frame aka Window",size = (300,200))
        panel = wx.Panel(self)
        self.status=self.CreateStatusBar()
        self.status.SetStatusText("Status bar text")
        menubar=wx.MenuBar()
        firstm=wx.Menu()
        secondm=wx.Menu()

        fm1 = wx.MenuItem(firstm, wx.NewIdRef(), 'New Window\tAlt+N')
        firstm.Append(fm1)
        self.Bind(wx.EVT_MENU, self.OnMenu1, id=fm1.GetId())
        fm2 = wx.MenuItem(firstm, wx.NewIdRef(), 'Open', "Text for the statusbar")
        firstm.Append(fm2)
        self.Bind(wx.EVT_MENU, self.OnMenu2, id=fm2.GetId())
        fm3 = wx.MenuItem(firstm, -1, 'Quit\tAlt+Q')
        firstm.Append(fm3)
        self.Bind(wx.EVT_MENU, self.OnMenu3, id=fm3.GetId())

        sm1 = wx.MenuItem(firstm, wx.ID_ANY, 'Re-Do', "Statusbar Re-Do")
        secondm.Append(sm1)
        self.Bind(wx.EVT_MENU, self.OnsMenu1, id=sm1.GetId())
        sm2 = wx.MenuItem(secondm, wx.ID_ANY, 'Un-Do', "Statusbar Un-Do")
        secondm.Append(sm2)
        self.Bind(wx.EVT_MENU, self.OnsMenu2, id=sm2.GetId())

        menubar.Append(firstm,"File")
        menubar.Append(secondm,"Edit")

        self.SetMenuBar(menubar)

        t = wx.StaticText(panel,-1,"Hello i'm a test", pos=(10,20))

    def OnMenu1(self, event):
        print("Menu item 1",event.GetId())

    def OnMenu2(self, event):
        print("Menu item 2",event.GetId())
        
    def OnMenu3(self, event):
        print("Menu item 3 Quit",event.GetId())
        self.Destroy()
                
    def OnsMenu1(self, event):
        print("2nd Menu item 1",event.GetId())

    def OnsMenu2(self, event):
        print("2nd Menu item 2",event.GetId())

if __name__=='__main__':
    app=wx.App()
    frame=Test(None)
    frame.Show()
    app.MainLoop()

您对两个菜单项使用相同的
Id
,即
wx.Id\u EXIT
,正如@Petr Blahos所指出的,这会导致您的问题。
然而,Petr的回答存在一个问题,尽管在技术上是正确的,
wx.NewId
现在已被弃用
,尽管它仍然有效,但已被
wx.NewIdRef
取代

wx.NewId()
Generates an integer identifier unique to this run of the program.

Return type
int

Deprecated IDs generated by this function can possibly conflict with IDs used elsewhere in the application code. It is recommended to instead use the wx.ID_ANY ID to assign generated IDs for the controls, menu items and etc. that you create in the application. These IDs are guaranteed to not conflict with the other IDs that are in use in the application. For those cases where you need to create an ID that can be used more than once then please see wx.NewIdRef.

wx.NewIdRef(count=1)
Reserves a new Window ID (or range of WindowIDs) and returns a wx.WindowIDRef object (or list of them) that will help manage the reservation of that ID.

This function is intended to be a drop-in replacement of the old and deprecated wx.NewId function, with the added benefit that the ID should never conflict with an in-use ID or other IDs generated by this function.
wx.NewIdRef
还具有一个
count
功能,因此它可用于
获取所需的一组id。i、 e

>>> myIds = wx.NewIdRef(count=6)
>>> myIds
[WindowIDRef: -31973, WindowIDRef: -31972, WindowIDRef: -31971, WindowIDRef: -31970, WindowIDRef: -31969, WindowIDRef: -31968]
>>> useId = myIds[3].Id
>>> useId
-31970
请注意,
wx.NewIdRef
wx.ID\u ANY
-1
都可以在此菜单上下文中使用。请参见以下简单示例:

import wx

class Test(wx.Frame):

    def __init__(self,parent):
        wx.Frame.__init__(self,parent,title="Frame aka Window",size = (300,200))
        panel = wx.Panel(self)
        self.status=self.CreateStatusBar()
        self.status.SetStatusText("Status bar text")
        menubar=wx.MenuBar()
        firstm=wx.Menu()
        secondm=wx.Menu()

        fm1 = wx.MenuItem(firstm, wx.NewIdRef(), 'New Window\tAlt+N')
        firstm.Append(fm1)
        self.Bind(wx.EVT_MENU, self.OnMenu1, id=fm1.GetId())
        fm2 = wx.MenuItem(firstm, wx.NewIdRef(), 'Open', "Text for the statusbar")
        firstm.Append(fm2)
        self.Bind(wx.EVT_MENU, self.OnMenu2, id=fm2.GetId())
        fm3 = wx.MenuItem(firstm, -1, 'Quit\tAlt+Q')
        firstm.Append(fm3)
        self.Bind(wx.EVT_MENU, self.OnMenu3, id=fm3.GetId())

        sm1 = wx.MenuItem(firstm, wx.ID_ANY, 'Re-Do', "Statusbar Re-Do")
        secondm.Append(sm1)
        self.Bind(wx.EVT_MENU, self.OnsMenu1, id=sm1.GetId())
        sm2 = wx.MenuItem(secondm, wx.ID_ANY, 'Un-Do', "Statusbar Un-Do")
        secondm.Append(sm2)
        self.Bind(wx.EVT_MENU, self.OnsMenu2, id=sm2.GetId())

        menubar.Append(firstm,"File")
        menubar.Append(secondm,"Edit")

        self.SetMenuBar(menubar)

        t = wx.StaticText(panel,-1,"Hello i'm a test", pos=(10,20))

    def OnMenu1(self, event):
        print("Menu item 1",event.GetId())

    def OnMenu2(self, event):
        print("Menu item 2",event.GetId())
        
    def OnMenu3(self, event):
        print("Menu item 3 Quit",event.GetId())
        self.Destroy()
                
    def OnsMenu1(self, event):
        print("2nd Menu item 1",event.GetId())

    def OnsMenu2(self, event):
        print("2nd Menu item 2",event.GetId())

if __name__=='__main__':
    app=wx.App()
    frame=Test(None)
    frame.Show()
    app.MainLoop()

谢谢我真的很感谢你的帮助!!谢谢我真的很感谢你的帮助!!