MCSTP
Богатый аддон телеметрии игрового состояния для MCCTP. Каждый тик передаёт по WebSocket статистику игрока, боевой контекст, сканирование угроз, состояние ввода, информацию об экране и эффекты статуса.
- Загрузчики
- Fabric
- Скачиваний на Modrinth
- 179
- Подписчиков на Modrinth
- 1
- версии
- 2
- Обновлён
- 3 марта 20263 мар.
- Опубликован
- в 2026
Коротко о моде
Ставится только в игру; на сервер ставить не нужно
MCSTP - Minecraft State Transfer Protocol
Мод для Fabric, который добавляет подробную телеметрию игрового состояния в MCCTP. Он передаёт насыщенные снимки состояния через WebSocket MCCTP каждый тик — информацию об игроке, боевой контекст, сканирование угроз, состояние ввода, состояние экрана, эффекты статуса и многое другое.
Возможности
- Полное состояние игры каждый тик — позиция, здоровье, инвентарь, бой, угрозы, ввод, экран, эффекты статуса
- Сканирование угроз — обнаруживает враждебных мобов в радиусе 16 блоков, ближайшее расстояние/угол, количество
- Зеркалирование ввода — сообщает, какие клавиши нажимает игрок, и смещения мыши
- Осведомлённость об экране — знает, когда открыт GUI, позицию курсора, состояние мыши/shift
- Отслеживание эффектов статуса — булевы флаги для 11 распространённых эффектов
- Действия GUI — позиционирование курсора и симуляция кликов для открытых экранов
- Архитектура плагинов — регистрируется через API MCCTP, использует то же WebSocket-соединение
Требования
- Minecraft 1.21.11
- Fabric Loader >= 0.16.0
- Fabric API
- MCCTP >= 1.0.0
- Java 21+
Установка
# Сначала соберите MCCTP (MCSTP зависит от его JAR)
cd mcctp
./gradlew build
# Затем соберите MCSTP
cd ../MCSTP
./gradlew buildСкопируйте оба JAR из build/libs/ в папку .minecraft/mods/.
Как это работает
MCSTP подключается к MCCTP как модуль. При инициализации он регистрирует провайдер состояния и два обработчика действий через API MCCTP. Он не запускает собственный сервер — WebSocket MCCTP обрабатывает всё. Когда оба мода установлены, клиенты получают рукопожатие при подключении:
{"type": "handshake", "modules": ["mcctp", "mcstp"], "version": "1.0"}Если установлен только MCCTP, modules равно ["mcctp"], и состояние не передаётся.
Протокол
Состояние игры (Сервер → Клиент)
MCSTP расширяет полезную нагрузку состояния игры, которую передаёт MCCTP. Все базовые поля MCCTP присутствуют, плюс эти дополнительные секции:
{
"type": "game_state",
"timestamp": 1700000000000,
"selectedSlot": 0,
"heldItem": {
"name": "minecraft:diamond_sword",
"category": "SWORD",
"stackCount": 1,
"maxDurability": 1561,
"currentDurability": 1400
},
"offhandItem": {
"name": "minecraft:shield",
"category": "SHIELD",
"stackCount": 1,
"maxDurability": 336,
"currentDurability": 336
},
"playerState": {
"health": 18.0,
"maxHealth": 20.0,
"hunger": 19,
"saturation": 3.0,
"x": 142.5,
"y": 72.0,
"z": -38.3,
"yaw": 45.0,
"pitch": -10.0,
"onGround": true,
"sprinting": false,
"sneaking": false,
"swimming": false,
"flying": false,
"inWater": false,
"onFire": false,
"experienceLevel": 24,
"experienceProgress": 0.65,
"totalExperience": 897
},
"combatContext": {
"isUsingItem": false,
"isBlocking": false,
"activeHand": "MAIN_HAND",
"crosshairTarget": "ENTITY",
"crosshairEntityType": "minecraft:zombie",
"crosshairBlockPos": null,
"crosshairDistance": 3.2,
"crosshairEntityHealth": 14.0,
"crosshairEntityMaxHealth": 20.0
},
"playerInput": {
"movementForward": 1.0,
"movementSideways": 0.0,
"jump": false,
"sprint": true,
"sneak": false,
"attack": false,
"useItem": false,
"drop": false,
"swapOffhand": false,
"openInventory": false,
"yawDelta": 2.35,
"pitchDelta": -0.5
},
"screenState": {
"screenOpen": false,
"screenType": null,
"cursorX": 0.0,
"cursorY": 0.0,
"mouseLeft": false,
"mouseRight": false,
"shiftHeld": false
},
"statusEffects": {
"speed": false,
"slowness": false,
"strength": true,
"fireResistance": false,
"poison": false,
"wither": false,
"regeneration": false,
"resistance": false,
"invisibility": false,
"waterBreathing": false,
"absorption": false,
"activeEffectCount": 1
},
"threat": {
"targetEntityHostile": true,
"targetDistance": 3.2,
"nearestHostileDist": 3.2,
"nearestHostileYaw": 45.0,
"hostileCount": 3
}
}Поля состояния игры
Поля из MCCTP (heldItem, offhandItem, базовые поля playerState, базовые поля combatContext) описаны в README MCCTP. MCSTP добавляет следующее: playerState (расширенное):
| Поле | Тип | Описание |
|---|---|---|
experienceLevel | int | Текущий уровень опыта |
experienceProgress | float | Прогресс до следующего уровня (0-1) |
totalExperience | int | Всего очков опыта |
combatContext (расширенное):
| Поле | Тип | Описание |
|---|---|---|
crosshairDistance | float | Расстояние до цели прицела (-1 при промахе) |
crosshairEntityHealth | float | Здоровье целевой сущности (-1 если не живая) |
crosshairEntityMaxHealth | float | Максимальное здоровье целевой сущности (-1 если не живая) |
playerInput:
| Поле | Тип | Описание |
|---|---|---|
movementForward | float | Ввод вперёд/назад (-1 до 1) |
movementSideways | float | Ввод влево/вправо (-1 до 1) |
jump | bool | Клавиша прыжка зажата |
sprint | bool | Клавиша спринта зажата |
sneak | bool | Клавиша приседания зажата |
attack | bool | Клавиша атаки зажата |
useItem | bool | Клавиша использования зажата |
drop | bool | Клавиша выброса зажата |
swapOffhand | bool | Клавиша смены рук зажата |
openInventory | bool | Клавиша инвентаря зажата |
yawDelta | float | Изменение рыскания с прошлого тика (градусы) |
pitchDelta | float | Изменение наклона с прошлого тика (градусы) |
screenState:
| Поле | Тип | Описание |
|---|---|---|
screenOpen | bool | Открыт любой экран GUI |
screenType | string? | Имя класса экрана (например, "InventoryScreen"), или null |
cursorX | float | Нормализованная позиция курсора по X (0-1) |
cursorY | float | Нормализованная позиция курсора по Y (0-1) |
mouseLeft | bool | Левая кнопка мыши зажата |
mouseRight | bool | Правая кнопка мыши зажата |
shiftHeld | bool | Клавиша Shift зажата (для shift-кликов) |
statusEffects:
| Поле | Тип | Описание |
|---|---|---|
speed | bool | Активен эффект Скорости |
slowness | bool | Активен эффект Замедления |
strength | bool | Активен эффект Силы |
fireResistance | bool | Активен эффект Огнестойкости |
poison | bool | Активен эффект Отравления |
wither | bool | Активен эффект Иссушения |
regeneration | bool | Активен эффект Регенерации |
resistance | bool | Активен эффект Сопротивления |
invisibility | bool | Активен эффект Невидимости |
waterBreathing | bool | Активен эффект Подводного дыхания |
absorption | bool | Активен эффект Поглощения |
activeEffectCount | int | Общее количество активных эффектов |
threat:
| Поле | Тип | Описание |
|---|---|---|
targetEntityHostile | bool | Цель под прицелом — враждебный моб |
targetDistance | float | Расстояние до цели под прицелом (-1, если не враждебный) |
nearestHostileDist | float | Расстояние до ближайшего враждебного моба в пределах 16 блоков (-1, если нет) |
nearestHostileYaw | float | Угол рыскания до ближайшего враждебного моба (в градусах) |
hostileCount | int | Количество враждебных мобов в пределах 16 блоков |
Действия (клиент → сервер)
MCSTP добавляет два действия для взаимодействия с GUI поверх 14 базовых действий MCCTP:
| Действие | Параметры | Описание |
|---|---|---|
cursor | x: float (0-1), y: float (0-1) | Переместить курсор в нормализованную позицию на экране. Работает только при открытом экране. |
click | button: "left" "right" | Кликнуть в текущей позиции курсора. Работает только при открытом экране. |
Примеры действий
// Переместить курсор в центр экрана
{"action": "cursor", "params": {"x": 0.5, "y": 0.5}}
// Левый клик
{"action": "click", "params": {"button": "left"}}
// Правый клик
{"action": "click", "params": {"button": "right"}}Конфигурация
Файл конфигурации: .minecraft/config/mcstp.json (создаётся при первом запуске)
{
"tickInterval": 1
}| Поле | По умолчанию | Описание |
|---|---|---|
tickInterval | 1 | Рассылать состояние игры каждые N тиков (20 тиков = 1 секунда) |
Это переопределяет интервал тиков MCCTP, когда установлен MCSTP.
Архитектура
Любой клиент ←── WebSocket (JSON) ──→ MCCTP (Fabric Mod)
│
├── WebSocketServer (Netty)
├── ConnectionManager
├── ActionDispatcher
│ ├── 14 базовых обработчиков (move, look, jump, ...)
│ ├── CursorHandler ← MCSTP
│ └── ClickHandler ← MCSTP
│
└── StateProviderRegistry
└── MCSTPStateProvider ← MCSTP
├── PlayerStateInfo (расширенный)
├── HeldItemInfo + ItemCategorizer
├── CombatContextInfo (расширенный)
├── PlayerInputInfo
├── ScreenStateInfo
├── StatusEffectInfo
└── ThreatInfoКлючевые детали реализации:
- MCSTP регистрируется в MCCTP через
MCCTPApi.registerModule("mcstp")— это добавляет его в рукопожатие - Сбор состояния реализует интерфейс
StateProviderиз MCCTP — MCCTP вызывает его каждый тик и рассылает результат - Обработчики действий реализуют интерфейс
ActionHandlerиз MCCTP и регистрируются черезActionDispatcher.registerHandler() - Сканирование угроз использует
getEntitiesByClass(HostileEntity.class)в пределах ограничивающего бокса в 16 блоков - Состояние экрана напрямую читает состояние мыши/клавиш GLFW
- Ввод игрока использует
Input.getMovementInput()для вектора движения и привязки клавишGameOptionsдля состояния кнопок
Сборка из исходников
# Сначала нужно собрать MCCTP
cd mcctp
./gradlew build
# Затем MCSTP
cd ../MCSTP
./gradlew build
# Итоговый jar
build/libs/mcstp-1.0.0.jarСборка нацелена на Java 21. Протестировано с Gradle 9.2.0 и Fabric Loom 1.15.3.
Python-клиент
Python-пакет включён в python/. Предоставляет типизированные датаклассы для полного состояния игры:
import time
from mcctp import SyncMCCTPClient, Actions
from mcstp import GameState
from mcstp import Actions as MCSTPActions
with SyncMCCTPClient("localhost", 8765) as client:
def on_state(data: dict):
state = GameState.from_dict(data)
print(f"HP: {state.player_state.health} | Hostiles: {state.threat.hostile_count}")
if state.combat_context.crosshair_target == "ENTITY":
print(f" Target: {state.combat_context.crosshair_entity_type} "
f"({state.combat_context.crosshair_entity_health} HP)")
client.on_state(on_state)
# Действия MCCTP работают как обычно
client.send(Actions.move("forward", "start"))
time.sleep(2)
client.send(Actions.move("forward", "stop"))
# MCSTP добавляет cursor/click для GUI
client.send(Actions.open_inventory())
time.sleep(0.1)
client.send(MCSTPActions.cursor(0.5, 0.3))
client.send(MCSTPActions.click("left"))GameState.to_control_dict() возвращает плоский словарь с наиболее полезными полями для принятия решений (здоровье, позиция, предмет в руке, цель под прицелом, количество враждебных мобов, состояние экрана).
Лицензия
MIT
Частые вопросы
Как установить MCSTP?
Установите Fabric под свою версию Minecraft, скачайте MCSTP под ту же версию и загрузчик, положите файл в папку mods и запустите игру с профилем загрузчика.
Для каких версий Minecraft есть MCSTP?
У MCSTP есть сборки для Minecraft 1.21.11.
Нужен ли MCSTP на сервере?
Ставится только в игру; на сервер ставить не нужно