Почему мое буферизованное приложение GraphicsContext имеет проблему мерцания? - PullRequest
1 голос
/ 16 марта 2010
import wx

class MainFrame(wx.Frame):
    def __init__(self,parent,title):

        wx.Frame.__init__(self, parent, title=title, size=(640,480))
        self.mainPanel=DoubleBufferTest(self,-1)

        self.Show(True)

class DoubleBufferTest(wx.Panel):
    def __init__(self,parent=None,id=-1):
        wx.Panel.__init__(self,parent,id,style=wx.FULL_REPAINT_ON_RESIZE)

        self.SetBackgroundColour("#FFFFFF")

        self.timer = wx.Timer(self)
        self.timer.Start(100)        
        self.Bind(wx.EVT_TIMER, self.update, self.timer)
        self.Bind(wx.EVT_PAINT,self.onPaint)


    def onPaint(self,event):
        event.Skip()
        dc = wx.MemoryDC()
        dc.SelectObject(wx.EmptyBitmap(640, 480))
        gc = wx.GraphicsContext.Create(dc)
        gc.PushState()
        gc.SetBrush(wx.Brush("#CFCFCF"))
        bgRect=gc.CreatePath()
        bgRect.AddRectangle(0,0,640,480)
        gc.FillPath(bgRect)    
        gc.PopState()

        dc2=wx.PaintDC(self)
        dc2.Blit(0,0,640,480,dc,0,0)
    def update(self,event):
        self.Refresh()

app = wx.App(False)
f=MainFrame(None,"Test")
app.MainLoop()

Я придумал этот код, чтобы рисовать контент GraphicsContext с двойной буферизацией на панели, но в окне постоянно мерцают. Я пробовал разные пути, например, линии и кривые, но они все еще там, и я не знаю, что их вызывает.

Ответы [ 2 ]

2 голосов
/ 19 марта 2010

Вы получаете мерцание, потому что каждый Refresh() вызывает стирание фона перед вызовом onPaint. Вам нужно привязать к EVT_ERASE_BACKGROUND и сделать его недоступным.

class DoubleBufferTest(wx.Panel):
    def __init__(self,parent=None,id=-1):
        # ... existing code ...
        self.Bind(wx.EVT_ERASE_BACKGROUND, self.onErase)
    def onErase(self, event):
        pass
    # ... existing code ...
1 голос
/ 16 марта 2010

Если вы используете относительно современные wxWidgets, вы можете использовать wx.BufferedPaintDC и избежать необходимости возиться с DC памяти и рисовать и бить самостоятельно. Кроме того, в окнах FULL_REPAINT_ON_RESIZE часто вызывает мерцание, даже если вы не изменяете размер окна из-за забавных вещей, происходящих под крышками - если вам это не нужно, переход с NO_FULL_REPAINT_ON_RESIZE может помочь. В противном случае вы захотите немного упростить свой код, чтобы убедиться, что вы можете заставить работать самое простое, и, возможно, взглянуть на вики-страницу DoubleBufferedDrawing на wxpython.org.

...