emacs-diffs
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Emacs-diffs] master 903e3d4: Fix frame resize flicker on macOS (bug#306


From: Alan Third
Subject: [Emacs-diffs] master 903e3d4: Fix frame resize flicker on macOS (bug#30699)
Date: Mon, 19 Mar 2018 13:17:54 -0400 (EDT)

branch: master
commit 903e3d43310638014a33fec64700e7db8e0774d0
Author: Alan Third <address@hidden>
Commit: Alan Third <address@hidden>

    Fix frame resize flicker on macOS (bug#30699)
    
    * src/nsterm.h (ns_enable_screen_updates): New function.
    * src/nsterm.m (ns_enable_screen_updates):
    (ns_disable_screen_updates): New functions.
    (disable_screen_updates_count): Count of number of times we've called
    NSDisableScreenUpdates.
    (x_set_window_size): Disable screen updates when not in a live resize
    loop.
    * src/xdisp.c (redisplay_internal): Reenable screen updates when
    redisplay doesn't complete due to a popup.
    (unwind_redisplay): Reenable screen updates.
---
 src/nsterm.h |  3 +++
 src/nsterm.m | 46 ++++++++++++++++++++++++++++++++++++++++++++++
 src/xdisp.c  | 16 +++++++++++++++-
 3 files changed, 64 insertions(+), 1 deletion(-)

diff --git a/src/nsterm.h b/src/nsterm.h
index 8b98593..df59a7d 100644
--- a/src/nsterm.h
+++ b/src/nsterm.h
@@ -1160,6 +1160,9 @@ extern void ns_release_autorelease_pool (void *);
 extern const char *ns_get_defaults_value (const char *key);
 extern void ns_init_locale (void);
 
+#ifdef NS_IMPL_COCOA
+extern void ns_enable_screen_updates (void);
+#endif
 
 /* in nsmenu */
 extern void update_frame_tool_bar (struct frame *f);
diff --git a/src/nsterm.m b/src/nsterm.m
index 75e0b83..f9107c4 100644
--- a/src/nsterm.m
+++ b/src/nsterm.m
@@ -288,6 +288,9 @@ static BOOL gsaved = NO;
 static BOOL ns_fake_keydown = NO;
 #ifdef NS_IMPL_COCOA
 static BOOL ns_menu_bar_is_hidden = NO;
+
+/* The number of times NSDisableScreenUpdates has been called.  */
+static int disable_screen_updates_count = 0;
 #endif
 /*static int debug_lock = 0; */
 
@@ -727,6 +730,40 @@ ns_release_autorelease_pool (void *pool)
 }
 
 
+#ifdef NS_IMPL_COCOA
+/* Disabling screen updates can be used to make several actions appear
+   "atomic" to the end user.  It seems some actions can still update
+   the display, though.
+
+   When we re-enable screen updates the number of calls to
+   NSEnableScreenUpdates should match the number to
+   NSDisableScreenUpdates.
+
+   We use these functions to prevent the user seeing a blank frame
+   after it has been resized.  x_set_window_size disables updates and
+   when redisplay completes unwind_redisplay enables them again
+   (bug#30699).  */
+
+static void
+ns_disable_screen_updates (void)
+{
+  NSDisableScreenUpdates ();
+  disable_screen_updates_count++;
+}
+
+void
+ns_enable_screen_updates (void)
+/* Re-enable screen updates.  Called from unwind_redisplay.  */
+{
+  while (disable_screen_updates_count > 0)
+    {
+      NSEnableScreenUpdates ();
+      disable_screen_updates_count--;
+    }
+}
+#endif
+
+
 static BOOL
 ns_menu_bar_should_be_hidden (void)
 /* True, if the menu bar should be hidden.  */
@@ -1877,6 +1914,15 @@ x_set_window_size (struct frame *f,
 
   block_input ();
 
+#ifdef NS_IMPL_COCOA
+  /* To prevent showing the user a blank frame, stop updates being
+     flushed to the screen until after redisplay has completed.  This
+     breaks live resize (resizing with a mouse), so don't do it if
+     we're in a live resize loop.  */
+  if (![view inLiveResize])
+    ns_disable_screen_updates ();
+#endif
+
   if (pixelwise)
     {
       pixelwidth = FRAME_TEXT_TO_PIXEL_WIDTH (f, width);
diff --git a/src/xdisp.c b/src/xdisp.c
index a97d4db..4778f53 100644
--- a/src/xdisp.c
+++ b/src/xdisp.c
@@ -13918,7 +13918,15 @@ redisplay_internal (void)
 
 #if defined (USE_X_TOOLKIT) || defined (USE_GTK) || defined (HAVE_NS)
   if (popup_activated ())
-    return;
+    {
+#ifdef NS_IMPL_COCOA
+      /* On macOS we may have disabled screen updates due to window
+         resizing.  We should re-enable them so the popup can be
+         displayed.  */
+      ns_enable_screen_updates ();
+#endif
+      return;
+    }
 #endif
 
   /* I don't think this happens but let's be paranoid.  */
@@ -14722,6 +14730,12 @@ unwind_redisplay (void)
 {
   redisplaying_p = false;
   unblock_buffer_flips ();
+#ifdef NS_IMPL_COCOA
+  /* On macOS we may have disabled screen updates due to window
+     resizing.  When redisplay completes we want to re-enable
+     them.  */
+  ns_enable_screen_updates ();
+#endif
 }
 
 



reply via email to

[Prev in Thread] Current Thread [Next in Thread]