1
Fork 0
mirror of https://github.com/SapphireServer/Sapphire.git synced 2025-04-27 14:57:44 +00:00

Merge pull request #453 from NotAdam/housing

Better errors, fix client trigger params being read incorrectly for housing estates
This commit is contained in:
Mordred 2018-12-18 21:03:25 +01:00 committed by GitHub
commit 8e4c42bcf9
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
14 changed files with 140 additions and 74 deletions

14
.gitignore vendored
View file

@ -5,6 +5,16 @@
[Bb]in/world
[Bb]in/lobby
[Bb]in/dbm
src/tools/[Bb]in/*.exe
src/tools/[Bb]in/*.pdb
src/tools/[Bb]in/discovery_parser
src/tools/[Bb]in/event_object_parser
src/tools/[Bb]in/exd_common_gen
src/tools/[Bb]in/exd_struct_test
src/tools/[Bb]in/mob_parse
src/tools/[Bb]in/pcb_reader2
src/tools/[Bb]in/quest_parse
src/tools/[Bb]in/exd_struct_gen
# Script Directory
# TODO: Sperate script directory from bin
@ -129,3 +139,7 @@ cotire/
# doxygen output folder
doxygen/generated/
doxygen/*.tmp
# ignore config directory contents except the default file
bin/config/*.ini
!bin/config/config.ini.default

View file

@ -74,6 +74,7 @@ bool loadSettings( int32_t argc, char* argv[] )
if( !m_pConfig->loadConfig( configPath ) )
{
g_log.fatal( "Error loading config " + configPath );
g_log.fatal( "If this is the first time starting the server, we've copied the default one for your editing pleasure." );
return false;
}
@ -140,9 +141,11 @@ bool loadSettings( int32_t argc, char* argv[] )
}
g_log.info( "Setting up generated EXD data" );
if( !g_exdDataGen.init( m_pConfig->getValue< std::string >( "GlobalParameters", "DataPath", "" ) ) )
auto dataPath = m_pConfig->getValue< std::string >( "GlobalParameters", "DataPath", "" );
if( !g_exdDataGen.init( dataPath ) )
{
g_log.fatal( "Error setting up generated EXD data " );
g_log.fatal( "Error setting up generated EXD data. Make sure that DataPath is set correctly in config.ini" );
g_log.fatal( "DataPath: " + dataPath );
return false;
}

View file

@ -17,8 +17,8 @@ bool Sapphire::ConfigMgr::loadConfig( const std::string& configName )
if( !fs::exists( configFile ) )
{
if( !copyDefaultConfig( configName ) )
return false;
copyDefaultConfig( configName );
return false;
}
m_pInih = std::unique_ptr< INIReader >( new INIReader( configFile.string() ) );

View file

@ -1078,7 +1078,7 @@ struct FFXIVIpcCharaNameReq :
struct FFXIVIpcItemInfo :
FFXIVIpcBasePacket< ItemInfo >
{
uint32_t sequence;
uint32_t containerSequence;
uint32_t unknown;
uint16_t containerId;
uint16_t slot;
@ -1113,7 +1113,7 @@ struct FFXIVIpcItemInfo :
struct FFXIVIpcContainerInfo :
FFXIVIpcBasePacket< ContainerInfo >
{
uint32_t sequence;
uint32_t containerSequence;
uint32_t numItems;
uint32_t containerId;
uint32_t unknown;
@ -1126,7 +1126,7 @@ struct FFXIVIpcContainerInfo :
struct FFXIVIpcCurrencyCrystalInfo :
FFXIVIpcBasePacket< CurrencyCrystalInfo >
{
uint32_t sequence;
uint32_t containerSequence;
uint16_t containerId;
uint16_t slot;
uint32_t quantity;

View file

@ -90,6 +90,7 @@ bool ServerLobby::loadSettings( int32_t argc, char* argv[] )
if( !m_pConfig->loadConfig( m_configPath ) )
{
g_log.fatal( "Error loading config " + m_configPath );
g_log.fatal( "If this is the first time starting the server, we've copied the default one for your editing pleasure." );
return false;
}
std::vector< std::string > args( argv + 1, argv + argc );

View file

@ -27,6 +27,7 @@
#include "Network/PacketWrappers/ServerNoticePacket.h"
#include "Network/PacketWrappers/ActorControlPacket143.h"
#include "Manager/InventoryMgr.h"
#include "Framework.h"
#include <Network/CommonActorControl.h>
@ -358,54 +359,13 @@ void Sapphire::Entity::Player::sendInventory()
{
InventoryMap::iterator it;
int32_t count = 0;
for( it = m_storageMap.begin(); it != m_storageMap.end(); ++it, count++ )
auto pInvMgr = g_fw.get< World::Manager::InventoryMgr >();
uint32_t count = 0;
for( it = m_storageMap.begin(); it != m_storageMap.end(); ++it, ++count )
{
auto pMap = it->second->getItemMap();
auto itM = pMap.begin();
for( ; itM != pMap.end(); ++itM )
{
if( !itM->second )
return;
if( it->second->getId() == InventoryType::Currency || it->second->getId() == InventoryType::Crystal )
{
auto currencyInfoPacket = makeZonePacket< FFXIVIpcCurrencyCrystalInfo >( getId() );
currencyInfoPacket->data().sequence = count;
currencyInfoPacket->data().catalogId = itM->second->getId();
currencyInfoPacket->data().unknown = 1;
currencyInfoPacket->data().quantity = itM->second->getStackSize();
currencyInfoPacket->data().containerId = it->second->getId();
currencyInfoPacket->data().slot = 0;
queuePacket( currencyInfoPacket );
}
else
{
auto itemInfoPacket = makeZonePacket< FFXIVIpcItemInfo >( getId() );
itemInfoPacket->data().sequence = count;
itemInfoPacket->data().containerId = it->second->getId();
itemInfoPacket->data().slot = itM->first;
itemInfoPacket->data().quantity = itM->second->getStackSize();
itemInfoPacket->data().catalogId = itM->second->getId();
itemInfoPacket->data().condition = itM->second->getDurability();
itemInfoPacket->data().spiritBond = 0;
itemInfoPacket->data().hqFlag = itM->second->isHq() ? 1 : 0;
itemInfoPacket->data().stain = itM->second->getStain();
queuePacket( itemInfoPacket );
}
}
auto containerInfoPacket = makeZonePacket< FFXIVIpcContainerInfo >( getId() );
containerInfoPacket->data().sequence = count;
containerInfoPacket->data().numItems = it->second->getEntryCount();
containerInfoPacket->data().containerId = it->second->getId();
queuePacket( containerInfoPacket );
pInvMgr->sendInventoryContainer( *this, it->second, count );
}
}
Sapphire::Entity::Player::InvSlotPairVec Sapphire::Entity::Player::getSlotsOfItemsInInventory( uint32_t catalogId )

View file

@ -87,20 +87,14 @@ void Sapphire::World::Manager::HousingMgr::sendLandSignOwned( Entity::Player& pl
auto land = hZone->getLand( ident.landId );
if( !land )
{
land = getLandByOwnerId( player.getId() );
}
return;
auto landInfoSignPacket = makeZonePacket< Server::FFXIVIpcLandInfoSign >( player.getId() );
uint32_t playerId = land->getPlayerOwner();
std::string playerName = g_fw.get< Sapphire::ServerMgr >()->getPlayerNameFromDb( playerId );
//memcpy( &landInfoSignPacket->data().estateGreeting, "Hello World", 11 );
//memcpy( &landInfoSignPacket->data().estateName, land->getLandName().c_str(), land->getLandName().size() );
landInfoSignPacket->data().houseSize = land->getSize();
landInfoSignPacket->data().houseType = static_cast< uint8_t >( land->getLandType() );
landInfoSignPacket->data().landIdent = ident;
landInfoSignPacket->data().houseIconAdd = land->getSharing();
landInfoSignPacket->data().ownerId = player.getContentId(); // should be real owner contentId, not player.contentId()
landInfoSignPacket->data().ownerId = player.getContentId(); // todo: should be real owner contentId, not player.contentId()
if( auto house = land->getHouse() )
{
@ -108,6 +102,9 @@ void Sapphire::World::Manager::HousingMgr::sendLandSignOwned( Entity::Player& pl
std::strcpy( landInfoSignPacket->data().estateGreeting, house->getHouseGreeting().c_str() );
}
uint32_t playerId = land->getPlayerOwner();
std::string playerName = g_fw.get< Sapphire::ServerMgr >()->getPlayerNameFromDb( playerId );
memcpy( &landInfoSignPacket->data().ownerName, playerName.c_str(), playerName.size() );
player.queuePacket( landInfoSignPacket );
@ -453,13 +450,22 @@ void Sapphire::World::Manager::HousingMgr::requestEstateEditGuestAccess( Entity:
player.queuePacket( packet );
}
Sapphire::Common::LandIdent Sapphire::World::Manager::HousingMgr::clientTriggerParamsToLandIdent( uint32_t param11, uint32_t param12 ) const
Sapphire::Common::LandIdent Sapphire::World::Manager::HousingMgr::clientTriggerParamsToLandIdent( uint32_t param11, uint32_t param12, bool use16bits ) const
{
Common::LandIdent ident;
ident.worldId = param11 >> 16;
ident.territoryTypeId = param11 & 0xFFFF;
ident.wardNum = param12 >> 16;
ident.landId = param12 & 0xFFFF;
if( use16bits )
{
ident.wardNum = param12 >> 16;
ident.landId = param12 & 0xFFFF;
}
else
{
ident.wardNum = (param12 >> 8) & 0xFF;
ident.landId = param12 & 0xFF;
}
return ident;
}

View file

@ -33,7 +33,7 @@ namespace Sapphire::World::Manager
/*!
* @brief Converts param1 of a client trigger into a Common::LandIndent
*/
Common::LandIdent clientTriggerParamsToLandIdent( uint32_t param11, uint32_t param12 ) const;
Common::LandIdent clientTriggerParamsToLandIdent( uint32_t param11, uint32_t param12, bool use16bits = true ) const;
void sendWardLandInfo( Entity::Player& player, uint8_t wardId, uint16_t territoryTypeId );

