EmacsをWindowsで最大化またはフルスクリーンで使う

言葉の意味

  • 最大化:タイトルバーの右の最大化ボタンで最大化した状態のこと。タイトルバーやタスクバーは表示されている状態
  • フルスクリーン:最大化した状態でタイトルバーとタスクバーが表示されていない状態のこと。全画面

問題点

GNU EmacsWindowsで最大化またはフルスクリーンで使おうとすると、こういう問題が起きる。

  1. 画面を最大化して起動するオプション --maximized, -mm が効かない
  2. 画面をフルスクリーンで起動するオプション --fullscreen, -fs が効かない
  3. 画面を最大化すると、画面の下や右に隙間ができることがある
  4. 画面を最大化した状態で、メニューバーを出したり消したりすると、画面のサイズが変わる
  5. 画面を最大化した状態で、フォントのサイズを変えると、画面のサイズが変わる
  6. (set-frame-parameter (selected-frame) 'fullscreen 'maximized) とかが効かない

それぞれ、原因と対策を考えてみる。

1. 画面を最大化して起動するオプション --maximized, -mm が効かない

現象
emacs.exe --maximized    ←効かない
emacs.exe -mm            ←効かない
runemacs.exe --maximized ←効かない
runemacs.exe -mm         ←効かない
原因

効くように作られていない。

対策

とりあえずの対策は、GNU Emacs FAQ 5.49 How can I start Emacs in fullscreen mode on MS-Windows? によると、.emacs

     (add-hook 'term-setup-hook
               #'(lambda () (w32-send-sys-command ?\xF030)))

と書いておくと最大化するらしいが、なぜか効果がなかった。

     (add-hook 'window-setup-hook
               #'(lambda () (w32-send-sys-command ?\xF030)))

にしたらできた。

根本的な対策は、ソースを修正する。
w32term.c, w32fns.cをなんとかするとどうにかなりそうな気がする(後述)。

2. 画面をフルスクリーンで起動するオプション --fullscreen, -fs が効かない

現象
emacs.exe --fullscreen    ←効かない
(以下省略)
原因

効くように作られていない。

対策

とりあえずの対策は、http://www.emacswiki.org/emacs/FullScreen にいろいろ書いてある。
emacs-fullscreen-win32, https://bitbucket.org/alexander_manenko/emacs-fullscreen-win32/wiki/Home
を入れる。

根本的な対策は、ソースを修正する。
w32term.c, w32fns.cをなんとかするとどうにかなりそうな気がする。
w32fns.cの修正がいくらなんでもいい加減なのが、何とかしたいところ。

diff -r 945b06ed9b49 -r 4332c25c5519 src/w32fns.c
--- a/src/w32fns.c	Sun Oct 28 23:10:16 2012 +0900
+++ b/src/w32fns.c	Thu Jan 17 18:59:42 2013 +0900
@@ -3691,9 +3691,15 @@
 
     case WM_EMACS_SETWINDOWPOS:
       {
-	WINDOWPOS * pos = (WINDOWPOS *) wParam;
-	return SetWindowPos (hwnd, pos->hwndInsertAfter,
-			     pos->x, pos->y, pos->cx, pos->cy, pos->flags);
+	WINDOWPLACEMENT wp;
+	GetWindowPlacement (hwnd, &wp);
+	if (wp.showCmd != SW_SHOWMAXIMIZED)
+	  {
+	    WINDOWPOS * pos = (WINDOWPOS *) wParam;
+	    return SetWindowPos (hwnd, pos->hwndInsertAfter,
+				 pos->x, pos->y, pos->cx, pos->cy, pos->flags);
+	  }
+	return 0;
       }
 
     case WM_EMACS_DESTROYWINDOW:
diff -r 945b06ed9b49 -r 4332c25c5519 src/w32term.c
--- a/src/w32term.c	Sun Oct 28 23:10:16 2012 +0900
+++ b/src/w32term.c	Thu Jan 17 18:59:42 2013 +0900
@@ -5385,6 +5385,18 @@
     {
       int width, height, ign;
 
+      if (f->want_fullscreen == FULLSCREEN_MAXIMIZED)
+        {
+          /*  --maximized, -mm */
+          my_show_window (f, FRAME_W32_WINDOW (f), SW_SHOWMAXIMIZED);
+        }
+      else if (f->want_fullscreen == FULLSCREEN_BOTH)
+        {
+          /* --fullscreen, -fs */
+          SetWindowLongPtr(FRAME_W32_WINDOW (f), GWL_STYLE, GetWindowLongPtr(FRAME_W32_WINDOW (f), GWL_STYLE) & ~(WS_CAPTION | WS_BORDER | WS_THICKFRAME));
+          my_show_window(f, FRAME_W32_WINDOW (f), SW_MAXIMIZE);
+        }
+
       x_real_positions (f, &f->left_pos, &f->top_pos);
 
       x_fullscreen_adjust (f, &width, &height, &ign, &ign);

3. 画面を最大化すると、画面の下や右に隙間ができることがある

現象

MS ゴシック10ポイントを設定して最大化した状態。
最大化しているのに、下に隙間ができている。

環境によって再現したりしなかったりする。
何の違いによるのか不明。
フォントのサイズを72ポイントとかにすると再現させやすい。

see emacs maximize issue on windows xp, http://debbugs.gnu.org/cgi/bugreport.cgi?bug=7678

原因

バグだと思う。
Emacsには、ウィンドウをリサイズしたときに、ウィンドウのサイズをフォントの高さと幅に揃える機能がある。
この機能がウィンドウを最大化したときも働いている。
環境によって正しく最大化されるのは、Windows側の問題でたまたま正しく最大化されているように見えるだけだと思う。

対策

ソースを修正する。

diff -r 9c3e91c74acd -r d339bfd31039 src/w32fns.c
--- a/src/w32fns.c	Sat Jan 12 12:49:34 2013 +0900
+++ b/src/w32fns.c	Sat Jan 12 13:12:50 2013 +0900
@@ -3590,7 +3590,7 @@
 		     - 2 * internal_border)
 	      % line_height;
 
-	    if (wdiff || hdiff)
+	    if ((wdiff || hdiff) && wp.showCmd != SW_SHOWMAXIMIZED)
 	      {
 		/* For right/bottom sizing we can just fix the sizes.
 		   However for top/left sizing we will need to fix the X

4. 画面を最大化した状態で、メニューバーを出したり消したりすると、画面のサイズが変わる

現象

最大化してM-x menu-bar-mode した状態。
最大化しているのに、下に隙間ができている。

原因

バグ?

対策

ソースを修正?

5. 画面を最大化した状態で、フォントのサイズを変えると、画面のサイズが変わる

現象

最大化して、フォントのサイズを変えた状態(MS ゴシック10ポイント→8ポイント)
最大化しているのに、画面が小さくなっている。

原因

バグ?

対策

ソースを修正?

6. (set-frame-parameter (selected-frame) 'fullscreen 'maximized) とかが効かない

現象
(set-frame-parameter (selected-frame) 'fullscreen 'maximized)  ←効かない
(set-frame-parameter (selected-frame) 'fullscreen 'fullboth)   ←効かない
(set-frame-parameter (selected-frame) 'fullscreen 'nil)        ←効かない
対策

w32term.c:6181あたりの

  /* terminal->fullscreen_hook = XTfullscreen_hook; */

をなんとかすればどうにかなりそうな気がする。