X-Git-Url: https://code.delx.au/gnu-emacs/blobdiff_plain/5491fd1098d27b3ba3db054076b9ab60fb3558dc..93ae9f46e7947aeb2180e3b8a98b551fa143ba51:/src/w32fns.c
diff --git a/src/w32fns.c b/src/w32fns.c
index 777819edd5..5f40729011 100644
--- a/src/w32fns.c
+++ b/src/w32fns.c
@@ -29,6 +29,8 @@ along with GNU Emacs. If not, see . */
#include
#include
+#include
+
#include "lisp.h"
#include "w32term.h"
#include "frame.h"
@@ -157,8 +159,8 @@ typedef BOOL (WINAPI * TrackMouseEvent_Proc)
typedef LONG (WINAPI * ImmGetCompositionString_Proc)
(IN HIMC context, IN DWORD index, OUT LPVOID buffer, IN DWORD bufLen);
typedef HIMC (WINAPI * ImmGetContext_Proc) (IN HWND window);
-typedef HWND (WINAPI * ImmReleaseContext_Proc) (IN HWND wnd, IN HIMC context);
-typedef HWND (WINAPI * ImmSetCompositionWindow_Proc) (IN HIMC context,
+typedef BOOL (WINAPI * ImmReleaseContext_Proc) (IN HWND wnd, IN HIMC context);
+typedef BOOL (WINAPI * ImmSetCompositionWindow_Proc) (IN HIMC context,
IN COMPOSITIONFORM *form);
typedef HMONITOR (WINAPI * MonitorFromPoint_Proc) (IN POINT pt, IN DWORD flags);
typedef BOOL (WINAPI * GetMonitorInfo_Proc)
@@ -202,7 +204,8 @@ unsigned int msh_mousewheel = 0;
static unsigned menu_free_timer = 0;
#ifdef GLYPH_DEBUG
-static int image_cache_refcount, dpyinfo_refcount;
+static ptrdiff_t image_cache_refcount;
+static int dpyinfo_refcount;
#endif
static HWND w32_visible_system_caret_hwnd;
@@ -346,10 +349,6 @@ x_real_positions (struct frame *f, int *xptr, int *yptr)
/* Convert (0, 0) in the client area to screen co-ordinates. */
ClientToScreen (FRAME_W32_WINDOW (f), &pt);
- /* Remember x_pixels_diff and y_pixels_diff. */
- f->x_pixels_diff = pt.x - rect.left;
- f->y_pixels_diff = pt.y - rect.top;
-
*xptr = rect.left;
*yptr = rect.top;
}
@@ -1722,6 +1721,7 @@ x_change_tool_bar_height (struct frame *f, int height)
int old_height = FRAME_TOOL_BAR_HEIGHT (f);
int lines = (height + unit - 1) / unit;
int old_text_height = FRAME_TEXT_HEIGHT (f);
+ Lisp_Object fullscreen;
/* Make sure we redisplay all windows in this frame. */
windows_or_buffers_changed = 23;
@@ -1746,7 +1746,10 @@ x_change_tool_bar_height (struct frame *f, int height)
f->n_tool_bar_rows = 0;
adjust_frame_size (f, -1, -1,
- (!f->tool_bar_redisplayed_once ? 1
+ ((!f->tool_bar_redisplayed_once
+ && (NILP (fullscreen =
+ get_frame_param (f, Qfullscreen))
+ || EQ (fullscreen, Qfullwidth))) ? 1
: (old_height == 0 || height == 0) ? 2
: 4),
false, Qtool_bar_lines);
@@ -3291,12 +3294,12 @@ w32_wnd_proc (HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
field being reset to nil. */
f = x_window_to_frame (dpyinfo, hwnd);
if (!(f && FRAME_LIVE_P (f)))
- break;
+ goto dflt;
w = XWINDOW (FRAME_SELECTED_WINDOW (f));
/* Punt if someone changed the frame's selected window
behind our back. */
if (w != w32_system_caret_window)
- break;
+ goto dflt;
form.dwStyle = CFS_RECT;
form.ptCurrentPos.x = w32_system_caret_x;
@@ -3314,16 +3317,22 @@ w32_wnd_proc (HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam)
/* Punt if the window was deleted behind our back. */
if (!BUFFERP (w->contents))
- break;
+ goto dflt;
context = get_ime_context_fn (hwnd);
if (!context)
- break;
+ goto dflt;
set_ime_composition_window_fn (context, &form);
release_ime_context_fn (hwnd, context);
}
+ /* We should "goto dflt" here to pass WM_IME_STARTCOMPOSITION to
+ DefWindowProc, so that the composition window will actually
+ be displayed. But doing so causes trouble with displaying
+ dialog boxes, such as the file selection dialog or font
+ selection dialog. So something else is needed to fix the
+ former without breaking the latter. See bug#11732. */
break;
case WM_IME_ENDCOMPOSITION:
@@ -4668,8 +4677,6 @@ This function is an internal primitive--use `make-frame' instead. */)
"bufferPredicate", "BufferPredicate", RES_TYPE_SYMBOL);
x_default_parameter (f, parameters, Qtitle, Qnil,
"title", "Title", RES_TYPE_STRING);
- x_default_parameter (f, parameters, Qfullscreen, Qnil,
- "fullscreen", "Fullscreen", RES_TYPE_SYMBOL);
f->output_data.w32->dwStyle = WS_OVERLAPPEDWINDOW;
f->output_data.w32->parent_desc = FRAME_DISPLAY_INFO (f)->root_window;
@@ -4728,6 +4735,12 @@ This function is an internal primitive--use `make-frame' instead. */)
x_wm_set_size_hint (f, window_prompting, false);
unblock_input ();
+ /* Process fullscreen parameter here in the hope that normalizing a
+ fullheight/fullwidth frame will produce the size set by the last
+ adjust_frame_size call. */
+ x_default_parameter (f, parameters, Qfullscreen, Qnil,
+ "fullscreen", "Fullscreen", RES_TYPE_SYMBOL);
+
/* Make the window appear on the frame and enable display, unless
the caller says not to. However, with explicit parent, Emacs
cannot control visibility, so don't try. */
@@ -5668,7 +5681,7 @@ x_create_tip_frame (struct w32_display_info *dpyinfo,
ptrdiff_t count = SPECPDL_INDEX ();
struct gcpro gcpro1, gcpro2, gcpro3;
struct kboard *kb;
- int face_change_count_before = face_change_count;
+ bool face_change_before = face_change;
Lisp_Object buffer;
struct buffer *old_buffer;
@@ -5832,7 +5845,7 @@ x_create_tip_frame (struct w32_display_info *dpyinfo,
SET_FRAME_COLS (f, 0);
SET_FRAME_LINES (f, 0);
adjust_frame_size (f, width * FRAME_COLUMN_WIDTH (f),
- height * FRAME_LINE_HEIGHT (f), 0, true, Qnil);
+ height * FRAME_LINE_HEIGHT (f), 0, true, Qtip_frame);
/* Add `tooltip' frame parameter's default value. */
if (NILP (Fframe_parameter (frame, Qtooltip)))
@@ -5880,11 +5893,11 @@ x_create_tip_frame (struct w32_display_info *dpyinfo,
f->can_x_set_window_size = true;
/* Setting attributes of faces of the tooltip frame from resources
- and similar will increment face_change_count, which leads to the
+ and similar will set face_change, which leads to the
clearing of all current matrices. Since this isn't necessary
- here, avoid it by resetting face_change_count to the value it
+ here, avoid it by resetting face_change to the value it
had before we created the tip frame. */
- face_change_count = face_change_count_before;
+ face_change = face_change_before;
/* Discard the unwind_protect. */
return unbind_to (count, frame);
@@ -7028,7 +7041,28 @@ a ShowWindow flag:
#else /* !CYGWIN */
- current_dir = ENCODE_FILE (current_dir);
+ const char file_url_str[] = "file:///";
+ const int file_url_len = sizeof (file_url_str) - 1;
+ if (strncmp (SSDATA (document), file_url_str, file_url_len) == 0)
+ {
+ /* Passing "file:///" URLs to ShellExecute causes shlwapi.dll to
+ start a thread in some rare system configurations, for
+ unknown reasons. That thread is started in the context of
+ the Emacs process, but out of control of our code, and seems
+ to never exit afterwards. Each such thread reserves 8MB of
+ stack space (because that's the value recorded in the Emacs
+ executable at link time: Emacs needs a large stack). So a
+ large enough number of invocations of w32-shell-execute can
+ potentially cause the Emacs process to run out of available
+ address space, which is nasty. To work around this, we
+ convert such URLs to local file names, which seems to prevent
+ those threads from starting. See bug #20220. */
+ char *p = SSDATA (document) + file_url_len;
+
+ if (c_isalpha (*p) && p[1] == ':' && IS_DIRECTORY_SEP (p[2]))
+ document = Fsubstring_no_properties (document,
+ make_number (file_url_len), Qnil);
+ }
/* We have a situation here. If DOCUMENT is a relative file name,
but its name includes leading directories, i.e. it lives not in
CURRENT_DIR, but in its subdirectory, then ShellExecute below
@@ -7061,6 +7095,8 @@ a ShowWindow flag:
else
document = ENCODE_FILE (document);
UNGCPRO;
+
+ current_dir = ENCODE_FILE (current_dir);
if (use_unicode)
{
wchar_t document_w[MAX_PATH], current_dir_w[MAX_PATH];
@@ -7500,13 +7536,13 @@ elements (all size values are in pixels).
- `title-bar-height' is the height of the title bar of FRAME.
-- `menu-bar-external' if `t' means the menu bar is by default external
+- `menu-bar-external' if t means the menu bar is by default external
(not included in the inner size of FRAME).
- `menu-bar-size' is a cons of the width and height of the menu bar of
FRAME.
-- `tool-bar-external' if `t' means the tool bar is by default external
+- `tool-bar-external' if t means the tool bar is by default external
(not included in the inner size of FRAME).
- `tool-bar-side' tells tells on which side the tool bar on FRAME is by
@@ -7558,7 +7594,7 @@ elements (all size values are in pixels).
menu_bar_height = single_bar_height;
return
- listn (CONSTYPE_PURE, 10,
+ listn (CONSTYPE_HEAP, 10,
Fcons (Qframe_position,
Fcons (make_number (frame_outer_edges.left),
make_number (frame_outer_edges.top))),
@@ -8232,6 +8268,15 @@ w32_sys_ring_bell (struct frame *f)
MessageBeep (sound_type);
}
+DEFUN ("w32--menu-bar-in-use", Fw32__menu_bar_in_use, Sw32__menu_bar_in_use,
+ 0, 0, 0,
+ doc: /* Return non-nil when a menu-bar menu is being used.
+Internal use only. */)
+ (void)
+{
+ return menubar_in_use ? Qt : Qnil;
+}
+
/***********************************************************************
Initialization
@@ -8303,6 +8348,14 @@ syms_of_w32fns (void)
DEFSYM (Qworkarea, "workarea");
DEFSYM (Qmm_size, "mm-size");
DEFSYM (Qframes, "frames");
+ DEFSYM (Qtip_frame, "tip-frame");
+ DEFSYM (Qunicode_sip, "unicode-sip");
+
+ /* Symbols used elsewhere, but only in MS-Windows-specific code. */
+ DEFSYM (Qgnutls_dll, "gnutls");
+ DEFSYM (Qlibxml2_dll, "libxml2");
+ DEFSYM (Qserif, "serif");
+ DEFSYM (Qzlib_dll, "zlib");
Fput (Qundefined_color, Qerror_conditions,
listn (CONSTYPE_PURE, 2, Qundefined_color, Qerror));
@@ -8609,6 +8662,7 @@ only be necessary if the default setting causes problems. */);
defsubr (&Sw32_frame_rect);
defsubr (&Sw32_frame_menu_bar_size);
defsubr (&Sw32_battery_status);
+ defsubr (&Sw32__menu_bar_in_use);
#ifdef WINDOWSNT
defsubr (&Sfile_system_info);