summaryrefslogtreecommitdiff
path: root/src/w32fns.c
diff options
context:
space:
mode:
authorPo Lu <luangruo@yahoo.com>2022-04-29 11:33:41 +0800
committerPo Lu <luangruo@yahoo.com>2022-04-30 11:20:46 +0800
commitbc44455f778a256a861c8063e87a662a13f603e1 (patch)
treea7426525ab8b5a9d9ca5fc28633e45d0dd3bb5c1 /src/w32fns.c
parenta33bf0114920a67926761ec2f51c040265b8dfd1 (diff)
downloademacs-bc44455f778a256a861c8063e87a662a13f603e1.tar.gz
Implement double buffering on MS Windows
* etc/NEWS: Announce changes. * src/w32fns.c (w32_set_inhibit_double_buffering): New function. (w32_wnd_proc): (Fx_create_frame): (w32_create_tip_frame): Set `inhibit-double-buffering' parameter. (w32_frame_parm_handlers): Add new handler. * src/w32term.c (w32_show_back_buffer): (w32_release_paint_buffer): New functions. (w32_frame_up_to_date): Show back buffer if applicable. (w32_buffer_flipping_unblocked_hook): New hook. (w32_scroll_run): Use BitBlt to scroll instead of window scrolling functions. (w32_scroll_bar_clear): Don't clear scroll bars when double buffered. (w32_read_socket): Flip buffers after reading input events in some cases. (w32_free_frame_resources): Free back buffer. (w32_create_terminal): Add new hook. * src/w32term.h (struct w32_output): New fields for handling back buffers. * src/w32xfns.c (select_palette): Fix indentation. (get_frame_dc, release_frame_dc): Return back buffer when appropriate and set dirty flag.
Diffstat (limited to 'src/w32fns.c')
-rw-r--r--src/w32fns.c33
1 files changed, 31 insertions, 2 deletions
diff --git a/src/w32fns.c b/src/w32fns.c
index a880136d0ac..d4e4b2a30bf 100644
--- a/src/w32fns.c
+++ b/src/w32fns.c
@@ -1802,6 +1802,25 @@ w32_set_tool_bar_lines (struct frame *f, Lisp_Object value, Lisp_Object oldval)
w32_change_tool_bar_height (f, nlines * FRAME_LINE_HEIGHT (f));
}
+static void
+w32_set_inhibit_double_buffering (struct frame *f,
+ Lisp_Object new_value,
+ Lisp_Object old_value)
+{
+ block_input ();
+
+ if (NILP (new_value))
+ FRAME_OUTPUT_DATA (f)->want_paint_buffer = 1;
+ else
+ {
+ FRAME_OUTPUT_DATA (f)->want_paint_buffer = 0;
+ w32_release_paint_buffer (f);
+
+ SET_FRAME_GARBAGED (f);
+ }
+
+ unblock_input ();
+}
/* Set the pixel height of the tool bar of frame F to HEIGHT. */
void
@@ -4093,7 +4112,9 @@ w32_wnd_proc (HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
{
case WM_ERASEBKGND:
f = w32_window_to_frame (dpyinfo, hwnd);
- if (f)
+
+ enter_crit ();
+ if (f && !FRAME_OUTPUT_DATA (f)->paint_buffer)
{
HDC hdc = get_frame_dc (f);
GetUpdateRect (hwnd, &wmsg.rect, FALSE);
@@ -4107,6 +4128,7 @@ w32_wnd_proc (HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
wmsg.rect.right, wmsg.rect.bottom));
#endif /* W32_DEBUG_DISPLAY */
}
+ leave_crit ();
return 1;
case WM_PALETTECHANGED:
/* ignore our own changes */
@@ -6080,6 +6102,10 @@ DEFUN ("x-create-frame", Fx_create_frame, Sx_create_frame,
? make_fixnum (0) : make_fixnum (1),
NULL, NULL, RES_TYPE_NUMBER);
+ gui_default_parameter (f, parameters, Qinhibit_double_buffering, Qnil,
+ "inhibitDoubleBuffering", "InhibitDoubleBuffering",
+ RES_TYPE_BOOLEAN);
+
gui_default_parameter (f, parameters, Qbuffer_predicate, Qnil,
"bufferPredicate", "BufferPredicate", RES_TYPE_SYMBOL);
gui_default_parameter (f, parameters, Qtitle, Qnil,
@@ -7096,6 +7122,9 @@ w32_create_tip_frame (struct w32_display_info *dpyinfo, Lisp_Object parms)
"alpha", "Alpha", RES_TYPE_NUMBER);
gui_default_parameter (f, parms, Qalpha_background, Qnil,
"alphaBackground", "AlphaBackground", RES_TYPE_NUMBER);
+ gui_default_parameter (f, parms, Qinhibit_double_buffering, Qnil,
+ "inhibitDoubleBuffering", "InhibitDoubleBuffering",
+ RES_TYPE_BOOLEAN);
/* Add `tooltip' frame parameter's default value. */
if (NILP (Fframe_parameter (frame, Qtooltip)))
@@ -10432,7 +10461,7 @@ frame_parm_handler w32_frame_parm_handlers[] =
gui_set_alpha,
0, /* x_set_sticky */
0, /* x_set_tool_bar_position */
- 0, /* x_set_inhibit_double_buffering */
+ w32_set_inhibit_double_buffering,
w32_set_undecorated,
w32_set_parent_frame,
w32_set_skip_taskbar,