View file

@ -0,0 +1,58 @@
#include "InventoryMgr.h"
#include <Common.h>
#include "Actor/Player.h"
#include "Inventory/ItemContainer.h"
#include "Inventory/Item.h"
#include <Network/PacketDef/Zone/ServerZoneDef.h>
#include <Network/GamePacketNew.h>
using namespace Sapphire::Network::Packets;
void Sapphire::World::Manager::InventoryMgr::sendInventoryContainer( Sapphire::Entity::Player& player,
Sapphire::ItemContainerPtr container,
uint32_t sequence )
{
auto pMap = container->getItemMap();
for( auto itM = pMap.begin(); itM != pMap.end(); ++itM )
{
if( !itM->second )
return;
if( container->getId() == Common::InventoryType::Currency || container->getId() == Common::InventoryType::Crystal )
{
auto currencyInfoPacket = makeZonePacket< Server::FFXIVIpcCurrencyCrystalInfo >( player.getId() );
currencyInfoPacket->data().containerSequence = sequence;
currencyInfoPacket->data().catalogId = itM->second->getId();
currencyInfoPacket->data().unknown = 1;
currencyInfoPacket->data().quantity = itM->second->getStackSize();
currencyInfoPacket->data().containerId = container->getId();
currencyInfoPacket->data().slot = 0;
player.queuePacket( currencyInfoPacket );
}
else
{
auto itemInfoPacket = makeZonePacket< Server::FFXIVIpcItemInfo >( player.getId() );
itemInfoPacket->data().containerSequence = sequence;
itemInfoPacket->data().containerId = container->getId();
itemInfoPacket->data().slot = itM->first;
itemInfoPacket->data().quantity = itM->second->getStackSize();
itemInfoPacket->data().catalogId = itM->second->getId();
itemInfoPacket->data().condition = itM->second->getDurability();
itemInfoPacket->data().spiritBond = 0;
itemInfoPacket->data().hqFlag = itM->second->isHq() ? 1 : 0;
itemInfoPacket->data().stain = itM->second->getStain();
player.queuePacket( itemInfoPacket );
}
}
auto containerInfoPacket = makeZonePacket< Server::FFXIVIpcContainerInfo >( player.getId() );
containerInfoPacket->data().containerSequence = sequence;
containerInfoPacket->data().numItems = container->getEntryCount();
containerInfoPacket->data().containerId = container->getId();
player.queuePacket( containerInfoPacket );
}

