本記事では CMD.EXE
のことをコマンドプロンプトと呼び,コマンド入力待ちの文字列のことは単にプロンプト文字列と呼び分けています。
はじめに
Windows 10 のいつ頃からでしょうか,コマンドプロンプト内でカーソルが消えてしまうという現象が起こるようになりました。同様な事例は他のユーザーからも報告1されており,消えたカーソルの復旧方法2も編み出されてはいますが,それは PowerShell を利用するというもので,Windows に標準で添付されているとはいえ起動の重さから常用が躊躇われ,筆者は下記のようなバッチファイルを作成して愛用していました。
これは Windows 10 の途中から使えるようになった VT100 互換のエスケープシーケンスを用いたカーソルの復旧方法です。カーソルがもしも見えなくなった場合,自作の cursor
コマンドを実行するだけでよいのですが,先日,もっと良い方法を思いつきました。
最初に結論を書く
それはプロンプト文字列にカーソル復帰のエスケープシーケンスを仕込ませるというものです。まず,下記のようなバッチファイル PROFILE.CMD
を作成します。
@echo off
prompt $p$g$e[0m$e[?25h
筆者はさらにデスクトップ上に CMD.EXE
のショートカットを置き,起動オプション /K
で上記の PROFILE.CMD
を指定するようにしています。
上記のショートカットを用いてコマンドプロンプトを起動すれば,カーソルが消えたり,あるいは文字の色が変わってしまった場合でも,プロンプト文字列が再表示された時点で元の状態に自動復帰します。
参考資料
プロンプト文字列をカスタマイズできる PROMPT
コマンドのヘルプメッセージを以下に示します。
※Windows 10 22H2 のものです。
c:\>prompt /?
cmd.exe のコマンド プロンプトを変更します。
PROMPT [文字列]
文字列 新しいコマンド プロンプトを指定します。
PROMPT には通常の文字と次に示す特殊コードを使用できます:
$A & (アンパサンド)
$B | (パイプ)
$C ( (左かっこ)
$D 現在の日付
$E エスケープ コード (ASCII コードの 27)
$F ) (右かっこ)
$G > (不等号 (より大))
$H バックスペース (直前の文字を削除します)
$L < (不等号 (より小))
$N 現在のドライブ
$P 現在のドライブとパス
$Q = (等号)
$S (空白)
$T 現在の時刻
$V Windows のバージョン番号
$_ キャリッジ リターンとラインフィード
$$ $ (ドル記号)
コマンド拡張機能を有効にすると、PROMPT コマンドは、次の追加の書式
文字をサポートするようになります:
$+ PUSHD ディレクトリ スタックの深さに応じて、0 個以上のプラス
記号 (+) を指定します。1 個のプラス記号が、プッシュされた
1 レベルを表します。
$M 現在のドライブ文字に関連付けられているリモート名を表示します。
現在のドライブがネットワーク ドライブでない場合は、空の文字列
を表示します。
本記事で用いたエスケープシーケンスを以下に示します。エスケープシーケンスについての詳しい情報は Microsoft 公式サイト3を参照下さい。
シーケンス | コード | 説明 | 動作 |
---|---|---|---|
ESC [ ? 25 h |
DECTCEM | テキストカーソル 有効化モード表示 |
カーソルを表示します |
ESC [ ? 25 l |
DECTCEM | テキストカーソル 有効化モード非表示 |
カーソルを非表示にします |
シーケンス | コード | 説明 | 動作 |
---|---|---|---|
ESC [ 0 m |
SGR | 既定値 | すべての属性※を変更前の 既定の状態に戻します |
※ここでいう「すべての属性」とはあくまでテキストの前景色や背景色に関わる属性のことです。カーソルの可視性の属性は含まれません。
まとめ
プロンプト文字列にカーソル復帰のエスケープシーケンスを仕込ませて以来,カーソルが消える事象は一度も起こっていません。
謝辞
下記サイトの情報がヒントになりました。バッチファイルの冒頭部分でいきなり Prompt;$H
と実行しており,この $H
って何だろう(バックスペースの意味)とリファレンスを調べたのがきっかけです。エスケープコード $E
を出力できるのならエスケープシーケンスを使ってプロンプト文字列の色を変えられますし,今回のようにカーソル表示のオン/オフも可能です。