aboutsummaryrefslogtreecommitdiffstats
path: root/lisp/frameset.el
diff options
context:
space:
mode:
authorMartin Rudalics2017-04-12 10:38:25 +0200
committerMartin Rudalics2017-04-12 10:38:25 +0200
commit3fdd3bb56c006a2a24761b8fcea0cbd9b0cba422 (patch)
treea0b8f5e431ba812b4fe69261a8515e973a3e7ed3 /lisp/frameset.el
parent449bc49c768a4733411c7e05186be7efc163cd7c (diff)
downloademacs-3fdd3bb56c006a2a24761b8fcea0cbd9b0cba422.tar.gz
emacs-3fdd3bb56c006a2a24761b8fcea0cbd9b0cba422.zip
Add new frame parameters and associated functions
Add new frame parameters `undecorated', `override-redirect', `parent-frame', `skip-taskbar', `no-focus-on-map', `no-accept-focus', `z-group', `delete-before', `no-other-frame', `mouse-wheel-frame', `min-width', `min-height'. Add new functions `frame-restack' and `frame-list-z-order'. * lisp/cus-start.el (focus-follows-mouse): Adapt customization type. * lisp/frame.el (handle-delete-frame): Handle child and `delete-before' frames. (other-frame): Stop looking for other frame after one round. (frame-list-z-order, frame-restack): New functions. (delete-other-frames): Handle child frames. * lisp/frameset.el (frameset-persistent-filter-alist) (frameset--record-relationships): Handle `delete-before', `parent-frame' and `mouse-wheel-frame' parameters. Rename latter from `frameset--record-minibuffer-relationships'. (frameset--restore-frame): Handle ‘parent-frame’ parameter specially. (frameset-restore): Handle `delete-before', `parent-frame' and `mouse-wheel-frame' parameters. * lisp/mwheel.el (mwheel-scroll): Handle `mouse-wheel-frame' parameter. * lisp/window.el (window--min-size-ignore-p): Fix doc-string. (mouse-autoselect-window-select, handle-select-window): Major rewrite. Try to not ignore errors. Handle auto-selection of child frames and different values of `focus-follows-mouse'. * src/frame.c (frame_windows_min_size): Handle new `min-width' and `min-height' frame parameters. (make_frame): Initialize new frame structure members. (do_switch_frame): Don't reset internal_last_event_frame for descendant frames. (Fframe_parent, frame_ancestor_p, Fframe_ancestor_p): New functions. (candidate_frame): Don't return `no-other-frame' frame. (other_frames): New function replacing other_visible_frames. (delete_frame): Rewrite. Handle child and `delete-before' frames. (Fmake_frame_invisible): Call other_frames. (store_frame_param): Check `delete-before' and `parent-frame' parameters for circular dependencies. (frame_parms, syms_of_frame): Add entries for and define new frame parameters. (focus_follows_mouse): New meaningful value `auto-raise'. * src/frame.h (z_group): New enumeration type. (frame): New slots parent_frame, undecorated, override_redirect, skip_taskbar, no_focus_on_map, no_accept_focus, z_group. (fset_parent_frame): New inlined function. (FRAME_UNDECORATED, FRAME_OVERRIDE_REDIRECT) (FRAME_PARENT_FRAME, FRAME_SKIP_TASKBAR, FRAME_NO_FOCUS_ON_MAP) (FRAME_NO_ACCEPT_FOCUS, FRAME_Z_GROUP, FRAME_Z_GROUP_NONE) (FRAME_Z_GROUP_ABOVE, FRAME_Z_GROUP_ABOVE_SUSPENDED) (FRAME_Z_GROUP_BELOW): New macros. (frame_ancestor_p): Add declaration. * src/gtkutil.c (xg_create_frame_widgets): Handle `undecorated' and `override-redirect' frame parameters. (x_wm_set_size_hint): None for child frames. (xg_set_undecorated, xg_frame_restack, xg_set_skip_taskbar) (xg_set_no_focus_on_map, xg_set_no_accept_focus) (xg_set_override_redirect): New functions. (xg_update_scrollbar_pos, xg_update_horizontal_scrollbar_pos): Don't let scrollbars obscure child frames. * src/gtkutil.h: (xg_set_undecorated, xg_frame_restack) (xg_set_skip_taskbar, xg_set_no_focus_on_map) (xg_set_no_accept_focus, xg_set_override_redirect): Add extern declarations. * src/nsfns.m (ns_frame_parm_handlers): Add entries for new frame parameters. (Fx_create_frame): Install `min-width' and `min-height' frame parameters. * src/nsterm.m (mouseMoved:): Handle focus_follows_mouse change. * src/w32fns.c (WS_EX_NOACTIVATE): Define if necessary. (x_real_positions): Handle child frames. (x_set_menu_bar_lines): Don't for child frames. (x_set_undecorated, x_set_parent_frame, x_set_skip_taskbar) (x_set_no_focus_on_map, x_set_no_accept_focus) (x_set_z_group): New functions. (w32_createvscrollbar, w32_createhscrollbar): Don't draw scroll bars over child frames. (w32_createwindow): Handle new frame parameters and child frames. (w32_wnd_proc): Let mouse clicks into a child frame activate the frame. Try to handle the `no-accept-focus' parameter. Do SetFocus when our window is brought to top or becomes the foreground window. (w32_window): Don't initialize menu bar for child frames. (Fx_create_frame): Handle new frame parameters. (x_create_tip_frame): Set explicit_parent slot. (w32_dialog_in_progress): New function. (Fx_file_dialog): Handle `z-group-above' frames. (w32_frame_list_z_order, Fw32_frame_list_z_order) (w32_frame_restack, Fw32_frame_restack): New functions. (w32_frame_parm_handlers): Add entries for new frame parameters. * src/w32font.c (Fx_select_font): Handle `z-group-above' frames during font selection dialogue. * src/w32term.c (construct_mouse_wheel): Construct mouse wheel event from F's w32 window. (w32_mouse_position): Handle child frames. (w32_set_vertical_scroll_bar, w32_set_horizontal_scroll_bar): Don't draw scroll bars over child frames. (w32_read_socket): Always erase background of child frames. When generating SELECT_WINDOW_EVENTs handle new value of `focus-follows-mouse' and handle `no-accept-focus' parameter. Handle `mouse-wheel-frame' parameter. (x_calc_absolute_position, x_set_offset, x_set_window_size): Handle child frames. (x_make_frame_visible): Handle child frames specially. Handle `no-focus-on-map' parameter. * src/w32term.h (w32_dialog_in_progress): Add external declaration. * src/xdisp.c (x_consider_frame_title, prepare_menu_bars): Not for child frames. * src/xfns.c (Xm/MwmUtil.h): Include for WM hints. (PropMotifWmHints, PROP_MOTIF_WM_HINTS_ELEMENTS): Define for non-Motif, non-GTK case. (x_real_pos_and_offsets): Handle child frames. (x_set_undecorated, x_set_parent_frame) (x_set_no_focus_on_map, x_set_no_accept_focus) (x_set_override_redirect): New functions. (x_set_menu_bar_lines): Not for child frames. (x_window): Handle `undecorated' and `override_redirect' cases. (Fx_create_frame): Handle new frame parameters. (frame_geometry): Handle child frames and outer border. (x_frame_list_z_order, Fx_frame_list_z_order) (x_frame_restack, Fx_frame_restack): New functions. (Fx_file_dialog, Fx_select_font): Set x_menu_set_in_use. (x_frame_parm_handlers): Add entries for new frame parameters. * src/xmenu.c (x_menu_set_in_use): Handle `z-group-above' frames. * src/xterm.c (x_set_frame_alpha): Don't set alpha of parent for child frames. (XTmouse_position): Handle child frames. (x_scroll_bar_create, x_scroll_bar_expose): Don't let scroll bars obscure child frames. (handle_one_xevent): Handle child frame positions. If necessary set `skip-taskbar' and reassign proper `z-group' when we are mapped. When generating SELECT_WINDOW_EVENTs handle new value of `focus-follows-mouse'. Handle `mouse-wheel-frame' parameter. Let mouse clicks into a child frame activate the frame. (x_calc_absolute_position, x_set_offset): Handle child frames specially. (x_set_skip_taskbar, x_set_z_group): New functions. (x_make_frame_visible): Handle child frames. (ATOM_REFS_INIT): Add entries for Xatom_net_wm_state_skip_taskbar, Xatom_net_wm_state_above, Xatom_net_wm_state_below. * src/xterm.h (top-level): Declare Xatom_net_wm_state_above, Xatom_net_wm_state_below and Xatom_net_wm_state_skip_taskbar. (x_set_skip_taskbar, x_set_z_group): Add extern declarations.
Diffstat (limited to 'lisp/frameset.el')
-rw-r--r--lisp/frameset.el100
1 files changed, 81 insertions, 19 deletions
diff --git a/lisp/frameset.el b/lisp/frameset.el
index 2dd3050ef76..ebf09d3ab5c 100644
--- a/lisp/frameset.el
+++ b/lisp/frameset.el
@@ -446,6 +446,7 @@ DO NOT MODIFY. See `frameset-filter-alist' for a full description.")
446 (buffer-list . :never) 446 (buffer-list . :never)
447 (buffer-predicate . :never) 447 (buffer-predicate . :never)
448 (buried-buffer-list . :never) 448 (buried-buffer-list . :never)
449 (delete-before . :never)
449 (font . frameset-filter-shelve-param) 450 (font . frameset-filter-shelve-param)
450 (foreground-color . frameset-filter-sanitize-color) 451 (foreground-color . frameset-filter-sanitize-color)
451 (fullscreen . frameset-filter-shelve-param) 452 (fullscreen . frameset-filter-shelve-param)
@@ -455,7 +456,9 @@ DO NOT MODIFY. See `frameset-filter-alist' for a full description.")
455 (GUI:width . frameset-filter-unshelve-param) 456 (GUI:width . frameset-filter-unshelve-param)
456 (height . frameset-filter-shelve-param) 457 (height . frameset-filter-shelve-param)
457 (outer-window-id . :never) 458 (outer-window-id . :never)
459 (parent-frame . :never)
458 (parent-id . :never) 460 (parent-id . :never)
461 (mouse-wheel-frame . :never)
459 (tty . frameset-filter-tty-to-GUI) 462 (tty . frameset-filter-tty-to-GUI)
460 (tty-type . frameset-filter-tty-to-GUI) 463 (tty-type . frameset-filter-tty-to-GUI)
461 (width . frameset-filter-shelve-param) 464 (width . frameset-filter-shelve-param)
@@ -717,9 +720,18 @@ If nil, check all live frames."
717 720
718;; Saving framesets 721;; Saving framesets
719 722
720(defun frameset--record-minibuffer-relationships (frame-list) 723(defun frameset--record-relationships (frame-list)
721 "Process FRAME-LIST and record minibuffer relationships. 724 "Process FRAME-LIST and record relationships.
722FRAME-LIST is a list of frames. Internal use only." 725FRAME-LIST is a list of frames.
726
727The relationships recorded for each frame are
728
729- `minibuffer' via `frameset--mini'
730- `delete-before' via `frameset--delete-before'
731- `parent-frame' via `frameset--parent-frame'
732- `mouse-wheel-frame' via `frameset--mouse-wheel-frame'
733
734Internal use only."
723 ;; Record frames with their own minibuffer 735 ;; Record frames with their own minibuffer
724 (dolist (frame (minibuffer-frame-list)) 736 (dolist (frame (minibuffer-frame-list))
725 (when (memq frame frame-list) 737 (when (memq frame frame-list)
@@ -730,22 +742,41 @@ FRAME-LIST is a list of frames. Internal use only."
730 (set-frame-parameter frame 742 (set-frame-parameter frame
731 'frameset--mini 743 'frameset--mini
732 (cons t (eq frame default-minibuffer-frame))))) 744 (cons t (eq frame default-minibuffer-frame)))))
733 ;; Now link minibufferless frames with their minibuffer frames 745 ;; Now link minibufferless frames with their minibuffer frames and
746 ;; store `parent-frame', `delete-before' and `mouse-wheel-frame'
747 ;; relationships in a similar way.
734 (dolist (frame frame-list) 748 (dolist (frame frame-list)
735 (unless (frame-parameter frame 'frameset--mini) 749 (let ((parent-frame (frame-parent frame))
736 (frameset--set-id frame) 750 (delete-before (frame-parameter frame 'delete-before))
737 (let ((mb-frame (window-frame (minibuffer-window frame)))) 751 (mouse-wheel-frame (frame-parameter frame 'mouse-wheel-frame))
738 ;; For minibufferless frames, frameset--mini is a cons 752 (nomini (not (frame-parameter frame 'frameset--mini))))
739 ;; (nil . FRAME-ID), where FRAME-ID is the frameset--id of 753 (when (or nomini parent-frame delete-before mouse-wheel-frame)
740 ;; the frame containing its minibuffer window. 754 (when nomini
741 ;; FRAME-ID can be set to nil, if FRAME-LIST doesn't contain 755 (frameset--set-id frame))
742 ;; the minibuffer frame of a minibufferless frame; we allow 756 (when parent-frame
743 ;; it without trying to second-guess the user. 757 (set-frame-parameter
744 (set-frame-parameter frame 758 frame 'frameset--parent-frame (frameset-frame-id parent-frame)))
745 'frameset--mini 759 (when delete-before
746 (cons nil 760 (set-frame-parameter
747 (and mb-frame 761 frame 'frameset--delete-before (frameset-frame-id delete-before)))
748 (frameset-frame-id mb-frame)))))))) 762 (when mouse-wheel-frame
763 (set-frame-parameter
764 frame 'frameset--mouse-wheel-frame
765 (frameset-frame-id mouse-wheel-frame)))
766 (when nomini
767 (let ((mb-frame (window-frame (minibuffer-window frame))))
768 ;; For minibufferless frames, frameset--mini is a cons
769 ;; (nil . FRAME-ID), where FRAME-ID is the frameset--id of
770 ;; the frame containing its minibuffer window.
771 ;; FRAME-ID can be set to nil, if FRAME-LIST doesn't contain
772 ;; the minibuffer frame of a minibufferless frame; we allow
773 ;; it without trying to second-guess the user.
774 (set-frame-parameter
775 frame
776 'frameset--mini
777 (cons nil
778 (and mb-frame
779 (frameset-frame-id mb-frame))))))))))
749 780
750;;;###autoload 781;;;###autoload
751(cl-defun frameset-save (frame-list 782(cl-defun frameset-save (frame-list
@@ -768,7 +799,7 @@ PROPERTIES is a user-defined property list to add to the frameset."
768 (cl-delete-if-not predicate list) 799 (cl-delete-if-not predicate list)
769 list))) 800 list)))
770 fs) 801 fs)
771 (frameset--record-minibuffer-relationships frames) 802 (frameset--record-relationships frames)
772 (setq fs (frameset--make 803 (setq fs (frameset--make
773 :app app 804 :app app
774 :name name 805 :name name
@@ -993,6 +1024,14 @@ Internal use only."
993 (frameset--initial-params filtered-cfg)))) 1024 (frameset--initial-params filtered-cfg))))
994 (puthash frame :created frameset--action-map)) 1025 (puthash frame :created frameset--action-map))
995 1026
1027 ;; Try to assign parent-frame right here - it will improve things
1028 ;; for minibuffer-less child frames.
1029 (let* ((frame-id (frame-parameter frame 'frameset--parent-frame))
1030 (parent-frame
1031 (and frame-id (frameset-frame-with-id frame-id))))
1032 (when (frame-live-p parent-frame)
1033 (set-frame-parameter frame 'parent-frame parent-frame)))
1034
996 (modify-frame-parameters frame 1035 (modify-frame-parameters frame
997 (if (eq (frame-parameter frame 'fullscreen) fullscreen) 1036 (if (eq (frame-parameter frame 'fullscreen) fullscreen)
998 ;; Workaround for bug#14949 1037 ;; Workaround for bug#14949
@@ -1205,6 +1244,29 @@ All keyword parameters default to nil."
1205 (error 1244 (error
1206 (delay-warning 'frameset (error-message-string err) :error)))))) 1245 (delay-warning 'frameset (error-message-string err) :error))))))
1207 1246
1247 ;; Setting the parent frame after the frame has been created is a
1248 ;; pain because one can see the frame move on the screen. Ideally,
1249 ;; we would restore minibuffer equipped child frames after their
1250 ;; respective parents have been made but this might interfere with
1251 ;; the reordering of minibuffer frames. Left to the experts ...
1252 (dolist (frame (frame-list))
1253 (let* ((frame-id (frame-parameter frame 'frameset--parent-frame))
1254 (parent-frame
1255 (and frame-id (frameset-frame-with-id frame-id))))
1256 (when (and (not (eq (frame-parameter frame 'parent-frame) parent-frame))
1257 (frame-live-p parent-frame))
1258 (set-frame-parameter frame 'parent-frame parent-frame)))
1259 (let* ((frame-id (frame-parameter frame 'frameset--delete-before))
1260 (delete-before
1261 (and frame-id (frameset-frame-with-id frame-id))))
1262 (when (frame-live-p delete-before)
1263 (set-frame-parameter frame 'delete-before delete-before)))
1264 (let* ((frame-id (frame-parameter frame 'frameset--mouse-wheel-frame))
1265 (mouse-wheel-frame
1266 (and frame-id (frameset-frame-with-id frame-id))))
1267 (when (frame-live-p mouse-wheel-frame)
1268 (set-frame-parameter frame 'mouse-wheel-frame mouse-wheel-frame))))
1269
1208 ;; In case we try to delete the initial frame, we want to make sure that 1270 ;; In case we try to delete the initial frame, we want to make sure that
1209 ;; other frames are already visible (discussed in thread for bug#14841). 1271 ;; other frames are already visible (discussed in thread for bug#14841).
1210 (sit-for 0 t) 1272 (sit-for 0 t)