mozcの候補をposframeで表示するEmacs拡張を作った

最近家に帰ってからめっきりプログラミングをしなくなってしまいました。いろいろやることがあると同時並行では難しいですね。 さて、今回はmozcの候補表示pluginを作ってみたというお話です。 <!–more–> https://github.com/derui/mozc-posframe mozcの候補表示は、標準で存在する Echo Areaへの表示、overlayでの表示のほか、 mozc-popup という拡張があり、大抵はこれを利用している方が多そうです。私もこれを利用していました。 (Emacs上での日本語入力にfcitxとかを利用している人は対象外です。そういう人のほうが多いんだろうか・・・) mozc-popupの利点 mozc-popupを利用していたのは、やはり利便性を重視してのことでしたが、特に以下の点がキーだったと思います。 変換位置と候補が近い overlayでもだいたい一緒ですが 実績あるpopup.elの利用 Spacemacsから入った人は知らないかもしれない、auto-completeで熟成したpopup表示に特化したlibraryです この結果、標準のoverlayよりも高速でした だんだんででくる問題点 mozc-popupを利用する前は、mozc + popupという組み合わせで長年使っていましたが、最近色々と問題が見えるようになってきました。 org-modeとpopup.elの相性が悪い 新しい拡張を作ることにした最大の契機 特に多数の折りたたみがあるときに顕著で、表示までの時間や、表示の崩れが非常に激しかった popup.elの更新頻度 一時代を築いたpopup.elですが、companyが台頭してからはだいぶ表舞台から消えてしまった感があります その仕組み上も複雑で、メンテナンスが困難だという話も child frameという潮流 Emacs 26から、frameに大きな拡張が入り、child frameと呼ばれる形態が可能になりました。端的に言うと、frameをfloating windowとして扱うことができる、というものです。 すでに様々なライブラリで利用されており、名実ともにEmacs26の目玉機能となっています。(個人の観測範囲では) https://github.com/sebastiencs/company-box https://github.com/emacs-lsp/lsp-ui しかし、あくまでframeを扱うものであるため、そのままだとpixel単位での操作が必要となり、非常に煩雑です。WIN32 APIでwindow作っていた時代になった気分です。それをラッピングしたlibraryが、 posframe です。 mozc + posframe 前述したmozc-popupの問題は、つまるところoverlayでの表現に限界があった、ということに尽きると思います。overlayはあくまでtextのpropertyでしかないので、複数のoverlayが設定された場合、その時時で異なる問題が出るであろうことは想像に難くありません PCで日本語を入力する場合、大抵はIMEを使うかと思います。Windows/macOS/Linux いずれも、候補表示そのものは 独立したWindow です。つまり、Child frameをこの用途に使うと丁度いいんじゃないか?というのは前々から考えていました。 すでにあるだろうと探してもなかったので自作することにしたわけですが。 mozc-popupとの比較 Pros org-modeやそれ以外でも、候補表示の時間がほぼ一定 調整の余地はありますが 表示崩れがない これがposframeを利用する最大の利点です 独立したframeを表示しているだけなので、複数のoverlayが設定されることに起因する問題から開放されています Cons install方法が煩雑 melpaとかに入っていないので、どうしてもstraight.elとかが必要です Emacs26以上 + GUIでないと動かない 個人的に、端末上で利用するのはもはや趣味の領域でしかないと思ってます 描画性能もほとんどの場合GUIツールキットの方が早いし、ChildFrameは性質上GUIでしか動きません 端末しかない?諦めてVimった方が幸せになれるかと・・・ ありがとう、mozc-popup mozc-posframeは、mozc-popupのソースを7割くらい流用しています。mozc-popupがなければ、そもそもmozc-posframeを作ろうと思ってなかったと思います。 まだmozc-posframeは若干のバグや性能向上の余地がありますが、すでに常用できるものになっている(というか常用してる)と思うので、よければ利用してみてください。

June 7, 2019 · derui

Emacsの設定を色々いじった -その1-

