10 #include "../CommandOutput.h"
12 #include "../IniFile.h"
13 #include "../Entities/Player.h"
29 m_bReloadPlugins(false),
30 m_DeadlockDetect(a_DeadlockDetect)
62 for (
auto & item: Contents)
69 Folders.push_back(item);
75 if (std::find(Folders.cbegin(), Folders.cend(), plugin->GetFolderName()) == Folders.end())
82 for (
auto & folder: Folders)
84 bool hasFound =
false;
87 if (plugin->GetFolderName() == folder)
117 LOG(
"-- Loading Plugins --");
128 for (
auto & pluginFolder: ToLoad)
135 if (NumLoadedPlugins == 0)
137 LOG(
"-- No Plugins Loaded --");
139 else if (NumLoadedPlugins == 1)
141 LOG(
"-- Loaded 1 Plugin --");
145 LOG(
"-- Loaded %u Plugins --",
static_cast<unsigned>(NumLoadedPlugins));
157 a_Settings.
AddValue(
"Plugins",
"Core",
"1");
158 a_Settings.
AddValue(
"Plugins",
"ChatLog",
"1");
159 a_Settings.
AddValue(
"Plugins",
"ProtectionAreas",
"0");
175 for (
auto & CurrentPlugin : PluginsNeedAction)
177 auto & Action = CurrentPlugin.first;
178 auto & Folder = CurrentPlugin.second;
180 bool WasLoaded =
false;
181 bool WasFound =
false;
184 if (Plugin->GetFolderName() == Folder)
187 if (Plugin->IsLoaded())
211 LOG(
"Cannot act on plugin in folder \"%s\", there's no such plugin folder", Folder.c_str());
215 LOG(
"Cannot act on plugin in folder \"%s\", it has not been loaded.", Folder.c_str());
231 for (
auto * Plugin : Plugins->second)
241 template <
typename HookFunction>
244 auto Plugins =
m_Hooks.find(a_HookName);
250 return std::any_of(Plugins->second.begin(), Plugins->second.end(), a_HookFunction);
261 return a_Plugin->
OnBlockSpread(a_World, a_BlockPos.
x, a_BlockPos.
y, a_BlockPos.
z, a_Source);
276 const cItem * a_Tool,
282 return a_Plugin->
OnBlockToPickups(a_World, a_BlockPos, a_BlockType, a_BlockMeta, a_BlockEntity, a_Digger, a_Tool, a_Pickups);
338 a_Player.
SendMessageFailure(fmt::format(FMT_STRING(
"Something went wrong while executing command \"{}\""), a_Message));
345 a_Player.
SendMessageFailure(fmt::format(FMT_STRING(
"Forbidden command; insufficient privileges: \"{}\""), a_Message));
357 if (!a_Message.empty() && (a_Message[0] ==
'/'))
361 a_Player.
SendMessageInfo(fmt::format(FMT_STRING(
"Unknown command: \"{}\""), a_Message));
362 LOGINFO(
"Player %s issued an unknown command: \"%s\"", a_Player.
GetName(), a_Message);
368 return a_Plugin->
OnChat(a_Player, a_Message);
394 return a_Plugin->
OnChunkGenerated(a_World, a_ChunkX, a_ChunkZ, a_ChunkDesc);
485 return a_Plugin->
OnEntityAddEffect(a_Entity, a_EffectType, a_EffectDurationTicks, a_EffectIntensity, a_DistanceModifier);
536 if (a_Player !=
nullptr)
541 if (world !=
nullptr)
544 worldAge = world->GetWorldAge().count();
548 worldName =
"<no world>";
551 LOG(
"Player %s is executing command \"%s\" in world \"%s\" at world age %lld.",
553 a_EntireCommand.c_str(),
561 return a_Plugin->
OnExecuteCommand(a_Player, a_Split, a_EntireCommand, a_Result);
574 return a_Plugin->
OnExploded(a_World, a_ExplosionSize, a_CanCauseFire, a_X, a_Y, a_Z, a_Source, a_SourceData);
587 return a_Plugin->
OnExploding(a_World, a_ExplosionSize, a_CanCauseFire, a_X, a_Y, a_Z, a_Source, a_SourceData);
600 return a_Plugin->
OnHandshake(a_ClientHandle, a_Username);
613 return a_Plugin->
OnHopperPullingItem(a_World, a_Hopper, a_DstSlotNum, a_SrcEntity, a_SrcSlotNum);
626 return a_Plugin->
OnHopperPushingItem(a_World, a_Hopper, a_SrcSlotNum, a_DstEntity, a_DstSlotNum);
639 return a_Plugin->
OnDropSpense(a_World, a_DropSpenser, a_SlotNum);
652 return a_Plugin->
OnKilled(a_Victim, a_TDI, a_DeathMessage);
665 return a_Plugin->
OnKilling(a_Victim, a_Killer, a_TDI);
678 return a_Plugin->
OnLogin(a_Client, a_ProtocolVersion, a_Username);
717 return a_Plugin->
OnPlayerBreakingBlock(a_Player, a_BlockPos.
x, a_BlockPos.
y, a_BlockPos.
z, a_BlockFace, a_BlockType, a_BlockMeta);
730 return a_Plugin->
OnPlayerBrokenBlock(a_Player, a_BlockPos.
x, a_BlockPos.
y, a_BlockPos.
z, a_BlockFace, a_BlockType, a_BlockMeta);
782 return a_Plugin->
OnPlayerFished(a_Player, a_Reward, ExperienceAmount);
795 return a_Plugin->
OnPlayerFishing(a_Player, a_Reward, ExperienceAmount);
821 return a_Plugin->
OnPlayerLeftClick(a_Player, a_BlockPos.
x, a_BlockPos.
y, a_BlockPos.
z, a_BlockFace, a_Status);
834 return a_Plugin->
OnPlayerMoving(a_Player, a_OldPosition, a_NewPosition, a_PreviousIsOnGround);
899 return a_Plugin->
OnPlayerRightClick(a_Player, a_BlockPos.
x, a_BlockPos.
y, a_BlockPos.
z, a_BlockFace, a_CursorPos.
x, a_CursorPos.
y, a_CursorPos.
z);
964 return a_Plugin->
OnPlayerUsedBlock(a_Player, a_BlockPos.
x, a_BlockPos.
y, a_BlockPos.
z, a_BlockFace, a_CursorPos.
x, a_CursorPos.
y, a_CursorPos.
z, a_BlockType, a_BlockMeta);
977 return a_Plugin->
OnPlayerUsedItem(a_Player, a_BlockPos.
x, a_BlockPos.
y, a_BlockPos.
z, a_BlockFace, a_CursorPos.
x, a_CursorPos.
y, a_CursorPos.
z);
990 return a_Plugin->
OnPlayerUsingBlock(a_Player, a_BlockPos.
x, a_BlockPos.
y, a_BlockPos.
z, a_BlockFace, a_CursorPos.
x, a_CursorPos.
y, a_CursorPos.
z, a_BlockType, a_BlockMeta);
1003 return a_Plugin->
OnPlayerUsingItem(a_Player, a_BlockPos.
x, a_BlockPos.
y, a_BlockPos.
z, a_BlockFace, a_CursorPos.
x, a_CursorPos.
y, a_CursorPos.
z);
1034 for (
auto * Plugin : Plugins->second)
1036 if (!Plugin->OnPluginsLoaded())
1078 return a_Plugin->
OnProjectileHitBlock(a_Projectile, a_BlockPos.
x, a_BlockPos.
y, a_BlockPos.
z, a_Face, a_BlockHitPos);
1104 return a_Plugin->
OnServerPing(a_ClientHandle, a_ServerDescription, a_OnlinePlayersCount, a_MaxPlayersCount, a_Favicon);
1182 return a_Plugin->
OnUpdatingSign(a_World, a_BlockPos.
x, a_BlockPos.
y, a_BlockPos.
z, a_Line1, a_Line2, a_Line3, a_Line4, a_Player);
1195 return a_Plugin->
OnUpdatedSign(a_World, a_BlockPos.
x, a_BlockPos.
y, a_BlockPos.
z, a_Line1, a_Line2, a_Line3, a_Line4, a_Player);
1247 return a_Plugin->
OnWorldTick(a_World, a_Dt, a_LastTickDurationMSec);
1264 CommandMap::iterator cmd =
m_Commands.find(Split[0]);
1269 if (!a_Command.empty() && (a_Command[0] ==
'/'))
1284 LOGINFO(
"Player %s tried executing command \"%s\" that was stopped by the HOOK_EXECUTE_COMMAND hook", a_Player.
GetName().c_str(), Split[0].c_str());
1290 a_ShouldCheckPermissions &&
1291 !cmd->second.m_Permission.empty() &&
1295 LOGINFO(
"Player %s tried to execute forbidden command: \"%s\"", a_Player.
GetName().c_str(), Split[0].c_str());
1299 ASSERT(cmd->second.m_Handler !=
nullptr);
1301 if (!cmd->second.m_Handler->ExecuteCommand(Split, &a_Player, a_Command,
nullptr))
1326 if (plugin->IsLoaded())
1361 if (plugin->GetFolderName() == a_FolderName)
1363 if (!plugin->IsLoaded())
1365 return plugin->Load();
1372 LOG(
"Cannot load plugin, folder \"%s\" not found.", a_FolderName.c_str());
1384 Hook.second.remove(a_Plugin);
1396 if (itr->second.m_Plugin == a_Plugin)
1398 CommandMap::iterator EraseMe = itr;
1417 if (plugin->GetName() == a_PluginName)
1437 CommandMap::iterator cmd =
m_Commands.find(a_Command);
1440 LOGWARNING(
"Command \"%s\" is already bound to plugin \"%s\".", a_Command.c_str(), cmd->second.m_Plugin->GetName().c_str());
1445 reg.m_Plugin = a_Plugin;
1446 reg.m_Handler = std::move(a_Handler);
1447 reg.m_Permission = a_Permission;
1448 reg.m_HelpString = a_HelpString;
1460 if (a_Callback.
Command(itr.first, itr.second.m_Plugin, itr.second.m_Permission, itr.second.m_HelpString))
1483 CommandMap::iterator cmd =
m_Commands.find(a_Command);
1484 return (cmd ==
m_Commands.end()) ?
"" : cmd->second.m_Permission;
1513 if (itr->second.m_Plugin == a_Plugin)
1515 CommandMap::iterator EraseMe = itr;
1540 if (cmd->second.m_Plugin ==
nullptr)
1542 LOGWARNING(
"Console command \"%s\" is already bound internally by Cuberite, cannot bind in plugin \"%s\".", a_Command.c_str(), a_Plugin->
GetName().c_str());
1546 LOGWARNING(
"Console command \"%s\" is already bound to plugin \"%s\", cannot bind in plugin \"%s\".", a_Command.c_str(), cmd->second.m_Plugin->GetName().c_str(), a_Plugin->
GetName().c_str());
1552 reg.m_Plugin = a_Plugin;
1553 reg.m_Handler = std::move(a_Handler);
1554 reg.m_Permission =
"";
1555 reg.m_HelpString = a_HelpString;
1567 if (a_Callback.
Command(itr.first, itr.second.m_Plugin,
"", itr.second.m_HelpString))
1590 if (a_Split.empty())
1605 if (cmd->second.m_Plugin ==
nullptr)
1618 return cmd->second.m_Handler->ExecuteCommand(a_Split,
nullptr, a_Command, &a_Output);
1629 if (
NoCaseCompare(Command.first.substr(0, a_Text.length()), a_Text) != 0)
1634 if ((a_Player !=
nullptr) && !a_Player->
HasPermission(Command.second.m_Permission))
1650 size_t LastSpaceInText = a_Text.find_last_of(
' ') + 1;
1651 size_t LastSpaceInSuggestion = Command.first.find_last_of(
' ') + 1;
1653 if (LastSpaceInText != LastSpaceInSuggestion)
1659 a_Results.push_back(Command.first.substr(LastSpaceInSuggestion));
1669 return ((a_HookType >= 0) && (a_HookType <=
HOOK_MAX));
1681 if (plugin->GetName() == a_PluginName)
1683 return a_Callback(*plugin);
1698 if (a_Callback(*plugin))
1715 if (plugin->GetName() == a_PluginName)
1717 return plugin->GetFolderName();
1729 if (a_Plugin ==
nullptr)
1731 LOGWARN(
"Called cPluginManager::AddHook() with a_Plugin == nullptr");
1735 if (std::find(Plugins.cbegin(), Plugins.cend(), a_Plugin) == Plugins.cend())
1737 Plugins.push_back(a_Plugin);
1759 if (plugin->IsLoaded())
1783 auto OldValues = a_Settings.
GetValues(
"Plugins");
1784 for (
const auto & NameValue : OldValues)
1786 AString ValueName = NameValue.first;
1787 if (ValueName.compare(
"Plugin") == 0)
1789 AString PluginFile = NameValue.second;
1791 !PluginFile.empty() &&
1792 (PluginFile !=
"0") &&
1797 a_Settings.
SetValue(
"Plugins", PluginFile,
"1");
1803 auto Values = a_Settings.
GetValues(
"Plugins");
1804 for (
const auto & NameValue : Values)
1809 res.push_back(NameValue.first);
unsigned char NIBBLETYPE
The datatype used by nibbledata (meta, light, skylight)
unsigned char BLOCKTYPE
The datatype used by blockdata.
eExplosionSource
The source of an explosion.
eBlockFace
Block face constants, used in PlayerDigging and PlayerBlockPlacement packets and bbox collision calc.
std::basic_string_view< std::byte > ContiguousByteBufferView
void LOGWARNING(std::string_view a_Format, const Args &... args)
void LOG(std::string_view a_Format, const Args &... args)
void LOGINFO(std::string_view a_Format, const Args &... args)
AStringVector StringSplit(const AString &str, const AString &delim)
Split the string at any of the listed delimiters.
int NoCaseCompare(const AString &s1, const AString &s2)
Case-insensitive string comparison.
std::vector< AString > AStringVector
std::map< AString, AString > AStringMap
A string dictionary, used for key-value pairs.
bool Enabled(const BlockState Block)
virtual bool OnPostCrafting(cPlayer &a_Player, cCraftingGrid &a_Grid, cCraftingRecipe &a_Recipe)=0
virtual bool OnSpawningMonster(cWorld &a_World, cMonster &a_Monster)=0
virtual bool OnEntityAddEffect(cEntity &a_Entity, int a_EffectType, int a_EffectDurationTicks, int a_EffectIntensity, double a_DistanceModifier)=0
virtual bool OnPlayerBreakingBlock(cPlayer &a_Player, int a_BlockX, int a_BlockY, int a_BlockZ, eBlockFace a_BlockFace, BLOCKTYPE a_BlockType, NIBBLETYPE a_BlockMeta)=0
virtual bool OnPlayerPlacedBlock(cPlayer &a_Player, const sSetBlock &a_BlockChange)=0
virtual bool OnPlayerEating(cPlayer &a_Player)=0
virtual bool OnPlayerFishing(cPlayer &a_Player, cItems &a_Reward, int &ExperienceAmount)=0
virtual bool OnWorldStarted(cWorld &a_World)=0
virtual bool OnPlayerFished(cPlayer &a_Player, const cItems &a_Reward, const int ExperienceAmount)=0
virtual bool OnEntityTeleport(cEntity &a_Entity, const Vector3d &a_OldPosition, const Vector3d &a_NewPosition)=0
virtual bool OnPlayerBrokenBlock(cPlayer &a_Player, int a_BlockX, int a_BlockY, int a_BlockZ, eBlockFace a_BlockFace, BLOCKTYPE a_BlockType, NIBBLETYPE a_BlockMeta)=0
virtual bool OnChunkUnloading(cWorld &a_World, int a_ChunkX, int a_ChunkZ)=0
virtual bool OnChunkGenerating(cWorld &a_World, int a_ChunkX, int a_ChunkZ, cChunkDesc *a_ChunkDesc)=0
virtual bool OnEntityChangingWorld(cEntity &a_Entity, cWorld &a_World)=0
virtual bool OnPlayerUsingItem(cPlayer &a_Player, int a_BlockX, int a_BlockY, int a_BlockZ, eBlockFace a_BlockFace, int a_CursorX, int a_CursorY, int a_CursorZ)=0
virtual bool OnBrewingCompleting(cWorld &a_World, cBrewingstandEntity &a_BrewingstandEntity)=0
virtual bool OnServerPing(cClientHandle &a_ClientHandle, AString &a_ServerDescription, int &a_OnlinePlayersCount, int &a_MaxPlayersCount, AString &a_Favicon)=0
virtual bool OnProjectileHitBlock(cProjectileEntity &a_Projectile, int a_BlockX, int a_BlockY, int a_BlockZ, eBlockFace a_Face, const Vector3d &a_BlockHitPos)=0
virtual bool OnPlayerUsedItem(cPlayer &a_Player, int a_BlockX, int a_BlockY, int a_BlockZ, eBlockFace a_BlockFace, int a_CursorX, int a_CursorY, int a_CursorZ)=0
virtual bool OnPlayerCrouched(cPlayer &a_Player)=0
virtual bool OnUpdatedSign(cWorld &a_World, int a_BlockX, int a_BlockY, int a_BlockZ, const AString &a_Line1, const AString &a_Line2, const AString &a_Line3, const AString &a_Line4, cPlayer *a_Player)=0
virtual bool OnExploding(cWorld &a_World, double &a_ExplosionSize, bool &a_CanCauseFire, double a_X, double a_Y, double a_Z, eExplosionSource a_Source, void *a_SourceData)=0
const AString & GetName(void) const
virtual bool OnCollectingPickup(cPlayer &a_Player, cPickup &a_Pickup)=0
virtual bool OnEntityChangedWorld(cEntity &a_Entity, cWorld &a_World)=0
virtual bool OnPlayerSpawned(cPlayer &a_Player)=0
virtual bool OnSpawningEntity(cWorld &a_World, cEntity &a_Entity)=0
virtual bool OnSpawnedEntity(cWorld &a_World, cEntity &a_Entity)=0
virtual bool OnPlayerOpeningWindow(cPlayer &a_Player, cWindow &a_Window)=0
virtual bool OnHopperPullingItem(cWorld &a_World, cHopperEntity &a_Hopper, int a_DstSlotNum, cBlockEntityWithItems &a_SrcEntity, int a_SrcSlotNum)=0
virtual bool OnExecuteCommand(cPlayer *a_Player, const AStringVector &a_Split, const AString &a_EntireCommand, cPluginManager::CommandResult &a_Result)=0
virtual bool OnWorldTick(cWorld &a_World, std::chrono::milliseconds a_Dt, std::chrono::milliseconds a_LastTickDurationMSec)=0
virtual bool OnPluginMessage(cClientHandle &a_Client, const AString &a_Channel, ContiguousByteBufferView a_Message)=0
virtual bool OnChunkGenerated(cWorld &a_World, int a_ChunkX, int a_ChunkZ, cChunkDesc *a_ChunkDesc)=0
virtual bool OnPlayerAnimation(cPlayer &a_Player, int a_Animation)=0
virtual bool OnBlockSpread(cWorld &a_World, int a_BlockX, int a_BlockY, int a_BlockZ, eSpreadSource a_Source)=0
Calls the specified hook with the params given.
virtual bool OnPlayerRightClickingEntity(cPlayer &a_Player, cEntity &a_Entity)=0
virtual bool OnCraftingNoRecipe(cPlayer &a_Player, cCraftingGrid &a_Grid, cCraftingRecipe &a_Recipe)=0
virtual bool OnTakeDamage(cEntity &a_Receiver, TakeDamageInfo &a_TakeDamageInfo)=0
virtual bool OnPlayerPlacingBlock(cPlayer &a_Player, const sSetBlock &a_BlockChange)=0
virtual bool OnPlayerUsingBlock(cPlayer &a_Player, int a_BlockX, int a_BlockY, int a_BlockZ, eBlockFace a_BlockFace, int a_CursorX, int a_CursorY, int a_CursorZ, BLOCKTYPE a_BlockType, NIBBLETYPE a_BlockMeta)=0
virtual bool OnKilled(cEntity &a_Victim, TakeDamageInfo &a_TDI, AString &a_DeathMessage)=0
virtual bool OnBrewingCompleted(cWorld &a_World, cBrewingstandEntity &a_BrewingstandEntity)=0
virtual bool OnDropSpense(cWorld &a_World, cDropSpenserEntity &a_DropSpenser, int a_SlotNum)=0
virtual bool OnPlayerMoving(cPlayer &a_Player, const Vector3d &a_OldPosition, const Vector3d &a_NewPosition, bool a_PreviousIsOnGround)=0
virtual bool OnKilling(cEntity &a_Victim, cEntity *a_Killer, TakeDamageInfo &a_TDI)=0
virtual bool OnPlayerRightClick(cPlayer &a_Player, int a_BlockX, int a_BlockY, int a_BlockZ, eBlockFace a_BlockFace, int a_CursorX, int a_CursorY, int a_CursorZ)=0
virtual bool OnLogin(cClientHandle &a_Client, UInt32 a_ProtocolVersion, const AString &a_Username)=0
virtual bool OnPlayerDestroyed(cPlayer &a_Player)=0
virtual bool OnPlayerLeftClick(cPlayer &a_Player, int a_BlockX, int a_BlockY, int a_BlockZ, eBlockFace a_BlockFace, char a_Status)=0
virtual bool OnHandshake(cClientHandle &a_Client, const AString &a_Username)=0
virtual bool OnProjectileHitEntity(cProjectileEntity &a_Projectile, cEntity &a_HitEntity)=0
virtual bool OnPlayerTossingItem(cPlayer &a_Player)=0
virtual bool OnLoginForge(cClientHandle &a_Client, const AStringMap &a_Mods)=0
virtual bool OnExploded(cWorld &a_World, double a_ExplosionSize, bool a_CanCauseFire, double a_X, double a_Y, double a_Z, eExplosionSource a_Source, void *a_SourceData)=0
virtual bool OnWeatherChanged(cWorld &a_World)=0
virtual bool OnPlayerJoined(cPlayer &a_Player)=0
virtual bool OnChat(cPlayer &a_Player, AString &a_Message)=0
virtual bool OnDisconnect(cClientHandle &a_Client, const AString &a_Reason)=0
virtual bool OnWeatherChanging(cWorld &a_World, eWeather &a_NewWeather)=0
virtual bool OnPlayerUsedBlock(cPlayer &a_Player, int a_BlockX, int a_BlockY, int a_BlockZ, eBlockFace a_BlockFace, int a_CursorX, int a_CursorY, int a_CursorZ, BLOCKTYPE a_BlockType, NIBBLETYPE a_BlockMeta)=0
virtual bool OnPreCrafting(cPlayer &a_Player, cCraftingGrid &a_Grid, cCraftingRecipe &a_Recipe)=0
virtual bool OnUpdatingSign(cWorld &a_World, int a_BlockX, int a_BlockY, int a_BlockZ, AString &a_Line1, AString &a_Line2, AString &a_Line3, AString &a_Line4, cPlayer *a_Player)=0
virtual bool OnHopperPushingItem(cWorld &a_World, cHopperEntity &a_Hopper, int a_SrcSlotNum, cBlockEntityWithItems &a_DstEntity, int a_DstSlotNum)=0
virtual bool OnChunkAvailable(cWorld &a_World, int a_ChunkX, int a_ChunkZ)=0
virtual bool OnSpawnedMonster(cWorld &a_World, cMonster &a_Monster)=0
virtual bool OnPlayerShooting(cPlayer &a_Player)=0
virtual bool OnChunkUnloaded(cWorld &a_World, int a_ChunkX, int a_ChunkZ)=0
virtual bool OnBlockToPickups(cWorld &a_World, Vector3i a_BlockPos, BLOCKTYPE a_BlockType, NIBBLETYPE a_BlockMeta, const cBlockEntity *a_BlockEntity, const cEntity *a_Digger, const cItem *a_Tool, cItems &a_Pickups)=0
virtual bool OnPlayerFoodLevelChange(cPlayer &a_Player, int a_NewFoodLevel)=0
void InsertDefaultPlugins(cSettingsRepositoryInterface &a_Settings)
Handles writing default plugins if 'Plugins' key not found using a settings repo expected to be intia...
cPluginManager(cDeadlockDetect &a_DeadlockDetect)
bool CallHookPlayerAnimation(cPlayer &a_Player, int a_Animation)
bool CallHookChunkGenerated(cWorld &a_World, int a_ChunkX, int a_ChunkZ, cChunkDesc *a_ChunkDesc)
AString GetCommandPermission(const AString &a_Command)
Returns the permission needed for the specified command; empty string if command not found.
bool CallHookEntityAddEffect(cEntity &a_Entity, int a_EffectType, int a_EffectDurationTicks, int a_EffectIntensity, double a_DistanceModifier)
bool CallHookSpawnedEntity(cWorld &a_World, cEntity &a_Entity)
bool CallHookChunkGenerating(cWorld &a_World, int a_ChunkX, int a_ChunkZ, cChunkDesc *a_ChunkDesc)
bool CallHookPlayerRightClickingEntity(cPlayer &a_Player, cEntity &a_Entity)
bool CallHookPlayerRightClick(cPlayer &a_Player, Vector3i a_BlockPos, eBlockFace a_BlockFace, Vector3i a_CursorPos)
static bool IsValidHookType(int a_HookType)
Returns true if the specified hook type is within the allowed range.
AStringVector GetFoldersToLoad(cSettingsRepositoryInterface &a_Settings)
Returns the folders that are specified in the settings ini to load plugins from.
bool CallHookChunkAvailable(cWorld &a_World, int a_ChunkX, int a_ChunkZ)
cDeadlockDetect & m_DeadlockDetect
The deadlock detect in which all plugins should track their CSs.
bool ForEachPlugin(cPluginCallback a_Callback)
Calls the specified callback for each plugin in m_Plugins.
bool CallHookPlayerFishing(cPlayer &a_Player, cItems &a_Reward, int &ExperienceAmount)
bool CallHookPlayerFoodLevelChange(cPlayer &a_Player, int a_NewFoodLevel)
bool CallHookPlayerShooting(cPlayer &a_Player)
bool ExecuteConsoleCommand(const AStringVector &a_Split, cCommandOutputCallback &a_Output, const AString &a_Command)
Executes the command split into a_Split, as if it was given on the console.
bool CallHookPlayerEating(cPlayer &a_Player)
bool CallHookHandshake(cClientHandle &a_ClientHandle, const AString &a_Username)
bool LoadPlugin(const AString &a_PluginFolder)
Loads the plugin from the specified plugin folder.
static cPluginManager * Get(void)
Returns the instance of the Plugin Manager (there is only ever one)
void RemovePluginCommands(cPlugin *a_Plugin)
Removes all command bindings that the specified plugin has made.
bool CallHookPlayerUsingItem(cPlayer &a_Player, Vector3i a_BlockPos, eBlockFace a_BlockFace, Vector3i a_CursorPos)
bool CallHookPlayerTossingItem(cPlayer &a_Player)
bool CallHookServerPing(cClientHandle &a_ClientHandle, AString &a_ServerDescription, int &a_OnlinePlayersCount, int &a_MaxPlayersCount, AString &a_Favicon)
bool CallHookPlayerLeftClick(cPlayer &a_Player, Vector3i a_BlockPos, eBlockFace a_BlockFace, char a_Status)
CommandMap m_ConsoleCommands
bool CallHookBlockToPickups(cWorld &a_World, Vector3i a_BlockPos, BLOCKTYPE a_BlockType, NIBBLETYPE a_BlockMeta, const cBlockEntity *a_BlockEntity, const cEntity *a_Digger, const cItem *a_Tool, cItems &a_Pickups)
bool CallHookCollectingPickup(cPlayer &a_Player, cPickup &a_Pickup)
bool CallHookSpawnedMonster(cWorld &a_World, cMonster &a_Monster)
void ReloadPluginsNow(void)
Reloads all plugins, defaulting to settings.ini for settings location.
bool CallHookSpawningEntity(cWorld &a_World, cEntity &a_Entity)
bool CallHookLogin(cClientHandle &a_Client, UInt32 a_ProtocolVersion, const AString &a_Username)
bool CallHookDropSpense(cWorld &a_World, cDropSpenserEntity &a_DropSpenser, int a_SlotNum)
bool CallHookUpdatedSign(cWorld &a_World, Vector3i a_BlockPos, const AString &a_Line1, const AString &a_Line2, const AString &a_Line3, const AString &a_Line4, cPlayer *a_Player)
void RemoveHooks(cPlugin *a_Plugin)
Removes all hooks the specified plugin has registered.
std::list< cPlugin * > PluginList
bool CallHookPlayerCrouched(cPlayer &a_Player)
size_t GetNumLoadedPlugins(void) const
Returns the number of plugins that are psLoaded.
bool CallHookChunkUnloaded(cWorld &a_World, int a_ChunkX, int a_ChunkZ)
void RefreshPluginList()
Refreshes the m_Plugins list based on the current contents of the Plugins folder.
bool CallHookPluginsLoaded(void)
bool CallHookPlayerPlacingBlock(cPlayer &a_Player, const sSetBlock &a_BlockChange)
void AddHook(cPlugin *a_Plugin, int a_HookType)
Adds the plugin to the list of plugins called for the specified hook type.
void UnloadPlugin(const AString &a_PluginFolder)
Queues the specified plugin to be unloaded in the next call to Tick().
bool CallHookPlayerSpawned(cPlayer &a_Player)
bool CallHookPlayerJoined(cPlayer &a_Player)
void RemovePluginConsoleCommands(cPlugin *a_Plugin)
Removes all console command bindings that the specified plugin has made.
bool ForEachConsoleCommand(cCommandEnumCallback &a_Callback)
Calls a_Callback for each bound console command, returns true if all commands were enumerated.
void Tick(float a_Dt)
Called each tick, calls the plugins' OnTick hook, as well as processes plugin events (addition,...
bool CallHookEntityChangingWorld(cEntity &a_Entity, cWorld &a_World)
bool CallHookPlayerDestroyed(cPlayer &a_Player)
bool CallHookPlayerOpeningWindow(cPlayer &a_Player, cWindow &a_Window)
bool CallHookWorldStarted(cWorld &a_World)
void TabCompleteCommand(const AString &a_Text, AStringVector &a_Results, cPlayer *a_Player)
Appends all commands beginning with a_Text (case-insensitive) into a_Results.
void ReloadPlugins()
Schedules a reload of the plugins to happen within the next call to Tick().
void UnloadPluginsNow(void)
Unloads all plugins.
bool CallHookPlayerUsingBlock(cPlayer &a_Player, Vector3i a_BlockPos, eBlockFace a_BlockFace, Vector3i a_CursorPos, BLOCKTYPE a_BlockType, NIBBLETYPE a_BlockMeta)
bool CallHookProjectileHitEntity(cProjectileEntity &a_Projectile, cEntity &a_HitEntity)
bool m_bReloadPlugins
If set to true, all the plugins will be reloaded within the next call to Tick().
bool CallHookPlayerMoving(cPlayer &a_Player, const Vector3d &a_OldPosition, const Vector3d &a_NewPosition, bool a_PreviousIsOnGround)
bool CallHookProjectileHitBlock(cProjectileEntity &a_Projectile, Vector3i a_BlockPos, eBlockFace a_Face, const Vector3d &a_BlockHitPos)
bool CallHookPostCrafting(cPlayer &a_Player, cCraftingGrid &a_Grid, cCraftingRecipe &a_Recipe)
cCriticalSection m_CSPluginsNeedAction
Protects m_PluginsToUnload against multithreaded access.
bool CallHookEntityTeleport(cEntity &a_Entity, const Vector3d &a_OldPosition, const Vector3d &a_NewPosition)
cPluginPtrs m_Plugins
All plugins that have been found in the Plugins folder.
bool CallHookExploding(cWorld &a_World, double &a_ExplosionSize, bool &a_CanCauseFire, double a_X, double a_Y, double a_Z, eExplosionSource a_Source, void *a_SourceData)
bool CallHookPlayerUsedBlock(cPlayer &a_Player, Vector3i a_BlockPos, eBlockFace a_BlockFace, Vector3i a_CursorPos, BLOCKTYPE a_BlockType, NIBBLETYPE a_BlockMeta)
bool CallHookHopperPullingItem(cWorld &a_World, cHopperEntity &a_Hopper, int a_DstSlotNum, cBlockEntityWithItems &a_SrcEntity, int a_SrcSlotNum)
bool DoWithPlugin(const AString &a_PluginName, cPluginCallback a_Callback)
Calls the specified callback with the plugin object of the specified plugin.
bool ForEachCommand(cCommandEnumCallback &a_Callback)
Calls a_Callback for each bound command, returns true if all commands were enumerated.
bool CallHookKilled(cEntity &a_Victim, TakeDamageInfo &a_TDI, AString &a_DeathMessage)
static AString GetPluginsPath(void)
Returns the path where individual plugins' folders are expected.
bool CallHookBrewingCompleting(cWorld &a_World, cBrewingstandEntity &a_Brewingstand)
bool CallHookChunkUnloading(cWorld &a_World, int a_ChunkX, int a_ChunkZ)
CommandResult ForceExecuteCommand(cPlayer &a_Player, const AString &a_Command)
Executes the command, as if it was requested by a_Player.
bool CallHookSpawningMonster(cWorld &a_World, cMonster &a_Monster)
bool CallHookEntityChangedWorld(cEntity &a_Entity, cWorld &a_World)
bool BindCommand(const AString &a_Command, cPlugin *a_Plugin, cCommandHandlerPtr a_Handler, const AString &a_Permission, const AString &a_HelpString)
Binds a command to the specified handler.
bool CallHookWeatherChanged(cWorld &a_World)
bool CallHookPlayerBrokenBlock(cPlayer &a_Player, Vector3i a_BlockPos, eBlockFace a_BlockFace, BLOCKTYPE a_BlockType, NIBBLETYPE a_BlockMeta)
bool IsCommandBound(const AString &a_Command)
Returns true if the command is in the command map.
bool CallHookDisconnect(cClientHandle &a_Client, const AString &a_Reason)
bool CallHookLoginForge(cClientHandle &a_Client, AStringMap &a_Mods)
bool CallHookPlayerPlacedBlock(cPlayer &a_Player, const sSetBlock &a_BlockChange)
bool IsConsoleCommandBound(const AString &a_Command)
Returns true if the console command is in the command map.
bool CallHookKilling(cEntity &a_Victim, cEntity *a_Killer, TakeDamageInfo &a_TDI)
bool CallHookUpdatingSign(cWorld &a_World, Vector3i a_BlockPos, AString &a_Line1, AString &a_Line2, AString &a_Line3, AString &a_Line4, cPlayer *a_Player)
CommandResult HandleCommand(cPlayer &a_Player, const AString &a_Command, bool a_ShouldCheckPermissions)
Tries to match a_Command to the internal table of commands, if a match is found, the corresponding pl...
@ HOOK_PLAYER_RIGHT_CLICK
@ HOOK_PLAYER_OPENING_WINDOW
@ HOOK_PROJECTILE_HIT_ENTITY
@ HOOK_HOPPER_PUSHING_ITEM
@ HOOK_ENTITY_CHANGING_WORLD
@ HOOK_PLAYER_TOSSING_ITEM
@ HOOK_ENTITY_CHANGED_WORLD
@ HOOK_PLAYER_USING_BLOCK
@ HOOK_PROJECTILE_HIT_BLOCK
@ HOOK_PLAYER_RIGHT_CLICKING_ENTITY
@ HOOK_HOPPER_PULLING_ITEM
@ HOOK_PLAYER_PLACING_BLOCK
@ HOOK_PLAYER_BREAKING_BLOCK
@ HOOK_PLAYER_PLACED_BLOCK
@ HOOK_BREWING_COMPLETING
@ HOOK_PLAYER_BROKEN_BLOCK
@ HOOK_CRAFTING_NO_RECIPE
@ HOOK_PLAYER_FOOD_LEVEL_CHANGE
bool CallHookPluginMessage(cClientHandle &a_Client, const AString &a_Channel, ContiguousByteBufferView a_Message)
bool CallHookChat(cPlayer &a_Player, AString &a_Message)
bool CallHookBlockSpread(cWorld &a_World, Vector3i a_BlockPos, eSpreadSource a_Source)
std::vector< std::pair< PluginAction, AString > > m_PluginsNeedAction
FolderNames of plugins that need an action (unload, reload, ...).
bool GenericCallHook(PluginHook a_HookName, HookFunction a_HookFunction)
Calls a_HookFunction on each plugin registered to the hook HookName.
bool CallHookHopperPushingItem(cWorld &a_World, cHopperEntity &a_Hopper, int a_SrcSlotNum, cBlockEntityWithItems &a_DstEntity, int a_DstSlotNum)
bool CallHookWorldTick(cWorld &a_World, std::chrono::milliseconds a_Dt, std::chrono::milliseconds a_LastTickDurationMSec)
bool CallHookPreCrafting(cPlayer &a_Player, cCraftingGrid &a_Grid, cCraftingRecipe &a_Recipe)
size_t GetNumPlugins() const
Returns the number of all plugins in m_Plugins (includes disabled, unloaded and errored plugins).
bool CallHookBrewingCompleted(cWorld &a_World, cBrewingstandEntity &a_Brewingstand)
virtual ~cPluginManager()
std::shared_ptr< cCommandHandler > cCommandHandlerPtr
CommandResult ExecuteCommand(cPlayer &a_Player, const AString &a_Command)
Executes the command, as if it was requested by a_Player.
bool CallHookExploded(cWorld &a_World, double a_ExplosionSize, bool a_CanCauseFire, double a_X, double a_Y, double a_Z, eExplosionSource a_Source, void *a_SourceData)
bool CallHookCraftingNoRecipe(cPlayer &a_Player, cCraftingGrid &a_Grid, cCraftingRecipe &a_Recipe)
bool CallHookTakeDamage(cEntity &a_Receiver, TakeDamageInfo &a_TDI)
void ReloadPlugin(const AString &a_PluginFolder)
Queues the specified plugin to be reloaded in the next call to Tick().
bool CallHookPlayerUsedItem(cPlayer &a_Player, Vector3i a_BlockPos, eBlockFace a_BlockFace, Vector3i a_CursorPos)
bool IsPluginLoaded(const AString &a_PluginName)
Returns true if the specified plugin is loaded.
bool CallHookExecuteCommand(cPlayer *a_Player, const AStringVector &a_Split, const AString &a_EntireCommand, CommandResult &a_Result)
bool CallHookWeatherChanging(cWorld &a_World, eWeather &a_NewWeather)
bool CallHookPlayerFished(cPlayer &a_Player, const cItems &a_Reward, const int ExperienceAmount)
AString GetPluginFolderName(const AString &a_PluginName)
Returns the name of the folder (cPlugin::GetFolderName()) from which the specified plugin was loaded.
bool CallHookPlayerBreakingBlock(cPlayer &a_Player, Vector3i a_BlockPos, eBlockFace a_BlockFace, BLOCKTYPE a_BlockType, NIBBLETYPE a_BlockMeta)
@ psNotFound
The plugin has been loaded before, but after a folder refresh it is no longer present.
bool BindConsoleCommand(const AString &a_Command, cPlugin *a_Plugin, cCommandHandlerPtr a_Handler, const AString &a_HelpString)
Binds a console command to the specified handler.
Used as a callback for enumerating bound commands.
virtual bool Command(const AString &a_Command, const cPlugin *a_Plugin, const AString &a_Permission, const AString &a_HelpString)=0
Called for each command; return true to abort enumeration For console commands, a_Permission is not u...
Interface for a callback that receives command output The Out() function is called for any output the...
cWorld * GetWorld(void) const
const AString & GetName(void) const
void SendMessageInfo(const AString &a_Message)
void SendMessageFailure(const AString &a_Message)
bool HasPermission(const AString &a_Permission) const
bool ReadFile(const AString &a_FileName, bool a_AllowExampleRedirect=true)
Reads the contents of the specified ini file If the file doesn't exist and a_AllowExampleRedirect is ...
This class bridges a vector of cItem for safe access via Lua.
RAII for cCriticalSection - locks the CS on creation, unlocks on destruction.
static bool IsFolder(const AString &a_Path)
Returns true if the specified path is a folder.
static AStringVector GetFolderContents(const AString &a_Folder)
Returns the list of all items in the specified folder (files, folders, nix pipes, whatever's there).
cPluginManager * GetPluginManager(void)
static void BindBuiltInConsoleCommands(void)
Binds the built-in console commands with the plugin manager.
virtual bool DeleteValue(const AString &keyname, const AString &valuename)=0
Deletes the specified key, value pair.
virtual int AddKeyName(const AString &keyname)=0
Add a key name.
virtual std::vector< std::pair< AString, AString > > GetValues(AString a_keyName)=0
returns a vector containing a name, value pair for each value under the key
virtual bool KeyExists(const AString keyname) const =0
Returns true iff the specified key exists.
virtual void AddValue(const AString &a_KeyName, const AString &a_ValueName, const AString &a_Value)=0
Adds a new value to the specified key.
virtual bool SetValue(const AString &a_KeyName, const AString &a_ValueName, const AString &a_Value, const bool a_CreateIfNotExists=true)=0
Overwrites the value of the key, value pair Specify the optional parameter as false if you do not wan...
const AString & GetName(void) const
Returns the name of the world.