キー入力の制御(#3)

いよいよシレンを操作するぞと意気込むものの、Windows系OSでプログラミングをしたことがないので、正直Windows APIが何なのか全然分かっていない。
Windowハンドルの取得や、入力の構造体などは大変苦労した。以下は自分へのメモ。

// ウィンドウハンドルの取得 (steamシレンのウィンドウは以下で取れる)
HWND hwnd = FindWindow(L"ShirenTheWandererWindowClass", nullptr);

// 入力の直前でウィンドウは再度アクティブにすること!
SetActiveWindow(hwnd);
SwitchToThisWindow(hwnd, true);
// INPUT構造体の設定
INPUT input;
input.type = INPUT_KEYBOARD;
input.ki.wVk = VK_RIGHT; // 右キー

input.ki.dwFlags = 0; // キーを押す
SendInput(1, &input, sizeof(INPUT)); 

sleep(70); // 要調整 (あまりにも入力を終えるのが早いと認識しないため)

input.ki.dwFlags = KEYEVENTF_KEYUP; // キーを離す
SendInput(1, &input, sizeof(INPUT));

ウィンドウ制御と入力構造体の仕組みが分かった所で、基本的な操作を今回で全て定義しておく。

void moveUp(void)       { sendKey(VK_UP); } // 上移動
void moveLeftUp(void)   { sendKey(static_cast<int>('W'), VK_LEFT, VK_UP);   } // 左上移動
void openMenu(void)     { sendKey(static_cast<int>('S')); } // メニューを開く
.....

 
ところで起動時のランチャーにはキー入力がざっくりと書かれているが、これを見る限り、Dボタンの足踏みや、Cボタンのマップ見渡しなどは書かれていない。
詳しくは取扱説明書を見てくださいとは書いてあるものの、結構大事な操作なので標準で書いてて欲しいと思った。

   f:id:ai_shiren:20201206193126p:plain

きちんとプログラム通りシレンが動いた所は感動的であったのだが(これがプログラミングの醍醐味!)、これを動画にしてアップする技量がないので、その辺はまた今度にしたい。
中々時間が取れないが、次回は前回やったマップ読み込みと、今回の操作を組み合わせて、ようやく初心者の家の問題1をクリアだ。