From 8b61a891130e081faa91a897e17c4cc26efdfb41 Mon Sep 17 00:00:00 2001 From: Jason Rumney Date: Sat, 28 Jun 2008 23:54:27 +0000 Subject: [PATCH] * w32term.c (pfnGetFontUnicodeRanges): Remove unused function pointer. (pfnSetLayeredWindowAttributes): New function pointer. (w32_initialize): Initialize it when supported. (x_set_frame_alpha): New function. * w32fns.c (Fx_create_frame): Initialize frame parameter `alpha'. (w32_frame_parm_handlers): Set alpha handler. * frame.c (x_set_alpha) [HAVE_NTGUI]: Call x_set_frame_alpha. --- src/ChangeLog | 12 ++++++++++ src/frame.c | 2 +- src/w32fns.c | 4 +++- src/w32term.c | 63 +++++++++++++++++++++++++++++++++++++++++++++++---- 4 files changed, 74 insertions(+), 7 deletions(-) diff --git a/src/ChangeLog b/src/ChangeLog index 85931f7abd1..df8c4b524be 100644 --- a/src/ChangeLog +++ b/src/ChangeLog @@ -1,3 +1,15 @@ +2008-06-28 Jason Rumney + + * w32term.c (pfnGetFontUnicodeRanges): Remove unused function pointer. + (pfnSetLayeredWindowAttributes): New function pointer. + (w32_initialize): Initialize it when supported. + (x_set_frame_alpha): New function. + + * w32fns.c (Fx_create_frame): Initialize frame parameter `alpha'. + (w32_frame_parm_handlers): Set alpha handler. + + * frame.c (x_set_alpha) [HAVE_NTGUI]: Call x_set_frame_alpha. + 2008-06-27 Jason Rumney * w32fns.c (x_to_w32_font, w32_to_x_font, x_to_w32_weight) diff --git a/src/frame.c b/src/frame.c index 6320d0ca1ff..a7f22fad6a9 100644 --- a/src/frame.c +++ b/src/frame.c @@ -3692,7 +3692,7 @@ x_set_alpha (f, arg, oldval) for (i = 0; i < 2; i++) f->alpha[i] = newval[i]; -#ifdef HAVE_X_WINDOWS +#if defined (HAVE_X_WINDOWS) || defined (HAVE_NTGUI) BLOCK_INPUT; x_set_frame_alpha (f); UNBLOCK_INPUT; diff --git a/src/w32fns.c b/src/w32fns.c index 2a042717ac1..c9a9a5ab359 100644 --- a/src/w32fns.c +++ b/src/w32fns.c @@ -4521,6 +4521,8 @@ This function is an internal primitive--use `make-frame' instead. */) "cursorType", "CursorType", RES_TYPE_SYMBOL); x_default_parameter (f, parameters, Qscroll_bar_width, Qnil, "scrollBarWidth", "ScrollBarWidth", RES_TYPE_NUMBER); + x_default_parameter (f, parameters, Qalpha, Qnil, + "alpha", "Alpha", RES_TYPE_NUMBER); /* Dimensions, especially FRAME_LINES (f), must be done via change_frame_size. Change will not be effected unless different from the current @@ -6883,7 +6885,7 @@ frame_parm_handler w32_frame_parm_handlers[] = 0, /* x_set_wait_for_wm, */ x_set_fullscreen, x_set_font_backend, - 0 /* x_set_alpha, */ + x_set_alpha }; void diff --git a/src/w32term.c b/src/w32term.c index 52c78b0558a..65028f75013 100644 --- a/src/w32term.c +++ b/src/w32term.c @@ -139,8 +139,12 @@ typedef struct tagGLYPHSET #endif -/* Dynamic linking to GetFontUnicodeRanges (not available on 95, 98, ME). */ -DWORD (PASCAL *pfnGetFontUnicodeRanges) (HDC device, GLYPHSET *ranges); +/* Dynamic linking to SetLayeredWindowAttribute (only since 2000). */ +BOOL (PASCAL *pfnSetLayeredWindowAttributes) (HWND, COLORREF, BYTE, DWORD); + +#ifndef LWA_ALPHA +#define LWA_ALPHA 0x02 +#endif /* Frame being updated by update_frame. This is declared in term.c. This is set by update_begin and looked at by all the @@ -412,6 +416,53 @@ w32_clear_window (f) release_frame_dc (f, hdc); } +#define OPAQUE_FRAME 255 + +void +x_set_frame_alpha (f) + struct frame *f; +{ + struct w32_display_info *dpyinfo = FRAME_W32_DISPLAY_INFO (f); + double alpha = 1.0; + double alpha_min = 1.0; + BYTE opac; + LONG ex_style; + HWND window = FRAME_W32_WINDOW (f); + + /* Older versions of Windows do not support transparency. */ + if (!pfnSetLayeredWindowAttributes) + return; + + if (dpyinfo->x_highlight_frame == f) + alpha = f->alpha[0]; + else + alpha = f->alpha[1]; + + if (FLOATP (Vframe_alpha_lower_limit)) + alpha_min = XFLOAT_DATA (Vframe_alpha_lower_limit); + else if (INTEGERP (Vframe_alpha_lower_limit)) + alpha_min = (XINT (Vframe_alpha_lower_limit)) / 100.0; + + if (alpha < 0.0 || 1.0 < alpha) + alpha = 1.0; + else if (alpha < alpha_min && alpha_min <= 1.0) + alpha = alpha_min; + + opac = alpha * OPAQUE_FRAME; + + ex_style = GetWindowLong (window, GWL_EXSTYLE); + + if (opac == OPAQUE_FRAME) + ex_style ^= WS_EX_LAYERED; + else + ex_style |= WS_EX_LAYERED; + + SetWindowLong (window, GWL_EXSTYLE, ex_style); + + if (opac != OPAQUE_FRAME) + pfnSetLayeredWindowAttributes (window, 0, opac, LWA_ALPHA); +} + /*********************************************************************** Starting and ending an update @@ -2616,6 +2667,7 @@ frame_highlight (f) struct frame *f; { x_update_cursor (f, 1); + x_set_frame_alpha (f); } static void @@ -2623,6 +2675,7 @@ frame_unhighlight (f) struct frame *f; { x_update_cursor (f, 1); + x_set_frame_alpha (f); } /* The focus has changed. Update the frames as necessary to reflect @@ -6291,15 +6344,15 @@ w32_initialize () UINT smoothing_type; BOOL smoothing_enabled; - HANDLE gdi_lib = LoadLibrary ("gdi32.dll"); + HANDLE user_lib = LoadLibrary ("user32.dll"); #define LOAD_PROC(lib, fn) pfn##fn = (void *) GetProcAddress (lib, #fn) - LOAD_PROC (gdi_lib, GetFontUnicodeRanges); + LOAD_PROC (user_lib, SetLayeredWindowAttributes); #undef LOAD_PROC - FreeLibrary (gdi_lib); + FreeLibrary (user_lib); /* Ensure scrollbar handle is at least 5 pixels. */ vertical_scroll_bar_min_handle = 5; -- 2.39.2