From: David De La Harpe Golden <david@harpegolden.net>
To: 9366@debbugs.gnu.org
Subject: bug#9366: Display geometry change hook
Date: Thu, 25 Aug 2011 06:16:58 +0100 [thread overview]
Message-ID: <4E55DACA.6080401@harpegolden.net> (raw)
[-- Attachment #1: Type: text/plain, Size: 1302 bytes --]
Severity: wishlist
Raised by Edward O'Connor in emacs-devel thread [1], filing in
bugtracker so it doesn't get lost over the feature freeze period.
Emacs doesn't appear to currently provide a hook that is reliably called
when the _display_ geometry changes on graphical window systems. e.g.
screen resolution changed by user, monitor hotplugging.
Emacs frame/window geometry might sometimes be considered to remain the
same by the window system terms despite changing overall display
geometry, so e.g. window-configuration-change-hook is not always run
when the display geometry changes.
Attached is an initial x11-only stab at an implementation that calls
window-configuration-change-hook when display geometry changes, though a
separate hook would be another design option.
For ns, Edward also mentioned:
"On GNUStep and Mac OS X, applications can listen for
NSApplicationDidChangeScreenParametersNotification for this sort of thing"
Dunno about w32 as yet, but presumably it has something similar.
[1] http://lists.gnu.org/archive/html/emacs-devel/2011-08/msg00544.html
From: "Edward O'Connor" <...>
Date: Fri, 12 Aug 2011 10:51:25 -0700
Message-ID:
<CAME3nGLnjLXixmSY45BWFX6qtCp2_XBR4x6a281hO6Mu=rnSuQ@mail.gmail.com>
Subject: is there a hook run when display geometry changes?
[-- Attachment #2: xrandr_monitoring_r1.diff --]
[-- Type: text/x-patch, Size: 9390 bytes --]
=== modified file 'configure.in'
--- configure.in 2011-08-04 17:04:39 +0000
+++ configure.in 2011-08-13 04:36:34 +0000
@@ -160,6 +160,8 @@
OPTION_DEFAULT_ON([xml2],[don't compile with XML parsing support])
OPTION_DEFAULT_ON([imagemagick],[don't compile with ImageMagick image support])
+OPTION_DEFAULT_ON([xrandr],[don't compile with XRandR support])
+
OPTION_DEFAULT_ON([xft],[don't use XFT for anti aliased fonts])
OPTION_DEFAULT_ON([libotf],[don't use libotf for OpenType font support])
OPTION_DEFAULT_ON([m17n-flt],[don't use m17n-flt for text shaping])
@@ -2590,6 +2592,21 @@
fi
AC_SUBST(LIBXSM)
+### Use xrandr (-lXrandr) if available
+HAVE_XRANDR=no
+XRANDR_LIBS=
+XRANDR_CFLAGS=
+if test "${HAVE_X11}" = "yes"; then
+ if test "${with_xrandr}" != "no"; then
+ PKG_CHECK_MODULES(XRANDR, xrandr > 1.0, HAVE_XRANDR=yes, HAVE_XRANDR=no)
+ if test "${HAVE_XRANDR}" = "yes"; then
+ AC_DEFINE(HAVE_XRANDR, 1, [Define to 1 if you have the Xrandr library (-lXrandr).])
+ fi
+ fi
+fi
+AC_SUBST(XRANDR_LIBS)
+AC_SUBST(XRANDR_CFLAGS)
+
### Use libxml (-lxml2) if available
if test "${with_xml2}" != "no"; then
### I'm not sure what the version number should be, so I just guessed.
@@ -3700,6 +3717,8 @@
echo " Does Emacs use -lotf? ${HAVE_LIBOTF}"
echo " Does Emacs use -lxft? ${HAVE_XFT}"
+echo " Does Emacs use -lXrandr? ${HAVE_XRANDR}"
+
echo " Does Emacs use toolkit scroll bars? ${USE_TOOLKIT_SCROLL_BARS}"
echo
=== modified file 'lisp/frame.el'
--- lisp/frame.el 2011-07-16 13:02:51 +0000
+++ lisp/frame.el 2011-08-13 04:04:16 +0000
@@ -1585,6 +1585,18 @@
(define-obsolete-variable-alias 'blink-cursor 'blink-cursor-mode "22.1")
\f
+;; Display geometry changes
+
+(defun handle-screen-change-notify-event (event)
+ "Handle screen-change-notify-event on the display in EVENT.
+ At present, just runs any window-configuration-changed-hook
+ for all frames on the display."
+ ; FIXME: do we want a completely separate hook instead?
+ (interactive "e")
+ (let ((display-name (nth 1 event)))
+ (mapcar #'run-window-configuration-change-hook
+ (frames-on-display-list display-name))))
+
;;;; Key bindings
(define-key ctl-x-5-map "2" 'make-frame-command)
@@ -1592,6 +1604,9 @@
(define-key ctl-x-5-map "0" 'delete-frame)
(define-key ctl-x-5-map "o" 'other-frame)
+(define-key special-event-map [screen-change-notify-event]
+ 'handle-screen-change-notify-event)
+
(provide 'frame)
;;; frame.el ends here
=== modified file 'src/Makefile.in'
--- src/Makefile.in 2011-08-04 17:04:39 +0000
+++ src/Makefile.in 2011-08-13 05:16:52 +0000
@@ -170,6 +170,9 @@
LIBXSM=@LIBXSM@
+XRANDR_CFLAGS = @XRANDR_CFLAGS@
+XRANDR_LIBS = @XRANDR_LIBS@
+
LIBXTR6=@LIBXTR6@
## $(LIBXMU) -lXt $(LIBXTR6) -lXext if USE_X_TOOLKIT, else $(LIBXSM).
@@ -313,6 +316,7 @@
$(SETTINGS_CFLAGS) $(FREETYPE_CFLAGS) $(FONTCONFIG_CFLAGS) \
$(LIBOTF_CFLAGS) $(M17N_FLT_CFLAGS) $(DEPFLAGS) $(PROFILING_CFLAGS) \
$(LIBGNUTLS_CFLAGS) \
+ $(XRANDR_CFLAGS) \
$(C_WARNINGS_SWITCH) $(CFLAGS)
ALL_OBJC_CFLAGS=$(ALL_CFLAGS) $(GNU_OBJC_CFLAGS)
@@ -388,7 +392,8 @@
$(LIBXML2_LIBS) $(LIBGPM) $(LIBRESOLV) $(LIBS_SYSTEM) \
$(LIBS_TERMCAP) $(GETLOADAVG_LIBS) $(SETTINGS_LIBS) $(LIBSELINUX_LIBS) \
$(FREETYPE_LIBS) $(FONTCONFIG_LIBS) $(LIBOTF_LIBS) $(M17N_FLT_LIBS) \
- $(LIBGNUTLS_LIBS) $(LIB_PTHREAD) $(LIB_PTHREAD_SIGMASK) \
+ $(LIBGNUTLS_LIBS) $(XRANDR_LIBS) \
+ $(LIB_PTHREAD) $(LIB_PTHREAD_SIGMASK) \
$(LIB_GCC) $(LIB_MATH) $(LIB_STANDARD) $(LIB_GCC)
all: emacs$(EXEEXT) $(OTHER_FILES)
=== modified file 'src/keyboard.c'
--- src/keyboard.c 2011-08-04 17:04:39 +0000
+++ src/keyboard.c 2011-08-13 03:41:32 +0000
@@ -331,6 +331,8 @@
#endif
static Lisp_Object Qconfig_changed_event;
+static Lisp_Object Qscreen_change_notify_event;
+
/* Lisp_Object Qmouse_movement; - also an event header */
/* Properties of event headers. */
@@ -4033,6 +4035,11 @@
obj = make_lispy_event (event);
kbd_fetch_ptr = event + 1;
}
+ else if (event->kind == SCREEN_CHANGE_NOTIFY_EVENT)
+ {
+ obj = make_lispy_event (event);
+ kbd_fetch_ptr = event + 1;
+ }
else
{
/* If this event is on a different frame, return a switch-frame this
@@ -5987,6 +5994,9 @@
Qnil));
}
#endif /* HAVE_GPM */
+ case SCREEN_CHANGE_NOTIFY_EVENT:
+ return Fcons (Qscreen_change_notify_event,
+ Fcons (event->frame_or_window, Qnil));
/* The 'kind' field of the event is something we don't recognize. */
default:
@@ -11527,6 +11537,7 @@
DEFSYM (Qsave_session, "save-session");
DEFSYM (Qconfig_changed_event, "config-changed-event");
DEFSYM (Qmenu_enable, "menu-enable");
+ DEFSYM (Qscreen_change_notify_event, "screen-change-notify-event");
#if defined (WINDOWSNT)
DEFSYM (Qlanguage_change, "language-change");
@@ -12288,6 +12299,10 @@
initial_define_lispy_key (Vspecial_event_map, "config-changed-event",
"ignore");
+
+ initial_define_lispy_key (Vspecial_event_map, "screen-change-notify-event",
+ "ignore");
+
}
/* Mark the pointers in the kboard objects.
=== modified file 'src/termhooks.h'
--- src/termhooks.h 2011-06-06 19:43:39 +0000
+++ src/termhooks.h 2011-08-13 03:18:24 +0000
@@ -206,6 +206,13 @@
, NS_NONKEY_EVENT
#endif
+ /* Generated when a bitmapped display's (upon which emacs has
+ frame(s) open) geometry changes dynamically e.g. by monitor
+ hotplugging or resolution change.
+ On X, that which is handled by the X Resize and Rotate
+ Extension. */
+ , SCREEN_CHANGE_NOTIFY_EVENT
+
};
/* If a struct input_event has a kind which is SELECTION_REQUEST_EVENT
=== modified file 'src/window.c'
--- src/window.c 2011-08-05 11:04:44 +0000
+++ src/window.c 2011-08-13 04:04:18 +0000
@@ -6542,7 +6542,11 @@
doc: /* Functions to call when window configuration changes.
The buffer-local part is run once per window, with the relevant window
selected; while the global part is run only once for the modified frame,
-with the relevant frame selected. */);
+with the relevant frame selected.
+
+If emacs can detect them, changes to the overall geometry of a display
+upon which a frame is open will by default also run this hook via
+the function `handle-screen-change-notify-event`. */);
Vwindow_configuration_change_hook = Qnil;
DEFVAR_LISP ("recenter-redisplay", Vrecenter_redisplay,
=== modified file 'src/xterm.c'
--- src/xterm.c 2011-08-04 11:06:22 +0000
+++ src/xterm.c 2011-08-13 05:00:47 +0000
@@ -85,6 +85,10 @@
#include <X11/Shell.h>
#endif
+#ifdef HAVE_XRANDR
+#include <X11/extensions/Xrandr.h>
+#endif
+
#ifdef HAVE_SYS_TIME_H
#include <sys/time.h>
#endif
@@ -359,7 +363,6 @@
static void x_wm_set_icon_pixmap (struct frame *, ptrdiff_t);
static void x_initialize (void);
-
/* Flush display of frame F, or of all frames if F is null. */
static void
@@ -6993,6 +6996,26 @@
break;
default:
+#ifdef HAVE_XRANDR
+ /* xrandr extension may or may not be present on a display =>
+ can't check for it as a constant C "case" arg, hence "if" here */
+ if (dpyinfo->xrandr_present &&
+ (event.type == (dpyinfo->xrandr_event_base + RRScreenChangeNotify)))
+ {
+ /* FIXME: is XRRUpdateConfiguration actually called by the toolkit/gtk+?
+ Even if it is, can/should we call it ourselves here? */
+#if !(defined USE_X_TOOLKIT || defined USE_GTK)
+ BLOCK_INPUT;
+ XRRUpdateConfiguration(&event);
+ UNBLOCK_INPUT;
+#endif
+ /* FIXME: do we really need a separate event kind? It seems
+ conceptually similar to a CONFIG_CHANGED_EVENT */
+ inev.ie.kind = SCREEN_CHANGE_NOTIFY_EVENT;
+ inev.ie.frame_or_window = XCAR(dpyinfo->name_list_element);
+ }
+ goto OTHER;
+#endif /* HAVE_XRANDR */
OTHER:
#ifdef USE_X_TOOLKIT
BLOCK_INPUT;
@@ -8169,6 +8192,25 @@
#endif /* not HAVE_X11R6_XIM */
+\f
+/***********************************************************************
+ X Resize and Rotate
+ ***********************************************************************/
+
+#ifdef HAVE_XRANDR
+
+static void
+xrandr_initialize (struct x_display_info *dpyinfo)
+{
+ dpyinfo->xrandr_present = XRRQueryExtension (dpyinfo->display,
+ &(dpyinfo->xrandr_event_base),
+ &(dpyinfo->xrandr_error_base));
+ if (dpyinfo->xrandr_present)
+ XRRSelectInput (dpyinfo->display, dpyinfo->root_window,
+ RRScreenChangeNotifyMask);
+}
+
+#endif /* HAVE_XRANDR */
\f
/* Calculate the absolute position in frame F
@@ -10315,6 +10357,10 @@
xim_initialize (dpyinfo, resource_name);
#endif
+#ifdef HAVE_XRANDR
+ xrandr_initialize (dpyinfo);
+#endif
+
xsettings_initialize (dpyinfo);
/* This is only needed for distinguishing keyboard and process input. */
=== modified file 'src/xterm.h'
--- src/xterm.h 2011-07-07 02:24:56 +0000
+++ src/xterm.h 2011-08-13 02:41:25 +0000
@@ -354,6 +354,14 @@
/* SM */
Atom Xatom_SM_CLIENT_ID;
+
+#ifdef HAVE_XRANDR
+ /* X Resize and Rotate */
+ Bool xrandr_present;
+ int xrandr_event_base;
+ int xrandr_error_base;
+#endif
+
};
#ifdef HAVE_X_I18N
next reply other threads:[~2011-08-25 5:16 UTC|newest]
Thread overview: 23+ messages / expand[flat|nested] mbox.gz Atom feed top
2011-08-25 5:16 David De La Harpe Golden [this message]
2011-08-25 5:55 ` bug#9366: Display geometry change hook Eli Zaretskii
2011-08-25 12:42 ` David De La Harpe Golden
2011-08-31 17:43 ` bug#9366: Attempting to add myself to this bug's CC list Edward O'Connor
2020-09-19 15:28 ` bug#9366: Display geometry change hook Lars Ingebrigtsen
2020-09-19 15:42 ` Eli Zaretskii
2020-09-20 8:14 ` martin rudalics
2020-09-20 8:25 ` Lars Ingebrigtsen
2020-09-20 8:56 ` Eli Zaretskii
2020-09-20 12:24 ` martin rudalics
2020-09-20 12:59 ` Eli Zaretskii
2020-09-21 7:26 ` martin rudalics
2020-09-21 14:21 ` Eli Zaretskii
2020-09-22 7:16 ` martin rudalics
2020-09-22 14:16 ` Eli Zaretskii
2020-09-23 7:15 ` martin rudalics
2020-09-23 7:47 ` Corwin Brust
2020-09-23 8:14 ` martin rudalics
2020-09-23 14:35 ` Eli Zaretskii
2020-09-23 14:29 ` Eli Zaretskii
2020-09-23 17:41 ` martin rudalics
2020-09-23 18:03 ` Eli Zaretskii
2020-09-22 15:04 ` Lars Ingebrigtsen
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
List information: https://www.gnu.org/software/emacs/
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=4E55DACA.6080401@harpegolden.net \
--to=david@harpegolden.net \
--cc=9366@debbugs.gnu.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
Code repositories for project(s) associated with this public inbox
https://git.savannah.gnu.org/cgit/emacs.git
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).