GUI System
GUI System
Section titled “GUI System”Journey’s GUI system lets you build and customize all in-game menus through JSON configuration files. Every menu — journal, party, bounty boards, backpacks — is defined as a config-driven GUI with slot types, state machines, MoLang-powered dynamic content, and template inheritance.
Configuration Location
Section titled “Configuration Location”Path: config/journey/guis/ (loaded server-side)
Built-in GUIs
Section titled “Built-in GUIs”| File | Description |
|---|---|
journal.json | Quest/task list and tracking |
task_detail.json | Detailed task information |
party.json | Party management and members |
party_create.json | Create new party dialog |
party_invites.json | Pending party invitations |
bounty_board.json | Bounty board tasks |
backpack.json | Quest item storage |
levelable.json | XP and level progression |
team_select.json | Pokemon team selector |
All built-in GUIs can be overridden by placing a file with the same name in config/journey/guis/.
GUI Structure
Section titled “GUI Structure”Every GUI file follows this format:
{ "gui_id": "unique_id", "title": "<gold>GUI Title", "size": "9x6", "extends": "", "states": {}, "placeholders": {}, "watchers": [], "slots": []}| Field | Type | Description |
|---|---|---|
gui_id | String | Unique identifier for this GUI |
title | String | Title displayed at top (supports MiniMessage and placeholders) |
size | String | Dimensions: 9x1 through 9x6 (chest inventory rows) |
extends | String | ID of another GUI to inherit from (see Extends) |
states | Object | State machine definitions (see States) |
placeholders | Object | Custom placeholder definitions |
watchers | Array | MoLang watchers that update the GUI reactively |
slots | Array | List of slot definitions |
Slot Types
Section titled “Slot Types”display
Section titled “display”Static item with no interaction.
{ "id": "info_display", "type": "display", "position": {"x": 4, "y": 0}, "enabled": true, "item": "minecraft:paper", "customModelData": 0, "name": "<gold>Information", "lore": [ "<gray>This is a display item", "<yellow>It shows information" ], "glow": false, "count": 1}button
Section titled “button”Clickable item that performs an action.
{ "id": "close_button", "type": "button", "position": {"x": 4, "y": 5}, "enabled": true, "item": "minecraft:barrier", "name": "<red>Close", "lore": ["<gray>Click to close"], "action": { "type": "close" }}Action Types:
| Type | Description | Extra Fields |
|---|---|---|
close | Close the GUI | — |
command | Run a command | "value": "/command" |
open_gui | Open another GUI | "value": "gui_id" |
next_page | Go to next page | — |
previous_page | Go to previous page | — |
toggle_setting | Toggle a boolean | "setting": "key" |
set_state | Change GUI state | "state": "state_name" |
script | Run MoLang script | "script": "q.player.add_flag('x');" |
open_party_invites | Open party invites | — |
open_player_invite | Open invite dialog | — |
task_list
Section titled “task_list”Paginated list of tasks with formatting for different states.
{ "id": "task_list", "type": "task_list", "position": {"x": 1, "y": 1}, "enabled": true, "size": {"width": 7, "height": 4}, "itemsPerPage": 28, "taskFormat": { "active": { "item": "minecraft:paper", "nameFormat": "<yellow>{task_name}", "loreFormat": [ "<gray>{task_description}", "", "{objectives}", "", "<green>Click to view details" ], "glow": false }, "completed": { "item": "minecraft:writable_book", "nameFormat": "<green>{task_name} <dark_gray>(Completed)", "loreFormat": ["{objectives}"], "glow": true }, "available": { "item": "minecraft:map", "nameFormat": "<gray>{task_name}", "loreFormat": ["<red>Not started"], "glow": false } }}party_member_list
Section titled “party_member_list”Displays party members with different formatting per role.
{ "id": "party_members", "type": "party_member_list", "position": {"x": 1, "y": 1}, "enabled": true, "size": {"width": 7, "height": 3}, "memberFormat": { "leader": { "item": "minecraft:golden_helmet", "nameFormat": "<gold>{member_name} <yellow>(Leader)", "glow": true }, "member": { "item": "minecraft:player_head", "nameFormat": "<green>{member_name}", "glow": false }, "offline": { "item": "minecraft:skeleton_skull", "nameFormat": "<dark_gray>{member_name} <gray>(Offline)", "glow": false } }}party_settings
Section titled “party_settings”Toggle switches for party configuration (leader only).
{ "id": "party_settings", "type": "party_settings", "leaderOnly": true, "settings": [ { "id": "public_toggle", "settingKey": "isPublic", "position": {"x": 0, "y": 4}, "enabled": { "item": "minecraft:lime_dye", "name": "<green>Public Party", "lore": ["<gray>Anyone can join", "", "<yellow>Click to make private"] }, "disabled": { "item": "minecraft:gray_dye", "name": "<gray>Private Party", "lore": ["<gray>Invite only", "", "<yellow>Click to make public"] } } ]}navigation
Section titled “navigation”Page navigation for multi-page GUIs.
{ "id": "navigation", "type": "navigation", "previous": { "position": {"x": 0, "y": 5}, "item": "minecraft:arrow", "name": "<yellow>Previous Page", "lore": ["<gray>Page {prev_page}/{max_pages}"] }, "next": { "position": {"x": 8, "y": 5}, "item": "minecraft:arrow", "name": "<yellow>Next Page", "lore": ["<gray>Page {next_page}/{max_pages}"] }, "hideWhenUnavailable": true}backpack_slots
Section titled “backpack_slots”Quest item storage area.
{ "id": "backpack_slots", "type": "backpack_slots", "position": {"x": 0, "y": 0}, "size": {"width": 9, "height": 6}, "emptySlot": { "item": "minecraft:gray_stained_glass_pane", "name": "", "lore": [] }}bounty_task_list
Section titled “bounty_task_list”Automatically displays bounty board tasks with formatting and click actions.
{ "id": "task_list", "type": "bounty_task_list", "position": {"x": 0, "y": 1}, "enabled": true}State Machines
Section titled “State Machines”GUIs can have multiple states, each showing different slots and layouts. This lets you build multi-page or multi-mode GUIs in a single file.
{ "gui_id": "shop", "title": "<gold>{state_title}", "size": "9x6", "states": { "browse": { "title": "Browse Items", "slots": [ { "id": "buy_tab", "type": "button", "position": {"x": 0, "y": 0}, "item": "minecraft:emerald", "name": "<green>Buy", "action": {"type": "set_state", "state": "buy"} } ] }, "buy": { "title": "Buy Items", "slots": [ { "id": "back_tab", "type": "button", "position": {"x": 0, "y": 0}, "item": "minecraft:arrow", "name": "<yellow>Back", "action": {"type": "set_state", "state": "browse"} } ] } }}The GUI starts in the first defined state. Buttons with set_state actions switch between states, updating the displayed slots and title.
Watchers
Section titled “Watchers”Watchers are MoLang expressions that are evaluated periodically. When a watcher’s value changes, the GUI updates automatically.
{ "watchers": [ { "id": "party_size_watcher", "expression": "q.player.player_party().size()", "interval": 20, "on_change": "refresh" } ]}| Field | Description |
|---|---|
id | Unique watcher identifier |
expression | MoLang expression to evaluate |
interval | Ticks between evaluations |
on_change | Action when value changes: "refresh" (re-render GUI) or "close" |
MoLang in GUIs
Section titled “MoLang in GUIs”Slot names, lore, and enabled conditions can use MoLang expressions wrapped in ${}:
{ "id": "level_display", "type": "display", "position": {"x": 4, "y": 0}, "item": "minecraft:experience_bottle", "name": "<gold>Level ${q.player.levelable_level('trainer_rank')}", "lore": [ "<gray>XP: <yellow>${q.player.levelable_experience('trainer_rank')}", "<gray>Mode: <yellow>${q.player.levelable_mode()}" ], "enabled_condition": "q.player.has_levelable('trainer_rank')"}The enabled_condition field accepts a MoLang expression. When it evaluates to 0.0, the slot is hidden.
Extends
Section titled “Extends”GUIs can inherit from other GUIs using extends. The child GUI starts with all parent slots, then overrides or adds its own.
{ "gui_id": "custom_journal", "extends": "journal", "title": "<blue>My Custom Journal", "slots": [ { "id": "custom_header", "type": "display", "position": {"x": 4, "y": 0}, "item": "minecraft:nether_star", "name": "<gold>Custom Header" } ]}This creates a journal that looks like the default but with a custom header item. Any slot with the same id as a parent slot replaces it; new IDs are added.
Placeholders
Section titled “Placeholders”Built-in Placeholders
Section titled “Built-in Placeholders”Task/Journal: {task_name}, {task_description}, {objectives}, {progress}, {target}
Party: {party_name}, {party_leader}, {party_size}, {party_max}, {member_name}, {member_role}
Bounty Board: {board_name}, {board_description}, {available_tasks}, {max_tasks}
Navigation: {prev_page}, {next_page}, {current_page}, {max_pages}
State: {state_title}, {state_id}
Common Slot Fields
Section titled “Common Slot Fields”All slots share these fields:
| Field | Type | Description |
|---|---|---|
id | String | Unique slot identifier |
type | String | Slot type name |
position | {x, y} | Slot position (x: 0-8, y: 0-5) |
enabled | Boolean | Whether slot is active |
enabled_condition | String | MoLang condition for dynamic visibility |
item | String | Item ID for display |
customModelData | Integer | Custom model data for resource packs |
name | String | Item name (supports MiniMessage, placeholders, and ${} MoLang) |
lore | Array | Item lore lines |
glow | Boolean | Enchantment glow effect |
count | Integer | Stack count (1-64) |
Reloading
Section titled “Reloading”After editing GUI files:
/journey reload guis- Place navigation buttons consistently on the bottom row
- Use empty strings
""in lore for blank lines - Use meaningful item icons: barrier for close, arrow for navigation, book for info
- Use
glow: trueto highlight important items - Keep GUIs as small as needed — don’t use
9x6when9x3is enough - Use
extendsto customize built-in GUIs without rewriting them from scratch - Use
enabled_conditionto show/hide slots based on player state - Use watchers to keep GUIs updated when player data changes