Skip to main content
Glama

ue5-gameplay-mcp

実行中のUnreal Engine 5のゲームをプレイするMCPサーバーです。 仮想ゲームパッド、キーボード、マウスの入力を受け付け、スクリーンキャプチャ、ログ行、UMGステータスを出力します。

これはエンジンプラグインではなく、クライアントです。2つのプラグインがすでにエンジン内の処理を担い、それぞれ独自のポートを保持しています。 このサーバーはその両方にダイヤルインし、1つのツールインターフェースとして提供します。

プラグイン

ポート

提供機能

RemoteConsole2

10101

IInputDeviceによるゲームパッド/キーボード/マウスのインジェクション、コンソールコマンド、UMGのダンプ/クリック/フォーカス、ライブログストリーム、構造化されたゲームステート

RemoteCapturePlugin

10102

JPEG/PNGスクリーンキャプチャ(PIEおよびパッケージ化されたビルドで動作)ue5_gamecapture_mcp 付属

両プラグインには、このサーバーのために少量のC++コードが追加されました。 これらは独立性を保ち、独自のプロトコルを維持しています。追加部分は後方互換性があるため、古いクライアントでも再ビルドされたゲームと通信可能です:

  • FImageMeta.SourceSize — ゲームのバックバッファサイズ。構造体のサイズを24バイトに保つため、以前は予約語だった領域にパックされています。これにより、クライアントはダウンスケールされたキャプチャ上の特定の点をウィンドウのピクセルにマッピングし直すことができます。

  • CMD_GET_GAME_STATE (520) および IRemoteGameStateProvider — 詳細は後述します。

セットアップ

cd ue5_gameplay_mcp
uv sync

MCP Python SDK v2 (mcp.server.MCPServer) が必要です。

Related MCP server: VERA MCP Server

実行方法

まずゲームを起動します。 このプロジェクトでは、Gameターゲットがクックされていないプロジェクトでは即座に終了してしまうため、スタンドアロンゲームはエディタのバイナリから実行されます:

"C:/Program Files/Epic Games/UE_5.8/Engine/Binaries/Win64/UnrealEditor.exe" "<PATH>/MyProject.uproject" -game -windowed -resx=1280 -resy=720 -log -nosplash

次にサーバーを登録します。 プロジェクトルートにある.mcp.jsonがすでにこれを行っているため、Claude Codeは自動的にこれを認識します。 手動で行う場合と同等のコマンドは以下の通りです:

claude mcp add ue5-gameplay -- uv run --directory <PATH>/ue5_gameplay_mcp -m ue5_gameplay_mcp

サーバーは遅延接続(レイジーコネクト)を行うため、実際の起動順序は重要ではありません。 ゲームより先に起動した場合でも、最初のツール呼び出し時に接続が行われます。

オプション: --host, --console-port, --capture-port, --format, --quality, --max-size, --grid-step, --transport streamable-http --mcp-port 14102

ツール

セッションgame_connect, game_status, game_reset_input

オブザベーション(観察)game_observe, game_state, game_log, game_wait_for_log

アクションgame_pad, game_pad_sequence, game_key, game_mouse, game_console, game_time_scale

UMGgame_ui_dump, game_ui_click, game_ui_focus

APIの設計とその理由

エージェントのラウンドトリップには数秒かかりますが、ゲームは60Hzで動作します。フレーム単位でのアクションは非現実的であるため、以下のようになっています:

  • すべてのアクションツールはduration(継続時間)を受け取り、押す/押し続ける/離すという一連の動作をローカル環境で通信速度に合わせて実行します。1回のラウンドトリップは1フレームではなく、1つの意図(インテント)を伝達します。

  • アクションツールはデフォルトで観察(Observe)を行います。 game_pad(ly=1.0, duration=0.5)は前進し、その結果のフレームを返します。これにより、行動と確認を別々に行う場合の半分のラウンドトリップで済みます。

  • game_pad_sequence は、入力間の確認よりも入力のタイミングが重要な場合に、コンボ全体を1回の呼び出しにまとめます。

  • game_time_scale(0.2) は、瞬間の精度が必要な場合にゲーム内時間を稼ぎます。

  • hold=True は、エージェントが思考している間もキャラクターが動き続けるように、ターンの間も入力を適用したままにします。game_reset_inputでこれをクリアします。

ピクセルではなく数値

game_stateは、レベル、ワールドタイム、ポーズ/タイムダイレーション、プレイヤーポーンのトランスフォーム、速度、移動モード、カメラ、そして最も近いアクタの距離と正規化された画面位置を返します。 これはgame_mouseが受け取るのと同じ0~1の座標であるため、ステータスレポート内で見つけた対象に即座に狙いを定めることができます。 この処理コストは画像の処理コストのほんの一部であり、HUDの数値を読み違えることもありません。

game_observe(state=True)はこれを観察に組み込み、game_pad(..., state=True)はアクションに組み込むため、移動と確認は依然として1回のラウンドトリップで済みます。

