From 2795af8c2bc608a28d8827c228feffef2883f516 Mon Sep 17 00:00:00 2001
From: Paul McCarthy <pauld.mccarthy@gmail.com>
Date: Wed, 20 Jan 2016 17:58:56 +0000
Subject: [PATCH] Fixed overlay flickering issue on movie mode (and on any
 other image texture changes).

---
 fsl/fsleyes/gl/lightboxcanvas.py | 13 +++++++++++--
 fsl/fsleyes/gl/slicecanvas.py    | 33 +++++++++++++++++++-------------
 2 files changed, 31 insertions(+), 15 deletions(-)

diff --git a/fsl/fsleyes/gl/lightboxcanvas.py b/fsl/fsleyes/gl/lightboxcanvas.py
index 7a635279c..5f6b21d31 100644
--- a/fsl/fsleyes/gl/lightboxcanvas.py
+++ b/fsl/fsleyes/gl/lightboxcanvas.py
@@ -741,6 +741,15 @@ class LightBoxCanvas(slicecanvas.SliceCanvas):
         if not self._setGLContext():
             return
 
+        overlays = self.displayCtx.getOrderedOverlays()
+        globjs   = [self._glObjects.get(o, None) for o in overlays]
+        globjs   = [g for g in globjs if g is not None]
+
+        # Skip the render if any GLObjects are not
+        # ready - see comments in SliceCanvas._draw.
+        if any([not g.ready() for g in globjs]):
+            return 
+
         if self.renderMode == 'offscreen':
             
             log.debug('Rendering to off-screen texture')
@@ -770,12 +779,12 @@ class LightBoxCanvas(slicecanvas.SliceCanvas):
             endSlice = self._nslices    
 
         # Draw all the slices for all the overlays.
-        for overlay in self.displayCtx.getOrderedOverlays():
+        for overlay, globj in zip(overlays, globjs):
 
             display = self.displayCtx.getDisplay(overlay)
             globj   = self._glObjects.get(overlay, None)
 
-            if (globj is None) or (not globj.ready()) or (not display.enabled):
+            if not display.enabled:
                 continue
 
             log.debug('Drawing {} slices ({} - {}) for '
diff --git a/fsl/fsleyes/gl/slicecanvas.py b/fsl/fsleyes/gl/slicecanvas.py
index 08068e11d..e708354f5 100644
--- a/fsl/fsleyes/gl/slicecanvas.py
+++ b/fsl/fsleyes/gl/slicecanvas.py
@@ -1202,31 +1202,38 @@ class SliceCanvas(props.HasProperties):
         if not self._setGLContext():
             return
 
+        overlays = self.displayCtx.getOrderedOverlays()
+        globjs   = [self._glObjects.get(o, None) for o in overlays]
+        
+        # If an overlay does not yet have a corresponding
+        # GLObject, we presume that it hasn't been created
+        # yet (and that the __genGLObject method is on the
+        # case).
+        globjs   = [g for g in globjs if g is not None]
+
+        # Do not draw anything if some globjects
+        # are not ready. This is because, if a
+        # GLObject was drawn, but is now temporarily
+        # not ready (e.g. it has an image texture
+        # that is being asynchronously refreshed),
+        # drawing the scene now would cause
+        # flickering of that GLObject.
+        if any([not g.ready() for g in globjs]):
+            return
+
         # Set the viewport to match the current 
         # display bounds and canvas size
         if self.renderMode is not 'offscreen':
             self._setViewport()
             glroutines.clear(self.bgColour)
             
-        for overlay in self.displayCtx.getOrderedOverlays():
+        for overlay, globj in zip(overlays, globjs):
 
             display = self.displayCtx.getDisplay(overlay)
             opts    = display.getDisplayOpts()
-            globj   = self._glObjects.get(overlay, None)
 
             if not display.enabled:
                 continue
-            
-            if globj is None:
-                # The GLObject has not been created
-                # yet - we assume here that the
-                # __genGLObject method is on the case
-                continue
-
-            # The GLObject is not ready
-            # to be drawn yet.
-            if not globj.ready():
-                continue
 
             # On-screen rendering - the globject is
             # rendered directly to the screen canvas
-- 
GitLab