Skip to content

Instantly share code, notes, and snippets.

@wsgac
Created May 9, 2025 14:41
Show Gist options
  • Save wsgac/7b701d85d7f7582fd5580d3d0edbcad8 to your computer and use it in GitHub Desktop.
Save wsgac/7b701d85d7f7582fd5580d3d0edbcad8 to your computer and use it in GitHub Desktop.
Kanji-mode exploration with tooltips
;;;;;;;;;;;;;;
;; Tooltips ;;
;;;;;;;;;;;;;;
;; TODO: These need polishing and weaving them into the broader
;; picture
(defun get-point-coordinates ()
(let* ((posn (posn-at-point))
(abs-pos (posn-x-y posn))
(win (posn-window posn))
(edges (window-inside-pixel-edges win)))
(cons (+ (car abs-pos) (car edges))
(+ (cdr abs-pos) (cadr edges)))))
(defun hiragana-tooltip ()
(interactive)
(setq current-prefix-arg '-)
(let ((inhibit-message t))
(call-interactively 'kanji-mode-kanji-to-hiragana))
(let* ((point-coords (get-point-coordinates))
(tooltip-frame-parameters
(cl-list* `(left . ,(car point-coords))
`(bottom . ,(cdr point-coords))
tooltip-frame-parameters)))
(tooltip-show (current-kill 0 t))))
;; First suggestion by ChatGPT - timeout
(defun show-svg-tooltip (svg-file)
"Show an SVG image in a child frame positioned at point."
(let* ((coords (get-point-coordinates))
(buf (get-buffer-create "*svg-tooltip*"))
(frame (make-frame
`((parent-frame . ,(selected-frame))
(left . ,(car coords))
(top . ,(cdr coords))
(width . 40)
(height . 20)
(undecorated . t)
(minibuffer . nil)
(visibility . nil)
(no-accept-focus . t)
(no-focus-on-map . t)
(border-width . 0)
(internal-border-width . 0)
(vertical-scroll-bars . nil)
(horizontal-scroll-bars . nil)
(menu-bar-lines . 0)
(tool-bar-lines . 0)
(line-spacing . 0)
(unsplittable . t)
(skip-taskbar . t)
(cursor-type . nil)
(left-fringe . 0)
(right-fringe . 0)
(child-frame-border-width . 0)
(no-other-frame . t)
(background-color . "white")
(type . child-frame)
(visibility . t)))))
(with-current-buffer buf
(erase-buffer)
(insert-image (create-image svg-file 'svg nil)))
(set-window-buffer (frame-root-window frame) buf)
(make-frame-visible frame)
;; Optionally: auto-hide after a timeout
(run-with-timer 3 nil (lambda () (delete-frame frame)))
))
;; ChatGPT-inspired solution to manually quit child frames on C-g
(let ((frame (make-frame `((parent-frame . ,(selected-frame))
(no-accept-focus . t)
(minibuffer . nil)
(undecorated . t)
(left . 200)
(top . 200)
(width . 40)
(height . 10)
(visibility . nil)))))
(make-frame-visible frame)
;; Handle `C-g` quit:
(condition-case err
(progn
;; Block and wait for user action
(while t
(sit-for 1))) ; wait passively
(quit
(delete-frame frame)
(message "Child frame deleted due to C-g."))))
;; Combined version
(defun show-svg-tooltip (svg-file)
"Show an SVG image in a child frame positioned at point."
(let* ((coords (get-point-coordinates))
(buf (get-buffer-create "*svg-tooltip*"))
(frame (make-frame
`((parent-frame . ,(selected-frame))
(left . ,(car coords))
(top . ,(cdr coords))
(width . 40)
(height . 20)
(undecorated . t)
(minibuffer . nil)
(visibility . nil)
(no-accept-focus . t)
(no-focus-on-map . t)
(border-width . 0)
(internal-border-width . 0)
(vertical-scroll-bars . nil)
(horizontal-scroll-bars . nil)
(menu-bar-lines . 0)
(tool-bar-lines . 0)
(line-spacing . 0)
(unsplittable . t)
(skip-taskbar . t)
(cursor-type . nil)
(left-fringe . 0)
(right-fringe . 0)
(child-frame-border-width . 0)
(no-other-frame . t)
(background-color . "white")
(type . child-frame)
(visibility . t)))))
(with-current-buffer buf
(erase-buffer)
(insert-image (create-image svg-file 'svg nil)))
(set-window-buffer (frame-root-window frame) buf)
(make-frame-visible frame)
;; Optionally: auto-hide after a timeout
;; (run-with-timer 3 nil (lambda () (delete-frame frame)))
(condition-case err
(progn
;; Block and wait for user action
(while t
(sit-for 1))) ; wait passively
(quit
(delete-frame frame)
(message "Child frame deleted due to C-g.")))
))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment