using System; using System.Collections.Generic; using MinecraftClient.Dialogs; using MinecraftClient.Inventory; using MinecraftClient.Logger; using MinecraftClient.Mapping; using MinecraftClient.Protocol.Message; using MinecraftClient.Protocol.ProfileKey; using MinecraftClient.Scripting; namespace MinecraftClient.Protocol { /// /// Interface for the MinecraftCom Handler. /// It defines some callbacks that the MinecraftCom handler must have. /// It allows the protocol handler to abstract from the other parts of the program. /// public interface IMinecraftComHandler { /* The MinecraftCom Handler must * provide these getters */ int GetServerPort(); string GetServerHost(); string GetUsername(); Guid GetUserUuid(); string GetUserUuidStr(); string GetSessionID(); string[] GetOnlinePlayers(); Dictionary GetOnlinePlayersWithUUID(); PlayerInfo? GetPlayerInfo(Guid uuid); PlayerKeyPair? GetPlayerKeyPair(); Location GetCurrentLocation(); World GetWorld(); bool GetIsSupportPreviewsChat(); bool GetTerrainEnabled(); bool SetTerrainEnabled(bool enabled); bool GetInventoryEnabled(); bool SetInventoryEnabled(bool enabled); bool GetEntityHandlingEnabled(); bool SetEntityHandlingEnabled(bool enabled); bool GetNetworkPacketCaptureEnabled(); void SetNetworkPacketCaptureEnabled(bool enabled); int GetProtocolVersion(); Container? GetInventory(int inventoryID); ILogger GetLogger(); void GetCookie(string key, out byte[]? data); void SetCookie(string key, byte[] data); void DeleteCookie(string key); void Transfer(string newHost, int newPort); /// /// Invoke a task on the main thread, wait for completion and retrieve return value. /// /// Task to run with any type or return value /// Any result returned from task, result type is inferred from the task /// bool result = InvokeOnMainThread(methodThatReturnsAbool); /// bool result = InvokeOnMainThread(() => methodThatReturnsAbool(argument)); /// int result = InvokeOnMainThread(() => { yourCode(); return 42; }); /// Type of the return value T InvokeOnMainThread(Func task); /// /// Invoke a task on the main thread and wait for completion /// /// Task to run without return value /// InvokeOnMainThread(methodThatReturnsNothing); /// InvokeOnMainThread(() => methodThatReturnsNothing(argument)); /// InvokeOnMainThread(() => { yourCode(); }); void InvokeOnMainThread(Action task); /// /// Called when a network packet received or sent /// /// /// Only called if is set to True /// /// Packet ID /// A copy of Packet Data /// The packet is login phase or playing phase /// The packet is received from server or sent by client void OnNetworkPacket(int packetID, List packetData, bool isLogin, bool isInbound); /// /// Called when a server was successfully joined /// void OnGameJoined(bool isOnlineMode); /// /// Received chat/system message from the server /// /// Message received public void OnTextReceived(ChatMessage message); /// /// Called when the server synchronizes a dialog registry entry. /// void OnDialogRegistryData(int protocolId, string resourceId, DialogDefinition dialog); /// /// Called when the server shows a custom dialog. /// void OnDialogShown(DialogDefinition dialog, DialogPhase phase); /// /// Called when the server shows a custom dialog by registry protocol ID. /// void OnDialogRegistryReferenceShown(int protocolId, DialogPhase phase); /// /// Called when the server clears the current custom dialog. /// void OnDialogCleared(); /// /// Called when the server sends updated server links. /// void OnServerLinksUpdated(IReadOnlyList links); /// /// Will be called every animations of the hit and place block /// /// Player ID /// 0 = LMB, 1 = RMB (RMB Corrent not work) void OnEntityAnimation(int entityID, byte animation); /// /// Will be called when a Synchronization sequence is recevied, this sequence need to be sent when breaking or placing blocks /// /// Sequence ID void OnBlockChangeAck(int sequenceId); /// /// Will be called every player break block in gamemode 0 /// /// Player ID /// Block location /// Destroy stage, maximum 255 void OnBlockBreakAnimation(int entityID, Location location, byte stage); /// /// This method is called when the protocol handler receives a title /// void OnTitle(int action, string titletext, string subtitletext, string actionbartext, int fadein, int stay, int fadeout, string json); /// /// Called when receiving a connection keep-alive from the server /// void OnServerKeepAlive(); /// /// This method is called when the protocol handler receives server data /// /// Indicates if the server has a motd message /// Server MOTD message /// Indicates if the server has a an icon /// Server icon in Base 64 format /// Indicates if the server previews chat void OnServerDataRecived(bool hasMotd, string motd, bool hasIcon, string iconBase64, bool previewsChat); /// /// This method is called when the protocol handler receives "Set Display Chat Preview" packet /// /// Indicates if the server previews chat public void OnChatPreviewSettingUpdate(bool previewsChat); /// /// Called when an inventory is opened /// void OnInventoryOpen(int inventoryID, Container inventory); /// /// Called when an inventory is closed /// void OnInventoryClose(int inventoryID); /// /// Called when the player respawns, which happens on login, respawn and world change. /// void OnRespawn(); /// /// Triggered when a new player joins the game /// /// player info public void OnPlayerJoin(PlayerInfo player); /// /// This method is called when a player has left the game /// /// UUID of the player void OnPlayerLeave(Guid uuid); /// /// This method is called when a player has been killed by another entity /// /// Killer's entity if /// message sent in chat when player is killed void OnPlayerKilled(int killerEntityId, string chatMessage); /// /// Called when the server sets the new location for the player /// /// New location of the player /// New yaw /// New pitch void UpdateLocation(Location location, float yaw, float pitch); /// /// This method is called when the connection has been lost /// void OnConnectionLost(ChatBot.DisconnectReason reason, string message); /// /// Called 20 times per second (20 ticks per second) /// Useful for updating bots in other parts of the program /// void OnUpdate(); /// /// Registers the given plugin channel for the given bot. /// /// The channel to register. /// The bot to register the channel for. void RegisterPluginChannel(string channel, ChatBot bot); /// /// Unregisters the given plugin channel for the given bot. /// /// The channel to unregister. /// The bot to unregister the channel for. void UnregisterPluginChannel(string channel, ChatBot bot); /// /// Sends a plugin channel packet to the server. /// See http://wiki.vg/Plugin_channel for more information about plugin channels. /// /// The channel to send the packet on. /// The payload for the packet. /// Whether the packet should be sent even if the server or the client hasn't registered it yet. /// Whether the packet was sent: true if it was sent, false if there was a connection error or it wasn't registered. bool SendPluginChannelMessage(string channel, byte[] data, bool sendEvenIfNotRegistered = false); /// /// Called when a plugin channel message was sent from the server. /// /// The channel the message was sent on /// The data from the channel void OnPluginChannelMessage(string channel, byte[] data); /// /// Called when the server asks the client to open a book UI. /// /// Book hand, 0 main hand, 1 off hand. void OnBookOpen(int hand); /// /// Called when an entity has spawned /// /// Spawned entity void OnSpawnEntity(Entity entity); /// /// Called when an entity has spawned /// /// Entity id /// Equipment slot. 0: main hand, 1: off hand, 2–5: armor slot (2: boots, 3: leggings, 4: chestplate, 5: helmet)/param> /// Item/param> void OnEntityEquipment(int entityid, int slot, Item? item); /// /// Called when a player spawns or enters the client's render distance /// /// Entity ID /// Entity UUID /// Entity location /// Player head yaw /// Player head pitch void OnSpawnPlayer(int entityID, Guid uuid, Location location, byte yaw, byte pitch); /// /// Called when entities have despawned /// /// List of Entity ID that have despawned void OnDestroyEntities(int[] EntityID); /// /// Called when an entity moved by coordinate offset /// /// Entity ID /// X offset /// Y offset /// Z offset /// TRUE if on ground void OnEntityPosition(int entityID, Double dx, Double dy, Double dz, bool onGround); /// /// Called when an entity moved and rotated /// /// Entity ID /// X offset /// Y offset /// Z offset /// Yaw /// Pitch /// TRUE if on ground void OnEntityPosition(int entityID, Double dx, Double dy, Double dz, float yaw, float pitch, bool onGround); /// /// Called when an entity rotated /// /// Entity ID /// Yaw /// Pitch /// TRUE if on ground void OnEntityRotation(int entityID, float yaw, float pitch, bool onGround); /// /// Called when an entity moved to fixed coordinates /// /// Entity ID /// X /// Y /// Z /// TRUE if on ground void OnEntityTeleport(int entityID, Double x, Double y, Double z, bool onGround); /// /// Called when an entity velocity update packet is received. /// Velocity values are in blocks per tick. /// /// Entity ID /// Velocity X /// Velocity Y /// Velocity Z void OnEntityVelocity(int entityID, double velocityX, double velocityY, double velocityZ); /// /// Called when additional properties have been received for an entity /// /// Entity ID /// Dictionary of properties void OnEntityProperties(int entityID, Dictionary prop); /// /// Called when the status of an entity have been changed /// /// Entity ID /// Status ID void OnEntityStatus(int entityID, byte status); /// /// Called when the world age has been updated /// /// World age /// Time of Day void OnTimeUpdate(long worldAge, long timeOfDay); /// /// When received window properties from server. /// /// /// Inventory ID /// Property ID /// Property Value public void OnWindowProperties(byte inventoryID, short propertyId, short propertyValue); /// /// Called when inventory items have been received /// /// Inventory ID /// Item list /// State ID void OnWindowItems(byte inventoryID, Dictionary itemList, int stateId); /// /// Called when a single slot has been updated inside an inventory /// /// Window ID /// Slot ID /// Item (may be null for empty slot) /// State ID void OnSetSlot(byte inventoryID, short slotID, Item? item, int stateId); /// /// Called when player health or hunger changed. /// /// /// void OnUpdateHealth(float health, int food); /// /// Called when the health of an entity changed /// /// Entity ID /// The health of the entity void OnEntityHealth(int entityID, float health); /// /// Called when entity metadata or metadata changed. /// /// Entity ID /// Entity metadata void OnEntityMetadata(int EntityID, Dictionary metadata); /// /// Called when and explosion occurs on the server /// /// Explosion location /// Explosion strength /// Amount of affected blocks void OnExplosion(Location location, float strength, int affectedBlocks); /// /// Called when a sound packet is received. /// /// Sound key if available, otherwise null /// Sound location for world sounds, or null if unavailable /// Sound category id /// Sound volume /// Sound pitch /// Source entity id for entity-sound packets, if any void OnSoundEffect(string? soundName, Location? location, int category, float volume, float pitch, int? entityID); /// /// Called when a player's game mode has changed /// /// Affected player's UUID /// New game mode void OnGamemodeUpdate(Guid uuid, int gamemode); /// /// Called when a player's latency has changed /// /// Affected player's UUID /// latency void OnLatencyUpdate(Guid uuid, int latency); /// /// Called when Experience bar is updated /// /// Experience bar level /// Player Level /// Total experience void OnSetExperience(float Experiencebar, int Level, int TotalExperience); /// /// Called when client need to change slot. /// /// Used for setting player slot after joining game /// void OnHeldItemChange(byte slot); /// /// Called when an update of the map is sent by the server, take a look at https://wiki.vg/Protocol#Map_Data for more info on the fields /// Map format and colors: https://minecraft.wiki/w/Map_item_format /// /// Map ID of the map being modified /// A scale of the Map, from 0 for a fully zoomed-in map (1 block per pixel) to 4 for a fully zoomed-out map (16 blocks per pixel) /// Specifies whether player and item frame icons are shown /// True if the map has been locked in a cartography table /// A list of MapIcon objects of map icons, send only if trackingPosition is true /// Numbs of columns that were updated (map width) (NOTE: If it is 0, the next fields are not used/are set to default values of 0 and null respectively) /// Map height /// x offset of the westernmost column /// z offset of the northernmost row /// a byte array of colors on the map void OnMapData(int mapid, byte scale, bool trackingPosition, bool locked, List icons, byte columnsUpdated, byte rowsUpdated, byte mapCoulmnX, byte mapRowZ, byte[]? colors); /// /// Called when the Player entity ID has been received from the server /// /// Player entity ID void OnReceivePlayerEntityID(int EntityID); /// /// Called when the Entity use effects /// /// entity ID /// effect id /// effect amplifier /// effect duration /// effect flags /// has factor data /// factorCodec void OnEntityEffect(int entityid, Effects effect, int amplifier, int duration, byte flags, bool hasFactorData, Dictionary? factorCodec); /// /// Called when an entity has an effect removed /// /// Entity ID /// Effect that was removed void OnRemoveEntityEffect(int entityid, Effects effect); /// /// Get the player's active effects /// /// Dictionary of active effects Dictionary GetPlayerEffects(); /// /// Called when Soreboard Objective /// /// objective name /// 0 to create the scoreboard. 1 to remove the scoreboard. 2 to update the display text. /// Only if mode is 0 or 2. The text to be displayed for the score /// Only if mode is 0 or 2. 0 = "integer", 1 = "hearts". /// Number format: 0 - blank, 1 - styled, 2 - fixed void OnScoreboardObjective(string objectiveName, byte mode, string objectiveValue, int type, int numberFormat); /// /// Called when DisplayScoreboard /// /// The entity whose score this is. For players, this is their username; for other entities, it is their UUID. /// 0 to create/update an item. 1 to remove an item. /// The name of the objective the score belongs to /// The name of the objective the score belongs to, but with chat formatting /// The score to be displayed next to the entry. Only sent when Action does not equal 1. /// Number format: 0 - blank, 1 - styled, 2 - fixed void OnUpdateScore(string entityName, int action, string objectiveName, string objectiveDisplayName, int objectiveValue, int numberFormat); /// /// Called when a Teams packet is received from the server. /// /// Internal team name (up to 16 chars) /// 0=create, 1=remove, 2=update, 3=add players, 4=remove players /// Display name (formatted). Present when method is 0 or 2. /// Bit 0=allowFriendlyFire, bit 1=seeFriendlyInvisibles. Present when method is 0 or 2. /// Nametag visibility rule string. Present when method is 0 or 2. /// Collision rule string. Present when method is 0 or 2. /// ChatFormatting color value (-1=none). Present when method is 0 or 2. /// Member name prefix (formatted). Present when method is 0 or 2. /// Member name suffix (formatted). Present when method is 0 or 2. /// Player/entity names. Present when method is 0, 3, or 4. void OnTeam(string teamName, byte method, string displayName, byte friendlyFlags, string nameTagVisibility, string collisionRule, int color, string prefix, string suffix, List players); /// /// Called when the client received the Tab Header and Footer /// /// Header /// Footer void OnTabListHeaderAndFooter(string header, string footer); /// /// Called when tradeList is received from server /// /// Window ID /// List of trades. /// The level the villager is. /// The amount of experience the villager has. /// True if regular villagers and false if the wandering trader. /// If the villager can restock his trades at a workstation, True for regular villagers and false for the wandering trader. void OnTradeList(int windowID, List trades, VillagerInfo villagerInfo); /// /// This method is called when the protocol handler receives "Login Success" packet /// /// The player's UUID received from the server /// The player's username received from the server /// Tuple public void OnLoginSuccess(Guid uuid, string userName, Tuple[]? playerProperty); /// /// Used for a wide variety of game events, from weather to bed use to gamemode to demo messages. /// /// Event type /// Depends on Reason public void OnGameEvent(byte reason, float value); /// /// Called when a block is changed. /// /// The location of the block. /// The block public void OnBlockChange(Location location, Block block); /// /// Called when block entity update data is received for a loaded block. /// /// The block location. /// The block entity NBT payload. public void OnBlockEntityData(Location location, Dictionary? nbt); /// /// Called when "AutoComplete" completes. /// /// The number of this result. /// All commands. public void OnAutoCompleteDone(int transactionId, string[] result); public void SetCanSendMessage(bool canSendMessage); /// /// Called when recipe book recipes are added or replaced. /// /// Recipe entries to add /// True to replace the currently tracked recipe book entries public void OnRecipeBookAdd(RecipeBookRecipeEntry[] recipes, bool replace); /// /// Called when recipe book recipes are removed. /// /// Recipe identifiers to remove public void OnRecipeBookRemove(string[] recipeIds); /// /// Called when achievement/advancement data is received from the server. /// /// Achievements that were added or updated /// IDs of achievements that were removed /// True if all existing state should be cleared before applying public void OnAchievementsUpdate(IReadOnlyList added, IReadOnlyList removedIds, bool reset); /// /// Called when the server selects an advancement tab. /// /// The tab identifier, or null if no tab is selected public void OnSelectAdvancementTab(string? tabId); /// /// Send a click container button packet to the server. /// Used for Enchanting table, Lectern, stone cutter and loom /// /// Id of the window being clicked /// Id of the clicked button /// True if packet was successfully sent bool ClickContainerButton(int windowId, int buttonId); /// /// Send a rename item packet when the anvil inventory is open and there is an item in the first slot /// /// New name (max 50 characters) /// True if packet was successfully sent bool SendRenameItem(string itemName); } }