2014-01-07 123 views
0

我想通过鼠标移动在位图顶部绘制一个矩形。但矩形在位图下呈现。以下是我的代码。如何在顶层绘制矩形

#!/usr/bin/env python 

import sys, os 
import wx 
import wx.lib.scrolledpanel as scrolled 

class ImgPanel(scrolled.ScrolledPanel): 
    def __init__(self, parent): 
     super(ImgPanel, self).__init__(parent, 
             style = wx.SUNKEN_BORDER) 

     self.bitmap=wx.StaticBitmap(parent=self) 
     image = wx.Bitmap('image.jpg') 
     self.bitmap.SetBitmap(image) 

     self.imgSizer = wx.BoxSizer(wx.VERTICAL)   
     self.imgSizer.Add(self.bitmap, 1, wx.EXPAND) 
     self.SetSizer(self.imgSizer) 

     self.SetAutoLayout(1) 
     self.SetupScrolling()  
     self.Bind(wx.EVT_PAINT, self.OnPaint) 
     self.bitmap.Bind(wx.EVT_MOTION, self.OnMove) 
     self.bitmap.Bind(wx.EVT_LEFT_DOWN, self.OnLeftDown) 
     self.bitmap.Bind(wx.EVT_LEFT_UP, self.OnLeftUp) 
     self.IsRectReady = False 
     self.newRectPara=[0,0,0,0] 


    def OnMove(self,evt): 
     if True == self.IsRectReady: 
      self.newRectPara[2]=evt.GetPosition()[0]-self.newRectPara[0]+1 
      self.newRectPara[3]=evt.GetPosition()[1]-self.newRectPara[1]+1 
      self.Refresh() 

    def OnLeftDown(self, evt): 
     self.IsRectReady=True 
     self.newRectPara[0]=evt.GetPosition()[0] 
     self.newRectPara[1]=evt.GetPosition()[1] 


    def OnLeftUp(self, evt): 
     self.IsRectReady=False 

    def OnPaint(self, evt):   
     dc=wx.PaintDC(self) 
     dc.Clear() 
     if self.IsRectReady: 
      dc.DrawRectangle(self.newRectPara[0], self.newRectPara[1], 
          self.newRectPara[2], self.newRectPara[3]) 

class WinFrame(wx.Frame): 
    def __init__(self, parent, title, width, height): 
     super(WinFrame, self).__init__(parent, 
             title=title, 
             size=(width, height)) 

     self.imgPanel = ImgPanel(self) 
     self.frameSizer = wx.BoxSizer(wx.HORIZONTAL)   
     self.frameSizer.Add(self.imgPanel, 1, wx.EXPAND)   
     self.SetAutoLayout(True) 
     self.SetSizer(self.frameSizer) 
     self.Layout()  

     self.Centre() 
     self.Show(True)   


class MyApp(wx.App): 
    def __init__(self, width, height): 
     super(MyApp, self).__init__(0) 

     self.width = width 
     self.height = height 

    def createFrame(self): 
     self.frame = WinFrame(None, "test", self.width, self.height) 
     self.SetTopWindow(self.frame)  

def main(): 
    app = MyApp(640, 480) 
    app.createFrame() 
    app.MainLoop() 

if "__main__" == __name__ : 
    main() 
+1

在其他框架中,我一直使用一个容器,它可以容纳一个图像以及一个绘制的矩形(例如画布)。你不能用这样的东西吗? AFAICS认为'DC'的东西可能总是在图像下方,所以你的方法将无法工作。 – Alfe

+0

我认为首先使用'floatcanvas'。但我找不到好的教程。我使用'staticbitmap'小部件进入滚动面板来生成滚动条。我不知道其他方式来渲染一个大图像,同时可以生成滚动条 – Samuel

回答

2

由于wx.StaticBitmap是一个单独的(子)窗口,它将始终位于它的父级ImgPanel之上。换句话说,在ImgPanel上完成的任何绘图将始终位于位图小部件的后面或下面。如果你想要图像和图形进行组合,那么不要使用wx.StaticBitmap,而应该将位图添加到EVT_PAINT处理程序中。

+0

你是否应该使用'DC.DrawBitmap'而不是'StaticBitmap'小部件。我已经尝试过这种方法。但如果图像比面板大。它无法生成滚动条 – Samuel

+1

使用wx.ScrolledWindow,将窗口的虚拟大小设置为足够大以显示所有图像,并设置滚动率以设置滚动条将使用的增量。 – RobinDunn

+0

我在框架中有两个面板。一个面板是用于图像的。所以我应该在一个框架中使用一个面板和一个滚动窗口。对? – Samuel