Skip to content

Commit abb5775

Browse files
authored
Improved macOS behavior. (#1035)
Manage frame moving and display a screenshot of qwidget in background under macOS.
1 parent 3bc9c73 commit abb5775

File tree

3 files changed

+85
-84
lines changed

3 files changed

+85
-84
lines changed

core/view.py

+3
Original file line numberDiff line numberDiff line change
@@ -158,3 +158,6 @@ def try_hide_top_view(self):
158158
def destroy_view(self):
159159
# print("Destroy: ", self.buffer.url)
160160
self.destroy()
161+
162+
def screen_shot(self):
163+
return self.grab()

eaf.el

+56-84
Original file line numberDiff line numberDiff line change
@@ -1035,101 +1035,73 @@ provide at least one way to let everyone experience EAF. ;)"
10351035
(when (eaf-emacs-not-use-reparent-technology)
10361036
(cond
10371037
((eq system-type 'darwin)
1038-
(defcustom eaf--mac-safe-focus-change t
1039-
"Whether to verify the active application on Emacs frame focus change.
1040-
1041-
Only set this to nil if you do not use the mouse inside EAF buffers.
1042-
The benefit of setting this to nil is that application switching
1043-
is a lot faster but could be buggy."
1044-
:type 'boolean)
10451038

10461039
(defvar eaf--mac-switch-to-python nil
10471040
"Record if Emacs should switch to Python process.")
10481041

1049-
(defvar eaf--mac-has-focus t
1050-
"Record if Emacs has focus.")
1051-
1052-
(defvar eaf--mac-unsafe-focus-change-timer nil
1053-
"Use timer to ignore spurious focus events.
1054-
1055-
This is only used when `eaf--mac-safe-focus-change' is nil.
1056-
1057-
See
1058-
https://old.reddit.com/r/emacs/comments/\
1059-
kxsgtn/ignore_spurious_focus_events_for/")
1060-
1061-
(defun eaf--mac-unsafe-focus-change-handler ()
1062-
;; ignore errors related to
1063-
;; (wrong-type-argument eaf-epc-manager nil)
1064-
(ignore-errors
1065-
(if (frame-focus-state)
1066-
(eaf--mac-unsafe-focus-in)
1067-
(eaf--mac-unsafe-focus-out)))
1068-
(setq eaf--mac-unsafe-focus-change-timer nil))
1069-
10701042
(defun eaf--mac-focus-change ()
10711043
"Manage Emacs's focus change."
1072-
(if eaf--mac-safe-focus-change
1073-
(if (executable-find "app-frontmost")
1074-
(let ((front (shell-command-to-string "app-frontmost --name")))
1075-
(cond
1076-
((member front (list "Python\n" "python3\n"))
1077-
(setq eaf--mac-switch-to-python t))
1078-
1079-
((string= "Emacs\n" front)
1080-
(cond
1081-
(eaf--mac-switch-to-python
1082-
(setq eaf--mac-switch-to-python nil))
1083-
((not eaf--mac-has-focus)
1084-
(run-with-timer 0.1 nil #'eaf--mac-focus-in))
1085-
(eaf--mac-has-focus
1086-
(eaf--mac-focus-out))))
1087-
(t (eaf--mac-focus-out))))
1088-
(message "Please install app-frontmost from https://pypi.org/project/mac-app-frontmost/ to make EAF works with macOS platform."))
1089-
(setq eaf--mac-unsafe-focus-change-timer
1090-
(unless eaf--mac-unsafe-focus-change-timer
1091-
(run-at-time 0.06 nil
1092-
#'eaf--mac-unsafe-focus-change-handler)))))
1093-
1094-
(defun eaf--mac-replace-eaf-buffers ()
1095-
(dolist (window (window-list))
1096-
(select-window window)
1097-
(when (eq major-mode 'eaf-mode)
1098-
(get-buffer-create "*eaf temp*")
1099-
(switch-to-buffer "*eaf temp*" t))))
1100-
1101-
(defun eaf--mac-focus-in ()
1102-
(setq eaf--mac-has-focus t)
1103-
(ignore-errors
1104-
(set-window-configuration
1105-
(frame-parameter (selected-frame) 'eaf--mac-frame))
1106-
(bury-buffer "*eaf temp*")))
1107-
1108-
(defun eaf--mac-focus-out (&optional frame)
1109-
(when eaf--mac-has-focus
1110-
(setq eaf--mac-has-focus nil)
1111-
(set-frame-parameter (or frame (selected-frame))
1112-
'eaf--mac-frame (current-window-configuration))
1113-
(eaf--mac-replace-eaf-buffers)))
1114-
1115-
(defun eaf--mac-unsafe-focus-in ()
1116-
(eaf-call-async "show_top_views")
1117-
(set-window-configuration
1118-
(frame-parameter (selected-frame) 'eaf--mac-frame)))
1119-
1120-
(defun eaf--mac-unsafe-focus-out (&optional frame)
1121-
(eaf-call-async "hide_top_views")
1122-
(set-frame-parameter (or frame (selected-frame)) 'eaf--mac-frame
1123-
(current-window-configuration)))
1044+
(let ((front (shell-command-to-string "app-frontmost --name")))
1045+
(cond
1046+
((member front (list "Python\n" "python3\n"))
1047+
(setq eaf--mac-switch-to-python t))
1048+
((string= "Emacs\n" front)
1049+
(if eaf--mac-switch-to-python
1050+
(setq eaf--mac-switch-to-python nil)
1051+
(run-with-timer 0.1 nil #'eaf--mac-focus-update)))
1052+
(t (eaf--mac-focus-out)))))
1053+
1054+
(defun eaf--mac-focus-update ()
1055+
"Hide all eaf buffers, and then display new eaf buffers at front."
1056+
(eaf--mac-focus-out)
1057+
(when (frame-focus-state)
1058+
(dolist (window (window-list (selected-frame)))
1059+
(with-current-buffer (window-buffer window)
1060+
(when (derived-mode-p 'eaf-mode)
1061+
(eaf-call-async "show_buffer_view" eaf--buffer-id))))))
11241062

1063+
(defun eaf--mac-focus-out ()
1064+
"Prepare the screenshot and hide all eaf buffers."
1065+
(dolist (frame (frame-list))
1066+
(dolist (window (window-list frame))
1067+
(with-current-buffer (window-buffer window)
1068+
(when (derived-mode-p 'eaf-mode)
1069+
(eaf--clip-image window)
1070+
(eaf-call-sync "hide_buffer_view" eaf--buffer-id))))))
1071+
1072+
(add-to-list 'move-frame-functions #'eaf-monitor-configuration-change)
1073+
1074+
(defun eaf--clip-image (window)
1075+
"Clip the image of the qwidget."
1076+
(eaf-call-sync "clip_buffer" eaf--buffer-id)
1077+
(eaf--display-image window))
1078+
1079+
(defun eaf--display-image (window)
1080+
"Display the image of qwidget in eaf buffer."
1081+
(clear-image-cache)
1082+
(erase-buffer)
1083+
(insert-image (create-image (concat eaf-config-location eaf--buffer-id ".jpeg") 'jpeg nil
1084+
:width (window-pixel-width window)
1085+
:height (window-pixel-height window))))
1086+
11251087
(defun eaf--mac-delete-frame-handler (frame)
1126-
(if eaf--mac-safe-focus-change
1127-
(eaf--mac-focus-out frame)
1128-
(eaf--mac-unsafe-focus-out frame)))
1088+
(eaf--mac-focus-out))
1089+
1090+
(defun eaf--mac-clear-images-cache-handler ()
1091+
"Clear all images when quitting Emacs."
1092+
(shell-command-to-string (concat "rm " eaf-config-location "*.jpeg")))
1093+
1094+
(add-hook 'kill-emacs-hook #'eaf--mac-clear-images-cache-handler)
11291095

11301096
(add-function :after after-focus-change-function #'eaf--mac-focus-change)
1131-
(add-hook 'eaf-stop-process-hook (lambda () (remove-function after-focus-change-function #'eaf--mac-focus-change)))
1097+
1098+
(add-hook 'eaf-stop-process-hook
1099+
(lambda ()
1100+
(remove-function after-focus-change-function #'eaf--mac-focus-change)
1101+
(remove-hook 'move-frame-functions #'eaf-monitor-configuration-change)))
1102+
11321103
(add-to-list 'delete-frame-functions #'eaf--mac-delete-frame-handler))
1104+
11331105
(t
11341106
(defun eaf--wayland-focus-change ()
11351107
"Manage Emacs's focus change."

eaf.py

+26
Original file line numberDiff line numberDiff line change
@@ -317,6 +317,32 @@ def kill_buffer(self, buffer_id):
317317

318318
self.buffer_dict[buffer_id].destroy_buffer()
319319
self.buffer_dict.pop(buffer_id, None)
320+
321+
@PostGui()
322+
def clip_buffer(self, buffer_id):
323+
'''Clip the image of buffer for display.'''
324+
eaf_config_dir = get_emacs_config_dir()
325+
for key in list(self.view_dict):
326+
view = self.view_dict[key]
327+
if buffer_id == view.buffer_id:
328+
image = view.screen_shot().save(os.path.join(eaf_config_dir, buffer_id + ".jpeg"))
329+
#eval_in_emacs('eaf--display-image', [])
330+
331+
@PostGui()
332+
def show_buffer_view(self, buffer_id):
333+
'''Show the single buffer view.'''
334+
for key in list(self.view_dict):
335+
view = self.view_dict[key]
336+
if buffer_id == view.buffer_id:
337+
view.try_show_top_view()
338+
339+
@PostGui()
340+
def hide_buffer_view(self, buffer_id):
341+
'''Hide the single buffer view.'''
342+
for key in list(self.view_dict):
343+
view = self.view_dict[key]
344+
if buffer_id == view.buffer_id:
345+
view.try_hide_top_view()
320346

321347
@PostGui()
322348
def kill_emacs(self):

0 commit comments

Comments
 (0)