[[📒Articles]] > [[📒2026 Articles]]
![[2026-03-01.webp|cover-picture]]
[[macOS]]で理想のウィンドウ切り替えスクリプト『[[🦉JINRAI]]』をつくりました。
## ウィンドウ切り替えのユースケースと課題
パソコンで作業をしていると『ウィンドウ切り替え』を行う機会は多いでしょう。その手法も数多くあると思います。私の場合は主に以下3つのユースケースがあります。
![[2026-03-01-12-00-46.avif]]
### 1. 直前にアクティブだったウィンドウをアクティブにしたいとき
2つのウィンドウを行き来しながら交互に作業したい場合です。たとえば[[Google Chrome]]で調べ物をしつつ、[[Obsidian]]でメモをとる場合など。
そのようなときは[[AltTab]]を使ってきました。
<div class="link-card-v2">
<div class="link-card-v2-site">
<img class="link-card-v2-site-icon" src="https://alt-tab-macos.netlify.app/public/favicon-32x32.png" />
<span class="link-card-v2-site-name">alt-tab-macos.netlify.app</span>
</div>
<div class="link-card-v2-title">
AltTab - Windows alt-tab on macOS
</div>
<div class="link-card-v2-content">
Windows alt-tab on macOS
</div>
<a href="https://alt-tab-macos.netlify.app/"></a>
</div>
しかし、[[AltTab]]には2つの課題がありました。
- **直前のウィンドウに移動しないときがある**
- 再現条件不明
- 不定期に発生するので地味にストレス
- **表示してほしくないウィンドウまで表示されてしまう**
- 設定で緩和できるが[[Scoot]]などのアプリケーションでは効果がない
- 閉じているつもりの待機アプリケーションも表示される
- 設定で非表示にしているつもりだが、私のやり方が悪いのかも......
- [[📝AltTabで起動しているつもりのないアプリケーションが表示されてしまう]]
### 2. 視界にある別のウィンドウをアクティブにしたいとき
目では認識している別のウィンドウをアクティブにしたいときは、トラックパッドや[[ポインティングスティック]]で移動することが多いです。
大きな問題はありませんが、以下の理由から至高の方法とは言えないでしょう。
- **キーボードから一時的に手を離すことになる**
- 距離は近いので大きな問題ではない
- **マウスポインタの位置を見失っているときは、別のウィンドウへと速やかにマウスポインタを移動できない**
別の方法もありますが、いずれもツール起動後に判断が必要となるため効率的とは言えません。
- **[[AltTab]]で別のウィンドウを選んで移動する**
- 別のウィンドウが何番目に表示されているかを **[[AltTab]]起動後に** 目視で確認し、必要なキータッチ数を決める必要がある
- **[[Scoot]]で別のウィンドウが表示されている領域に移動する**
- 別のウィンドウが表示されている領域のキーマップを **[[Scoot]]起動後に** 目視で確認し、キー入力する必要がある
<div class="link-card-v2">
<div class="link-card-v2-site">
<img class="link-card-v2-site-icon" src="https://github.githubassets.com/favicons/favicon.svg" />
<span class="link-card-v2-site-name">GitHub</span>
</div>
<div class="link-card-v2-title">
GitHub - mjrusso/scoot: Keyboard-driven MacOS cursor actuator
</div>
<div class="link-card-v2-content">
Keyboard-driven MacOS cursor actuator. Contribute to mjrusso/scoot development by creating an account on GitHub.
</div>
<img class="link-card-v2-image" src="https://repository-images.githubusercontent.com/360176893/2dd81e80-ab4a-11eb-847e-bd51bae42fdd" />
<a href="https://github.com/mjrusso/scoot"></a>
</div>
### 3. 視界にない別のウィンドウをアクティブにしたいとき
視界に入らない、または背面に存在して不可視のウィンドウをアクティブにしたいときは、[[ミッションコントロール]]ですべてのウィンドウプレビューを表示してから、トラックパッドや[[ポインティングスティック]]で移動することが多いです。
こちらも大きな問題はありませんが、場合によってはかなり非効率な方法になります。
- **キーボードから一時的に手を離すことになる**
- **距離は近いので大きな問題ではない**
- **マウスポインタの位置を見失っているときは、別のウィンドウへと速やかにマウスポインタを移動できない**
- **マウスポインタの位置が別のウィンドウのプレビューから離れているときは、マウスポインタの移動に時間がかかる**
- [[AltTab]]を使うと解決できるが、判断回数を減らすならはじめから[[AltTab]]に統一すべき
- その場合は[[AltTab]]特有の課題がつきまとう
### 課題と要件の整理
[[AltTab]]は3つのユースケースすべてのソリューションを提供する素晴らしいツールですが、**UIのフィードバックなしには再現性のある操作がしづらい**という点が残ります。一方で、マウスカーソルに頼る方法は効率の理論値が高いとは言えません。
![[2026-03-01-12-07-02.avif]]
これらの不満から、私が理想とするウィンドウ切り替えの要件をあぶり出してみました。
- **ツールを起動する前から** 希望する操作に必要なキー操作が確定的である
- 操作がキーボードで完結する
- 3つのウィンドウ切り替えユースケースに対して、**ユースケースごとに直感的に**操作できる
具体的な機能要件などが他にもありますが、量が多くなってしまうので軸となる要件のみに留めました。
## JINRAI(迅雷)を作成
先ほどの要件をすべて満たす既存ツールはなさそうでしたので、[[Hammerspoon]]のスクリプトとして動くものを自分でつくりました。
<div class="link-card-v2">
<div class="link-card-v2-site">
<img class="link-card-v2-site-icon" src="https://github.githubassets.com/favicons/favicon.svg" />
<span class="link-card-v2-site-name">GitHub</span>
</div>
<div class="link-card-v2-title">
GitHub - tadashi-aikawa/jinrai: 迅雷: 思考の速度で素早くウィンドウの切り替えや認識を行うためのhammerspoonスクリプト
</div>
<div class="link-card-v2-content">
迅雷: 思考の速度で素早くウィンドウの切り替えや認識を行うためのhammerspoonスクリプト. Contribute to tadashi-aikawa/jinrai development by creating an ...
</div>
<img class="link-card-v2-image" src="https://opengraph.githubassets.com/640940cdfeaecf35ad56e8a03369bd5f53a4179d9c1f2419e1d5d4bf0618b21b/tadashi-aikawa/jinrai" />
<a href="https://github.com/tadashi-aikawa/jinrai"></a>
</div>
![[2026-03-01-12-17-57.avif]]
インストール・セットアップ方法はREADMEをご覧ください。
> [!attention]
> 前提として[[Hammerspoon]]のインストールが必要です。
> [!left-bubble] ![[colot-face.webp]] **[[コロット]]**
> コーディングは『[[GitHub Copilot CLI]] x [[Claude Opus 4.6]]』で行っております。
## 機能紹介
主な機能は以下の3つです。特に **『Window Hints』** には力を入れています。
- 🔠 **[[Window Hints (JINRAI)|Window Hints]]**
- アプリアイコン+キーヒントによるウィンドウ切り替え
- アプリ名の頭文字をキーヒントのプレフィックスに自動割り当て
- 同一プレフィックスのウィンドウが複数ある場合は複数キー入力で絞り込み
- 他のウィンドウに完全に隠れたウィンドウは画面下部にドック形式+プレビュー付きで表示
- アクティブウィンドウをオーバーレイでハイライト表示
- 🔳 **[[Focus Border (JINRAI)|Focus Border]]**
- フォーカスが移動したウィンドウの枠を一瞬だけハイライト表示
- ↩️ **[[Focus Back (JINRAI)|Focus Back]]**
- ホットキーで直前にアクティブだったウィンドウに戻る
画像で説明するのは難しいので、動画をご覧ください。