実際のマップでは、最も近いアクタのほとんどが背景オブジェクトであるため、レポートにはclass_counts(半径内のすべてのオブジェクトの調査結果)も含まれます。これを一度読み取り、class_filter="Enemy"で絞り込みます。

ゲーム独自の数値の追加

組み込みのレポートにはゲーム側のコードは必要ありません。ヘルス、スコア、クエストフラグなど、そのプロジェクトのみが知る情報については、任意のアクタにIRemoteGameStateProviderPlugins/RemoteConsole2/Source/RemoteConsole2/RemoteGameState.h)を実装し、JSONオブジェクトの文字列を返すようにします:

FString AMyGameMode::GetRemoteGameState_Implementation()
{
    return FString::Printf( TEXT("{\"score\":%d,\"wave\":%d}"), Score, Wave );
}

これはBlueprintNativeEventであるため、Blueprintのみのプロジェクトでもオーバーライド可能です。 返された値はすべて、アクタ名をキーとしてcustomの下に格納されます。 プロバイダは距離フィルタに関係なく収集されるため、原点に配置されたスコアキーパーもレポートを送信します。 有効なJSONではないテキストは破棄されず、文字列としてそのままパススルーされるため、立ち上げ時の簡単なPrintfによるデバッグでも有用です。

メニューを操作する3つの方法(推奨順)

  1. game_ui_dump + game_ui_click — 正確かつ高速ですが、UMG経由で登録されたウィジェットしか認識しません。カスタムのSlate UIを持つゲームでは何も返されませんが、ハングアップする代わりにツールがその旨を伝えます。

  2. パッドナビゲーションgame_pad(buttons=["DOWN"]), game_pad(buttons=["A"])。ほぼすべてのゲームで機能します。

  3. ルック&クリックgame_observe(grid=True)は、ラベル付きの0~1の座標グリッドをオーバーレイ表示します。画像からターゲットを読み取り、同じ数値をgame_mouse(x=..., y=...)に渡します。解像度に依存せず、UIの構築方法に関係なく機能します。

規則(コンベンション)

  • スティックはUEの仕様に従います: ly=+1が前進です。(通信プロトコルではY軸が反転しますが、ここではそれを元に戻しているため、ツールAPIはゲーム独自の軸マッピングの意味と一致します)。

  • マウス座標は左上を原点として0~1に正規化されており、ゲームの実際のバックバッファサイズを使用してピクセルに変換されます。キャプチャはリサイズ後の寸法を報告するため、このサイズは別途プローブされます。

  • game_observeは前回の観察以降の新しいログ行のみを返すため、長時間のセッションでも同じ出力が再送されることはありません。

既知の問題点・未完成な部分

  • エディタバイナリでゲームをホストしている場合、コンソールコマンドはPythonを経由してルーティングされます。 FGameAccessAPI::ExecConsoleCommandIConsoleCommandExecutorの実装[0]にディスパッチしますが、エディタのPythonプラグインがロードされている場合、そのスロットはCmdではなくPythonになります。そのため、単なるstat fpsSyntaxErrorとして返されます。サーバーは初回使用時に一度プローブを行い、これを検出した場合はコマンドをunreal.SystemLibrary.execute_console_commandでラップします。パッケージ化されたビルドにはPythonエグゼキュータがないため、この回避策は不要です。game_console(via="cmd")でオーバーライド可能です。

  • 画面のクリックは、キャプチャがゲームウィンドウ全体を満たしていることを前提としています。 -game -windowedの場合はこれが当てはまります。レターボックス化されたフルスクリーンモードの場合、報告されるソースサイズ内に黒帯が含まれることになり、マッピングがずれます。

  • game_stateは、呼び出されるたびにレベル内のすべてのアクタを走査します。 通常のマップの規模であれば問題ありませんが、ストリーミングされるオープンワールドではTActorIteratorの代わりに空間クエリが必要になるでしょう。

テスト

uv run test/smoke_test.py

ゲームと直接通信し、smoke_*.jpgを書き出します。これにより、キャプチャやグリッドのオーバーレイを目視で確認できます。

uv run test/mcp_client_test.py

標準入出力(stdio)経由でサーバーを実際のMCPクライアントとして起動し、エラーパスを含めてすべてのツールを実行・テストします。

Install Server
A
license - permissive license
A
quality
C
maintenance

Maintenance

Maintainers
Response time
Release cycle
Releases (12mo)
Commit activity

Resources

Unclaimed servers have limited discoverability.

Looking for Admin?

If you are the server author, to access and configure the admin panel.

Related MCP Servers

View all related MCP servers

Related MCP Connectors

  • Control Unreal Engine to browse assets, import content, and manage levels and sequences. Automate…

  • A comprehensive Model Context Protocol (MCP) server that enables AI assistants to control Unreal E…

  • Drive a live Cinevva game session: edit game files, import CC0 assets, preview changes.

View all MCP Connectors

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/hiroog/ue5_gameplay_mcp'

If you have feedback or need assistance with the MCP directory API, please join our Discord server