在模式行中确定窗口焦点?

时间:2014-09-26 14:22:45

标签: emacs elisp

是否有正确的谓词用于确定窗口是否在模式行中具有焦点?我正在尝试在我的模式行中做一些需要比使用mode-line-inactive更灵活的事情。

我一直在做:

(defun window-has-focus-p ()
  "When called in eval sexp in mode or header line template,
returns true if this is the active window."
  (eq
   (frame-selected-window)
   (get-buffer-window)))

它在我的两台计算机上工作了好几个月(Windows 7和Debian)。但是,我昨天尝试在另一个Debian盒子上使用它,它在每个窗口的每个模式行中报告t ......完全坏了。

我无法为此目的找到一个标准的谓词调用,我无法弄清楚为什么这个hacked-up似乎在某些设备而不是其他设备上工作。另外,我确实使用 M - 评估了(force-mode-line-update t),但没有帮助。

Emacs版本为24.3

2 个答案:

答案 0 :(得分:2)

在为给定窗口评估模式行格式时,此窗口暂时为selected-window。在Emacs< = 24.3中,这只是中途:selected-window已更改,但不是frame-selected-window。这意味着暂时(frame-selected-window)不等于(selected-window)并且打破此(通常)不变量是各种角落案例错误的来源。所以我们在24.4中修复它,这意味着你的代码坏了。

要使其在24.4中运行,您需要保存"选择窗口"在处理模式行格式之前由用户看到。 你可以用

做到这一点
(defvar my-real-selected-window nil)
(add-function :before pre-redisplay-function
              (lambda (_wins) (setq my-real-selected-window (selected-window))))

然后,您可以在my-real-selected-window中使用mode-line-format来了解哪个窗口是应该特别突出显示的窗口。

答案 1 :(得分:1)

我一直在我的配置中使用它

;;; active modeline detection hack
(add-hook 'post-command-hook
          (lambda ()
            (when (not (minibuffer-selected-window))
              (setq powerline-selected-window (selected-window)))))

也许post-command-hook不是最优雅的解决方案,但对我来说是正常的。