今天用wxPython写一个输入关键词自动生成文章工具,设置部分需要用模式对话框来打开设置界面。下面介绍wxPython Modal Dialog模式对话框:

1. Modal Dialog(模式对话框)

A modal dialog blocks other widgets from receiving user events until it is closed;

in other words, it places the user in dialog mode for the duration of its existence.

模式对话框阻塞了别的窗口部件接收用户事件,直到该模式对话框被关闭。

严格来说,dialog 与 frame 在外观上没有区别,只是处理事件(event)的方式不一样。

通常,dialog 在外观上要稍微简单一点,所以很少使用 wx.Panel。

wx.Dialog 具备 wx.Panel 的性质,widgets 一般直接添加到 wx.Dialog 中即可。

# -*- coding: utf-8 -*- 
 
import wx 
import wx.xrc 
import json 
import os 
 
########################################################################### 
## Class MyDialog2 
########################################################################### 
 
class MySettingDialog(wx.Dialog): 
    def __init__(self, parent): 
        wx.Dialog.__init__(self, parent, id=wx.ID_ANY, title=u"设置", pos=wx.DefaultPosition, size=wx.Size(350, 235), 
                           style=wx.DEFAULT_DIALOG_STYLE) 
 
        self.SetSizeHints(wx.DefaultSize, wx.DefaultSize) 
 
        bSizer3 = wx.BoxSizer(wx.VERTICAL) 
 
        wSizer3 = wx.WrapSizer(wx.HORIZONTAL, wx.WRAPSIZER_DEFAULT_FLAGS) 
 
        self.m_staticText45 = wx.StaticText(self, wx.ID_ANY, u"智能写作API:", wx.DefaultPosition, wx.DefaultSize, 0) 
        self.m_staticText45.Wrap(-1) 
 
        wSizer3.Add(self.m_staticText45, 0, wx.ALL | wx.ALIGN_CENTER_VERTICAL, 10) 
 
        self.m_textCtrl2 = wx.TextCtrl(self, wx.ID_ANY, wx.EmptyString, wx.DefaultPosition, wx.Size(215, -1), 0) 
        wSizer3.Add(self.m_textCtrl2, 0, wx.ALL | wx.ALIGN_CENTER_VERTICAL, 5) 
 
        bSizer3.Add(wSizer3, 0, 0, 5) 
 
        wSizer4 = wx.WrapSizer(wx.HORIZONTAL, wx.WRAPSIZER_DEFAULT_FLAGS) 
 
        self.m_staticText46 = wx.StaticText(self, wx.ID_ANY, u"自动排版API:", wx.DefaultPosition, wx.DefaultSize, 0) 
        self.m_staticText46.Wrap(-1) 
 
        wSizer4.Add(self.m_staticText46, 0, wx.ALL | wx.ALIGN_CENTER_VERTICAL, 10) 
 
        self.m_textCtrl3 = wx.TextCtrl(self, wx.ID_ANY, wx.EmptyString, wx.DefaultPosition, wx.Size(215, -1), 0) 
        wSizer4.Add(self.m_textCtrl3, 0, wx.ALL | wx.ALIGN_CENTER_VERTICAL, 5) 
 
        bSizer3.Add(wSizer4, 0, 0, 5) 
 
        wSizer5 = wx.WrapSizer(wx.HORIZONTAL, wx.WRAPSIZER_DEFAULT_FLAGS) 
 
        self.m_staticText47 = wx.StaticText(self, wx.ID_ANY, u"智能标题API:", wx.DefaultPosition, wx.DefaultSize, 0) 
        self.m_staticText47.Wrap(-1) 
 
        wSizer5.Add(self.m_staticText47, 0, wx.ALL | wx.ALIGN_CENTER_VERTICAL, 10) 
 
        self.m_textCtrl4 = wx.TextCtrl(self, wx.ID_ANY, wx.EmptyString, wx.DefaultPosition, wx.Size(215, -1), 0) 
        wSizer5.Add(self.m_textCtrl4, 0, wx.ALL | wx.ALIGN_CENTER_VERTICAL, 5) 
 
        bSizer3.Add(wSizer5, 0, 0, 5) 
 
        wSizer6 = wx.WrapSizer(wx.HORIZONTAL, wx.WRAPSIZER_DEFAULT_FLAGS) 
 
        self.m_button1 = wx.Button(self, wx.ID_ANY, u"取消", wx.DefaultPosition, wx.DefaultSize, 0) 
        wSizer6.Add(self.m_button1, 0, wx.ALL, 10) 
 
        self.m_button2 = wx.Button(self, wx.ID_ANY, u"保存", wx.DefaultPosition, wx.DefaultSize, 0) 
        wSizer6.Add(self.m_button2, 0, wx.ALL, 10) 
 
        bSizer3.Add(wSizer6, 0, wx.ALIGN_RIGHT, 5) 
 
        wSizer7 = wx.WrapSizer(wx.HORIZONTAL, wx.WRAPSIZER_DEFAULT_FLAGS) 
 
        self.m_staticText48 = wx.StaticText(self, wx.ID_ANY, u"API说明请访问小发猫官网。", wx.DefaultPosition, wx.DefaultSize, 0) 
        self.m_staticText48.Wrap(-1) 
 
        wSizer7.Add(self.m_staticText48, 0, wx.ALL | wx.ALIGN_CENTER_VERTICAL, 10) 
 
        bSizer3.Add(wSizer7, 0, 0, 5) 
 
        self.SetSizer(bSizer3) 
        self.Layout() 
 
        self.Centre(wx.BOTH) 
        self.filename = 'config.json' 
        self.make_sure_config_exists() 
        self.read_config() 
 
        self.m_button1.Bind(wx.EVT_LEFT_UP, self.m_button1OnLeftUp) 
        self.m_button2.Bind(wx.EVT_LEFT_UP, self.m_button2OnLeftUp) 
        self.Bind(wx.EVT_CLOSE, self.OnClose) 
 
    def __del__(self): 
        pass 
 
 
    def OnClose(self, event): 
        self.Destroy() 
 
    # Virtual event handlers, overide them in your derived class 
    def m_button2OnLeftUp(self, event): 
        rewrite_url = self.m_textCtrl2.GetValue() 
        title_url = self.m_textCtrl4.GetValue() 
        type_url = self.m_textCtrl3.GetValue() 
        self.save_config(rewrite_url, title_url, type_url) 
        self.OnClose(event) 
        #event.Skip() 
 
    def m_button1OnLeftUp(self, event): 
        self.OnClose(event) 
        #event.Skip() 
 
    def read_config(self): 
        with open(self.filename, "r") as f: 
            ajson = json.load(f) 
            load_dict = json.loads(ajson) 
            print(load_dict) 
            self.m_textCtrl2.SetValue(load_dict['rewrite']) 
            self.m_textCtrl4.SetValue(load_dict['title']) 
            self.m_textCtrl3.SetValue(load_dict['type']) 
 
 
    def save_config(self, rewrite, title, type): 
        dict_var = { 
            'rewrite': rewrite, 
            'title': title, 
            'type': type 
        } 
        new_dict = json.dumps(dict_var) 
        with open(self.filename, "w") as f: 
            json.dump(new_dict, f) 
 
 
    def make_sure_config_exists(self): 
        filename = self.filename 
        if os.path.exists(filename): 
            return True 
        else: 
            save_config('', '', '') 
 
        return True 
 
