C言語で簡単なキー入力システム(キーバインド付き)

先ず実装に必要なキーバインドやキー入力の状態を保持する構造体を用意します。

// キー情報用構造体
struct KeyInfo
{
	int keyBind[KeyBindMax];	// キーバインド情報
	int keyState;			// キーステート
	int keyStateOld;		// 前回のキーステート
};
// キー情報を実体を定義
static KeyInfo	s_keyState;


キー入力の状態はここに全てが格納されていきます。

次に初期化処理です。

// 入力システムの初期化
void InitializeInput(void)
{
	for( int i=0; i < KeyBindMax; i++ )
	{
		s_keyState.keyBind[i] = -1;
	}
	s_keyState.keyState = 0;
	s_keyState.keyStateOld = 0;
}

// 入力システムの解放
void FinalizeInput(void)
{
	InitializeInput();
}


特に特殊な機能は使わないので両方とも構造体の内容を初期化するだけです。
ここでkeyBindに-1を入れていますが、-1はバインドが未設定として扱います。

次にキーバインドです。

// キーバインドの設定
void BindKey(EKeyBind key, int keycode)
{
	s_keyState.keyBind[key] = keycode;
}


単純ですね。

EKeyBindで指定された場所に入力に使用したいキーコードを設定します。
これでEKeyBindとkeycodeが関連付けられました。

次に更新処理です。

// 入力状況の更新
void UpdateInput(void)
{
	BYTE keyboardState[256];
	// キーボード状態の取得
	GetKeyboardState(keyboardState);

	int keyState = 0;
	for( int i=0; i < KeyBindMax; i++ )
	{
		// キーがバインドされていなければスルーする
		int key = s_keyState.keyBind[i];
		if( key == -1 ) continue;

		// 入力されている場合はキーのビットを立てる
		if( keyboardState[key] & 0x80 )
		{
			keyState |= (1 << i);
		}
	}
	// ステートの更新
	s_keyState.keyStateOld = s_keyState.keyState;
	s_keyState.keyState = keyState;
}


キーボードの入力状態を取得した後にキーバインドの設定に合わせてステートを設定していっています。

最後は前回と今回のステートを更新しています。

ここではint型のkeyStateに対してbitフラグで管理をしています。
※int型は32bitなので最大32個のキーしか扱えません。

これでキー入力の判定に必要な処理は実装が出来ました。

最後にキー判定です。

// キーが押されているか?
bool IsKeyPress(EKeyBind key);
// キーが押されたか?
bool IsKeyPush(EKeyBind key);
// キーが離されたか?
bool IsKeyReleases(EKeyBind key);


キー判定の処理はこの3つとなります。

実装もかなり単純になっています。

// キーが押されているか?
bool IsKeyPress(EKeyBind key)
{
	int bit = (1 << key);
	// 単純に現在のステートから判定
	int state = s_keyState.keyState;
	return (state & bit)? true: false;
}

// キーが押されたか?
bool IsKeyPush(EKeyBind key)
{
	int bit = (1 << key);
	// 今回と前回とのステートの差(1 & ~0)で判定
	int state = s_keyState.keyState & ~s_keyState.keyStateOld;
	return (state & bit)? true: false;
}

// キーが離されたか?
bool IsKeyReleases(EKeyBind key)
{
	int bit = (1 << key);
	// 前回と今回のステートの差(1 & ~0)で判定
	int state = s_keyState.keyStateOld & ~s_keyState.keyState;
	return (state & bit)? true: false;
}


全てがビット演算だけで判定できてしまいます。

では最後に使い方の説明をしていきます。

1 2 3

コメントを残す

メールアドレスが公開されることはありません。 * が付いている欄は必須項目です