用Python创建一个Doubletalk浏览器
Ok, 现在让我们做些有用的东西,用这种方法学习更多关于wxPython框架的知识。就象其它的GUI工具包所展示的,我们将创建一个小型的应用程序,围绕着D oubletalk类库(它允许浏览和编辑交易)。
MDI框架
我们打算实现一个多文档界面(译注,即MDI),子框架除了为独立的“文档”外,其中还包含着交易数据的不同视图。如同前面的例子,要做的第一件事就是创建一个应用程序类,并且在它的O nInit方法中创
建一个主框架:
from wxPython.wx import *
class DoubleTalkBrowserApp(wxApp):
def OnInit(self):
frame = MainFrame(NULL)
frame.Show(true)
self.SetTopWindow(frame)
return true
app = DoubleTalkBrowserApp(0)
app.MainLoop()
因为我们正在使用MDI,所以需要一个特别的类用来做为框架的基本类。这里的给出主程序框架的初始化方法的代码:
class MainFrame(wxMDIParentFrame):
title = "Doubletalk Browser - wxPython Edition"
def __init__(self, parent):
wxMDIParentFrame.__init__(self, parent, -1, self.title)
self.bookset = None
self.views = []
if wxPlatform == ’__WXMSW__’:
self.icon = wxIcon(’chart7.ico’, wxBITMAP_TYPE_ICO)
self.SetIcon(self.icon)
# 创建一个状态条,在右边显示时间和日期
sb = self.CreateStatusBar(2)
sb.SetStatusWidths([-1, 150])
self.timer = wxPyTimer(self.Notify)
self.timer.Start(1000)
self.Notify()
menu = self.MakeMenu(false)
self.SetMenuBar(menu)
menu.EnableTop(1, false)
EVT_MENU(self, ID_OPEN, self.OnMenuOpen)
EVT_MENU(self, ID_CLOSE, self.OnMenuClose)
EVT_MENU(self, ID_SAVE, self.OnMenuSave)
EVT_MENU(self, ID_SAVEAS,self.OnMenuSaveAs)
EVT_MENU(self, ID_EXIT, self.OnMenuExit)
EVT_MENU(self, ID_ABOUT, self.OnMenuAbout)
EVT_MENU(self, ID_ADD, self.OnAddTrans)
EVT_MENU(self, ID_JRNL, self.OnViewJournal)
EVT_MENU(self, ID_DTAIL, self.OnViewDetail)
EVT_CLOSE(self, self.OnCloseWindow)
图4显示了到现在应用程序的状态。
图4. 第一个MDI wxPython程序
很明显,我们没有展示全部的代码,但是随着我们一点一点地学习,我们将最终将其变得完整。
注意,使用wxMDIParentFrame作为MainFrame的基类。通过使用这个类,你会自动地获得为实现MDI应用程序的所有需要的东西,不需要关心在外表后面发生了什么。w xMDIParentFrame 类有着与wxFrame类同样的接口,只是拥有一些额外的方法。通常将一个单文档接口程序改为一个多文档程序只是象改变应用程序派生类的基类一样容易。对于w xMDIParentFrame 类,存在相对应的wxMDIChildFrame类,用于作文档窗口,在后面就会看到。如果你需要处理MDI父窗口的客户区域(或背景区域),你可以使用 w xMDIClientWindow类。你可以使用它来在所有子窗口的后面放置一个背景图像。
在文件对话框成功完成之后,要做的第一件事就是询问对话框被选中的路径名是什么,然后使用这个路径来修改框架的标题,然后打开一个B ookSet文件。
看一下后面一行。它重新使BookSet菜单有效,因为现在已经存在一个打开文件了。它实际是两行语句合成一句,相当于这两行:
menu = self.GetMenuBar()
menu.EnableTop(1, true)
因为当用户打开一个文件时,让他们确实地看到一些东西是有意义的,你应该创建并且显示其中一个视图,用上面的OnMenuOpen处理函数中最后几行代码。在下面,我们会看到。
wxListCtrl
日志视图是由wxListCtrl组成,其中每一个交易都有一个单行的小计。这个控件放置在wxMDIChildFrame中,并且因为它是框架中唯一的东西,所以不用担心设置或维护大小,框架会自动维护它。(不幸地是,因为某些平台在不同的时间发送第一个改变大小(r esize)事件,有时候窗口显示时,它的子窗口大小会不正确。)
class JournalView(wxMDIChildFrame):
def __init__(self, parent, bookset, editID):
wxMDIChildFrame.__init__(self, parent, -1, "")
self.bookset = bookset
self.parent = parent
tID = wxNewId()
self.lc = wxListCtrl(self, tID, wxDefaultPosition,
wxDefaultSize, wxLC_REPORT)
## Forces a resize event to get around a minor bug...
self.SetSize(self.GetSize())
self.lc.InsertColumn(0, "Date")
self.lc.InsertColumn(1, "Comment")
self.lc.InsertColumn(2, "Amount")
self.currentItem = 0
EVT_LIST_ITEM_SELECTED(self, tID, self.OnItemSelected)
EVT_LEFT_DCLICK(self.lc, self.OnDoubleClick)
menu = parent.MakeMenu(true)
self.SetMenuBar(menu)
EVT_MENU(self, editID, self.OnEdit)
EVT_CLOSE(self, self.OnCloseWindow)
self.UpdateView()
图6 显示出应用程序处理的很好,并且看上去象一个正规的Windows应用程序。