Skip to Content

Events

Myriad posts events for everything that happens: ticks, packets, input, rendering, the world, the UI. Handle one by annotating a method with @Subscribe. A module’s handlers run only while it’s on.

@Subscribe(inGame = true) // skipped unless there's a world and a player private void onTick(TickEvent.Pre e) { ... } @Subscribe(priority = Priority.HIGH) // higher runs first; any int works private void onChat(ChatReceiveEvent e) { if (e.message().getString().contains("spam")) e.cancel(); } @Subscribe(packets = ClientboundSetTimePacket.class) // only for these packets: far cheaper than instanceof private void onTime(PacketEvent.Receive e) { ... }
@Subscribe option
priorityorder among handlers (Priority.HIGHEST 200 … LOWEST -200; BEFORE_ACTIONS runs before services act)
inGameskip the handler unless a world and player exist
packetson a PacketEvent handler: only these packet classes
receiveCancelledstill receive the event after another handler cancelled it

A handler for a supertype receives its subtypes too. A handler that keeps throwing is logged against its addon and then turned off, so one broken addon can’t break the game.

Outside modules

// Any object's @Subscribe methods, until you unsubscribe it: ctx.events().subscribe(sessionStats); // One handler, as a lambda; keep the Subscription to drop it: Subscription sub = Myriad.events().listen(WorldEvent.Join.class, e -> joinedAt = System.currentTimeMillis()); sub.unsubscribe();

Timing

Act (click, place, break, attack, switch slots) in TickEvent.Pre, before the player moves, as vanilla does. Grim flags actions sent after the tick’s movement packet; Myriad holds any that come later until the start of the next tick, so they’re safe but a tick late. The services act at the right time on their own.

Core events

Event
TickEvent.Pre, TickEvent.Postevery client tick (20 a second), before and after the player
Render2DEventthe HUD frame; canvas() draws in GUI pixels
Render3DEventthe world frame; shapes() draws boxes and lines (see Drawing)
PacketEvent.Send, PacketEvent.Receiveevery packet, bundles split; cancel or setPacket to replace
MovementPacketsEventthe movement packet about to go out: rewrite position, rotation, on-ground
PlayerMoveEventthis tick’s movement: change speed, fly
InputEventthe movement keys for this tick: press or release them
MouseLookEventturning the camera: scale or cancel it
CollisionShapeEventwhat a block collides as: walk on water, avoid cactus
TeleportEventthe server set your position (a teleport, a rubberband)
HealthEventyour health and food from the server, with the damage taken
AttackEventbefore an attack goes out (cancellable)
InteractEvent.Block, .Item, .EntityTargetright-clicks (cancellable)
ItemUseEvent.Finished, .Stoppedeating, drinking, drawing a bow
BlockBreakEvent.Start, .Progress, BlockBrokenEventmining
BlockUpdateEventthe server changed a block (old and new state)
ChunkEvent.Loaded, .Unloadedchunks
EntityEvent.Added, .Removed, .TotemPopped, .Diedentities
ContainerEvent.Opened, .Loaded, .SlotUpdated, .Closedcontainers (chests, your inventory)
ContainerScreenEvent.SlotDrawn, .Tooltip, .Clickicons on slots, previews, taking over clicks
ItemTooltipEventadd tooltip lines
ChatReceiveEvent, ChatSendEventchat in and out (cancel, change); parsed() says who and whether it’s a whisper
BlockRenderEventleave a block out of the chunk mesh (X-ray)
EntityRenderEvent.Visible, .Nametag, .Modelhide an entity, replace its name tag, draw its model again
HighlightEvent.Entity, .Shapesshader outlines and glows (see Highlights)
GlideEventan elytra glide’s movement this tick
CameraEvent, PlaySoundEventthe camera; cancel any sound
KeyEvent, MouseButtonEvent, MouseScrollEvent, CharEventinput
ScreenOpenEventa screen about to open: replace or cancel it
WorldEvent.Join, .Leave, DisconnectEventjoining and leaving
ModuleToggleEventany module turned on or off
WindowResizeEvent, GameReadyEvent, ShutdownEventthe game window and lifecycle

Event objects are made by Myriad (their constructors are @ApiStatus.Internal). Some are reused for every call (HighlightEvent.Entity is): don’t keep one past your handler.