ModsJava
ChatActivities
Periodic chat games where the first correct answer wins. Trivia, unscramble, math, typing races, fully configurable.
⬇ Download on Hangar
ChatActivities runs games in chat on a timer. It posts a question, and the first player to type the correct answer wins
whatever rewards you configure.
Nine game types ship with it, from hand-written trivia to generated word puzzles and arithmetic. Everything is
configurable: the questions, how strictly answers are matched, how often games run, what winning gives you, and every line of text players see.


- **Five generated game types** plus your own hand-written questions
- **Whole question banks in one entry** so a large trivia pool does not swamp your other games
- **Flexible answer matching** with exact, contains, regex or fuzzy modes, and typo tolerance
- **Progressive hints** that reveal the answer gradually and never give it away completely
- **Reward commands** run from console or as the winner, with placeholder support
- **Win statistics** with a leaderboard and fastest-time tracking, stored in SQLite
- **PlaceholderAPI in both directions**: use `%placeholders%` in rewards, and expose `%chatactivities_...%` to your
scoreboards and holograms
- **Players can opt out** with a single command if they would rather not see the games
- **MiniMessage formatting** throughout, with optional sounds, titles and action bars
- **A developer API** with four events so other plugins can filter, redirect or react

1. Drop the jar into your `plugins` folder
2. Restart the server
3. Edit `plugins/ChatActivities/games.yml` and `config.yml`
4. Run `/ca reload`
**Requirements**
- Paper 26.2
- Java 25 or newer
**Optional**
- PlaceholderAPI, if you want to use `%placeholders%` in reward commands or show ChatActivities stats in other plugins
**Java 25 is required.** Paper 26.2 needs it too, so this plugin cannot run on anything older. Run `java -version` to
check before you install.
The first time the plugin starts it downloads one extra file it needs for saving statistics, around 12 MB. This is
automatic and happens only once, but your server needs internet access for it. Without it the plugin will not start.

A game is either **static** (you write the question and its answers) or **generated** (a `type:` produces both fresh
each round).
| Game type (`type`) | What players see | Answer |
|--------------------|--------------------------------------|--------------------------------|
| *none* | Your question, your answers | Whatever you listed |
| `unscramble` | `domniad` | `diamond` |
| `reversed` | `regalliv` | `villager` |
| `random-string` | `f6zqqh` | The string, a pure typing race |
| `random-trivia` | A question drawn from your pool | That entry's answers |
| `math` | `9 + 22`, `√49`, `20% of 150`, `12²` | The result |
**A static question**
```yaml
games:
capital-france:
question: "Quick! What is the capital of France?"
answers: [ "paris" ]
notification: trivia
timeout: 30s
commands:
- "console: say {player} knew it in {time}!"
```
**A whole trivia bank in one entry**
Prefer this over one game per question. A hundred separate entries would crowd out every other game when selection is weighted.
```yaml
general-trivia:
type: random-trivia
question: "Trivia: {question}"
pool:
- q: "Which mob explodes when it gets close to you?"
a: [ "creeper" ]
- q: "What is the strongest vanilla armour material?"
a: netherite # a single answer needs no brackets
```
**Arithmetic**
`mode` picks the flavour: `expression`, `square`, `root` or `percent`. Division is always exact, so answers are never
fractions.
```yaml
quick-maths:
type: math
question: "Solve: {problem}"
mode: expression
operations: [ add, subtract, multiply, divide ]
operands: "2-25"
terms: 2
```

Main command is `/chatactivities`, with `/chatact` and `/ca` as aliases.
| Command | Permission | Default |
|----------------------|-------------------------|----------|
| `/ca start [game]` | `chatactivities.admin` | op |
| `/ca stop` | `chatactivities.admin` | op |
| `/ca reload` | `chatactivities.admin` | op |
| `/ca list` | `chatactivities.admin` | op |
| `/ca toggle` | `chatactivities.toggle` | everyone |
| `/ca stats [player]` | `chatactivities.stats` | everyone |
| `/ca top` | `chatactivities.stats` | everyone |
Viewing another player's stats needs `chatactivities.stats.other` (op by default). Each game also registers
`chatactivities.receive.`, granted to everyone by default. Revoke it to hide a particular category of game
from a group.

Three files, all reloadable with `/ca reload`. A malformed game is reported by name in the console and skipped, so one bad entry never stops the rest from loading.
**`config.yml`** holds timing, matching, hints, rewards and storage.
```yaml
timing:
interval: 300s # base delay between games
variance: 60s # actual delay is the interval plus or minus this
timeout: 45s # how long players have to answer
min-players: 2 # below this, the scheduler waits
selection:
mode: weighted # random | weighted
avoid-repeat: 3 # don't replay any of the last N games
matching:
mode: exact # exact | contains | regex | fuzzy
fuzzy-tolerance: 1 # how many typos to forgive
```
Matching is **always case-insensitive**. There is deliberately no option for it.
**Hints** reveal the answer a little at a time, and are capped so the final character is always hidden. Answers shorter
than `min-answer-length` get no hints at all, because on a two-character answer even the first hint would hand it over.
**Rewards** accept a `console:` or `player:` prefix and the placeholders `{player}`, `{uuid}`, `{game}`, `{answer}` and
`{time}`. `default-commands` run when a game defines none of its own; `always-commands` run on every win regardless.
**`games.yml`** holds the games, **`messages.yml`** every line of text, in
[MiniMessage](https://docs.advntr.dev/minimessage/format) format. Any message can also carry a sound, title, subtitle, action bar or boss bar.

**Using placeholders.** If PlaceholderAPI is installed, `%placeholders%` from any expansion are resolved in reward
commands. This applies to reward commands only, not to `messages.yml` or to game questions.
**Providing placeholders.** Other plugins can read these:
| Placeholder | Value |
|----------------------------------|------------------------------------|
| `%chatactivities_wins%` | The player's total wins |
| `%chatactivities_fastest%` | Their best time, e.g. `1.42s` |
| `%chatactivities_fastest_ms%` | Their best time in milliseconds |
| `%chatactivities_rank%` | Leaderboard position |
| `%chatactivities_total_wins%` | Every win on the server |
| `%chatactivities_total_players%` | Players who have won at least once |
| `%chatactivities_active%` | `true` while a game is running |
| `%chatactivities_active_game%` | The running game's name |
| `%chatactivities_top_name_1%` | Name at that place |
| `%chatactivities_top_wins_1%` | Wins at that place |
| `%chatactivities_top_fastest_1%` | Best time at that place |
Values come from a cache that refreshes on a configurable interval, so scoreboards asking many times a second never touch the database.

Four events, all on the main thread.
| Event | Cancellable | Fired |
|------------------------------|-------------|----------------------------------------------------------|
| `ChatActivityStartEvent` | yes | Before a game is broadcast |
| `ChatActivityBroadcastEvent` | yes | For every message sent, with a **mutable recipient set** |
| `ChatActivityWinEvent` | yes | On a correct answer, before rewards run |
| `ChatActivityEndEvent` | no | When a round ends, however it ended |
`ChatActivityBroadcastEvent` is the integration point for chat management plugins. It carries the message, the game, its notification tag and the recipients, all of which you can change.
Writing a separate plugin against this API is explicitly permitted by the licence, and your plugin remains entirely your
own.
---
**Licence:** All Rights Reserved. You may run ChatActivities on any server you operate. You may not redistribute, modify or resell it.
If you encounter any issues, message me on Discord [@escyth](https://discord.com/users/168375981050953728).
ChatActivities is a free Minecraft Java mod. Compatible with Minecraft 26.2. Downloaded 1 times (via Hangar). Download it and open it directly in the game.