いろいろ書くネタを探しているうちに4月になってしまったので、3月にやったEmacs改善について書いてみようかと思います。結構量が多くなったので、分割します。 <!–more–> なお、かなりの部分で Emacsモダン化計画 -かわEmacs編- を参考にさせていただきました。私の.emacs.dはGithubにおいてあります。 https://github.com/derui/dot.emacs.d doom-modeline + all-the-icons doom-modeline all-the-icons 最初に入れたパッケージです。modelineが一気にかっこよくなりました。all-the-iconsでは色々調べましたが・・・。 (use-package all-the-icons :custom (all-the-icons-scale-factor 1.0)) (use-package doom-modeline :commands (doom-modeline-def-modeline) :custom (doom-modeline-buffer-file-name-style 'truncate-with-project) (doom-modeline-icon t) (doom-modeline-major-mode-icon nil) (doom-modeline-minor-modes nil) :hook (after-init . doom-modeline-mode) :config (line-number-mode 0) (column-number-mode 0) (doom-modeline-def-modeline 'main '(bar workspace-number window-number evil-state ryo-modal xah-fly-keys matches buffer-info remote-host buffer-position parrot selection-info) '(misc-info persp-name debug minor-modes input-method major-mode process vcs checker))) なお、全体的にuse-packageを利用しています。 which-key which-key ...

April 4, 2019 · derui

all-the-iconsとCicaの組み合わせでアイコンがずれる

最近 Emacsモダン化計画 -かわEmacs編- を参考にしつつ、しばらくいじっていなかったEmacsをいじっています。しかし、all-the-iconsを導入したときに、アイコンが色々?な感じになってしまいました。 原因を探ったり何なりで解決できたので、備忘録として残しておきます。 <!–more–> 発生していた事象 普段Emacs上ではCicaフォントを使っています。以前はRictyを利用していましたが、Rictyよりもこちらのほうが好みだったので、1年くらい前から愛用しています。 https://github.com/miiton/Cica ところが、Cicaを利用している環境でall-the-iconsを有効にしたら、色々と問題が発生しました。スクショは撮っていなかったので画像はありませんが、次のような状態でした。 doom-modelineのアイコンが明らかにおかしい 保存アイコンが gopher になってたり、gopherのアイコン自体が違ってたり Gitのアイコンが地球儀になってたり アイコンのサイズが色々おかしい all-the-iconsのアイコンを全部表示すると、明らかに別のアイコンが表示されている という感じで、もう完全に何かが干渉していることは明らかでした。 調査 だいたいまずいのはフォント設定周りだろうと、使っているフォント設定自体を無効化すると、うまい具合に表示できました。これから、以下のような仮定を立てました。 追加で行っている設定では、 create-fontset-from-ascii-font で作ったものに set-fontset-font していた set-fontset-font の範囲は 'unicode だった=all-the-iconsで利用している範囲を上書きしていた? 仕様上、一回設定したものを上書きできないっぽい=Cica側の特徴に原因が? ここまでで、大体Cicaに設定されている絵文字部分とall-the-iconsが干渉している、と判断しました。 解決した 最終的には、Cicaから絵文字を除いたバージョンに切り替え、フォント設定を以下のようにしました。 (defun my:font-initialize () "Initialize fonts on window-system" (interactive) (cond ((eq window-system 'x) (let* ((size my:font-size) (asciifont "Cica") (jpfont "Cica") (h (round (* size 10))) (jp-fontspec (font-spec :family jpfont))) (set-face-attribute 'default nil :family asciifont :height h) (unless (string= asciifont jpfont) (set-fontset-font nil 'unicode jp-fontspec nil 'append)) (when (featurep 'all-the-icons) (set-fontset-font nil 'unicode (font-spec :family (all-the-icons-alltheicon-family)) nil 'append) (set-fontset-font nil 'unicode (font-spec :family (all-the-icons-material-family)) nil 'append) (set-fontset-font nil 'unicode (font-spec :family (all-the-icons-fileicon-family)) nil 'append) (set-fontset-font nil 'unicode (font-spec :family (all-the-icons-faicon-family)) nil 'append) (set-fontset-font nil 'unicode (font-spec :family (all-the-icons-octicon-family)) nil 'append) (set-fontset-font nil 'unicode (font-spec :family (all-the-icons-wicon-family)) nil 'append)) (message (format "Setup for %s with %f" asciifont size)))) (t (message "Not have window-system")))) この設定を、after-init-hookで実行しています。元々asciiとjpで異なるフォントを利用していた名残の設定だったので、整理しました。普通にset-face-attributeだけでいいんじゃないの?と思われるかもしれませんが、部屋のデスクトップと現場のラップトップでフォントサイズを切り替えられるようにしているので、若干複雑な設定をしています。 ...

March 9, 2019 · derui