In-game panels
Everything Ecstacy shows staff in game, and how to change it.
The menus
/ecstacy menu opens the main panel. From there:
| Panel | Reached by | Shows |
|---|---|---|
| Main menu | /ecstacy menu |
Plugin info, a live server status tile (cloud state + TPS, refreshed every second), and links to Checks and Global Logs |
| Checks | /ecstacy checks or the main menu |
One dye per check. Green enabled, grey disabled. Lore shows status, fail.max and whether punish is on |
| Check detail | Right-click a check | Toggle the check, or open its settings |
| Check settings | The book in check detail | One item per editable key, with current value and valid range |
| Global logs | Main menu | Server-wide flag list, paginated; click through to a player, then to a single flag |
| Player info | /ecstacy player <name> |
Head, reputation, audit logs, recent flags, and per-check exemptions |
| Reputation | /ecstacy reputation [player] |
Trust score, recent violations, latest flag |
| Violations | /ecstacy violations [player] |
One row per recorded violation |
| Review queue | /ecstacy suspicious |
Player heads for players the models rate SUSPECT: tracking near the bar without flagging. Clicking spectates them |
| Feedback | [Report] on an alert |
Three buttons: true positive, don't know, false positive |
Paginated panels always use the same controls: previous on slot 46, back to menu on 50, next on 54. Clicks inside a panel never move items. You cannot take anything out of them.
Editing a check in game
/ecstacy checks- Left-click a check to toggle it on or off.
- Right-click → Configure settings for its values.
- In the settings panel, a true/false or list value cycles on left-click in place. A
number closes the panel and asks you to type the new value in chat: type it, or type
cancel.
What you type is intercepted before it reaches chat, so the value is never broadcast to the server. Out-of-range input is rejected with the valid range and the panel reopens unchanged.
Every accepted change is written to checks.yml, applied to the running server immediately,
and synced to the cloud. If the cloud link is down the change is parked and replayed on
reconnect. You do not have to redo it.
Note
Only a curated set of keys is editable from the GUI: fail.max, punish.enable and each
check's precision. Everything else in checks.yml is read-only from in game. Edit the file
and run /ecstacy reload.
The chat-input path is rate limited per player:
checks-edit:
rate-limit:
max: 5
window-seconds: 60Checks your licence does not include appear as a barrier marked coming soon and cannot be toggled.
Alerts
Default format, from messages.yml:
alert:
format: "%prefix% &f%player% &7failed &d%check% &7| &fVL: &d%vl%"| Placeholder | Value |
|---|---|
%prefix% |
The active theme's chat prefix |
%player% / %name% |
The flagged player |
%check% |
Check name |
%vl% / %maxvl% |
Current and maximum violation level. %maxvl% renders as ∞ when there is no threshold |
%vl_styled% |
The violation bar drawn with the theme's symbols |
%confidence% |
Detection verdict. CHEATING. Appended inline |
%detail% |
Extra detail for heuristic checks. The rule that tripped. Shown on hover for players, inline on the console. Empty for model checks, whose detail is the verdict |
Verdicts
Model-backed checks report one of two values, and never a number:
| Verdict | Meaning |
|---|---|
CHEATING |
The window flagged. This is what reaches alerts, /ecstacy logs, the dashboard and the CSV export |
SUSPECT |
Tracked near the bar without flagging. Surfaces in /ecstacy suspicious |
The value behind the verdict stays server-side by design: a numeric readout of a detection is also a map of where its boundary sits, which is exactly what an evasion needs. Heuristic checks are unaffected and still report the rule that tripped.
Two clickable suffixes can appear. [Report] opens the feedback panel for that flag. It needs
feedback.enabled: true and the ecstacy.feedback permission. [Replay] appears only when a clip
was recorded for that flag and plays it back for you alone; it needs ecstacy.replay. See
Replay recording.
Who sees an alert is per check, from checks.yml:
fail.alert.viewer: ALL: every online player- anything else (i.e.
STAFF). Operators, holders ofecstacy.alerts, or holders ofecstacy.staff fail.alert.console(defaulttrue). Whether the console gets a copyfail.alert.mode: WEB_ONLY: nobody in chat; the flag is dashboard-only.INHERIT(the default) followsalerts.modeinsettings.yml. See Alert visibility
Tip
If nobody on the server matches the STAFF rule, the plugin logs a warning saying the flag was
shown to no one. If your staff report "the anticheat stopped alerting", check that warning
before touching precision. It usually means a permission group changed, not a detection.
fail.alert.every throttles the chat line only. The flag is still recorded, still counts toward
fail.max, and still reaches the dashboard.
Themes
A theme sets the chat prefix, the colour palette used across messages and panels, and the symbols the violation bar is drawn with.
Pick one with /ecstacy theme. The choice is per server, not per player: it is stored as a
single key:
themes:
active: "ecstacy"Two themes ship: ecstacy (pink/purple, * and | bar symbols) and neon (cyan, ◉ and ◌).
To add your own, drop a copy into plugins/EcstacyAC/themes/<name>.yml and it appears in
/ecstacy theme automatically. A theme file defines prefix, a gui block for how it looks in
the picker, a colors palette, and a violations block for the bar.
Warning
On a fresh install messages.yml ships with themes.active: "purple", but the bundled file is
themes/ecstacy.yml: there is no purple.yml. The server starts with
Theme file themes/purple.yml not found! Using default palette. in the log. Set it to
ecstacy (or your own theme) to clear the warning.
Panel appearance
menus.yml controls titles, slots, materials, item names and lore for the player-info, reputation
and violations panels. Names and lore accept & codes, &#RRGGBB hex and
<gradient:#A:#B>text</gradient>.
player-info-panel:
title: "&d&lEcstacy &8▸ &7{player}"
size: 45Placeholders available there: {player}, {uuid}, {online}, {score}, {score_color},
{rank}, {violations_count}, {logs_count}, {latest_violation},
{latest_violation_time}, {count}, {percentage}, {latest_check}.
Important
Button behaviour is deliberately not configurable. Only appearance. You can move a button, recolour it or rename it; you cannot repoint it at a different action.
The main, info and theme blocks in menus.yml are not what you see either: the live main
menu is driven by the gui.main.* keys in messages.yml, and the theme picker is built by
scanning the themes/ folder. Editing those menus.yml blocks changes nothing.
Every other visible string is overridable under gui.* in messages.yml, or in a
lang/<code>.yml file if you are translating.
Sounds and animations
sounds.yml defines sounds for command results and per-check flags. In the current build only
two are actually played: the success sound when you toggle a check, and the error sound when you
click a check your licence does not include. The violations.* entries are present in the file
but nothing plays them yet.
animations.yml describes particle effects on flag and punish. It is not read in the current
build. Treat it as reserved.
Both files are safe to leave alone.
Join-time messages
Two things staff see on join, driven from settings.yml and templated in messages.yml:
- Client brand:
client.joinannounces the detected client and version. See Integrations. - Low reputation:
reputation.alertwarns staff when a player joins below the alert threshold. See Enforcement.
Tip
The kick and ban screens in messages.yml (punishment.banned, reputation.banned, …) ship
with a placeholder appeal link, example.com/appeal. Change it before you enable punishments,
or banned players will be sent to a page that does not exist.