''' 
app = wx.App(False) 
dlg = MySettingDialog(None) 
dlg.Show() 
app.MainLoop() 
''' 

  

2. 展示与关闭 Dialog
Modal Dialog 与 普通的 Frame 用法略有差别。

最简单的示例代码如下:

import wx 
 
class SubclassDialog(wx.Dialog): 
    def __init__(self): 
        wx.Dialog.__init__(self, None, -1, 'Dialog Subclass', size=(300, 100)) 
        okButton = wx.Button(self, wx.ID_OK, "OK", pos=(15, 15)) 
        okButton.SetDefault() 
        cancelButton = wx.Button(self, wx.ID_CANCEL, "Cancel", pos=(115, 15)) 
 
if __name__ == '__main__': 
    app = wx.PySimpleApp() 
    dialog = SubclassDialog() 
    result = dialog.ShowModal() 
    if result == wx.ID_OK: 
        print "OK" 
    else: 
        print "Cancel" 
    dialog.Destroy() 

2.1 展示 Dialog

展示 Dialog 使用 ShowModal(),程序会等待 ShowModal() 执行结束并获取其返回值。

此时,Dialog 是 wxPython 应用接受用户事件的唯一组件。其他应用不受影响。

2.2 结束 Dialog Mode

调用 EndModal(retCode) 方法可以关闭(close)Dialog Mode,retCode 是 int 值,被 ShowModal() 返回。

此时,只是结束了 Dialog Mode,并未摧毁 Dialog。可以在其他地方继续展示该 Dialog。

通常在 event 的 handler 中调用 EndModal()。

2.3 摧毁 Dialog

调用 Destroy() 方法

2.4 典型用法

dialog = SubclassDialog() 
result = dialog.ShowModal()  # 展示对话框,并等待结果 
if result == wx.ID_OK:  # 判断结果,并执行相应处理 
    print "OK" 
else: 
    print "Cancel" 
dialog.Destroy()  # 摧毁 Dialog 

  

2.5 自定义 event 的 handler,一般需要调用 EndModal()

例如,用于连接数据库的 handler 实现如下:

def OnConnect(self, event=None): 
    host = self.input_host.GetValue() 
    port = int(self.input_port.GetValue()) 
    if db.connect(host, port):  # connected 
        self.EndModal(wx.ID_OK) 
    else: 
        msg_error = 'Error connecting to host(%s)' % host 
        wx.MessageBox(msg_error, 'Error', wx.OK | wx.ICON_ERROR) 

  

我的其他文章:

python字符串中字符出现次数(python获取字符串个数)

小发猫AI标题自动生成神器,人工智能能做的东西有很多

从学习python到用wxpython编写接口和客户端

不要再纠结Python哪个版本好,2020年用Python3就对了

为什么用Python,高级的Python是一种高级编程语言


评论关闭
IT干货网

微信公众号号:IT虾米 (左侧二维码扫一扫)欢迎添加!

python @修饰符,这篇文章写得明明白白的