mirror of
https://github.com/SapphireServer/Sapphire.git
synced 2025-04-25 14:07:46 +00:00
switch debugcommandhandler for scripted implementation
This commit is contained in:
parent
99300d746a
commit
dde0a30fa3
28 changed files with 770 additions and 818 deletions
|
@ -39,7 +39,7 @@ foreach(_scriptDir ${children})
|
|||
endforeach()
|
||||
|
||||
add_library("script_${_name}" MODULE "${SCRIPT_FILES}" "${SCRIPT_INCLUDE_FILES}" "${_scriptDir}/ScriptLoader.cpp")
|
||||
target_link_libraries("script_${_name}" sapphire_zone)
|
||||
target_link_libraries("script_${_name}" sapphire_zone common xivdat ${Boost_LIBRARIES})
|
||||
|
||||
if(MSVC)
|
||||
set_target_properties("script_${_name}" PROPERTIES
|
||||
|
@ -53,6 +53,10 @@ foreach(_scriptDir ${children})
|
|||
)
|
||||
endif()
|
||||
|
||||
if(EXISTS "${_scriptDir}/PreInclude.h")
|
||||
set(PreScriptIncludes "#include \"${_scriptDir}/PreInclude.h\"")
|
||||
endif()
|
||||
|
||||
configure_file("${CMAKE_CURRENT_SOURCE_DIR}/ScriptLoader.cpp.in" "${_scriptDir}/ScriptLoader.cpp")
|
||||
|
||||
add_custom_command(TARGET "script_${_name}" POST_BUILD
|
||||
|
@ -63,5 +67,6 @@ foreach(_scriptDir ${children})
|
|||
|
||||
unset(ScriptIncludes)
|
||||
unset(ScriptNames)
|
||||
unset(PreScriptIncludes)
|
||||
endif()
|
||||
endforeach()
|
||||
|
|
|
@ -1,7 +1,5 @@
|
|||
#include <vector>
|
||||
|
||||
class ScriptObject;
|
||||
|
||||
@PreScriptIncludes@
|
||||
@ScriptIncludes@
|
||||
|
||||
const ScriptObject* ptrs[] =
|
||||
|
|
102
scripts/native/debugcommands/Add.cpp
Normal file
102
scripts/native/debugcommands/Add.cpp
Normal file
|
@ -0,0 +1,102 @@
|
|||
#include <ScriptObject.h>
|
||||
#include <common/Network/PacketDef/Zone/ServerZoneDef.h>
|
||||
#include <common/Network/GamePacketNew.h>
|
||||
#include <Actor/BattleNpc.h>
|
||||
#include <Zone/Zone.h>
|
||||
|
||||
class Add : public DebugCommandScript
|
||||
{
|
||||
public:
|
||||
Add() : DebugCommandScript( "add", "Executes ADD command", 1 )
|
||||
{ }
|
||||
|
||||
virtual void run( Entity::Player& player, const std::string& data, const std::string &subCommand, const std::string ¶ms )
|
||||
{
|
||||
if( subCommand == "status" )
|
||||
{
|
||||
int32_t id;
|
||||
int32_t duration;
|
||||
uint16_t param;
|
||||
|
||||
sscanf( params.c_str(), "%d %d %hu", &id, &duration, ¶m );
|
||||
|
||||
StatusEffect::StatusEffectPtr effect( new StatusEffect::StatusEffect( id, player.getAsPlayer(), player.getAsPlayer(), duration, 3000 ) );
|
||||
effect->setParam( param );
|
||||
|
||||
player.addStatusEffect( effect );
|
||||
}
|
||||
else if( subCommand == "title" )
|
||||
{
|
||||
uint32_t titleId;
|
||||
sscanf( params.c_str(), "%u", &titleId );
|
||||
|
||||
player.addTitle( titleId );
|
||||
player.sendNotice( "Added title (ID: " + std::to_string( titleId ) + ")" );
|
||||
}
|
||||
else if( subCommand == "spawn" )
|
||||
{
|
||||
int32_t model, name;
|
||||
|
||||
sscanf( params.c_str(), "%d %d", &model, &name );
|
||||
|
||||
Entity::BattleNpcPtr pBNpc( new Entity::BattleNpc( model, name, player.getPos() ) );
|
||||
|
||||
auto pZone = player.getCurrentZone();
|
||||
pBNpc->setCurrentZone( pZone );
|
||||
pZone->pushActor( pBNpc );
|
||||
|
||||
}
|
||||
else if( subCommand == "op" )
|
||||
{
|
||||
// temporary research packet
|
||||
int32_t opcode;
|
||||
sscanf( params.c_str(), "%x", &opcode );
|
||||
Network::Packets::GamePacketPtr pPe( new Network::Packets::GamePacket( opcode, 0x30, player.getId(), player.getId() ) );
|
||||
player.queuePacket( pPe );
|
||||
}
|
||||
else if( subCommand == "actrl" )
|
||||
{
|
||||
|
||||
// temporary research packet
|
||||
|
||||
int32_t opcode;
|
||||
int32_t param1;
|
||||
int32_t param2;
|
||||
int32_t param3;
|
||||
int32_t param4;
|
||||
int32_t param5;
|
||||
int32_t param6;
|
||||
int32_t playerId;
|
||||
|
||||
sscanf( params.c_str(), "%x %x %x %x %x %x %x %x", &opcode, ¶m1, ¶m2, ¶m3, ¶m4, ¶m5, ¶m6, &playerId );
|
||||
|
||||
player.sendNotice( "Injecting ACTOR_CONTROL " + std::to_string( opcode ) );
|
||||
|
||||
Network::Packets::ZoneChannelPacket< Network::Packets::Server::FFXIVIpcActorControl143 > actorControl( playerId, player.getId() );
|
||||
actorControl.data().category = opcode;
|
||||
actorControl.data().param1 = param1;
|
||||
actorControl.data().param2 = param2;
|
||||
actorControl.data().param3 = param3;
|
||||
actorControl.data().param4 = param4;
|
||||
actorControl.data().param5 = param5;
|
||||
actorControl.data().param6 = param6;
|
||||
player.queuePacket( actorControl );
|
||||
|
||||
|
||||
/*sscanf(params.c_str(), "%x %x %x %x %x %x %x", &opcode, ¶m1, ¶m2, ¶m3, ¶m4, ¶m5, ¶m6, &playerId);
|
||||
|
||||
Network::Packets::Server::ServerNoticePacket noticePacket( player, "Injecting ACTOR_CONTROL " + std::to_string( opcode ) );
|
||||
|
||||
player.queuePacket( noticePacket );
|
||||
|
||||
Network::Packets::Server::ActorControlPacket143 controlPacket( player, opcode,
|
||||
param1, param2, param3, param4, param5, param6, playerId );
|
||||
player.queuePacket( controlPacket );*/
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
player.sendUrgent( subCommand + " is not a valid ADD command." );
|
||||
}
|
||||
}
|
||||
};
|
31
scripts/native/debugcommands/Get.cpp
Normal file
31
scripts/native/debugcommands/Get.cpp
Normal file
|
@ -0,0 +1,31 @@
|
|||
#include <ScriptObject.h>
|
||||
|
||||
#include <Zone/Zone.h>
|
||||
|
||||
class Get : public DebugCommandScript
|
||||
{
|
||||
public:
|
||||
Get() : DebugCommandScript( "get", "Executes GET commands", 1 )
|
||||
{ }
|
||||
|
||||
virtual void run( Entity::Player& player, const std::string& data, const std::string& subCommand, const std::string& params )
|
||||
{
|
||||
if( ( subCommand == "pos" ) )
|
||||
{
|
||||
|
||||
int16_t map_id = m_objects->m_exd->m_zoneInfoMap[player.getCurrentZone()->getTerritoryId()].map_id;
|
||||
|
||||
player.sendNotice( "Pos:\n" +
|
||||
std::to_string( player.getPos().x ) + "\n" +
|
||||
std::to_string( player.getPos().y ) + "\n" +
|
||||
std::to_string( player.getPos().z ) + "\n" +
|
||||
std::to_string( player.getRotation() ) + "\nMapId: " +
|
||||
std::to_string( map_id ) + "\nZoneID: " +
|
||||
std::to_string(player.getCurrentZone()->getTerritoryId() ) + "\n" );
|
||||
}
|
||||
else
|
||||
{
|
||||
player.sendUrgent( subCommand + " is not a valid GET command." );
|
||||
}
|
||||
}
|
||||
};
|
23
scripts/native/debugcommands/Help.cpp
Normal file
23
scripts/native/debugcommands/Help.cpp
Normal file
|
@ -0,0 +1,23 @@
|
|||
#include <ScriptObject.h>
|
||||
|
||||
#include <Script/NativeScriptManager.h>
|
||||
|
||||
class Help : public DebugCommandScript
|
||||
{
|
||||
public:
|
||||
Help() : DebugCommandScript( "help", "Displays server build information", 0 )
|
||||
{ }
|
||||
|
||||
virtual void run( Entity::Player& player, const std::string& data, const std::string& subCommand, const std::string& params )
|
||||
{
|
||||
player.sendDebug( "Available debug commands:" );
|
||||
|
||||
for( std::pair< uint32_t, ScriptObject* > s : m_objects->m_scriptMgr->getNativeScriptHandler().getScriptsOfType< DebugCommandScript >() )
|
||||
{
|
||||
auto script = dynamic_cast< DebugCommandScript* >( s.second );
|
||||
|
||||
if( player.getGmRank() >= script->getGmLevel() )
|
||||
player.sendDebug( " - " + script->getCmd() + " - " + script->getHelpText() );
|
||||
}
|
||||
}
|
||||
};
|
21
scripts/native/debugcommands/InjectChatPacket.cpp
Normal file
21
scripts/native/debugcommands/InjectChatPacket.cpp
Normal file
|
@ -0,0 +1,21 @@
|
|||
#include <ScriptObject.h>
|
||||
|
||||
#include <common/Network/PacketContainer.h>
|
||||
#include <Session.h>
|
||||
#include <Network/GameConnection.h>
|
||||
#include <common/Network/CommonNetwork.h>
|
||||
|
||||
|
||||
class InjectChatPacket : public DebugCommandScript
|
||||
{
|
||||
public:
|
||||
InjectChatPacket() : DebugCommandScript( "injectc", "Injects a premade chat packet", 1 )
|
||||
{ }
|
||||
|
||||
virtual void run( Entity::Player& player, const std::string& data, const std::string& subCommand, const std::string& params )
|
||||
{
|
||||
auto pSession = m_objects->m_zone->getSession( player.getId() );
|
||||
if( pSession )
|
||||
pSession->getChatConnection()->injectPacket( data.c_str() + 8, player );
|
||||
}
|
||||
};
|
20
scripts/native/debugcommands/InjectPacket.cpp
Normal file
20
scripts/native/debugcommands/InjectPacket.cpp
Normal file
|
@ -0,0 +1,20 @@
|
|||
#include <ScriptObject.h>
|
||||
|
||||
#include <common/Network/PacketContainer.h>
|
||||
#include <Session.h>
|
||||
#include <Network/GameConnection.h>
|
||||
#include <common/Network/CommonNetwork.h>
|
||||
|
||||
class InjectPacket : public DebugCommandScript
|
||||
{
|
||||
public:
|
||||
InjectPacket() : DebugCommandScript( "inject", "Injects a premade packet", 0 )
|
||||
{ }
|
||||
|
||||
virtual void run( Entity::Player& player, const std::string& data, const std::string& subCommand, const std::string& params )
|
||||
{
|
||||
auto pSession = m_objects->m_zone->getSession( player.getId() );
|
||||
if( pSession )
|
||||
pSession->getZoneConnection()->injectPacket( data.c_str() + 7, player );
|
||||
}
|
||||
};
|
56
scripts/native/debugcommands/Nudge.cpp
Normal file
56
scripts/native/debugcommands/Nudge.cpp
Normal file
|
@ -0,0 +1,56 @@
|
|||
#include <ScriptObject.h>
|
||||
#include <common/Util/UtilMath.h>
|
||||
#include <common/Network/PacketDef/Zone/ServerZoneDef.h>
|
||||
#include <common/Network/GamePacketNew.h>
|
||||
|
||||
class Nudge : public DebugCommandScript
|
||||
{
|
||||
public:
|
||||
Nudge() : DebugCommandScript( "nudge", "Nudge player in a direction", 1 )
|
||||
{ }
|
||||
|
||||
virtual void run( Entity::Player& player, const std::string& data, const std::string& subCommand, const std::string& params )
|
||||
{
|
||||
// check if the command has parameters
|
||||
std::string tmpCommand = std::string( data.c_str() + m_cmd.length() + 1 );
|
||||
|
||||
std::size_t spos = tmpCommand.find_first_of( " " );
|
||||
|
||||
auto& pos = player.getPos();
|
||||
|
||||
int32_t offset = 0;
|
||||
char direction[20];
|
||||
memset( direction, 0, 20 );
|
||||
|
||||
sscanf( tmpCommand.c_str(), "%d %s", &offset, direction );
|
||||
|
||||
if( direction[0] == 'u' || direction[0] == '+' )
|
||||
{
|
||||
pos.y += offset;
|
||||
player.sendNotice( "nudge: Placing up " + std::to_string( offset ) + " yalms" );
|
||||
}
|
||||
else if( direction[0] == 'd' || direction[0] == '-' )
|
||||
{
|
||||
pos.y -= offset;
|
||||
player.sendNotice( "nudge: Placing down " + std::to_string( offset ) + " yalms" );
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
float angle = player.getRotation() + ( PI / 2 );
|
||||
pos.x -= offset * cos( angle );
|
||||
pos.z += offset * sin( angle );
|
||||
player.sendNotice( "nudge: Placing forward " + std::to_string( offset ) + " yalms" );
|
||||
}
|
||||
if( offset != 0 )
|
||||
{
|
||||
Network::Packets::ZoneChannelPacket< Network::Packets::Server::FFXIVIpcActorSetPos >
|
||||
setActorPosPacket( player.getId() );
|
||||
setActorPosPacket.data().x = player.getPos().x;
|
||||
setActorPosPacket.data().y = player.getPos().y;
|
||||
setActorPosPacket.data().z = player.getPos().z;
|
||||
setActorPosPacket.data().r16 = Math::Util::floatToUInt16Rot( player.getRotation() );
|
||||
player.queuePacket( setActorPosPacket );
|
||||
}
|
||||
}
|
||||
};
|
7
scripts/native/debugcommands/PreInclude.h
Normal file
7
scripts/native/debugcommands/PreInclude.h
Normal file
|
@ -0,0 +1,7 @@
|
|||
#ifndef SAPPHIRE_PREINCLUDE_H
|
||||
#define SAPPHIRE_PREINCLUDE_H
|
||||
|
||||
// fixes an issue where winsock is included before asio causing builds to fail
|
||||
#include <boost/asio.hpp>
|
||||
|
||||
#endif //SAPPHIRE_PREINCLUDE_H
|
29
scripts/native/debugcommands/Replay.cpp
Normal file
29
scripts/native/debugcommands/Replay.cpp
Normal file
|
@ -0,0 +1,29 @@
|
|||
#include <ScriptObject.h>
|
||||
#include <Session.h>
|
||||
|
||||
class Replay : public DebugCommandScript
|
||||
{
|
||||
public:
|
||||
Replay() : DebugCommandScript( "replay", "Replays a saved capture", 1 )
|
||||
{ }
|
||||
|
||||
virtual void run( Entity::Player& player, const std::string& data, const std::string& subCommand, const std::string& params )
|
||||
{
|
||||
if( subCommand == "start" )
|
||||
{
|
||||
auto pSession = m_objects->m_zone->getSession( player.getId() );
|
||||
if( pSession )
|
||||
pSession->startReplay( params );
|
||||
}
|
||||
else if( subCommand == "stop" )
|
||||
{
|
||||
auto pSession = m_objects->m_zone->getSession( player.getId() );
|
||||
if( pSession )
|
||||
pSession->stopReplay();
|
||||
}
|
||||
else
|
||||
{
|
||||
player.sendUrgent( subCommand + " is not a valid replay command." );
|
||||
}
|
||||
}
|
||||
};
|
86
scripts/native/debugcommands/Script.cpp
Normal file
86
scripts/native/debugcommands/Script.cpp
Normal file
|
@ -0,0 +1,86 @@
|
|||
#include <ScriptObject.h>
|
||||
|
||||
#include <Script/NativeScriptManager.h>
|
||||
#include <boost/format.hpp>
|
||||
|
||||
class Script : public DebugCommandScript
|
||||
{
|
||||
public:
|
||||
Script() : DebugCommandScript( "script", "Script management commands", 0 )
|
||||
{ }
|
||||
|
||||
virtual void run( Entity::Player& player, const std::string& args, const std::string& subCommand, const std::string& params )
|
||||
{
|
||||
if( subCommand == "unload" )
|
||||
{
|
||||
if ( subCommand == params )
|
||||
player.sendDebug( "Command failed: requires name of script" );
|
||||
else
|
||||
if( m_objects->m_scriptMgr->getNativeScriptHandler().unloadScript( params ) )
|
||||
player.sendDebug( "Unloaded script successfully." );
|
||||
else
|
||||
player.sendDebug( "Failed to unload script: " + params );
|
||||
}
|
||||
else if( subCommand == "find" || subCommand == "f" )
|
||||
{
|
||||
if( subCommand == params )
|
||||
player.sendDebug( "Because reasons of filling chat with nonsense, please enter a search term" );
|
||||
else
|
||||
{
|
||||
std::set< Core::Scripting::ScriptInfo* > scripts;
|
||||
m_objects->m_scriptMgr->getNativeScriptHandler().findScripts( scripts, params );
|
||||
|
||||
if( !scripts.empty() )
|
||||
{
|
||||
player.sendDebug( "Found " + std::to_string( scripts.size() ) + " scripts" );
|
||||
|
||||
for( auto it = scripts.begin(); it != scripts.end(); ++it )
|
||||
{
|
||||
auto script = *it;
|
||||
player.sendDebug( " - '" + script->library_name + "' loaded at @ 0x" +
|
||||
boost::str( boost::format( "%|X|" ) % script->handle ) +
|
||||
", num scripts: " + std::to_string( script->scripts.size() ) );
|
||||
}
|
||||
}
|
||||
else
|
||||
player.sendDebug( "No scripts found with search term: " + params );
|
||||
}
|
||||
}
|
||||
else if( subCommand == "load" || subCommand == "l" )
|
||||
{
|
||||
if( subCommand == params )
|
||||
player.sendDebug( "Command failed: requires relative path to script" );
|
||||
else
|
||||
{
|
||||
if ( m_objects->m_scriptMgr->getNativeScriptHandler().loadScript( params ) )
|
||||
player.sendDebug( "Loaded '" + params + "' successfully" );
|
||||
else
|
||||
player.sendDebug( "Failed to load '" + params + "'" );
|
||||
}
|
||||
|
||||
}
|
||||
else if( subCommand == "queuereload" || subCommand == "qrl" )
|
||||
{
|
||||
if( subCommand == params )
|
||||
player.sendDebug( "Command failed: requires name of script to reload" );
|
||||
else
|
||||
{
|
||||
m_objects->m_scriptMgr->getNativeScriptHandler().queueScriptReload( params );
|
||||
player.sendDebug( "Queued script reload for script: " + params );
|
||||
}
|
||||
}
|
||||
else if( subCommand == "build" || subCommand == "b" )
|
||||
{
|
||||
if( subCommand == params )
|
||||
player.sendDebug( "Command failed: requires name of cmake target" );
|
||||
else
|
||||
{
|
||||
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
player.sendDebug( "Unknown script subcommand: " + subCommand );
|
||||
}
|
||||
}
|
||||
};
|
17
scripts/native/debugcommands/ServerInfo.cpp
Normal file
17
scripts/native/debugcommands/ServerInfo.cpp
Normal file
|
@ -0,0 +1,17 @@
|
|||
#include <ScriptObject.h>
|
||||
|
||||
#include <common/Version.h>
|
||||
|
||||
class ServerInfo : public DebugCommandScript
|
||||
{
|
||||
public:
|
||||
ServerInfo() : DebugCommandScript( "serverinfo", "Displays server build information", 0 )
|
||||
{ }
|
||||
|
||||
virtual void run( Entity::Player& player, const std::string& data, const std::string& subCommand, const std::string& params )
|
||||
{
|
||||
player.sendDebug( "Sapphire Zone " + Version::VERSION + "\nRev: " + Version::GIT_HASH );
|
||||
player.sendDebug( "Compiled: " __DATE__ " " __TIME__ );
|
||||
player.sendDebug( "Sessions: " + std::to_string( m_objects->m_zone->getSessionCount() ) );
|
||||
}
|
||||
};
|
148
scripts/native/debugcommands/Set.cpp
Normal file
148
scripts/native/debugcommands/Set.cpp
Normal file
|
@ -0,0 +1,148 @@
|
|||
#include <ScriptObject.h>
|
||||
|
||||
#include <Session.h>
|
||||
#include <common/Network/PacketContainer.h>
|
||||
#include <Network/GameConnection.h>
|
||||
#include <common/Network/PacketDef/Zone/ServerZoneDef.h>
|
||||
#include <common/Network/GamePacketNew.h>
|
||||
#include <servers/sapphire_zone/Network/PacketWrappers/InitUIPacket.h>
|
||||
#include <cinttypes>
|
||||
|
||||
class Set : public DebugCommandScript
|
||||
{
|
||||
public:
|
||||
Set() : DebugCommandScript( "set", "Executes SET commands", 1 )
|
||||
{ }
|
||||
|
||||
virtual void run( Entity::Player& player, const std::string& data, const std::string& subCommand, const std::string& params )
|
||||
{
|
||||
player.sendDebug( subCommand );
|
||||
player.sendDebug( params );
|
||||
|
||||
if( ( ( subCommand == "pos" ) || ( subCommand == "posr" ) ) && ( params != "" ) )
|
||||
{
|
||||
int32_t posX;
|
||||
int32_t posY;
|
||||
int32_t posZ;
|
||||
|
||||
sscanf( params.c_str(), "%d %d %d", &posX, &posY, &posZ );
|
||||
|
||||
if( ( posX == 0xcccccccc ) || ( posY == 0xcccccccc ) || ( posZ == 0xcccccccc ) )
|
||||
{
|
||||
player.sendUrgent( "Syntaxerror." );
|
||||
return;
|
||||
}
|
||||
|
||||
if( subCommand == "pos" )
|
||||
player.setPosition( static_cast< float >( posX ),
|
||||
static_cast< float >( posY ),
|
||||
static_cast< float >( posZ ) );
|
||||
else
|
||||
player.setPosition( player.getPos().x + static_cast< float >( posX ),
|
||||
player.getPos().y + static_cast< float >( posY ),
|
||||
player.getPos().z + static_cast< float >( posZ ) );
|
||||
|
||||
Network::Packets::ZoneChannelPacket< Network::Packets::Server::FFXIVIpcActorSetPos >
|
||||
setActorPosPacket( player.getId() );
|
||||
setActorPosPacket.data().x = player.getPos().x;
|
||||
setActorPosPacket.data().y = player.getPos().y;
|
||||
setActorPosPacket.data().z = player.getPos().z;
|
||||
player.queuePacket( setActorPosPacket );
|
||||
|
||||
}
|
||||
else if( ( subCommand == "tele" ) && ( params != "" ) )
|
||||
{
|
||||
int32_t aetheryteId;
|
||||
sscanf( params.c_str(), "%i", &aetheryteId );
|
||||
|
||||
player.teleport( aetheryteId );
|
||||
}
|
||||
else if( ( subCommand == "discovery" ) && ( params != "" ) )
|
||||
{
|
||||
int32_t map_id;
|
||||
int32_t discover_id;
|
||||
sscanf( params.c_str(), "%i %i", &map_id, &discover_id );
|
||||
|
||||
Network::Packets::ZoneChannelPacket< Network::Packets::Server::FFXIVIpcDiscovery > discoveryPacket( player.getId() );
|
||||
discoveryPacket.data().map_id = map_id;
|
||||
discoveryPacket.data().map_part_id = discover_id;
|
||||
player.queuePacket( discoveryPacket );
|
||||
}
|
||||
|
||||
// else if( ( subCommand == "discovery_pos" ) && ( params != "" ) )
|
||||
// {
|
||||
// int32_t map_id;
|
||||
// int32_t discover_id;
|
||||
// int32_t pos_id;
|
||||
// sscanf( params.c_str(), "%i %i %i", &pos_id, &map_id, &discover_id );
|
||||
//
|
||||
// std::string query2 = "UPDATE IGNORE `discoveryinfo` SET `discover_id` = '" + std::to_string( discover_id ) +
|
||||
// "' WHERE `discoveryinfo`.`id` = " + std::to_string( pos_id ) + ";";
|
||||
//
|
||||
// std::string query1 = "INSERT IGNORE INTO `discoveryinfo` (`id`, `map_id`, `discover_id`) VALUES ('" + std::to_string( pos_id ) +
|
||||
// "', '" + std::to_string( map_id ) +
|
||||
// "', '" + std::to_string( discover_id ) + "')";
|
||||
//
|
||||
// g_charaDb.execute( query1 );
|
||||
// g_charaDb.execute( query2 );
|
||||
//
|
||||
// }
|
||||
|
||||
else if( subCommand == "discovery_reset" )
|
||||
{
|
||||
player.resetDiscovery();
|
||||
player.queuePacket( Network::Packets::Server::InitUIPacket( player ) );
|
||||
}
|
||||
else if( subCommand == "classjob" )
|
||||
{
|
||||
int32_t id;
|
||||
|
||||
sscanf( params.c_str(), "%d", &id );
|
||||
|
||||
if( player.getLevelForClass( static_cast< Common::ClassJob > ( id ) ) == 0 )
|
||||
{
|
||||
player.setLevelForClass( 1, static_cast< Common::ClassJob > ( id ) );
|
||||
player.setClassJob( static_cast< Common::ClassJob > ( id ) );
|
||||
}
|
||||
else
|
||||
player.setClassJob( static_cast< Common::ClassJob > ( id ) );
|
||||
}
|
||||
else if ( subCommand == "cfpenalty" )
|
||||
{
|
||||
int32_t minutes;
|
||||
sscanf( params.c_str(), "%d", &minutes );
|
||||
|
||||
player.setCFPenaltyMinutes( minutes );
|
||||
}
|
||||
else if ( subCommand == "eorzeatime" )
|
||||
{
|
||||
uint64_t timestamp;
|
||||
sscanf( params.c_str(), "%" SCNu64, ×tamp );
|
||||
|
||||
player.setEorzeaTimeOffset( timestamp );
|
||||
player.sendNotice( "Eorzea time offset: " + std::to_string( timestamp ) );
|
||||
}
|
||||
else if ( subCommand == "model" )
|
||||
{
|
||||
uint32_t slot;
|
||||
uint32_t val;
|
||||
sscanf( params.c_str(), "%d %d", &slot, &val );
|
||||
|
||||
player.setModelForSlot( static_cast< Inventory::EquipSlot >( slot ), val );
|
||||
player.sendModel();
|
||||
player.sendDebug( "Model updated" );
|
||||
}
|
||||
else if ( subCommand == "mount" )
|
||||
{
|
||||
int32_t id;
|
||||
sscanf( params.c_str(), "%d", &id );
|
||||
|
||||
player.dismount();
|
||||
player.mount( id );
|
||||
}
|
||||
else
|
||||
{
|
||||
player.sendUrgent( subCommand + " is not a valid SET command." );
|
||||
}
|
||||
}
|
||||
};
|
|
@ -1,64 +0,0 @@
|
|||
#ifndef _GAMECOMMAND_H_
|
||||
#define _GAMECOMMAND_H_
|
||||
|
||||
#include <common/Common.h>
|
||||
|
||||
#include "Actor/Player.h"
|
||||
#include "Forwards.h"
|
||||
|
||||
namespace Core {
|
||||
|
||||
class DebugCommandHandler;
|
||||
|
||||
class DebugCommand
|
||||
{
|
||||
public:
|
||||
|
||||
using pFunc = void ( DebugCommandHandler::* )( char *, Entity::Player&, boost::shared_ptr< DebugCommand > );
|
||||
|
||||
// String for the command
|
||||
std::string m_commandName;
|
||||
|
||||
// command callback
|
||||
pFunc m_pFunc;
|
||||
|
||||
// helptext
|
||||
std::string m_helpText;
|
||||
|
||||
// userlevel needed to execute the command
|
||||
uint8_t m_gmLevel;
|
||||
|
||||
DebugCommand( const std::string& n, pFunc functionPtr, const std::string& hText, uint8_t uLevel )
|
||||
{
|
||||
m_commandName = n;
|
||||
m_pFunc = functionPtr;
|
||||
m_helpText = hText;
|
||||
m_gmLevel = uLevel;
|
||||
}
|
||||
|
||||
~DebugCommand()
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
const std::string& getName() const
|
||||
{
|
||||
return m_commandName;
|
||||
}
|
||||
|
||||
const std::string& getHelpText() const
|
||||
{
|
||||
return m_helpText;
|
||||
}
|
||||
|
||||
uint8_t getRequiredGmLevel() const
|
||||
{
|
||||
return m_gmLevel;
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
|
||||
#endif
|
|
@ -1,657 +0,0 @@
|
|||
#include <boost/lexical_cast.hpp>
|
||||
|
||||
#include <common/Common.h>
|
||||
#include <common/Version.h>
|
||||
#include <common/Network/GamePacketNew.h>
|
||||
#include <common/Network/CommonNetwork.h>
|
||||
#include <common/Util/UtilMath.h>
|
||||
#include <common/Network/PacketContainer.h>
|
||||
#include <common/Logging/Logger.h>
|
||||
#include <common/Exd/ExdData.h>
|
||||
#include <common/Database/DatabaseDef.h>
|
||||
|
||||
#include "DebugCommand.h"
|
||||
#include "DebugCommandHandler.h"
|
||||
|
||||
#include "Network/PacketWrappers/ServerNoticePacket.h"
|
||||
#include "Network/PacketWrappers/ActorControlPacket142.h"
|
||||
#include "Network/PacketWrappers/ActorControlPacket143.h"
|
||||
#include "Network/PacketWrappers/InitUIPacket.h"
|
||||
#include "Network/GameConnection.h"
|
||||
#include "Script/ScriptManager.h"
|
||||
#include "Script/NativeScriptManager.h"
|
||||
|
||||
#include "Actor/Player.h"
|
||||
#include "Actor/BattleNpc.h"
|
||||
|
||||
#include "Zone/Zone.h"
|
||||
|
||||
#include "ServerZone.h"
|
||||
|
||||
#include "StatusEffect/StatusEffect.h"
|
||||
#include "Session.h"
|
||||
#include <boost/make_shared.hpp>
|
||||
#include <boost/format.hpp>
|
||||
|
||||
|
||||
#include <cinttypes>
|
||||
|
||||
extern Core::Scripting::ScriptManager g_scriptMgr;
|
||||
extern Core::Data::ExdData g_exdData;
|
||||
extern Core::Logger g_log;
|
||||
extern Core::ServerZone g_serverZone;
|
||||
|
||||
// instanciate and initialize commands
|
||||
Core::DebugCommandHandler::DebugCommandHandler()
|
||||
{
|
||||
// Push all commands onto the register map ( command name - function - description - required GM level )
|
||||
registerCommand( "set", &DebugCommandHandler::set, "Executes SET commands.", 1 );
|
||||
registerCommand( "get", &DebugCommandHandler::get, "Executes GET commands.", 1 );
|
||||
registerCommand( "add", &DebugCommandHandler::add, "Executes ADD commands.", 1 );
|
||||
registerCommand( "inject", &DebugCommandHandler::injectPacket, "Loads and injects a premade packet.", 1 );
|
||||
registerCommand( "injectc", &DebugCommandHandler::injectChatPacket, "Loads and injects a premade chat packet.", 1 );
|
||||
registerCommand( "replay", &DebugCommandHandler::replay, "Replays a saved capture folder.", 1 );
|
||||
registerCommand( "nudge", &DebugCommandHandler::nudge, "Nudges you forward/up/down.", 1 );
|
||||
registerCommand( "info", &DebugCommandHandler::serverInfo, "Show server info.", 0 );
|
||||
registerCommand( "unlock", &DebugCommandHandler::unlockCharacter, "Unlock character.", 1 );
|
||||
registerCommand( "help", &DebugCommandHandler::help, "Shows registered commands.", 0 );
|
||||
registerCommand( "script", &DebugCommandHandler::script, "Server script utilities.", 1 );
|
||||
}
|
||||
|
||||
// clear all loaded commands
|
||||
Core::DebugCommandHandler::~DebugCommandHandler()
|
||||
{
|
||||
for( auto it = m_commandMap.begin(); it != m_commandMap.end(); ++it )
|
||||
( *it ).second.reset();
|
||||
}
|
||||
|
||||
// add a command set to the register map
|
||||
void Core::DebugCommandHandler::registerCommand( const std::string& n, DebugCommand::pFunc functionPtr,
|
||||
const std::string& hText, uint8_t uLevel )
|
||||
{
|
||||
m_commandMap[std::string( n )] = boost::make_shared< DebugCommand >( n, functionPtr, hText, uLevel );
|
||||
}
|
||||
|
||||
// try to retrieve the command in question, execute if found
|
||||
void Core::DebugCommandHandler::execCommand( char * data, Entity::Player& player )
|
||||
{
|
||||
|
||||
// define callback pointer
|
||||
void ( DebugCommandHandler::*pf )( char *, Entity::Player&, boost::shared_ptr< DebugCommand > );
|
||||
|
||||
std::string commandString;
|
||||
|
||||
// check if the command has parameters
|
||||
std::string tmpCommand = std::string( data );
|
||||
std::size_t pos = tmpCommand.find_first_of( " " );
|
||||
|
||||
if( pos != std::string::npos )
|
||||
// command has parameters, grab the first part
|
||||
commandString = tmpCommand.substr( 0, pos );
|
||||
else
|
||||
// no parameters, just get the command
|
||||
commandString = tmpCommand;
|
||||
|
||||
// try to retrieve the command
|
||||
auto it = m_commandMap.find( commandString );
|
||||
|
||||
if( it == m_commandMap.end() )
|
||||
// no command found, do something... or not
|
||||
player.sendUrgent( "Command not found." );
|
||||
else
|
||||
{
|
||||
if( player.getGmRank() < it->second->getRequiredGmLevel() )
|
||||
{
|
||||
player.sendUrgent( "You are not allowed to use this command." );
|
||||
return;
|
||||
}
|
||||
|
||||
// command found, call the callback function and pass parameters if present.
|
||||
pf = ( *it ).second->m_pFunc;
|
||||
( this->*pf )( data, player, ( *it ).second );
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////////////
|
||||
// Definition of the commands
|
||||
///////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
void Core::DebugCommandHandler::help( char* data, Entity::Player& player, boost::shared_ptr< DebugCommand > command )
|
||||
{
|
||||
player.sendDebug( "Registered debug commands:" );
|
||||
for ( auto cmd : m_commandMap )
|
||||
{
|
||||
if ( player.getGmRank( ) >= cmd.second->m_gmLevel )
|
||||
{
|
||||
player.sendDebug( " - " + cmd.first + " - " + cmd.second->getHelpText( ) );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void Core::DebugCommandHandler::set( char * data, Entity::Player& player, boost::shared_ptr< DebugCommand > command )
|
||||
{
|
||||
std::string subCommand = "";
|
||||
std::string params = "";
|
||||
|
||||
// check if the command has parameters
|
||||
std::string tmpCommand = std::string( data + command->getName().length() + 1 );
|
||||
|
||||
std::size_t pos = tmpCommand.find_first_of( " " );
|
||||
|
||||
if( pos != std::string::npos )
|
||||
// command has parameters, grab the first part
|
||||
subCommand = tmpCommand.substr( 0, pos );
|
||||
else
|
||||
// no subcommand given
|
||||
subCommand = tmpCommand;
|
||||
|
||||
if( command->getName().length() + 1 + pos + 1 < strlen( data ) )
|
||||
params = std::string( data + command->getName().length() + 1 + pos + 1 );
|
||||
|
||||
g_log.debug( "[" + std::to_string( player.getId() ) + "] " +
|
||||
"subCommand " + subCommand + " params: " + params );
|
||||
|
||||
|
||||
if( ( ( subCommand == "pos" ) || ( subCommand == "posr" ) ) && ( params != "" ) )
|
||||
{
|
||||
int32_t posX;
|
||||
int32_t posY;
|
||||
int32_t posZ;
|
||||
|
||||
sscanf( params.c_str(), "%d %d %d", &posX, &posY, &posZ );
|
||||
|
||||
if( ( posX == 0xcccccccc ) || ( posY == 0xcccccccc ) || ( posZ == 0xcccccccc ) )
|
||||
{
|
||||
player.sendUrgent( "Syntaxerror." );
|
||||
return;
|
||||
}
|
||||
|
||||
if( subCommand == "pos" )
|
||||
player.setPosition( static_cast< float >( posX ),
|
||||
static_cast< float >( posY ),
|
||||
static_cast< float >( posZ ) );
|
||||
else
|
||||
player.setPosition( player.getPos().x + static_cast< float >( posX ),
|
||||
player.getPos().y + static_cast< float >( posY ),
|
||||
player.getPos().z + static_cast< float >( posZ ) );
|
||||
|
||||
Network::Packets::ZoneChannelPacket< Network::Packets::Server::FFXIVIpcActorSetPos >
|
||||
setActorPosPacket( player.getId() );
|
||||
setActorPosPacket.data().x = player.getPos().x;
|
||||
setActorPosPacket.data().y = player.getPos().y;
|
||||
setActorPosPacket.data().z = player.getPos().z;
|
||||
player.queuePacket( setActorPosPacket );
|
||||
|
||||
}
|
||||
else if( ( subCommand == "tele" ) && ( params != "" ) )
|
||||
{
|
||||
int32_t aetheryteId;
|
||||
sscanf( params.c_str(), "%i", &aetheryteId );
|
||||
|
||||
player.teleport( aetheryteId );
|
||||
}
|
||||
else if( ( subCommand == "discovery" ) && ( params != "" ) )
|
||||
{
|
||||
int32_t map_id;
|
||||
int32_t discover_id;
|
||||
sscanf( params.c_str(), "%i %i", &map_id, &discover_id );
|
||||
|
||||
Network::Packets::ZoneChannelPacket< Network::Packets::Server::FFXIVIpcDiscovery > discoveryPacket( player.getId() );
|
||||
discoveryPacket.data().map_id = map_id;
|
||||
discoveryPacket.data().map_part_id = discover_id;
|
||||
player.queuePacket( discoveryPacket );
|
||||
}
|
||||
|
||||
else if( ( subCommand == "discovery_pos" ) && ( params != "" ) )
|
||||
{
|
||||
int32_t map_id;
|
||||
int32_t discover_id;
|
||||
int32_t pos_id;
|
||||
sscanf( params.c_str(), "%i %i %i", &pos_id, &map_id, &discover_id );
|
||||
|
||||
std::string query2 = "UPDATE IGNORE `discoveryinfo` SET `discover_id` = '" + std::to_string( discover_id ) +
|
||||
"' WHERE `discoveryinfo`.`id` = " + std::to_string( pos_id ) + ";";
|
||||
|
||||
std::string query1 = "INSERT IGNORE INTO `discoveryinfo` (`id`, `map_id`, `discover_id`) VALUES ('" + std::to_string( pos_id ) +
|
||||
"', '" + std::to_string( map_id ) +
|
||||
"', '" + std::to_string( discover_id ) + "')";
|
||||
|
||||
g_charaDb.execute( query1 );
|
||||
g_charaDb.execute( query2 );
|
||||
|
||||
}
|
||||
|
||||
else if( subCommand == "discovery_reset" )
|
||||
{
|
||||
player.resetDiscovery();
|
||||
player.queuePacket( Network::Packets::Server::InitUIPacket( player ) );
|
||||
}
|
||||
else if( subCommand == "classjob" )
|
||||
{
|
||||
int32_t id;
|
||||
|
||||
sscanf( params.c_str(), "%d", &id );
|
||||
|
||||
if( player.getLevelForClass( static_cast< Common::ClassJob > ( id ) ) == 0 )
|
||||
{
|
||||
player.setLevelForClass( 1, static_cast< Common::ClassJob > ( id ) );
|
||||
player.setClassJob( static_cast< Common::ClassJob > ( id ) );
|
||||
}
|
||||
else
|
||||
player.setClassJob( static_cast< Common::ClassJob > ( id ) );
|
||||
}
|
||||
else if ( subCommand == "cfpenalty" )
|
||||
{
|
||||
int32_t minutes;
|
||||
sscanf( params.c_str(), "%d", &minutes );
|
||||
|
||||
player.setCFPenaltyMinutes( minutes );
|
||||
}
|
||||
else if ( subCommand == "eorzeatime" )
|
||||
{
|
||||
uint64_t timestamp;
|
||||
sscanf( params.c_str(), "%" SCNu64, ×tamp );
|
||||
|
||||
player.setEorzeaTimeOffset( timestamp );
|
||||
player.sendNotice( "Eorzea time offset: " + std::to_string( timestamp ) );
|
||||
}
|
||||
else if ( subCommand == "model" )
|
||||
{
|
||||
uint32_t slot;
|
||||
uint32_t val;
|
||||
sscanf( params.c_str(), "%d %d", &slot, &val );
|
||||
|
||||
player.setModelForSlot( static_cast< Inventory::EquipSlot >( slot ), val );
|
||||
player.sendModel();
|
||||
player.sendDebug( "Model updated" );
|
||||
}
|
||||
else if ( subCommand == "mount" )
|
||||
{
|
||||
int32_t id;
|
||||
sscanf( params.c_str(), "%d", &id );
|
||||
|
||||
player.dismount();
|
||||
player.mount( id );
|
||||
}
|
||||
else
|
||||
{
|
||||
player.sendUrgent( subCommand + " is not a valid SET command." );
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
void Core::DebugCommandHandler::add( char * data, Entity::Player& player, boost::shared_ptr< DebugCommand > command )
|
||||
{
|
||||
std::string subCommand;
|
||||
std::string params = "";
|
||||
|
||||
// check if the command has parameters
|
||||
std::string tmpCommand = std::string( data + command->getName().length() + 1 );
|
||||
|
||||
std::size_t pos = tmpCommand.find_first_of( " " );
|
||||
|
||||
if( pos != std::string::npos )
|
||||
// command has parameters, grab the first part
|
||||
subCommand = tmpCommand.substr( 0, pos );
|
||||
else
|
||||
// no subcommand given
|
||||
subCommand = tmpCommand;
|
||||
|
||||
if( command->getName().length() + 1 + pos + 1 < strlen( data ) )
|
||||
params = std::string( data + command->getName().length() + 1 + pos + 1 );
|
||||
|
||||
g_log.debug( "[" + std::to_string( player.getId() ) + "] " +
|
||||
"subCommand " + subCommand + " params: " + params );
|
||||
|
||||
|
||||
if( subCommand == "status" )
|
||||
{
|
||||
int32_t id;
|
||||
int32_t duration;
|
||||
uint16_t param;
|
||||
|
||||
sscanf( params.c_str(), "%d %d %hu", &id, &duration, ¶m );
|
||||
|
||||
StatusEffect::StatusEffectPtr effect( new StatusEffect::StatusEffect( id, player.getAsPlayer(), player.getAsPlayer(), duration, 3000 ) );
|
||||
effect->setParam( param );
|
||||
|
||||
player.addStatusEffect( effect );
|
||||
}
|
||||
else if( subCommand == "title" )
|
||||
{
|
||||
uint32_t titleId;
|
||||
sscanf( params.c_str(), "%u", &titleId );
|
||||
|
||||
player.addTitle( titleId );
|
||||
player.sendNotice( "Added title (ID: " + std::to_string( titleId ) + ")" );
|
||||
}
|
||||
else if( subCommand == "spawn" )
|
||||
{
|
||||
int32_t model, name;
|
||||
|
||||
sscanf( params.c_str(), "%d %d", &model, &name );
|
||||
|
||||
Entity::BattleNpcPtr pBNpc( new Entity::BattleNpc( model, name, player.getPos() ) );
|
||||
|
||||
auto pZone = player.getCurrentZone();
|
||||
pBNpc->setCurrentZone( pZone );
|
||||
pZone->pushActor( pBNpc );
|
||||
|
||||
}
|
||||
else if( subCommand == "op" )
|
||||
{
|
||||
// temporary research packet
|
||||
int32_t opcode;
|
||||
sscanf( params.c_str(), "%x", &opcode );
|
||||
Network::Packets::GamePacketPtr pPe( new Network::Packets::GamePacket( opcode, 0x30, player.getId(), player.getId() ) );
|
||||
player.queuePacket( pPe );
|
||||
}
|
||||
else if( subCommand == "actrl" )
|
||||
{
|
||||
|
||||
// temporary research packet
|
||||
|
||||
int32_t opcode;
|
||||
int32_t param1;
|
||||
int32_t param2;
|
||||
int32_t param3;
|
||||
int32_t param4;
|
||||
int32_t param5;
|
||||
int32_t param6;
|
||||
int32_t playerId;
|
||||
|
||||
sscanf( params.c_str(), "%x %x %x %x %x %x %x %x", &opcode, ¶m1, ¶m2, ¶m3, ¶m4, ¶m5, ¶m6, &playerId );
|
||||
|
||||
player.sendNotice( "Injecting ACTOR_CONTROL " + std::to_string( opcode ) );
|
||||
|
||||
Network::Packets::ZoneChannelPacket< Network::Packets::Server::FFXIVIpcActorControl143 > actorControl( playerId, player.getId() );
|
||||
actorControl.data().category = opcode;
|
||||
actorControl.data().param1 = param1;
|
||||
actorControl.data().param2 = param2;
|
||||
actorControl.data().param3 = param3;
|
||||
actorControl.data().param4 = param4;
|
||||
actorControl.data().param5 = param5;
|
||||
actorControl.data().param6 = param6;
|
||||
player.queuePacket( actorControl );
|
||||
|
||||
|
||||
/*sscanf(params.c_str(), "%x %x %x %x %x %x %x", &opcode, ¶m1, ¶m2, ¶m3, ¶m4, ¶m5, ¶m6, &playerId);
|
||||
|
||||
Network::Packets::Server::ServerNoticePacket noticePacket( player, "Injecting ACTOR_CONTROL " + std::to_string( opcode ) );
|
||||
|
||||
player.queuePacket( noticePacket );
|
||||
|
||||
Network::Packets::Server::ActorControlPacket143 controlPacket( player, opcode,
|
||||
param1, param2, param3, param4, param5, param6, playerId );
|
||||
player.queuePacket( controlPacket );*/
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
player.sendUrgent( subCommand + " is not a valid ADD command." );
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
void Core::DebugCommandHandler::get( char * data, Entity::Player& player, boost::shared_ptr< DebugCommand > command )
|
||||
{
|
||||
std::string subCommand;
|
||||
std::string params = "";
|
||||
|
||||
// check if the command has parameters
|
||||
std::string tmpCommand = std::string( data + command->getName().length() + 1 );
|
||||
|
||||
std::size_t pos = tmpCommand.find_first_of( " " );
|
||||
|
||||
if( pos != std::string::npos )
|
||||
// command has parameters, grab the first part
|
||||
subCommand = tmpCommand.substr( 0, pos );
|
||||
else
|
||||
// no subcommand given
|
||||
subCommand = tmpCommand;
|
||||
|
||||
if( command->getName().length() + 1 + pos + 1 < strlen( data ) )
|
||||
params = std::string( data + command->getName().length() + 1 + pos + 1 );
|
||||
|
||||
g_log.debug( "[" + std::to_string( player.getId() ) + "] " +
|
||||
"subCommand " + subCommand + " params: " + params );
|
||||
|
||||
|
||||
if( ( subCommand == "pos" ) )
|
||||
{
|
||||
|
||||
int16_t map_id = g_exdData.m_zoneInfoMap[player.getCurrentZone()->getTerritoryId()].map_id;
|
||||
|
||||
player.sendNotice( "Pos:\n" +
|
||||
std::to_string( player.getPos().x ) + "\n" +
|
||||
std::to_string( player.getPos().y ) + "\n" +
|
||||
std::to_string( player.getPos().z ) + "\n" +
|
||||
std::to_string( player.getRotation() ) + "\nMapId: " +
|
||||
std::to_string( map_id ) + "\nZoneID: " +
|
||||
std::to_string(player.getCurrentZone()->getTerritoryId() ) + "\n" );
|
||||
}
|
||||
else
|
||||
{
|
||||
player.sendUrgent( subCommand + " is not a valid GET command." );
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
void Core::DebugCommandHandler::injectPacket( char * data, Entity::Player& player, boost::shared_ptr< DebugCommand > command )
|
||||
{
|
||||
auto pSession = g_serverZone.getSession( player.getId() );
|
||||
if( pSession )
|
||||
pSession->getZoneConnection()->injectPacket( data + 7, player );
|
||||
}
|
||||
|
||||
void Core::DebugCommandHandler::injectChatPacket( char * data, Entity::Player& player, boost::shared_ptr< DebugCommand > command )
|
||||
{
|
||||
auto pSession = g_serverZone.getSession( player.getId() );
|
||||
if( pSession )
|
||||
pSession->getChatConnection()->injectPacket( data + 8, player );
|
||||
}
|
||||
|
||||
void Core::DebugCommandHandler::replay( char * data, Entity::Player& player, boost::shared_ptr< DebugCommand > command )
|
||||
{
|
||||
std::string subCommand;
|
||||
std::string params = "";
|
||||
|
||||
// check if the command has parameters
|
||||
std::string tmpCommand = std::string( data + command->getName().length() + 1 );
|
||||
|
||||
std::size_t pos = tmpCommand.find_first_of( " " );
|
||||
|
||||
if( pos != std::string::npos )
|
||||
// command has parameters, grab the first part
|
||||
subCommand = tmpCommand.substr( 0, pos );
|
||||
else
|
||||
// no subcommand given
|
||||
subCommand = tmpCommand;
|
||||
|
||||
if( command->getName().length() + 1 + pos + 1 < strlen( data ) )
|
||||
params = std::string( data + command->getName().length() + 1 + pos + 1 );
|
||||
|
||||
g_log.debug( "[" + std::to_string( player.getId() ) + "] " +
|
||||
"subCommand " + subCommand + " params: " + params );
|
||||
|
||||
|
||||
if( subCommand == "start" )
|
||||
{
|
||||
auto pSession = g_serverZone.getSession( player.getId() );
|
||||
if( pSession )
|
||||
pSession->startReplay( params );
|
||||
}
|
||||
else if( subCommand == "stop" )
|
||||
{
|
||||
auto pSession = g_serverZone.getSession( player.getId() );
|
||||
if( pSession )
|
||||
pSession->stopReplay();
|
||||
}
|
||||
else
|
||||
{
|
||||
player.sendUrgent( subCommand + " is not a valid replay command." );
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
void Core::DebugCommandHandler::nudge( char * data, Entity::Player& player, boost::shared_ptr< DebugCommand > command )
|
||||
{
|
||||
std::string subCommand;
|
||||
|
||||
// check if the command has parameters
|
||||
std::string tmpCommand = std::string( data + command->getName().length() + 1 );
|
||||
|
||||
std::size_t spos = tmpCommand.find_first_of( " " );
|
||||
|
||||
auto& pos = player.getPos();
|
||||
|
||||
int32_t offset = 0;
|
||||
char direction[20];
|
||||
memset( direction, 0, 20 );
|
||||
|
||||
sscanf( tmpCommand.c_str(), "%d %s", &offset, direction );
|
||||
|
||||
if( direction[0] == 'u' || direction[0] == '+' )
|
||||
{
|
||||
pos.y += offset;
|
||||
player.sendNotice( "nudge: Placing up " + std::to_string( offset ) + " yalms" );
|
||||
}
|
||||
else if( direction[0] == 'd' || direction[0] == '-' )
|
||||
{
|
||||
pos.y -= offset;
|
||||
player.sendNotice( "nudge: Placing down " + std::to_string( offset ) + " yalms" );
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
float angle = player.getRotation() + ( PI / 2 );
|
||||
pos.x -= offset * cos( angle );
|
||||
pos.z += offset * sin( angle );
|
||||
player.sendNotice( "nudge: Placing forward " + std::to_string( offset ) + " yalms" );
|
||||
}
|
||||
if( offset != 0 )
|
||||
{
|
||||
Network::Packets::ZoneChannelPacket< Network::Packets::Server::FFXIVIpcActorSetPos >
|
||||
setActorPosPacket( player.getId() );
|
||||
setActorPosPacket.data().x = player.getPos().x;
|
||||
setActorPosPacket.data().y = player.getPos().y;
|
||||
setActorPosPacket.data().z = player.getPos().z;
|
||||
setActorPosPacket.data().r16 = Math::Util::floatToUInt16Rot( player.getRotation() );
|
||||
player.queuePacket( setActorPosPacket );
|
||||
}
|
||||
}
|
||||
|
||||
void Core::DebugCommandHandler::serverInfo( char * data, Entity::Player& player, boost::shared_ptr< DebugCommand > command )
|
||||
{
|
||||
player.sendDebug( "SapphireServer " + Version::VERSION + "\nRev: " + Version::GIT_HASH );
|
||||
player.sendDebug( "Compiled: " __DATE__ " " __TIME__ );
|
||||
player.sendDebug( "Sessions: " + std::to_string( g_serverZone.getSessionCount() ) );
|
||||
}
|
||||
|
||||
void Core::DebugCommandHandler::unlockCharacter( char* data, Entity::Player& player, boost::shared_ptr< DebugCommand > command )
|
||||
{
|
||||
player.unlock();
|
||||
}
|
||||
|
||||
void Core::DebugCommandHandler::script( char* data, Entity::Player &player, boost::shared_ptr< DebugCommand > command )
|
||||
{
|
||||
std::string subCommand;
|
||||
std::string params = "";
|
||||
|
||||
// check if the command has parameters
|
||||
std::string tmpCommand = std::string( data + command->getName().length() + 1 );
|
||||
|
||||
std::size_t pos = tmpCommand.find_first_of( " " );
|
||||
|
||||
if( pos != std::string::npos )
|
||||
// command has parameters, grab the first part
|
||||
subCommand = tmpCommand.substr( 0, pos );
|
||||
else
|
||||
// no subcommand given
|
||||
subCommand = tmpCommand;
|
||||
|
||||
// todo: fix params so it's empty if there's no params
|
||||
if( command->getName().length() + 1 + pos + 1 < strlen( data ) )
|
||||
params = std::string( data + command->getName().length() + 1 + pos + 1 );
|
||||
|
||||
g_log.debug( "[" + std::to_string( player.getId() ) + "] " +
|
||||
"subCommand " + subCommand + " params: " + params );
|
||||
|
||||
if( subCommand == "unload" )
|
||||
{
|
||||
if ( subCommand == params )
|
||||
player.sendDebug( "Command failed: requires name of script" );
|
||||
else
|
||||
if( g_scriptMgr.getNativeScriptHandler().unloadScript( params ) )
|
||||
player.sendDebug( "Unloaded script successfully." );
|
||||
else
|
||||
player.sendDebug( "Failed to unload script: " + params );
|
||||
}
|
||||
else if( subCommand == "find" || subCommand == "f" )
|
||||
{
|
||||
if( subCommand == params )
|
||||
player.sendDebug( "Because reasons of filling chat with nonsense, please enter a search term" );
|
||||
else
|
||||
{
|
||||
std::set< Core::Scripting::ScriptInfo* > scripts;
|
||||
g_scriptMgr.getNativeScriptHandler().findScripts( scripts, params );
|
||||
|
||||
if( !scripts.empty() )
|
||||
{
|
||||
player.sendDebug( "Found " + std::to_string( scripts.size() ) + " scripts" );
|
||||
|
||||
for( auto it = scripts.begin(); it != scripts.end(); ++it )
|
||||
{
|
||||
auto script = *it;
|
||||
player.sendDebug( " - '" + script->library_name + "' loaded at @ 0x" +
|
||||
boost::str( boost::format( "%|X|" ) % script->handle ) +
|
||||
", num scripts: " + std::to_string( script->scripts.size() ) );
|
||||
}
|
||||
}
|
||||
else
|
||||
player.sendDebug( "No scripts found with search term: " + params );
|
||||
}
|
||||
}
|
||||
else if( subCommand == "load" || subCommand == "l" )
|
||||
{
|
||||
if( subCommand == params )
|
||||
player.sendDebug( "Command failed: requires relative path to script" );
|
||||
else
|
||||
{
|
||||
if ( g_scriptMgr.getNativeScriptHandler().loadScript( params ) )
|
||||
player.sendDebug( "Loaded '" + params + "' successfully" );
|
||||
else
|
||||
player.sendDebug( "Failed to load '" + params + "'" );
|
||||
}
|
||||
|
||||
}
|
||||
else if( subCommand == "queuereload" || subCommand == "qrl" )
|
||||
{
|
||||
if( subCommand == params )
|
||||
player.sendDebug( "Command failed: requires name of script to reload" );
|
||||
else
|
||||
{
|
||||
g_scriptMgr.getNativeScriptHandler().queueScriptReload( params );
|
||||
player.sendDebug( "Queued script reload for script: " + params );
|
||||
}
|
||||
}
|
||||
else if( subCommand == "build" || subCommand == "b" )
|
||||
{
|
||||
if( subCommand == params )
|
||||
player.sendDebug( "Command failed: requires name of cmake target" );
|
||||
else
|
||||
{
|
||||
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
player.sendDebug( "Unknown script subcommand: " + subCommand );
|
||||
}
|
||||
}
|
|
@ -1,52 +0,0 @@
|
|||
#ifndef _GAMECOMMANDHANDLER_H_
|
||||
#define _GAMECOMMANDHANDLER_H_
|
||||
|
||||
#include <map>
|
||||
|
||||
#include "DebugCommand.h"
|
||||
#include <common/Common.h>
|
||||
#include "Forwards.h"
|
||||
|
||||
namespace Core {
|
||||
|
||||
|
||||
// handler for in game commands
|
||||
class DebugCommandHandler
|
||||
{
|
||||
private:
|
||||
// container mapping command string to command object
|
||||
std::map< std::string, boost::shared_ptr< DebugCommand > > m_commandMap;
|
||||
|
||||
public:
|
||||
DebugCommandHandler();
|
||||
~DebugCommandHandler();
|
||||
|
||||
// register command to command map
|
||||
void registerCommand( const std::string& n, DebugCommand::pFunc, const std::string& hText, uint8_t uLevel );
|
||||
|
||||
// execute command if registered
|
||||
void execCommand( char * data, Entity::Player& player );
|
||||
|
||||
// help command
|
||||
void help( char* data, Entity::Player& player, boost::shared_ptr< DebugCommand > command );
|
||||
|
||||
// command handler callbacks
|
||||
void set( char * data, Entity::Player& player, boost::shared_ptr< DebugCommand > command );
|
||||
void get( char * data, Entity::Player& player, boost::shared_ptr< DebugCommand > command );
|
||||
void add( char * data, Entity::Player& player, boost::shared_ptr< DebugCommand > command );
|
||||
//void debug( char * data, Entity::Player& player, boost::shared_ptr< DebugCommand > command );
|
||||
|
||||
void injectPacket( char * data, Entity::Player& player, boost::shared_ptr< DebugCommand > command );
|
||||
void injectChatPacket( char * data, Entity::Player& player, boost::shared_ptr< DebugCommand > command );
|
||||
void replay( char * data, Entity::Player& player, boost::shared_ptr< DebugCommand > command );
|
||||
void nudge( char* data, Entity::Player& player, boost::shared_ptr< DebugCommand > command );
|
||||
void serverInfo( char * data, Entity::Player& player, boost::shared_ptr< DebugCommand > command );
|
||||
|
||||
void unlockCharacter( char* data, Entity::Player& player, boost::shared_ptr< DebugCommand > command );
|
||||
|
||||
void script( char* data, Entity::Player& player, boost::shared_ptr< DebugCommand > command );
|
||||
|
||||
};
|
||||
|
||||
}
|
||||
#endif
|
|
@ -12,11 +12,9 @@
|
|||
#include "Session.h"
|
||||
#include "Zone/Zone.h"
|
||||
#include "Network/PacketWrappers/InitUIPacket.h"
|
||||
#include "DebugCommand/DebugCommandHandler.h"
|
||||
#include "Actor/Player.h"
|
||||
#include "Forwards.h"
|
||||
|
||||
extern Core::DebugCommandHandler g_gameCommandMgr;
|
||||
extern Core::Logger g_log;
|
||||
extern Core::ServerZone g_serverZone;
|
||||
|
||||
|
|
|
@ -26,7 +26,6 @@
|
|||
#include "Network/PacketWrappers/EventFinishPacket.h"
|
||||
#include "Network/PacketWrappers/PlayerStateFlagsPacket.h"
|
||||
|
||||
#include "DebugCommand/DebugCommandHandler.h"
|
||||
#include "Actor/Player.h"
|
||||
#include "Inventory/Inventory.h"
|
||||
#include "Forwards.h"
|
||||
|
@ -37,7 +36,6 @@
|
|||
extern Core::Logger g_log;
|
||||
extern Core::ServerZone g_serverZone;
|
||||
extern Core::Data::ExdData g_exdData;
|
||||
extern Core::DebugCommandHandler g_gameCommandMgr;
|
||||
|
||||
using namespace Core::Common;
|
||||
using namespace Core::Network::Packets;
|
||||
|
|
|
@ -27,19 +27,19 @@
|
|||
#include "Network/PacketWrappers/EventFinishPacket.h"
|
||||
#include "Network/PacketWrappers/PlayerStateFlagsPacket.h"
|
||||
|
||||
#include "DebugCommand/DebugCommandHandler.h"
|
||||
#include "Actor/Player.h"
|
||||
#include "Inventory/Inventory.h"
|
||||
#include "Forwards.h"
|
||||
#include "Event/EventHelper.h"
|
||||
#include "Action/Action.h"
|
||||
#include "Action/ActionTeleport.h"
|
||||
#include "Script/ScriptManager.h"
|
||||
|
||||
extern Core::Logger g_log;
|
||||
extern Core::ServerZone g_serverZone;
|
||||
extern Core::TerritoryMgr g_territoryMgr;
|
||||
extern Core::Data::ExdData g_exdData;
|
||||
extern Core::DebugCommandHandler g_gameCommandMgr;
|
||||
extern Core::Scripting::ScriptManager g_scriptMgr;
|
||||
|
||||
using namespace Core::Common;
|
||||
using namespace Core::Network::Packets;
|
||||
|
@ -127,6 +127,15 @@ void Core::Network::GameConnection::gm1Handler( const Packets::GamePacket& inPac
|
|||
return;
|
||||
auto targetPlayer = targetActor->getAsPlayer();
|
||||
|
||||
// auto script = g_scriptMgr.getNativeScriptHandler().getScript< GmCommandScript >( commandId );
|
||||
// if( script )
|
||||
// {
|
||||
// script->gm1Handler( param1, param2, param3 );
|
||||
// return;
|
||||
// }
|
||||
//
|
||||
// player.sendUrgent( "GM1 Command not implemented: " + std::to_string( commandId ) );
|
||||
|
||||
switch( commandId )
|
||||
{
|
||||
case GmCommand::Lv:
|
||||
|
|
|
@ -19,7 +19,6 @@
|
|||
#include "Network/PacketWrappers/ActorControlPacket143.h"
|
||||
#include "Network/PacketWrappers/ActorControlPacket144.h"
|
||||
|
||||
#include "DebugCommand/DebugCommandHandler.h"
|
||||
#include "Actor/Player.h"
|
||||
#include "Inventory/Inventory.h"
|
||||
#include "Forwards.h"
|
||||
|
@ -27,7 +26,6 @@
|
|||
extern Core::Logger g_log;
|
||||
extern Core::ServerZone g_serverZone;
|
||||
extern Core::Data::ExdData g_exdData;
|
||||
extern Core::DebugCommandHandler g_gameCommandMgr;
|
||||
|
||||
using namespace Core::Common;
|
||||
using namespace Core::Network::Packets;
|
||||
|
|
|
@ -29,7 +29,7 @@
|
|||
#include "Network/PacketWrappers/EventFinishPacket.h"
|
||||
#include "Network/PacketWrappers/PlayerStateFlagsPacket.h"
|
||||
|
||||
#include "DebugCommand/DebugCommandHandler.h"
|
||||
#include "Script/ScriptManager.h"
|
||||
#include "Actor/Player.h"
|
||||
#include "Inventory/Inventory.h"
|
||||
#include "Forwards.h"
|
||||
|
@ -42,7 +42,7 @@ extern Core::Logger g_log;
|
|||
extern Core::ServerZone g_serverZone;
|
||||
extern Core::TerritoryMgr g_territoryMgr;
|
||||
extern Core::Data::ExdData g_exdData;
|
||||
extern Core::DebugCommandHandler g_gameCommandMgr;
|
||||
extern Core::Scripting::ScriptManager g_scriptMgr;
|
||||
|
||||
using namespace Core::Common;
|
||||
using namespace Core::Network::Packets;
|
||||
|
@ -493,7 +493,7 @@ void Core::Network::GameConnection::chatHandler( const Packets::GamePacket& inPa
|
|||
if( chatString.at( 0 ) == '!' )
|
||||
{
|
||||
// execute game console command
|
||||
g_gameCommandMgr.execCommand( const_cast< char * >( chatString.c_str() ) + 1, player );
|
||||
g_scriptMgr.debugCommandHandler( chatString.substr( 1 ), player );
|
||||
return;
|
||||
}
|
||||
|
||||
|
|
|
@ -19,8 +19,6 @@
|
|||
|
||||
#include "Network/PacketWrappers/PlayerStateFlagsPacket.h"
|
||||
|
||||
#include "DebugCommand/DebugCommandHandler.h"
|
||||
|
||||
#include "Actor/Player.h"
|
||||
|
||||
#include "Forwards.h"
|
||||
|
|
|
@ -1,13 +1,19 @@
|
|||
#ifndef NATIVE_SCRIPT_API
|
||||
#define NATIVE_SCRIPT_API
|
||||
|
||||
#include "ScriptManager.h"
|
||||
|
||||
#include <string>
|
||||
#include <typeinfo>
|
||||
#include <typeindex>
|
||||
#include <utility>
|
||||
|
||||
#include <Actor/Actor.h>
|
||||
#include <Actor/Player.h>
|
||||
#include <StatusEffect/StatusEffect.h>
|
||||
#include <common/Logging/Logger.h>
|
||||
#include <ServerZone.h>
|
||||
#include <common/Exd/ExdData.h>
|
||||
|
||||
#ifdef _MSC_VER
|
||||
#define EXPORT __declspec( dllexport )
|
||||
|
@ -21,16 +27,28 @@ using namespace Core;
|
|||
#define EVENTSCRIPT_AETHERYTE_ID 0x50000
|
||||
#define EVENTSCRIPT_AETHERNET_ID 0x50001
|
||||
|
||||
class SapphireObjects
|
||||
{
|
||||
public:
|
||||
SapphireObjects() = default;
|
||||
|
||||
Core::Logger* m_logger;
|
||||
Core::ServerZone* m_zone;
|
||||
Core::Scripting::ScriptManager* m_scriptMgr;
|
||||
Core::Data::ExdData* m_exd;
|
||||
};
|
||||
|
||||
class ScriptObject
|
||||
{
|
||||
protected:
|
||||
uint32_t m_id;
|
||||
std::size_t m_type;
|
||||
SapphireObjects* m_objects;
|
||||
|
||||
public:
|
||||
ScriptObject( uint32_t id, std::size_t type ) :
|
||||
ScriptObject( uint32_t id, const type_info& type ) :
|
||||
m_id( id ),
|
||||
m_type( type )
|
||||
m_type( type.hash_code() )
|
||||
{ }
|
||||
|
||||
virtual uint32_t getId() const
|
||||
|
@ -38,18 +56,28 @@ public:
|
|||
return m_id;
|
||||
}
|
||||
|
||||
virtual void setId( const uint32_t id )
|
||||
{
|
||||
m_id = id;
|
||||
}
|
||||
|
||||
virtual std::size_t getType() const
|
||||
{
|
||||
return m_type;
|
||||
}
|
||||
|
||||
virtual void setObjects( SapphireObjects* ptr )
|
||||
{
|
||||
m_objects = ptr;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
class StatusEffectScript : public ScriptObject
|
||||
{
|
||||
public:
|
||||
StatusEffectScript( uint32_t effectId ) :
|
||||
ScriptObject( effectId, typeid( StatusEffectScript ).hash_code() )
|
||||
explicit StatusEffectScript( uint32_t effectId ) :
|
||||
ScriptObject( effectId, typeid( StatusEffectScript ) )
|
||||
{ }
|
||||
|
||||
virtual void onTick( Entity::Actor& actor ) { }
|
||||
|
@ -66,8 +94,8 @@ public:
|
|||
class ActionScript : public ScriptObject
|
||||
{
|
||||
public:
|
||||
ActionScript( uint32_t abilityId ) :
|
||||
ScriptObject( abilityId, typeid( ActionScript ).hash_code() )
|
||||
explicit ActionScript( uint32_t abilityId ) :
|
||||
ScriptObject( abilityId, typeid( ActionScript ) )
|
||||
{ }
|
||||
|
||||
virtual void onStart( Entity::Actor& sourceActor, Entity::Actor& targetActor ) { }
|
||||
|
@ -79,8 +107,8 @@ public:
|
|||
class EventScript : public ScriptObject
|
||||
{
|
||||
public:
|
||||
EventScript( uint32_t questId ) :
|
||||
ScriptObject( questId, typeid( EventScript ).hash_code() )
|
||||
explicit EventScript( uint32_t questId ) :
|
||||
ScriptObject( questId, typeid( EventScript ) )
|
||||
{ }
|
||||
|
||||
virtual void onTalk( uint32_t eventId, Entity::Player& player, uint64_t actorId ) { }
|
||||
|
@ -97,19 +125,63 @@ public:
|
|||
class BattleNpcScript : public ScriptObject
|
||||
{
|
||||
public:
|
||||
BattleNpcScript( uint32_t npcId ) :
|
||||
ScriptObject( npcId, typeid( BattleNpcScript ).hash_code() )
|
||||
explicit BattleNpcScript( uint32_t npcId ) :
|
||||
ScriptObject( npcId, typeid( BattleNpcScript ) )
|
||||
{ }
|
||||
};
|
||||
|
||||
class ZoneScript : public ScriptObject
|
||||
{
|
||||
public:
|
||||
ZoneScript( uint32_t zoneId ) :
|
||||
ScriptObject( zoneId, typeid( ZoneScript ).hash_code() )
|
||||
explicit ZoneScript( uint32_t zoneId ) :
|
||||
ScriptObject( zoneId, typeid( ZoneScript ) )
|
||||
{ }
|
||||
|
||||
virtual void onZoneInit() { }
|
||||
};
|
||||
|
||||
class GmCommandScript : public ScriptObject
|
||||
{
|
||||
public:
|
||||
explicit GmCommandScript( uint32_t cmdId ) :
|
||||
ScriptObject( cmdId, typeid( GmCommandScript ) )
|
||||
{ }
|
||||
|
||||
virtual void gm1Handler( uint32_t param1, uint32_t param2, uint32_t param3 ) { }
|
||||
virtual void gm2Handler( const std::string& param1 ) { }
|
||||
};
|
||||
|
||||
class DebugCommandScript : public ScriptObject
|
||||
{
|
||||
protected:
|
||||
std::string m_cmd;
|
||||
std::string m_helpText;
|
||||
uint8_t m_gmLevel;
|
||||
|
||||
public:
|
||||
explicit DebugCommandScript( const std::string& cmd, const std::string& helpText, uint8_t gmLevel) :
|
||||
ScriptObject( 0, typeid( DebugCommandScript ) ),
|
||||
m_cmd( cmd ),
|
||||
m_helpText( helpText ),
|
||||
m_gmLevel( gmLevel )
|
||||
{ }
|
||||
|
||||
virtual const std::string& getCmd()
|
||||
{
|
||||
return m_cmd;
|
||||
}
|
||||
|
||||
virtual const uint8_t getGmLevel()
|
||||
{
|
||||
return m_gmLevel;
|
||||
}
|
||||
|
||||
virtual const std::string getHelpText()
|
||||
{
|
||||
return m_helpText;
|
||||
}
|
||||
|
||||
virtual void run( Entity::Player& player, const std::string& args, const std::string& subCommand, const std::string& params ) { }
|
||||
};
|
||||
|
||||
#endif
|
|
@ -1,8 +1,30 @@
|
|||
#include <ServerZone.h>
|
||||
#include <common/Exd/ExdData.h>
|
||||
#include "NativeScriptManager.h"
|
||||
#include "ScriptManager.h"
|
||||
|
||||
extern Core::Scripting::ScriptManager g_scriptMgr;
|
||||
extern Core::Data::ExdData g_exdData;
|
||||
extern Core::Logger g_log;
|
||||
extern Core::ServerZone g_serverZone;
|
||||
|
||||
namespace Core {
|
||||
namespace Scripting {
|
||||
|
||||
NativeScriptManager::NativeScriptManager() :
|
||||
m_objects( new SapphireObjects )
|
||||
{
|
||||
m_objects->m_logger = &g_log;
|
||||
m_objects->m_zone = &g_serverZone;
|
||||
m_objects->m_scriptMgr = &g_scriptMgr;
|
||||
m_objects->m_exd = &g_exdData;
|
||||
}
|
||||
|
||||
NativeScriptManager::~NativeScriptManager()
|
||||
{
|
||||
delete m_objects;
|
||||
}
|
||||
|
||||
bool NativeScriptManager::loadScript( const std::string& path )
|
||||
{
|
||||
auto module = m_loader.loadModule( path );
|
||||
|
@ -27,6 +49,11 @@ namespace Scripting {
|
|||
auto script = scripts[i];
|
||||
module->scripts.push_back( script );
|
||||
|
||||
script->setObjects( m_objects );
|
||||
|
||||
if( script->getId() == 0 )
|
||||
script->setId( m_allocatedScriptIds[script->getType()]++ );
|
||||
|
||||
m_scripts[script->getType()][script->getId()] = script;
|
||||
|
||||
success = true;
|
||||
|
|
|
@ -20,15 +20,18 @@ namespace Scripting {
|
|||
{
|
||||
protected:
|
||||
std::unordered_map< std::size_t, std::unordered_map< uint32_t, ScriptObject* > > m_scripts;
|
||||
std::map< std::size_t, uint32_t > m_allocatedScriptIds;
|
||||
|
||||
ScriptLoader m_loader;
|
||||
SapphireObjects* m_objects;
|
||||
|
||||
std::queue< std::string > m_scriptLoadQueue;
|
||||
|
||||
bool unloadScript( ScriptInfo* info );
|
||||
|
||||
public:
|
||||
NativeScriptManager( ) = default;
|
||||
NativeScriptManager();
|
||||
~NativeScriptManager();
|
||||
|
||||
bool loadScript( const std::string& path );
|
||||
bool unloadScript( const std::string& name );
|
||||
|
@ -40,7 +43,7 @@ namespace Scripting {
|
|||
const std::string getModuleExtension();
|
||||
bool isModuleLoaded( const std::string& name );
|
||||
|
||||
template< typename T >
|
||||
template< class T >
|
||||
T* getScript( uint32_t scriptId )
|
||||
{
|
||||
auto type = typeid( T ).hash_code();
|
||||
|
@ -51,6 +54,14 @@ namespace Scripting {
|
|||
|
||||
return dynamic_cast< T* >( script->second );
|
||||
}
|
||||
|
||||
template< class T >
|
||||
std::unordered_map< uint32_t, ScriptObject* >& getScriptsOfType()
|
||||
{
|
||||
auto type = typeid( T ).hash_code();
|
||||
|
||||
return m_scripts[type];
|
||||
};
|
||||
};
|
||||
|
||||
|
||||
|
|
|
@ -20,9 +20,6 @@
|
|||
#include <boost/format.hpp>
|
||||
#include <boost/foreach.hpp>
|
||||
|
||||
|
||||
// enable the ambiguity fix for every platform to avoid #define nonsense
|
||||
#define WIN_AMBIGUITY_FIX
|
||||
#include <libraries/external/watchdog/Watchdog.h>
|
||||
|
||||
extern Core::Logger g_log;
|
||||
|
@ -50,7 +47,8 @@ bool Core::Scripting::ScriptManager::init()
|
|||
std::set< std::string > files;
|
||||
|
||||
loadDir( g_serverZone.getConfig()->getValue< std::string >( "Settings.General.Scripts.Path", "./compiledscripts/" ),
|
||||
files, m_nativeScriptManager->getModuleExtension() );
|
||||
files,
|
||||
m_nativeScriptManager->getModuleExtension() );
|
||||
|
||||
uint32_t scriptsFound = 0;
|
||||
uint32_t scriptsLoaded = 0;
|
||||
|
@ -65,7 +63,7 @@ bool Core::Scripting::ScriptManager::init()
|
|||
scriptsLoaded++;
|
||||
}
|
||||
|
||||
g_log.info( "ScriptManager: Loaded " + std::to_string( scriptsLoaded ) + "/" + std::to_string( scriptsFound ) + " scripts successfully" );
|
||||
g_log.info( "ScriptManager: Loaded " + std::to_string( scriptsLoaded ) + "/" + std::to_string( scriptsFound ) + " modules successfully" );
|
||||
|
||||
watchDirectories();
|
||||
|
||||
|
@ -89,17 +87,19 @@ void Core::Scripting::ScriptManager::watchDirectories()
|
|||
return;
|
||||
}
|
||||
|
||||
for( auto path : paths )
|
||||
for( const auto& path : paths )
|
||||
{
|
||||
if( m_nativeScriptManager->isModuleLoaded( path.stem().string() ) )
|
||||
{
|
||||
g_log.debug( "Reloading changed script: " + path.stem().string() );
|
||||
auto name = path.stem().string();
|
||||
|
||||
m_nativeScriptManager->queueScriptReload( path.stem( ).string( ));
|
||||
if( m_nativeScriptManager->isModuleLoaded( name ) )
|
||||
{
|
||||
g_log.debug( "Reloading changed script: " + name );
|
||||
|
||||
m_nativeScriptManager->queueScriptReload( name );
|
||||
}
|
||||
else
|
||||
{
|
||||
g_log.debug( "Loading new script: " + path.stem().string() );
|
||||
g_log.debug( "Loading new script: " + name );
|
||||
|
||||
m_nativeScriptManager->loadScript( path.string() );
|
||||
}
|
||||
|
@ -110,7 +110,7 @@ void Core::Scripting::ScriptManager::watchDirectories()
|
|||
void Core::Scripting::ScriptManager::loadDir( const std::string& dirname, std::set<std::string> &files, const std::string& ext )
|
||||
{
|
||||
|
||||
g_log.info( "ScriptEngine: loading scripts from " + dirname );
|
||||
g_log.info( "ScriptManager: loading scripts from " + dirname );
|
||||
|
||||
boost::filesystem::path targetDir( dirname );
|
||||
|
||||
|
@ -342,6 +342,74 @@ bool Core::Scripting::ScriptManager::onZoneInit( ZonePtr pZone )
|
|||
return false;
|
||||
}
|
||||
|
||||
bool Core::Scripting::ScriptManager::gm1Handler( uint32_t cmdId, uint32_t param1, uint32_t param2, uint32_t param3 )
|
||||
{
|
||||
auto script = m_nativeScriptManager->getScript< GmCommandScript >( cmdId );
|
||||
if( script )
|
||||
{
|
||||
script->gm1Handler( param1, param2, param3 );
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
bool Core::Scripting::ScriptManager::gm2Handler( uint32_t cmdId, const std::string& param1 )
|
||||
{
|
||||
auto script = m_nativeScriptManager->getScript< GmCommandScript >( cmdId );
|
||||
if( script )
|
||||
{
|
||||
script->gm2Handler( param1 );
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
bool Core::Scripting::ScriptManager::debugCommandHandler( const std::string& cmd, Entity::Player& player )
|
||||
{
|
||||
std::string command, params, subCommand;
|
||||
auto cmdPos = cmd.find_first_of( ' ' );
|
||||
|
||||
if( cmdPos != std::string::npos )
|
||||
{
|
||||
command = cmd.substr( 0, cmdPos );
|
||||
params = cmd.substr( cmdPos + 1 );
|
||||
|
||||
auto p = params.find_first_of( ' ' );
|
||||
|
||||
if( p != std::string::npos )
|
||||
{
|
||||
subCommand = params.substr( 0, p );
|
||||
params = params.substr( subCommand.length() + 1 );
|
||||
}
|
||||
else
|
||||
subCommand = params;
|
||||
}
|
||||
else
|
||||
command = cmd;
|
||||
|
||||
g_log.debug( "[" + std::to_string( player.getId() ) + "] " +
|
||||
"subCommand: " + subCommand + " params: " + params );
|
||||
|
||||
for( std::pair< uint32_t, ScriptObject* > pair : m_nativeScriptManager->getScriptsOfType< DebugCommandScript >() )
|
||||
{
|
||||
if( pair.second == nullptr )
|
||||
continue;
|
||||
|
||||
auto script = dynamic_cast< DebugCommandScript* >( pair.second );
|
||||
|
||||
if( player.getGmRank() >= script->getGmLevel() && script->getCmd() == command )
|
||||
{
|
||||
script->run( player, cmd, subCommand, params );
|
||||
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
Scripting::NativeScriptManager& Core::Scripting::ScriptManager::getNativeScriptHandler()
|
||||
{
|
||||
return *m_nativeScriptManager;
|
||||
|
|
|
@ -59,6 +59,10 @@ namespace Core
|
|||
bool onEventHandlerReturn( Entity::Player& player, uint32_t eventId, uint16_t subEvent, uint16_t param1, uint16_t param2, uint16_t param3 );
|
||||
bool onEventHandlerTradeReturn( Entity::Player& player, uint32_t eventId, uint16_t subEvent, uint16_t param, uint32_t catalogId );
|
||||
|
||||
bool gm1Handler( uint32_t cmdId, uint32_t param1, uint32_t param2, uint32_t param3 );
|
||||
bool gm2Handler( uint32_t cmdId, const std::string& param1 );
|
||||
|
||||
bool debugCommandHandler( const std::string& cmd, Entity::Player& player );
|
||||
|
||||
void loadDir( const std::string& dirname, std::set<std::string> &files, const std::string& ext );
|
||||
|
||||
|
|
|
@ -24,7 +24,7 @@
|
|||
|
||||
#include "Zone/TerritoryMgr.h"
|
||||
|
||||
#include "DebugCommand/DebugCommandHandler.h"
|
||||
#include "Actor/Player.h"
|
||||
|
||||
#include "Script/ScriptManager.h"
|
||||
#include "Linkshell/LinkshellMgr.h"
|
||||
|
@ -37,7 +37,6 @@
|
|||
#include <common/Util/Util.h>
|
||||
|
||||
Core::Logger g_log;
|
||||
Core::DebugCommandHandler g_gameCommandMgr;
|
||||
Core::Scripting::ScriptManager g_scriptMgr;
|
||||
Core::Data::ExdData g_exdData;
|
||||
Core::Data::ExdDataGenerated g_exdDataGen;
|
||||
|
|
Loading…
Add table
Reference in a new issue