Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
257 views
in Technique[技术] by (71.8m points)

python - What is the simplest way to create a shaped window in wxPython?

I'd like to create a simple shaped window in wxPython. More or less I want to do the wx equivalent to Tkinter's self.overrideredirect(1) (It get's rid of the default OS boarder), then round the corners on the window.

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

There's a shaped frame demo in the wxPython demos. I apologize for the indirect source. They originally came as a windows installer here:

source code

You'll want to look at shaped_frame_mobile.py or shaped_frame.py, which both call images.py from that listing for the sample window bitmap. It's not the exact equivalent to overrideredirect since you will have to provide an image to be drawn for the frame, but it could still help you accomplish something similar.

The important parts are the functions that set the window shape based on the bitmap and handle the wx.EVT_PAINT event:

def SetWindowShape(self, evt=None):
    r = wx.RegionFromBitmap(self.bmp)
    self.hasShape = self.SetShape(r)

def OnPaint(self, evt):
    dc = wx.PaintDC(self)
    dc.DrawBitmap(self.bmp, 0,0, True)

Edit - Here's an altered shaped_frame_mobile.py that loads the .png image specified in the IMAGE_PATH variable. Change that to point to your image:

import wx

# Create a .png image with something drawn on a white background
# and put the path to it here.
IMAGE_PATH = '/python26/projects/shapedwin/image.png'


class ShapedFrame(wx.Frame):
    def __init__(self):
        wx.Frame.__init__(self, None, -1, "Shaped Window",
                style = wx.FRAME_SHAPED | wx.SIMPLE_BORDER )
        self.hasShape = False
        self.delta = wx.Point(0,0)

        # Load the image
        image = wx.Image(IMAGE_PATH, wx.BITMAP_TYPE_PNG)
        image.SetMaskColour(255,255,255)
        image.SetMask(True)            
        self.bmp = wx.BitmapFromImage(image)

        self.SetClientSize((self.bmp.GetWidth(), self.bmp.GetHeight()))
        dc = wx.ClientDC(self)
        dc.DrawBitmap(self.bmp, 0,0, True)
        self.SetWindowShape()
        self.Bind(wx.EVT_LEFT_DCLICK, self.OnDoubleClick)
        self.Bind(wx.EVT_LEFT_DOWN, self.OnLeftDown)
        self.Bind(wx.EVT_LEFT_UP, self.OnLeftUp)
        self.Bind(wx.EVT_MOTION, self.OnMouseMove)
        self.Bind(wx.EVT_RIGHT_UP, self.OnExit)
        self.Bind(wx.EVT_PAINT, self.OnPaint)
        self.Bind(wx.EVT_WINDOW_CREATE, self.SetWindowShape)

    def SetWindowShape(self, evt=None):
        r = wx.RegionFromBitmap(self.bmp)
        self.hasShape = self.SetShape(r)

    def OnDoubleClick(self, evt):
        if self.hasShape:
            self.SetShape(wx.Region())
            self.hasShape = False
        else:
            self.SetWindowShape()

    def OnPaint(self, evt):
        dc = wx.PaintDC(self)
        dc.DrawBitmap(self.bmp, 0,0, True)

    def OnExit(self, evt):
        self.Close()

    def OnLeftDown(self, evt):
        self.CaptureMouse()
        pos = self.ClientToScreen(evt.GetPosition())
        origin = self.GetPosition()
        self.delta = wx.Point(pos.x - origin.x, pos.y - origin.y)

    def OnMouseMove(self, evt):
        if evt.Dragging() and evt.LeftIsDown():
            pos = self.ClientToScreen(evt.GetPosition())
            newPos = (pos.x - self.delta.x, pos.y - self.delta.y)
            self.Move(newPos)

    def OnLeftUp(self, evt):
        if self.HasCapture():
            self.ReleaseMouse()



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

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...