2010-02-24 19 views
6

koduję aplikację, która musi wybrać obszar ekranu. Muszę zmienić kursor na krzyżyk, a następnie narysować prostokąt na selekcji użytkownika. Pierwszą rzeczą, którą szukałem, było manipulowanie kursorem i natrafiłem na wxPython. Z wxPythonem mogłem z łatwością zrobić to w ramce z panelem, chodzi o to, że potrzebowałbym przezroczystego okna, aby użytkownik mógł zobaczyć jego ekran podczas wybierania żądanego obszaru, ale jeśli zrobię ramkę i panel obiekty przezroczyste wszystko się zapełnia.Python rysowanie na ekranie

Tak więc, jestem otwarty na każde rozwiązanie, używając wxPython lub nie używając go, ponieważ tak naprawdę nie wiem, czy używam go poprawnie.

Jestem nowy w Pythonie i nie jestem native speakerem, więc przykro mi, jeśli nie możesz czegoś zrozumieć.

To co mam zakodowane

import wx 

class SelectableFrame(wx.Frame): 

    c1 = None 
    c2 = None 

    def __init__(self, parent=None, id=-1, title=""): 
     wx.Frame.__init__(self, parent, id, title, size=wx.DisplaySize(), style=wx.TRANSPARENT_WINDOW) 

     self.panel = wx.Panel(self, size=self.GetSize(), style=wx.TRANSPARENT_WINDOW) 

     self.panel.Bind(wx.EVT_MOTION, self.OnMouseMove) 
     self.panel.Bind(wx.EVT_LEFT_DOWN, self.OnMouseDown) 
     self.panel.Bind(wx.EVT_LEFT_UP, self.OnMouseUp) 
     self.panel.Bind(wx.EVT_PAINT, self.OnPaint) 

     self.SetCursor(wx.StockCursor(wx.CURSOR_CROSS)) 

    def OnMouseMove(self, event): 
     if event.Dragging() and event.LeftIsDown(): 
      self.c2 = event.GetPosition() 
      self.Refresh() 

    def OnMouseDown(self, event): 
     self.c1 = event.GetPosition() 

    def OnMouseUp(self, event): 
     self.SetCursor(wx.StockCursor(wx.CURSOR_ARROW)) 

    def OnPaint(self, event): 
     if self.c1 is None or self.c2 is None: return 

     dc = wx.PaintDC(self.panel) 
     dc.SetPen(wx.Pen('red', 1)) 
     dc.SetBrush(wx.Brush(wx.Color(0, 0, 0), wx.TRANSPARENT)) 

     dc.DrawRectangle(self.c1.x, self.c1.y, self.c2.x - self.c1.x, self.c2.y - self.c1.y) 

    def PrintPosition(self, pos): 
     return str(pos.x) + " " + str(pos.y) 


class MyApp(wx.App): 

    def OnInit(self): 
     frame = SelectableFrame() 
     frame.Show(True) 
     self.SetTopWindow(frame) 

     return True 



app = MyApp(0) 
app.MainLoop() 

Odpowiedz

5

Nie należy używać wx.TRANSPARENT w tworzeniu okna, które jest najczęściej stosowane do malowania wxDC poleceń. Aby okno było przezroczyste, po prostu zadzwoń do win.SetTransparent (kwota), gdzie kwota wynosi od 0-255, 255 oznacza nieprzezroczystość, 0 oznacza całkowitą przejrzystość. zobacz http://www.wxpython.org/docs/api/wx.Window-class.html#SetTransparent

Zmodyfikowałem twój kod, będzie działać tylko, jeśli twoja platforma obsługuje przezroczyste okna, możesz to sprawdzić za pomocą CanSetTransparent. Testowałem to na Windows XP.

import wx 

class SelectableFrame(wx.Frame): 

    c1 = None 
    c2 = None 

    def __init__(self, parent=None, id=-1, title=""): 
     wx.Frame.__init__(self, parent, id, title, size=wx.DisplaySize()) 

     self.panel = wx.Panel(self, size=self.GetSize()) 

     self.panel.Bind(wx.EVT_MOTION, self.OnMouseMove) 
     self.panel.Bind(wx.EVT_LEFT_DOWN, self.OnMouseDown) 
     self.panel.Bind(wx.EVT_LEFT_UP, self.OnMouseUp) 
     self.panel.Bind(wx.EVT_PAINT, self.OnPaint) 

     self.SetCursor(wx.StockCursor(wx.CURSOR_CROSS)) 

     self.SetTransparent(50) 

    def OnMouseMove(self, event): 
     if event.Dragging() and event.LeftIsDown(): 
      self.c2 = event.GetPosition() 
      self.Refresh() 

    def OnMouseDown(self, event): 
     self.c1 = event.GetPosition() 

    def OnMouseUp(self, event): 
     self.SetCursor(wx.StockCursor(wx.CURSOR_ARROW)) 

    def OnPaint(self, event): 
     if self.c1 is None or self.c2 is None: return 

     dc = wx.PaintDC(self.panel) 
     dc.SetPen(wx.Pen('red', 1)) 
     dc.SetBrush(wx.Brush(wx.Color(0, 0, 0), wx.TRANSPARENT)) 

     dc.DrawRectangle(self.c1.x, self.c1.y, self.c2.x - self.c1.x, self.c2.y - self.c1.y) 

    def PrintPosition(self, pos): 
     return str(pos.x) + " " + str(pos.y) 


class MyApp(wx.App): 

    def OnInit(self): 
     frame = SelectableFrame() 
     frame.Show(True) 
     self.SetTopWindow(frame) 

     return True 


app = MyApp(0) 
app.MainLoop() 
+0

Dzięki, że naprawiłem problem z buggy, ale teraz mam inny problem! Prostokąt zaznaczenia również staje się przezroczysty, więc nie mogę uzyskać pełnego przezroczystości okna i nadal widzieć zaznaczenie. Ale na razie jest to w porządku. – Franco