GNU Emacs is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
-the Free Software Foundation, either version 3 of the License, or
-(at your option) any later version.
+the Free Software Foundation, either version 3 of the License, or (at
+your option) any later version.
GNU Emacs is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
XFree (tmp_children);
#endif
- if (wm_window == rootw || had_errors)
+ if (had_errors || wm_window == rootw)
break;
win = wm_window;
\f
DEFUN ("xw-color-defined-p", Fxw_color_defined_p, Sxw_color_defined_p, 1, 2, 0,
doc: /* Internal function called by `color-defined-p', which see.
-(Note that the Nextstep version of this function ignores FRAME.) */)
+\(Note that the Nextstep version of this function ignores FRAME.) */)
(Lisp_Object color, Lisp_Object frame)
{
XColor foo;
DEFUN ("x-server-vendor", Fx_server_vendor, Sx_server_vendor, 0, 1, 0,
doc: /* Return the "vendor ID" string of the GUI software on TERMINAL.
-(Labeling every distributor as a "vendor" embodies the false assumption
+\(Labeling every distributor as a "vendor" embodies the false assumption
that operating systems cannot be developed and distributed noncommercially.)
The optional argument TERMINAL specifies which display to ask about.
RROutput pxid = None;
struct MonitorInfo *monitors;
-#ifdef HAVE_XRRGETSCREENRESOURCESCURRENT
- resources = XRRGetScreenResourcesCurrent (dpy, dpyinfo->root_window);
+#define RANDR13_LIBRARY \
+ (RANDR_MAJOR > 1 || (RANDR_MAJOR == 1 && RANDR_MINOR >= 3))
+
+#if RANDR13_LIBRARY
+ /* Check if the display supports 1.3 too. */
+ bool randr13_avail = (dpyinfo->xrandr_major_version > 1
+ || (dpyinfo->xrandr_major_version == 1
+ && dpyinfo->xrandr_minor_version >= 3));
+
+ if (randr13_avail)
+ resources = XRRGetScreenResourcesCurrent (dpy, dpyinfo->root_window);
+ else
+ resources = XRRGetScreenResources (dpy, dpyinfo->root_window);
#else
resources = XRRGetScreenResources (dpy, dpyinfo->root_window);
#endif
n_monitors = resources->noutput;
monitors = xzalloc (n_monitors * sizeof *monitors);
-#ifdef HAVE_XRRGETOUTPUTPRIMARY
- pxid = XRRGetOutputPrimary (dpy, dpyinfo->root_window);
+#if RANDR13_LIBRARY
+ if (randr13_avail)
+ pxid = XRRGetOutputPrimary (dpy, dpyinfo->root_window);
#endif
for (i = 0; i < n_monitors; ++i)
xrr_ok = XRRQueryExtension (dpy, &xrr_event_base, &xrr_error_base);
if (xrr_ok)
{
- int xrr_major, xrr_minor;
- XRRQueryVersion (dpy, &xrr_major, &xrr_minor);
- xrr_ok = (xrr_major == 1 && xrr_minor >= 2) || xrr_major > 1;
+ XRRQueryVersion (dpy, &dpyinfo->xrandr_major_version,
+ &dpyinfo->xrandr_minor_version);
+ xrr_ok = ((dpyinfo->xrandr_major_version == 1
+ && dpyinfo->xrandr_minor_version >= 2)
+ || dpyinfo->xrandr_major_version > 1);
}
if (xrr_ok)
Sx_set_mouse_absolute_pixel_position, 2, 2, 0,
doc: /* Move mouse pointer to absolute pixel position (X, Y).
The coordinates X and Y are interpreted in pixels relative to a position
-(0, 0) of the selected frame's display. */)
+\(0, 0) of the selected frame's display. */)
(Lisp_Object x, Lisp_Object y)
{
struct frame *f = SELECTED_FRAME ();
Optional second arg XRM-STRING is a string of resources in xrdb format.
If the optional third arg MUST-SUCCEED is non-nil,
terminate Emacs if we can't open the connection.
-(In the Nextstep version, the last two arguments are currently ignored.) */)
+\(In the Nextstep version, the last two arguments are currently ignored.) */)
(Lisp_Object display, Lisp_Object xrm_string, Lisp_Object must_succeed)
{
char *xrm_option;
int win_x, win_y;
Window root, child;
unsigned pmask;
+ int min_x, min_y, max_x, max_y = -1;
/* User-specified position? */
left = Fcdr (Fassq (Qleft, parms));
if ((!INTEGERP (left) && !INTEGERP (right))
|| (!INTEGERP (top) && !INTEGERP (bottom)))
{
+ Lisp_Object frame, attributes, monitor, geometry;
+
block_input ();
XQueryPointer (FRAME_X_DISPLAY (f), FRAME_DISPLAY_INFO (f)->root_window,
&root, &child, root_x, root_y, &win_x, &win_y, &pmask);
unblock_input ();
+
+ XSETFRAME(frame, f);
+ attributes = Fx_display_monitor_attributes_list (frame);
+
+ /* Try to determine the monitor where the mouse pointer is and
+ its geometry. See bug#22549. */
+ while (CONSP (attributes))
+ {
+ monitor = XCAR (attributes);
+ geometry = Fassq (Qgeometry, monitor);
+ if (CONSP (geometry))
+ {
+ min_x = XINT (Fnth (make_number (1), geometry));
+ min_y = XINT (Fnth (make_number (2), geometry));
+ max_x = min_x + XINT (Fnth (make_number (3), geometry));
+ max_y = min_y + XINT (Fnth (make_number (4), geometry));
+ if (min_x <= *root_x && *root_x < max_x
+ && min_y <= *root_y && *root_y < max_y)
+ {
+ break;
+ }
+ max_y = -1;
+ }
+
+ attributes = XCDR (attributes);
+ }
+ }
+
+ /* It was not possible to determine the monitor's geometry, so we
+ assign some sane defaults here: */
+ if ( max_y < 0 )
+ {
+ min_x = 0;
+ min_y = 0;
+ max_x = x_display_pixel_width (FRAME_DISPLAY_INFO (f));
+ max_y = x_display_pixel_height (FRAME_DISPLAY_INFO (f));
}
if (INTEGERP (top))
*root_y = XINT (top);
else if (INTEGERP (bottom))
*root_y = XINT (bottom) - height;
- else if (*root_y + XINT (dy) <= 0)
- *root_y = 0; /* Can happen for negative dy */
- else if (*root_y + XINT (dy) + height
- <= x_display_pixel_height (FRAME_DISPLAY_INFO (f)))
+ else if (*root_y + XINT (dy) <= min_y)
+ *root_y = min_y; /* Can happen for negative dy */
+ else if (*root_y + XINT (dy) + height <= max_y)
/* It fits below the pointer */
*root_y += XINT (dy);
- else if (height + XINT (dy) <= *root_y)
+ else if (height + XINT (dy) + min_y <= *root_y)
/* It fits above the pointer. */
*root_y -= height + XINT (dy);
else
/* Put it on the top. */
- *root_y = 0;
+ *root_y = min_y;
if (INTEGERP (left))
*root_x = XINT (left);
else if (INTEGERP (right))
*root_x = XINT (right) - width;
- else if (*root_x + XINT (dx) <= 0)
+ else if (*root_x + XINT (dx) <= min_x)
*root_x = 0; /* Can happen for negative dx */
- else if (*root_x + XINT (dx) + width
- <= x_display_pixel_width (FRAME_DISPLAY_INFO (f)))
+ else if (*root_x + XINT (dx) + width <= max_x)
/* It fits to the right of the pointer. */
*root_x += XINT (dx);
- else if (width + XINT (dx) <= *root_x)
+ else if (width + XINT (dx) + min_x <= *root_x)
/* It fits to the left of the pointer. */
*root_x -= width + XINT (dx);
else
- /* Put it left-justified on the screen--it ought to fit that way. */
- *root_x = 0;
+ /* Put it left justified on the screen -- it ought to fit that way. */
+ *root_x = min_x;
}
items is unmapped. Redisplay the menu manually... */
{
Widget w;
- struct frame *f = SELECTED_FRAME ();
- w = f->output_data.x->menubar_widget;
+ struct frame *f = SELECTED_FRAME ();
+ if (FRAME_X_P (f) && FRAME_LIVE_P (f))
+ {
+ w = f->output_data.x->menubar_widget;
- if (!DoesSaveUnders (FRAME_DISPLAY_INFO (f)->screen)
- && w != NULL)
- {
- block_input ();
- xlwmenu_redisplay (w);
- unblock_input ();
- }
+ if (!DoesSaveUnders (FRAME_DISPLAY_INFO (f)->screen)
+ && w != NULL)
+ {
+ block_input ();
+ xlwmenu_redisplay (w);
+ unblock_input ();
+ }
+ }
}
#endif /* USE_LUCID */
}