zoukankan      html  css  js  c++  java
  • wxPython的使用--类似画板的界面

    # -*- coding: utf-8 -*-
    import wx
    import wx.lib.buttons
    import cPickle
    import os


    class PaintWindow(wx.Window):
    def __init__(self, parent, id):
    wx.Window.__init__(self, parent, id)
    self.SetBackgroundColour("Red")
    self.color = "Green"
    self.thickness = 10

    self.pen = wx.Pen(self.color, self.thickness, wx.SOLID)
    self.lines = []
    self.curLine = []
    self.pos = (0, 0)
    self.InitBuffer()

    self.Bind(wx.EVT_LEFT_DOWN, self.OnLeftDown)
    self.Bind(wx.EVT_LEFT_UP, self.OnLeftUp)
    self.Bind(wx.EVT_MOTION, self.OnMotion)
    self.Bind(wx.EVT_SIZE, self.OnSize)
    self.Bind(wx.EVT_IDLE, self.OnIdle)
    self.Bind(wx.EVT_PAINT, self.OnPaint)

    def InitBuffer(self):
    size = self.GetClientSize()

    self.buffer = wx.EmptyBitmap(size.width, size.height)
    dc = wx.BufferedDC(None, self.buffer)

    dc.SetBackground(wx.Brush(self.GetBackgroundColour()))
    dc.Clear()
    self.DrawLines(dc)
    self.reInitBuffer = False

    def GetLinesData(self):
    return self.lines[:]

    def SetLinesData(self, lines):
    self.lines = lines[:]
    self.InitBuffer()
    self.Refresh()

    def OnLeftDown(self, event):
    self.curLine = []
    self.pos = event.GetPositionTuple()
    self.CaptureMouse()

    def OnLeftUp(self, event):
    if self.HasCapture():
    self.lines.append((self.color,
    self.thickness,
    self.curLine))
    self.curLine = []
    self.ReleaseMouse()

    def OnMotion(self, event):
    if event.Dragging() and event.LeftIsDown():
    dc = wx.BufferedDC(wx.ClientDC(self), self.buffer)
    self.drawMotion(dc, event)
    event.Skip()

    def drawMotion(self, dc, event):
    dc.SetPen(self.pen)
    newPos = event.GetPositionTuple()
    coords = self.pos + newPos
    self.curLine.append(coords)
    dc.DrawLine(*coords)
    self.pos = newPos

    def OnSize(self, event):
    self.reInitBuffer = True

    def OnIdle(self, event):
    if self.reInitBuffer:
    self.InitBuffer()
    self.Refresh(False)

    def OnPaint(self, event):
    dc = wx.BufferedPaintDC(self, self.buffer)

    def DrawLines(self, dc):
    for colour, thickness, line in self.lines:
    pen = wx.Pen(colour, thickness, wx.SOLID)
    dc.SetPen(pen)
    for coords in line:
    dc.DrawLine(*coords)

    def SetColor(self, color):
    self.color = color
    self.pen = wx.Pen(self.color, self.thickness, wx.SOLID)

    def SetThickness(self, num):
    self.thickness = num
    self.pen = wx.Pen(self.color, self.thickness, wx.SOLID)


    class PaintFrame(wx.Frame):
    def __init__(self, parent):
    self.title = "Paint Frame"
    wx.Frame.__init__(self, parent, -1, self.title, size=(800, 600))
    self.paint = PaintWindow(self, -1)

    self.paint.Bind(wx.EVT_MOTION, self.OnPaintMotion)
    self.InitStatusBar()

    self.CreateMenuBar()

    self.filename = ""

    self.CreatePanel()

    def CreatePanel(self):
    controlPanel = ControlPanel(self, -1, self.paint)
    box = wx.BoxSizer(wx.HORIZONTAL)
    box.Add(controlPanel, 0, wx.EXPAND)
    box.Add(self.paint, -1, wx.EXPAND)
    self.SetSizer(box)

    def InitStatusBar(self):
    self.statusbar = self.CreateStatusBar()
    self.statusbar.SetFieldsCount(3)
    self.statusbar.SetStatusWidths([-1, -2, -3])

    def OnPaintMotion(self, event):

    self.statusbar.SetStatusText(u"鼠标位置:" + str(event.GetPositionTuple()), 0)

    self.statusbar.SetStatusText(u"当前线条长度:%s" % len(self.paint.curLine), 1)

    self.statusbar.SetStatusText(u"线条数目:%s" % len(self.paint.lines), 2)

    event.Skip()

    def MenuData(self):

    return [("&File", (
    ("&New", "New paint file", self.OnNew),
    ("&Open", "Open paint file", self.OnOpen),
    ("&Save", "Save paint file", self.OnSave),
    ("", "", ""),
    ("&Color", (
    ("&Black", "", self.OnColor, wx.ITEM_RADIO),
    ("&Red", "", self.OnColor, wx.ITEM_RADIO),
    ("&Green", "", self.OnColor, wx.ITEM_RADIO),
    ("&Blue", "", self.OnColor, wx.ITEM_RADIO),
    ("&Other", "", self.OnOtherColor, wx.ITEM_RADIO))),
    ("", "", ""),
    ("&Quit", "Quit", self.OnCloseWindow)))
    ]

    def CreateMenuBar(self):
    menuBar = wx.MenuBar()
    for eachMenuData in self.MenuData():
    menuLabel = eachMenuData[0]
    menuItems = eachMenuData[1]
    menuBar.Append(self.CreateMenu(menuItems), menuLabel)
    self.SetMenuBar(menuBar)

    def CreateMenu(self, menuData):
    menu = wx.Menu()
    for eachItem in menuData:
    if len(eachItem) == 2:
    label = eachItem[0]
    subMenu = self.CreateMenu(eachItem[1])
    menu.AppendMenu(wx.NewId(), label, subMenu)
    else:
    self.CreateMenuItem(menu, *eachItem)
    return menu

    def CreateMenuItem(self, menu, label, status, handler, kind=wx.ITEM_NORMAL):
    if not label:
    menu.AppendSeparator()
    return
    menuItem = menu.Append(-1, label, status, kind)
    self.Bind(wx.EVT_MENU, handler, menuItem)

    def OnNew(self, event):
    pass

    def OnOpen(self, event):
    file_wildcard = "Paint files(*.paint)|*.paint|All files(*.*)|*.*"
    dlg = wx.FileDialog(self, "Open paint file...",
    os.getcwd(),
    style=wx.OPEN,
    wildcard=file_wildcard)
    if dlg.ShowModal() == wx.ID_OK:
    self.filename = dlg.GetPath()
    self.ReadFile()
    self.SetTitle(self.title + '--' + self.filename)
    dlg.Destroy()

    def OnSave(self, event):
    if not self.filename:
    self.OnSaveAs(event)
    else:
    self.SaveFile()

    def OnSaveAs(self, event):
    file_wildcard = "Paint files(*.paint)|*.paint|All files(*.*)|*.*"
    dlg = wx.FileDialog(self,
    "Save paint as ...",
    os.getcwd(),
    style=wx.SAVE | wx.OVERWRITE_PROMPT,
    wildcard=file_wildcard)
    if dlg.ShowModal() == wx.ID_OK:
    filename = dlg.GetPath()
    if not os.path.splitext(filename)[1]:
    filename = filename + '.paint'
    self.filename = filename
    self.SaveFile()
    self.SetTitle(self.title + '--' + self.filename)
    dlg.Destroy()

    def OnColor(self, event):
    menubar = self.GetMenuBar()
    itemid = event.GetId()
    item = menubar.FindItemById(itemid)
    color = item.GetLabel()
    self.paint.SetColor(color)

    def OnOtherColor(self, event):
    dlg = wx.ColourDialog(self)
    dlg.GetColourData().SetChooseFull(True)
    if dlg.ShowModal() == wx.ID_OK:
    self.paint.SetColor(dlg.GetColourData().GetColour())
    dlg.Destroy()

    def OnCloseWindow(self, event):
    self.Destroy()

    def SaveFile(self):
    if self.filename:
    data = self.paint.GetLinesData()
    f = open(self.filename, 'w')
    cPickle.dump(data, f)
    f.close()

    def ReadFile(self):
    if self.filename:
    try:
    f = open(self.filename, 'r')
    data = cPickle.load(f)
    f.close()
    self.paint.SetLinesData(data)
    except cPickle.UnpicklingError:
    wx.MessageBox("%s is not a paint file."
    % self.filename, "error tip",
    style=wx.OK | wx.ICON_EXCLAMATION)


    class ControlPanel(wx.Panel):
    BMP_SIZE = 16
    BMP_BORDER = 3
    NUM_COLS = 4
    SPACING = 4

    colorList = ('Black', 'Yellow', 'Red', 'Green', 'Blue', 'Purple',
    'Brown', 'Aquamarine', 'Forest Green', 'Light Blue',
    'Goldenrod', 'Cyan', 'Orange', 'Navy', 'Dark Grey',
    'Light Grey')
    maxThickness = 16

    def __init__(self, parent, ID, paint):
    wx.Panel.__init__(self, parent, ID, style=wx.RAISED_BORDER)
    self.paint = paint
    buttonSize = (self.BMP_SIZE + 2 * self.BMP_BORDER,
    self.BMP_SIZE + 2 * self.BMP_BORDER)
    colorGrid = self.createColorGrid(parent, buttonSize)
    thicknessGrid = self.createThicknessGrid(buttonSize)
    self.layout(colorGrid, thicknessGrid)

    def createColorGrid(self, parent, buttonSize):
    self.colorMap = {}
    self.colorButtons = {}
    colorGrid = wx.GridSizer(cols=self.NUM_COLS, hgap=2, vgap=2)
    for eachColor in self.colorList:
    bmp = self.MakeBitmap(eachColor)
    b = wx.lib.buttons.GenBitmapToggleButton(self, -1, bmp, size=buttonSize)
    b.SetBezelWidth(1)
    b.SetUseFocusIndicator(False)
    self.Bind(wx.EVT_BUTTON, self.OnSetColour, b)
    colorGrid.Add(b, 0)
    self.colorMap[b.GetId()] = eachColor
    self.colorButtons[eachColor] = b
    self.colorButtons[self.colorList[0]].SetToggle(True)
    return colorGrid

    def createThicknessGrid(self, buttonSize):
    self.thicknessIdMap = {}
    self.thicknessButtons = {}
    thicknessGrid = wx.GridSizer(cols=self.NUM_COLS, hgap=2, vgap=2)
    for x in range(1, self.maxThickness + 1):
    b = wx.lib.buttons.GenToggleButton(self, -1, str(x), size=buttonSize)
    b.SetBezelWidth(1)
    b.SetUseFocusIndicator(False)
    self.Bind(wx.EVT_BUTTON, self.OnSetThickness, b)
    thicknessGrid.Add(b, 0)
    self.thicknessIdMap[b.GetId()] = 2
    self.thicknessButtons[x] = b
    self.thicknessButtons[1].SetToggle(True)
    return thicknessGrid

    def layout(self, colorGrid, thicknessGrid):
    box = wx.BoxSizer(wx.VERTICAL)
    box.Add(colorGrid, 0, wx.ALL, self.SPACING)
    box.Add(thicknessGrid, 0, wx.ALL, self.SPACING)
    self.SetSizer(box)
    box.Fit(self)

    def OnSetColour(self, event):
    color = self.colorMap[event.GetId()]
    if color != self.paint.color:
    self.colorButtons[self.paint.color].SetToggle(False)
    self.paint.SetColor(color)

    def OnSetThickness(self, event):
    thickness = self.thicknessIdMap[event.GetId()]
    if thickness != self.paint.thickness:
    self.thicknessButtons[self.paint.thickness].SetToggle(False)
    self.paint.SetThickness(thickness)

    def MakeBitmap(self, color):
    bmp = wx.EmptyBitmap(16, 15)
    dc = wx.MemoryDC(bmp)
    dc.SetBackground(wx.Brush(color))
    dc.Clear()
    dc.SelectObject(wx.NullBitmap)
    return bmp


    if __name__ == '__main__':
    app = wx.PySimpleApp()
    frame = PaintFrame(None)
    frame.Show(True)
    app.MainLoop()

    原文地址:http://www.cnblogs.com/dyx1024/archive/2012/07/15/2592202.html
  • 相关阅读:
    $(this)和this 区别
    文本溢出显示省略标记'...'的bug
    web中常用的20种字体 (share)
    Underscore.js 的模板功能
    iphone webapp如何隐藏地址栏
    制作自己博客的分享按钮
    css3动画事件—webkitAnimationEnd
    获取随机的颜色
    制作自己博客的翻译工具
    兼容IE getElementsByClassName取标签
  • 原文地址:https://www.cnblogs.com/qfdxxdr/p/7083871.html
Copyright © 2011-2022 走看看