> [!attention]
> 『Window Hints』のデフォルトホットキーは `Alt+f20` という見慣れないものになっています。これは私が[[karabiner.ts]]([[Karabiner-Elements]])を使って、`;<Space>` を `Alt+f20`に[[2キーバインド]] しているからです。
>
> 設定の `window_hints.hotkeyModifiers` と `window_hints.hotkeyKey` で変更できます。
> [!note]
> 動画ではシングルモニタのデモをしていますが、モニタが複数ある場合はウィンドウが所属しているモニタに対してそれぞれ表示されます。
## 効果をふりかえる
### 要件
冒頭の要件を満たしているかをふりかえってみます。
- **ツールを起動する前から希望する操作に必要なキー操作が確定的である**
- 😀 [[Window Hints (JINRAI)|Window Hints]] の起動 -> `アプリケーションの先頭文字` で大抵のケースは確定的
- **操作がキーボードで完結する**
- 😆 [[Window Hints (JINRAI)|Window Hints]] と [[Focus Back (JINRAI)|Focus Back]] で必要な操作は網羅
- **3つのウィンドウ切り替えユースケースに対して、ユースケースごとに直感的に操作できる**
- 😆 [[Window Hints (JINRAI)|Window Hints]] と [[Focus Back (JINRAI)|Focus Back]] で必要な操作は網羅
私は`G`から始まるアプリケーションを使っていることが多いので、『キー操作が確定的』でないことも多いです。ただ、その場合も『残りの候補から選んで1キー押すだけ』で良いので些細な問題に過ぎません。
![[2026-03-01-13-37-16.avif|frame]]
*Gで始まるツールの2キー目として `ASF` の候補が表示される*
### 課題
冒頭の課題から解決に直結したものを挙げてみます。
| 課題 | [[Window Hints (JINRAI) \| Window Hints]] | [[Focus Back (JINRAI) \| Focus Back]] | [[Focus Border (JINRAI) \| Focus Border]] |
| ---------------------------- | ----------------------------------------- | ------------------------------------- | ----------------------------------------- |
| **直前のウィンドウに移動しないときがある** | - | ✅ | - |
| **表示してほしくないウィンドウまで表示されてしまう** | ✅ | - | - |
| **キーボードから一時的に手を離すことになる** | ✅ | ✅ | - |
| **[[AltTab]]起動後に目視が必要** | ✅<br> | ✅<br> | - |
| **[[Scoot]]起動後に目視が必要** | ✅ | - | - |
| **マウスポインタの位置を見失う** | ✅ | - | ✅ |
[[Window Hints (JINRAI)|Window Hints]]と[[Focus Back (JINRAI)|Focus Back]]には `centerCursor` というオプションがあります。それを有効にすると『アクティブウィンドウを切り替えたあと、そのウィンドウの中央にマウスカーソルを移動』することができます。
デフォルトでは無効(`false`)になっていますが、**マウスカーソルを見失わなくなり、目的のウィンドウでマウスを使った操作をスムーズに行えるようになる** ので、差し支えなければ有効にしてみてください。
```lua
local jinrai = dofile("/path/to/jinrai/init.lua")
jinrai.setup({
window_hints = {
-- ここをtrueに
centerCursor = true,
},
focus_back = {
-- ここをtrueに
centerCursor = true,
},
})
```
## まとめ
[[macOS]]でのウィンドウ切り替えにいくつか不満があったので、理想のウィンドウ切り替えを行うために作成した[[🦉JINRAI]]を紹介しました。
まだ作成して数日しか経っていないので、1週間くらい使ってみて改善点が見つかるかもしれませんが、『UI/UX』にはこだわりをもって妥協せずにつくったつもりです。もともとは[[🦉Toki]]の内部スクリプトでしたが、公開して他の方にも使っていただけるクオリティに到達したと判断したので公開しました。[[🦉JINRAI]]の利用に伴い、[[AltTab]]と[[Scoot]]はアンインストールしました。
ウィンドウの切り替え操作にモヤモヤを抱えていた[[macOS]]ユーザーの方がいらっしゃいましたら、是非お試しいただければと思います。