emacs-elpa-diffs
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[elpa] externals/posframe 9a6bb60: Add parent-frame-poshandler argument


From: ELPA Syncer
Subject: [elpa] externals/posframe 9a6bb60: Add parent-frame-poshandler argument to posframe-show.
Date: Thu, 8 Apr 2021 02:57:11 -0400 (EDT)

branch: externals/posframe
commit 9a6bb60c55cea7627764f42fe3c296dea6abec8c
Author: Feng Shu <tumashu@163.com>
Commit: Feng Shu <tumashu@163.com>

    Add parent-frame-poshandler argument to posframe-show.
    
    * posframe.el (posframe--create-posframe, posframe-show)
    (posframe-run-poshandler): Handle parent-frame-poshandler argument.
    (posframe-parent-frame-poshandler-xwininfo): New function.
---
 posframe.el | 81 +++++++++++++++++++++++++++++++++++++++++++++++++++----------
 1 file changed, 68 insertions(+), 13 deletions(-)

diff --git a/posframe.el b/posframe.el
index 3148389..58292e6 100644
--- a/posframe.el
+++ b/posframe.el
@@ -324,7 +324,7 @@ This posframe's buffer is BUFFER-OR-NAME."
                        ,(when font
                           (cons 'font font))
                        (title . "posframe")
-                       (parent-frame . ,(or parent-frame (window-frame)))
+                       (parent-frame . ,parent-frame)
                        (keep-ratio ,keep-ratio)
                        (posframe-buffer . ,(cons (buffer-name buffer)
                                                  buffer))
@@ -418,6 +418,7 @@ This posframe's buffer is BUFFER-OR-NAME."
                          refresh
                          accept-focus
                          hidehandler
+                         parent-frame-poshandler
                          &allow-other-keys)
   "Pop up a posframe and show STRING at POSITION.
 
@@ -557,6 +558,18 @@ The builtin hidehandler functions are listed below:
 1. `posframe-hidehandler-when-buffer-switch'
 
 
+PARENT-FRAME-POSHANDLER is a function, posframe can get current
+frame's position in screen by call this function, PLEASE NOTE:
+this argument will disable child-frame feature, the user case at
+the moment I know is let ivy-posframe run properly in EXWM
+environment (let posframe show on the other appliction window).
+DO NOT USE UNLESS NECESSARY. an example parent frame poshandler
+function is:
+
+1. `posframe-parent-frame-poshandler-xwininfo'
+
+
+
 You can use `posframe-delete-all' to delete all posframes."
   (let* ((position (or (funcall posframe-arghandler buffer-or-name :position 
position) (point)))
          (poshandler (funcall posframe-arghandler buffer-or-name :poshandler 
poshandler))
@@ -587,6 +600,7 @@ You can use `posframe-delete-all' to delete all posframes."
          (refresh (funcall posframe-arghandler buffer-or-name :refresh 
refresh))
          (accept-focus (funcall posframe-arghandler buffer-or-name 
:accept-focus accept-focus))
          (hidehandler (funcall posframe-arghandler buffer-or-name :hidehandler 
hidehandler))
+         (parent-frame-poshandler (funcall posframe-arghandler buffer-or-name 
:parent-frame-poshandler parent-frame-poshandler))
          ;;-----------------------------------------------------
          (buffer (get-buffer-create buffer-or-name))
          (parent-window (selected-window))
@@ -601,6 +615,9 @@ You can use `posframe-delete-all' to delete all posframes."
          (parent-frame (window-frame parent-window))
          (parent-frame-width (frame-pixel-width parent-frame))
          (parent-frame-height (frame-pixel-height parent-frame))
+         (parent-frame-position
+          (when (functionp parent-frame-poshandler)
+            (funcall parent-frame-poshandler)))
          (font-width (default-font-width))
          (font-height (with-current-buffer (window-buffer parent-window)
                         (posframe--get-font-height position)))
@@ -627,7 +644,9 @@ You can use `posframe-delete-all' to delete all posframes."
             (posframe--create-posframe
              buffer
              :font font
-             :parent-frame parent-frame
+             :parent-frame
+             (unless parent-frame-position
+               parent-frame)
              :left-fringe left-fringe
              :right-fringe right-fringe
              :border-width border-width
@@ -671,6 +690,7 @@ You can use `posframe-delete-all' to delete all posframes."
                   :parent-frame parent-frame
                   :parent-frame-width parent-frame-width
                   :parent-frame-height parent-frame-height
+                  :parent-frame-position parent-frame-position
                   :parent-window parent-window
                   :parent-window-top parent-window-top
                   :parent-window-left parent-window-left
@@ -988,17 +1008,32 @@ of `posframe-show'."
   (if (equal info posframe--last-poshandler-info)
       posframe--last-posframe-pixel-position
     (setq posframe--last-poshandler-info info)
-    (funcall
-     (or (plist-get info :poshandler)
-         (let ((position (plist-get info :position)))
-           (cond ((integerp position)
-                  #'posframe-poshandler-point-bottom-left-corner)
-                 ((and (consp position)
-                       (integerp (car position))
-                       (integerp (cdr position)))
-                  #'posframe-poshandler-absolute-x-y)
-                 (t (error "Posframe: have no valid poshandler")))))
-     info)))
+    (let* ((posframe-width (plist-get info :posframe-width))
+           (posframe-height (plist-get info :posframe-height))
+           (parent-frame-position (plist-get info :parent-frame-position))
+           (parent-frame-x (or (car parent-frame-position) 0))
+           (parent-frame-y (or (cdr parent-frame-position) 0))
+           (position (funcall
+                      (or (plist-get info :poshandler)
+                          (let ((position (plist-get info :position)))
+                            (cond ((integerp position)
+                                   
#'posframe-poshandler-point-bottom-left-corner)
+                                  ((and (consp position)
+                                        (integerp (car position))
+                                        (integerp (cdr position)))
+                                   #'posframe-poshandler-absolute-x-y)
+                                  (t (error "Posframe: have no valid 
poshandler")))))
+                      info))
+           (x (car position))
+           (y (cdr position)))
+      (if (not parent-frame-position)
+          position
+        (when (< x 0)
+          (setq x (+ posframe-width x)))
+        (when (< y 0)
+          (setq y (+ posframe-height y)))
+        (cons (+ parent-frame-x x)
+              (+ parent-frame-y y))))))
 
 (cl-defun posframe-poshandler-argbuilder (&optional
                                           child-frame
@@ -1330,6 +1365,26 @@ bottom center.  The structure of INFO can be found in 
docstring of
           (+ window-top window-height
              (- 0 mode-line-height posframe-height)))))
 
+(defun posframe-parent-frame-poshandler-xwininfo ()
+  "Parent frame poshander function.
+Get the position of currentframe with the help of xwininfo."
+  (with-temp-buffer
+    (let ((case-fold-search nil))
+      (call-process shell-file-name nil t nil shell-command-switch
+                   (format "xwininfo -display %s -id %s"
+                           (frame-parameter nil 'display)
+                           (frame-parameter nil 'window-id)))
+      (goto-char (point-min))
+      (search-forward "\n  Absolute")
+      (cons (string-to-number
+             (buffer-substring-no-properties
+             (search-forward "X: ")
+             (line-end-position)))
+           (string-to-number
+             (buffer-substring-no-properties
+             (search-forward "Y: ")
+             (line-end-position)))))))
+
 
 (provide 'posframe)
 



reply via email to

[Prev in Thread] Current Thread [Next in Thread]