MIT License
Copyright (c) 2025 Dreamfire Studio
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
DreamChat — Beginner’s Guide & API
This guide explains how to use DreamChat and DreamMessageFormatter to send formatted messages in Minecraft using Kyori Adventure and optional PlaceholderAPI. It covers sending to players, console, permissions, and worlds, plus sanitizing messages for safe output.
What DreamChat Does
- Sends messages with MiniMessage formatting.
- Supports PlaceholderAPI expansion for player context.
- Provides utility methods for sending to console, players, worlds, or permission-based audiences.
- Splits multi-line messages using the
FormatTags.SplitLine token.
Quick Start
DreamChat.SendMessageToPlayer(player, "<green>Hello, <name>!", DreamMessageSettings.all());
DreamChat.BroadcastMessage("<yellow>Server restarting soon!", DreamMessageSettings.safeChat());
DreamChat.SendMessageToConsole("<red>[Debug] Something happened", DreamMessageSettings.plain());
Core Methods (DreamChat)
<tt>SendMessageToConsole(String, DreamMessageSettings)</tt>
Formats and sends a message to the console.
- Applies MiniMessage + PAPI (if enabled).
- Splits into multiple lines if the message contains
FormatTags.SplitLine.
<tt>SendMessageToPlayer(Player, String, DreamMessageSettings)</tt>
Sends a formatted message to a specific player.
- Uses
DreamMessageFormatter.format with the player context.
- Expands PlaceholderAPI if enabled.
<tt>BroadcastMessage(String, DreamMessageSettings)</tt>
Sends a message to all online players.
<tt>SendMessageToPerm(String, T permission, DreamMessageSettings)</tt>
Sends a message to all players who have a specific enum-based permission.
- Integrates with
DreamLuckPerms to resolve and check permissions.
- Example:
DreamChat.SendMessageToPerm("<green>You have admin rights!", MyPermissions.ADMIN, DreamMessageSettings.all());
<tt>SendMessageToWorld(String, String, DreamMessageSettings)</tt>
Sends a message to all players in a world by name.
- Case-insensitive world name check.
<tt>SendMessageToWorld(String, UUID, DreamMessageSettings)</tt>
Sends a message to all players in a world by UUID.
- ⚠️ Currently uses
== instead of .equals for UUID comparison → may fail if UUIDs are not reference-equal.
<tt>SplitMessage(String)</tt> (private)
Splits a message into multiple lines using FormatTags.SplitLine.
Core Methods (DreamMessageFormatter)
<tt>format(String, DreamMessageSettings)</tt>
Formats a raw string into an Adventure Component.
- Applies MiniMessage if enabled.
- Strips unsupported tags if MiniMessage is disabled.
<tt>format(String, Player, DreamMessageSettings)</tt>
Formats a raw string for a player context.
- Expands PlaceholderAPI placeholders.
- Respects MiniMessage settings.
<tt>format(Component, DreamMessageSettings)</tt>
Formats an Adventure component.
- If MiniMessage is disabled, returns as-is.
- Otherwise, serializes to MiniMessage → applies sanitization → deserializes back.
<tt>centerMessage(String, int)</tt>
Centers a plain string to a given width using spaces.
<tt>centerMessage(Component, int)</tt>
Centers a component by serializing to plain text, then re-wrapping.
<tt>limitMessage(String, int)</tt>
Truncates a string and appends ... if longer than the max length.
<tt>limitMessage(Component, int)</tt>
Truncates a component’s plain-text view and returns a new plain component.
<tt>capitalizeWords(String)</tt>
Capitalizes the first letter of each word.
<tt>reverseMessage(String)</tt>
Reverses a string.
<tt>placeholder(String, String)</tt>
Creates a MiniMessage placeholder tag that replaces <key> with a literal string.
<tt>placeholder(String, Component)</tt>
Creates a MiniMessage placeholder tag that replaces <key> with a Component.
DreamMessageSettings Presets
- **
all()** → placeholders + MiniMessage + colors + formatting + click/hover.
- **
safeChat()** → placeholders + MiniMessage + colors/formatting, no click/hover.
- **
plain()** → no placeholders, no MiniMessage, no colors.
FormatTags
- **
SplitLine("<:::>")** → token used to split multi-line messages.
DreamChat.SendMessageToPlayer(player, "Line1" + FormatTags.SplitLine.tag + "Line2", DreamMessageSettings.all());
Events
This system does not dispatch Bukkit events directly, but integrates with:
- DreamLuckPerms (for permission-based messaging).
- PlaceholderAPI (if installed).
Pitfalls & Notes
- UUID comparison bug in
SendMessageToWorld(message, UUID, settings) — replace == with .equals.
- PlaceholderAPI must be installed for PAPI placeholders to work.
- MiniMessage sanitization strips tags when disabled, preventing raw
<tags> from leaking.
- Centering is character-based — not pixel-based.
Suggestions
- Fix UUID comparison in
SendMessageToWorld(UUID) to use .equals.
- Add async/batch messaging for large broadcasts to reduce lag spikes.
- Add rich logging hooks for all chat sends.
- Provide pixel-width centering (Adventure has APIs for measuring font width).
- Add configurable message splitting (custom delimiter instead of
FormatTags.SplitLine).