View file

@ -0,0 +1,18 @@
#ifndef SAPPHIRE_INVENTORYMGR_H
#define SAPPHIRE_INVENTORYMGR_H
#include "ForwardsZone.h"
namespace Sapphire::World::Manager
{
class InventoryMgr
{
public:
void sendInventoryContainer( Sapphire::Entity::Player& player, Sapphire::ItemContainerPtr container,
uint32_t sequence = 0 );
};
}
#endif //SAPPHIRE_INVENTORYMGR_H

View file

@ -336,7 +336,7 @@ void Sapphire::Network::GameConnection::clientTriggerHandler( const Packets::FFX
{
auto pHousingMgr = g_fw.get< HousingMgr >();
auto ident = pHousingMgr->clientTriggerParamsToLandIdent( param11, param12 );
auto ident = pHousingMgr->clientTriggerParamsToLandIdent( param11, param12, false );
pHousingMgr->sendLandSignOwned( player, ident );
break;

View file

@ -36,6 +36,7 @@
#include "DebugCommand/DebugCommandHandler.h"
#include "Manager/PlayerMgr.h"
#include "Manager/ShopMgr.h"
#include "Manager/InventoryMgr.h"
extern Sapphire::Framework g_fw;
@ -69,6 +70,7 @@ bool Sapphire::ServerMgr::loadSettings( int32_t argc, char* argv[] )
if( !pConfig->loadConfig( m_configName ) )
{
pLog->fatal( "Error loading config " + m_configName );
pLog->fatal( "If this is the first time starting the server, we've copied the default one for your editing pleasure." );
return false;
}
@ -100,9 +102,11 @@ void Sapphire::ServerMgr::run( int32_t argc, char* argv[] )
pLog->info( "Setting up generated EXD data" );
auto pExdData = std::make_shared< Data::ExdDataGenerated >();
if( !pExdData->init( pConfig->getValue< std::string >( "GlobalParameters", "DataPath", "" ) ) )
auto dataPath = pConfig->getValue< std::string >( "GlobalParameters", "DataPath", "" );
if( !pExdData->init( dataPath ) )
{
pLog->fatal( "Error setting up generated EXD data " );
pLog->fatal( "Error setting up generated EXD data. Make sure that DataPath is set correctly in config.ini" );
pLog->fatal( "DataPath: " + dataPath );
return;
}
g_fw.set< Data::ExdDataGenerated >( pExdData );
@ -165,10 +169,12 @@ void Sapphire::ServerMgr::run( int32_t argc, char* argv[] )
auto pDebugCom = std::make_shared< DebugCommandHandler >();
auto pPlayerMgr = std::make_shared< Manager::PlayerMgr >();
auto pShopMgr = std::make_shared< Manager::ShopMgr >();
auto pInventoryMgr = std::make_shared< Manager::InventoryMgr >();
g_fw.set< DebugCommandHandler >( pDebugCom );
g_fw.set< Manager::PlayerMgr >( pPlayerMgr );
g_fw.set< Manager::ShopMgr >( pShopMgr );
g_fw.set< Manager::InventoryMgr >( pInventoryMgr );
pLog->info( "World server running on " + m_ip + ":" + std::to_string( m_port ) );

View file

@ -77,7 +77,7 @@ void Sapphire::Land::init()
m_size = res->getUInt( "Size" );
m_state = res->getUInt( "Status" );
m_currentPrice = res->getUInt( "LandPrice" );
m_ownerPlayerId = res->getUInt( "OwnerId" );
m_ownerPlayerId = res->getUInt64( "OwnerId" );
m_minPrice = m_landInfo->minPrice[ m_landId ];
m_maxPrice = m_landInfo->initialPrice[ m_landId ];
@ -240,12 +240,12 @@ uint32_t Sapphire::Land::getFcColor()
}
//Player
void Sapphire::Land::setPlayerOwner( uint32_t id )
void Sapphire::Land::setPlayerOwner( uint64_t id )
{
m_ownerPlayerId = id;
}
uint32_t Sapphire::Land::getPlayerOwner()
uint64_t Sapphire::Land::getPlayerOwner()
{
return m_ownerPlayerId;
}

View file

@ -45,8 +45,8 @@ namespace Sapphire
uint32_t getFcColor();
//Player
void setPlayerOwner( uint32_t id );
uint32_t getPlayerOwner();
void setPlayerOwner( uint64_t id );
uint64_t getPlayerOwner();
//Housing Functions
void setCurrentPrice( uint32_t currentPrice );
bool setPreset( uint32_t itemId );
@ -82,7 +82,7 @@ namespace Sapphire
Common::FFXIVARR_POSITION3 m_mapMarkerPosition;
uint32_t m_ownerPlayerId;
uint64_t m_ownerPlayerId;
Sapphire::Data::HousingLandSetPtr m_landInfo;
Sapphire::HousePtr m_pHouse;