ひどい炎暑のさなか、皆さまいかがお過しでしょうか。地区の田植えやそれに伴なう各種作業に手を取られ、前回からちょっと間が空いてしまいましたが、今回はgrubの起動画面の中心を占める「ブートメニュー」を中心に紹介します。
ブートメニューの各種設定
「ブートメニュー(boot_menu)」は、文字通り「起動項目の選択メニュー」を装飾するためのパーツです。図1の「メニューボックス」という囲みの部分の表示方法を設定するのが「ブートメニュー」の役割です。
図1 起動メニュー画面の各パーツ
「メニューアイテム」として表示される各起動項目は“grub.cfg”のmenuentryやsubmenuの定義を引き継ぐので、「ブートメニュー」の役割はそれらをどう見栄えよく表示するかに限定されるものの、その分、ずいぶん細かい部分まで設定可能になっています。
まずは前回、説明を略したサンプル用“theme.txt”の「ブートメニュー」の項目を改めて見てみましょう。
$ cat -n /usr/share/grub/themes/starfield/theme.txt
...
23 + boot_menu {
24 left = 10%
25 width = 80%
26 top = 20%
27 height = 50%
28 item_font = "DejaVu Sans Regular 12"
29 item_color = "#000"
30 selected_item_font = "DejaVu Sans Bold 14"
31 selected_item_color= "#000"
32 selected_item_pixmap_style = "blob_*.png"
33 icon_height = 25
34 icon_width = 25
35 item_height = 26
36 item_padding = 0
37 item_icon_space = 0
38 item_spacing = 1
39 scrollbar = true
40 scrollbar_width = 20
41 scrollbar_thumb = "slider_*.png"
42 menu_pixmap_style = "boot_menu_*.png"
43 }
24〜27行目のleft、width、top、heightの設定は、「メニューボックス」を画面上のどこに表示するかの指定で、「画面の左端から画面幅の10%(left=10%)」、「上端から画面高の20%(top=20%)」それぞれ離し、「画面幅の80%(width=80%)x画面高の50%(height=50%)」のサイズで表示する」という意味になります。
28〜31行目は「メニューアイテム」の表示フォントに関する設定で、selected_item_fontとselected_item_colorは選択対象となった(フォーカスが当たった)項目のフォントと色、item_fontとitem_colorが対象外の項目の表示を指定します。この例では、フォントは同じ“DejaVu Sans”ファミリーですが、選択対象は「太字(Bold)」で「サイズも一回り大きく(14)」表示されます。
32行目のselected_item_pixmap_styleは後述する「スタイル・ボックス(styled box)」による装飾で、選択対象となった項目を明示するためのマーク用画像を指定しています。
少し行が前後しますが、35行目のitem_heightは各アイテムの高さの指定、36行目のitem_paddingはメニューボックスの上端、左端からどれだけ離してアイテム表示を始めるかの指定、38行目のitem_spacingはアイテム間の間隔の指定となります。これら“%”が付かない数字は「ピクセル(ドット)数」として解釈されます。
33〜34行目のicon_heightとicon_widthは、各起動項目(OSやディストリビューション)を示すアイコンのサイズ指定で、37行目のitem_icon_spaceはアイコンとアイテムの間隔の指定です。なお、前回の例ではアイコン表示は使っていなかったので、アイコン回りは後で改めて説明しましょう。
39〜41行目も前回の例では使っていませんが、メニューアイテムが1画面に収まらなかった際に使用するスクロールバーの指定で、使用の有無やサイズ、表示する画像の指定になります。
42行目のmenu_pixmap_styleはメニューボックスを囲む枠の画像の指定で、前回の例では白い枠線を指定しています。
これらを実際の画面に反映してみると図2のようになります。なお、たいていのパラメータには、“theme.txt”で指定しなくてもそれなりの位置に表示されるように画面サイズを元に計算した値があらかじめ設定されており、“item_padding”や“item_spacing”はそれらの微調整に使われるようです。
図2 menu_boxの各設定の意味
「スタイル・ボックス」を用いた装飾
前節で紹介した「ブートメニュー」の設定の42行目はmenu_pixmap_style = "boot_menu_*.png"となっています。先に紹介したように、この指定はメニューボックスを囲む枠の画像で、boot_menu_n.pngやboot_menu_se.pngといったファイルが利用されます。
$ ls boot_menu_*.png
boot_menu_c.png boot_menu_n.png boot_menu_nw.png boot_menu_se.png boot_menu_w.png
boot_menu_e.png boot_menu_ne.png boot_menu_s.png boot_menu_sw.png
これらの画像ファイルは、画面のサイズに合わせて拡大しても正しく表示されるように、全体を9つのブロックに分割して用意します。grubではこの種の装飾を「スタイル・ボックス(styled box)」と呼んでおり、メニューボックスやターミナル画面の装飾に使っています。
スタイル・ボックスでの“*”は「ワイルドカード」ではなく、位置情報を含んだ“nw”、“ne”、“se”、“sw”、“n”、“e”、“s”、“w”、“c”と解釈されます。
わかりやすい周辺画像の例としてGRUB2 Graphical Menu Theme File Formatで紹介されているコンピュータ・ターミナル風の画像データを流用してみましょう。このファイルは図3に示すように“terminal_n.png”から“terminal_ne.png”の9つに分割された画像になっています。
図3 ターミナル風の装飾用画像
これらの画像ファイルを“theme.txt”と同じディレクトリに配置し、terminal-boxとmenu_pixmap_styleに設定しました。
$ cat -n /run/media/kojima/11B4-4E49/grub/themes/starfield/theme.txt
...
4 desktop-color: "cornflowerblue"
5 terminal-box : "terminal_*.png"
...
23 + boot_menu {
24 left = 10%
42 menu_pixmap_style = "terminal_*.png"
...
この変更を施してからgrubを再起動してやると、メニューボックスの周囲やコマンド入力用ターミナル画面の周囲に“terminal_*.png”が配置されて、ちょっとレトロなPC風の画面になりました(笑)。図からもわかるように「スタイル・ボックス」では画面サイズに合わせて伸展するのは4辺(n、e、s、w)の画像で、4隅(nw、ne、se、sw)の画像はそのまま利用されます。
図4 ターミナル風画像の装飾例
さて、このスタイル・ボックスを使った装飾は「メニューアイテム」(“item_pixmap_style”、“selected_item_pixmap_style”)にも使用可能で、実は今回の例でも、選択した項目を明示するためのマーク表示にselected_item_pixmap_styleを使っています。
32 selected_item_pixmap_style = "blob_*.png"
一方、“blob_*.png”に該当する画像ファイルは“terminal_*.png”のように9種ではなく、1つしかありません。
$ ls blob*
blob_w.png
これはどういうことかと言うと「スタイル・ボックスとして指定したファイル名(“blob_*.png”)に“n”や“ne”に該当するファイルが無ければその部分は描画されずに無視される」、という仕様になっているせいです。すなわち、今回のように該当するファイルが“blob_w.png”しかなければ、“w”の部分(左端)のみが描画され、ちょうど“blob_w.png”が提供する白くて丸いマークが選択対象を示すように表示されている、というわけです。
一方、この機能を使って、選択対象全体の色を変えることも可能です。たとえば、このような3種の画像ファイルを用意します。
図5 新しい装飾用画像
この画像ファイルを“selected_item_pixmap_style”に指定(selected_item_pixmap_style="select_*.png")すれば、左端が“select_w.png”、中央が“select_c.png”、右端が“select_e.png”で表示され、ちょうど選択項目をマーカーで強調したような表示になります。
図6 新しい装飾用画像を適用した例
スタイルボックスは他にも、メニューアイテムが1画面に収まらなかった際のスクロール・バー(“scroll_bar_frame”、“scroll_bar_thumb”)や、自動起動するまでの時間を示すプログレス・バー(“bar_style”、“highlight_style”)にも利用可能です。興味がある方は調べてみてください。
アイコン表示
メニューボックスでは、起動項目を表わすアイコンを表示することも可能です。今回利用している“starfield”テーマにはアイコン集は含まれていないものの、さまざまなデスクトップ・テーマを提供しているGNOME-look.orgにはダウンロード可能なGRUBテーマが多数あって、それらにはたいてい“icons”ディレクトリが含まれています。
今回はそれらの中から、カラフルな“Tela grub theme”をダウンロードしてみました。ダウンロードしたファイルを展開するとフルカラーのアイコン集が含まれています。
$ ls Tela-1080p/Tela/icons/
Manjaro.i686.png debian.png fedora.png kaos.png linuxmint.png recovery.png tz.png
Manjaro.x86_64.png deepin.png find.efi.png kbd.png lubuntu.png restart.png ubuntu.png
...
図7 Telaテーマに付属のカラーアイコン集
この“icons”ディレクトリを“theme.txt”と同じ場所にコピーして再起動してやると、Plamo Linuxのエントリにペンギン(Tux)アイコンが表示されるようになりました。なお、図ではアイコンを見やすくするため、“+boot_menu{..}”の指定のうち、“icon_height”、“icon_width”、“item_height”あたりを大きくしています。
図8 アイコンの適用例
ここに表示されるアイコンは、grub.cfgで定義された“menuentry”の--classの指定を反映します。Plamo Linuxの場合、grub-mkconfigが作るgrub.cfgにはこのようなエントリが登録されます。
menuentry 'Plamo GNU/Linux' --class plamo --class gnu-linux --class gnu --class os $menuentry_id_option
この“--class”で指定された名前を左から見ていき、“icons/”以下に同じ名前のファイル(拡張子を除く)が見つかれば、そのエントリ用のアイコンとしてメニューボックスに表示する、という仕組みです。今回の例では“plamo.png”というアイコンファイルは無いため、次の“gnu-linux.png”がマッチして見なれたペンギンアイコンが表示されました。
さて、最後にメニューボックスを賑やかすために少しアイコン設定を追加してみましょう。grub.cfgを直接イジって、submenuのエントリにも“--class”設定を追加してみます。
submenu 'Advanced options for Plamo GNU/Linux' --class arch --class gnu-linux --class gnu --class os
...
menuentry 'UEFI Firmware Settings' --class restart $menuentry_id_option 'uefi-firmware'
この設定で再起動してみると、他のメニューアイテムにもアイコンが表示されるようになりました。あまり気にしていませんでしたが、こうしてみるとgrub用にPlamo Linuxのアイコンも作ってみたいところです(笑)。
図9 各種アイコンの表示
3回に渡り、grubの起動画面を彩るテーマの書き方を解説してみました。grubの起動画面が表示されるのはほんの数秒、長くても数十秒程度なのに、その装飾用にこれだけ多彩な機能が盛り込まれているのはちょっとした驚きでした。
一方、grubの起動画面はシステム起動時にしか表示されないため、“theme.txt”の修正がどのように画面に反映されるのかを確認するのは、初回に紹介した「USBメモリからのUEFI起動」といったテクニックを使わないとすごく面倒です。
今回の記事でそのあたりはクリアできたはずなので、デザイン方面の才能も無い筆者に代わり、Plamo Linux用のクールな起動画面を作ってくれる人が出てくることを期待しています(笑)。