mirror of
https://github.com/EQEmu/Server.git
synced 2026-05-22 16:28:28 +00:00
Fix character creation tenancy operations
This commit is contained in:
+62
-2
@@ -1568,7 +1568,7 @@ bool Client::OPCharCreate(char *name, CharCreate_Struct *cc)
|
||||
/* Overrides if we have the tutorial flag set! */
|
||||
if (cc->tutorial && RuleB(World, EnableTutorialButton)) {
|
||||
pp.zone_id = RuleI(World, TutorialZoneID);
|
||||
database.GetSafePoints(pp.zone_id, 0, &pp.x, &pp.y, &pp.z);
|
||||
content_db.GetSafePoints(pp.zone_id, 0, &pp.x, &pp.y, &pp.z);
|
||||
}
|
||||
|
||||
/* Will either be the same as home or tutorial if enabled. */
|
||||
@@ -1592,7 +1592,7 @@ bool Client::OPCharCreate(char *name, CharCreate_Struct *cc)
|
||||
|
||||
// now we give the pp and the inv we made to StoreCharacter
|
||||
// to see if we can store it
|
||||
if (!database.StoreCharacter(GetAccountID(), &pp, &inv)) {
|
||||
if (!StoreCharacter(GetAccountID(), &pp, &inv)) {
|
||||
LogInfo("Character creation failed: [{}]", pp.name);
|
||||
return false;
|
||||
}
|
||||
@@ -2075,3 +2075,63 @@ void Client::SetClassLanguages(PlayerProfile_Struct *pp)
|
||||
}
|
||||
}
|
||||
|
||||
bool Client::StoreCharacter(
|
||||
uint32 account_id,
|
||||
PlayerProfile_Struct *p_player_profile_struct,
|
||||
EQEmu::InventoryProfile *p_inventory_profile
|
||||
)
|
||||
{
|
||||
uint32 character_id = 0;
|
||||
char zone[50];
|
||||
character_id = database.GetCharacterID(p_player_profile_struct->name);
|
||||
|
||||
if (!character_id) {
|
||||
LogError("StoreCharacter: no character id");
|
||||
return false;
|
||||
}
|
||||
|
||||
const char *zone_name = content_db.GetZoneName(p_player_profile_struct->zone_id);
|
||||
if (zone_name == nullptr) {
|
||||
/* Zone not in the DB, something to prevent crash... */
|
||||
strn0cpy(zone, "qeynos", 49);
|
||||
p_player_profile_struct->zone_id = 1;
|
||||
}
|
||||
else {
|
||||
strn0cpy(zone, zone_name, 49);
|
||||
}
|
||||
|
||||
database.SaveCharacterCreate(character_id, account_id, p_player_profile_struct);
|
||||
|
||||
std::string invquery;
|
||||
for (int16 i = EQEmu::invslot::EQUIPMENT_BEGIN; i <= EQEmu::invbag::BANK_BAGS_END;) {
|
||||
const EQEmu::ItemInstance *new_inventory_item = p_inventory_profile->GetItem(i);
|
||||
if (new_inventory_item) {
|
||||
invquery = StringFormat(
|
||||
"INSERT INTO `inventory` (charid, slotid, itemid, charges, color) VALUES (%u, %i, %u, %i, %u)",
|
||||
character_id,
|
||||
i,
|
||||
new_inventory_item->GetItem()->ID,
|
||||
new_inventory_item->GetCharges(),
|
||||
new_inventory_item->GetColor()
|
||||
);
|
||||
|
||||
auto results = database.QueryDatabase(invquery);
|
||||
}
|
||||
|
||||
if (i == EQEmu::invslot::slotCursor) {
|
||||
i = EQEmu::invbag::GENERAL_BAGS_BEGIN;
|
||||
continue;
|
||||
}
|
||||
else if (i == EQEmu::invbag::CURSOR_BAG_END) {
|
||||
i = EQEmu::invslot::BANK_BEGIN;
|
||||
continue;
|
||||
}
|
||||
else if (i == EQEmu::invslot::BANK_END) {
|
||||
i = EQEmu::invbag::BANK_BAGS_BEGIN;
|
||||
continue;
|
||||
}
|
||||
i++;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -22,6 +22,7 @@
|
||||
|
||||
#include "../common/linked_list.h"
|
||||
#include "../common/timer.h"
|
||||
#include "../common/inventory_profile.h"
|
||||
//#include "zoneserver.h"
|
||||
|
||||
#include "../common/eq_packet_structs.h"
|
||||
@@ -71,6 +72,12 @@ public:
|
||||
inline EQEmu::versions::ClientVersion GetClientVersion() { return m_ClientVersion; }
|
||||
inline ClientListEntry* GetCLE() { return cle; }
|
||||
inline void SetCLE(ClientListEntry* iCLE) { cle = iCLE; }
|
||||
bool StoreCharacter(
|
||||
uint32 account_id,
|
||||
PlayerProfile_Struct *p_player_profile_struct,
|
||||
EQEmu::InventoryProfile *p_inventory_profile
|
||||
);
|
||||
|
||||
private:
|
||||
|
||||
uint32 ip;
|
||||
|
||||
+8
-12
@@ -247,17 +247,10 @@ int main(int argc, char** argv) {
|
||||
if (argc > 1) {
|
||||
LogSys.SilenceConsoleLogging();
|
||||
|
||||
/**
|
||||
* Get Config
|
||||
*/
|
||||
WorldConfig::LoadConfig();
|
||||
Config = WorldConfig::get();
|
||||
|
||||
/**
|
||||
* Load database
|
||||
*/
|
||||
LoadDatabaseConnections();
|
||||
|
||||
LogSys.EnableConsoleLogging();
|
||||
|
||||
WorldserverCommandHandler::CommandHandler(argc, argv);
|
||||
@@ -340,12 +333,15 @@ int main(int argc, char** argv) {
|
||||
LogInfo("Clearing inventory snapshots");
|
||||
database.ClearInvSnapshots();
|
||||
LogInfo("Loading items");
|
||||
if (!database.LoadItems(hotfix_name))
|
||||
LogError("Error: Could not load item data. But ignoring");
|
||||
LogInfo("Loading skill caps");
|
||||
if (!database.LoadSkillCaps(std::string(hotfix_name)))
|
||||
LogError("Error: Could not load skill cap data. But ignoring");
|
||||
|
||||
if (!content_db.LoadItems(hotfix_name)) {
|
||||
LogError("Error: Could not load item data. But ignoring");
|
||||
}
|
||||
|
||||
LogInfo("Loading skill caps");
|
||||
if (!content_db.LoadSkillCaps(std::string(hotfix_name))) {
|
||||
LogError("Error: Could not load skill cap data. But ignoring");
|
||||
}
|
||||
|
||||
LogInfo("Loading guilds");
|
||||
guild_mgr.LoadGuilds();
|
||||
|
||||
+48
-26
@@ -215,7 +215,7 @@ void WorldDatabase::GetCharSelectInfo(uint32 account_id, EQApplicationPacket **o
|
||||
float x = atof(row_d[2]);
|
||||
float y = atof(row_d[3]);
|
||||
float z = atof(row_d[4]);
|
||||
if (x == 0 && y == 0 && z == 0) { GetSafePoints(player_profile_struct.binds[4].zoneId, 0, &x, &y, &z); }
|
||||
if (x == 0 && y == 0 && z == 0) { content_db.GetSafePoints(player_profile_struct.binds[4].zoneId, 0, &x, &y, &z); }
|
||||
player_profile_struct.binds[4].x = x;
|
||||
player_profile_struct.binds[4].y = y;
|
||||
player_profile_struct.binds[4].z = z;
|
||||
@@ -392,7 +392,11 @@ int WorldDatabase::MoveCharacterToBind(int CharID, uint8 bindnum)
|
||||
return zone_id;
|
||||
}
|
||||
|
||||
bool WorldDatabase::GetStartZone(PlayerProfile_Struct* in_pp, CharCreate_Struct* in_cc,bool isTitanium)
|
||||
bool WorldDatabase::GetStartZone(
|
||||
PlayerProfile_Struct *p_player_profile_struct,
|
||||
CharCreate_Struct *p_char_create_struct,
|
||||
bool is_titanium
|
||||
)
|
||||
{
|
||||
// SoF doesn't send the player_choice field in character creation, it now sends the real zoneID instead.
|
||||
//
|
||||
@@ -401,45 +405,63 @@ bool WorldDatabase::GetStartZone(PlayerProfile_Struct* in_pp, CharCreate_Struct*
|
||||
// For now, if no row matching row is found, send them to Crescent Reach, as that is probably the most likely
|
||||
// reason for no match being found.
|
||||
//
|
||||
if(!in_pp || !in_cc)
|
||||
if (!p_player_profile_struct || !p_char_create_struct) {
|
||||
return false;
|
||||
}
|
||||
|
||||
p_player_profile_struct->x = 0;
|
||||
p_player_profile_struct->y = 0;
|
||||
p_player_profile_struct->z = 0;
|
||||
p_player_profile_struct->heading = 0;
|
||||
p_player_profile_struct->zone_id = 0;
|
||||
p_player_profile_struct->binds[0].x = 0;
|
||||
p_player_profile_struct->binds[0].y = 0;
|
||||
p_player_profile_struct->binds[0].z = 0;
|
||||
p_player_profile_struct->binds[0].zoneId = 0;
|
||||
p_player_profile_struct->binds[0].instance_id = 0;
|
||||
|
||||
in_pp->x = in_pp->y = in_pp->z = in_pp->heading = in_pp->zone_id = 0;
|
||||
in_pp->binds[0].x = in_pp->binds[0].y = in_pp->binds[0].z = in_pp->binds[0].zoneId = in_pp->binds[0].instance_id = 0;
|
||||
// see if we have an entry for start_zone. We can support both titanium & SOF+ by having two entries per class/race/deity combo with different zone_ids
|
||||
std::string query = StringFormat("SELECT x, y, z, heading, start_zone, bind_id, bind_x, bind_y, bind_z FROM start_zones WHERE zone_id = %i "
|
||||
std::string query = StringFormat(
|
||||
"SELECT x, y, z, heading, start_zone, bind_id, bind_x, bind_y, bind_z FROM start_zones WHERE zone_id = %i "
|
||||
"AND player_class = %i AND player_deity = %i AND player_race = %i",
|
||||
in_cc->start_zone, in_cc->class_, in_cc->deity, in_cc->race);
|
||||
auto results = QueryDatabase(query);
|
||||
if(!results.Success()) {
|
||||
p_char_create_struct->start_zone,
|
||||
p_char_create_struct->class_,
|
||||
p_char_create_struct->deity,
|
||||
p_char_create_struct->race
|
||||
);
|
||||
|
||||
auto results = QueryDatabase(query);
|
||||
if (!results.Success()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
LogInfo("SoF Start zone query: [{}]\n", query.c_str());
|
||||
|
||||
if (results.RowCount() == 0) {
|
||||
printf("No start_zones entry in database, using defaults\n");
|
||||
isTitanium ? SetTitaniumDefaultStartZone(in_pp, in_cc) : SetSoFDefaultStartZone(in_pp, in_cc);
|
||||
if (results.RowCount() == 0) {
|
||||
printf("No start_zones entry in database, using defaults\n");
|
||||
is_titanium ? SetTitaniumDefaultStartZone(p_player_profile_struct, p_char_create_struct) : SetSoFDefaultStartZone(p_player_profile_struct, p_char_create_struct);
|
||||
}
|
||||
else {
|
||||
LogInfo("Found starting location in start_zones");
|
||||
auto row = results.begin();
|
||||
in_pp->x = atof(row[0]);
|
||||
in_pp->y = atof(row[1]);
|
||||
in_pp->z = atof(row[2]);
|
||||
in_pp->heading = atof(row[3]);
|
||||
in_pp->zone_id = atoi(row[4]);
|
||||
in_pp->binds[0].zoneId = atoi(row[5]);
|
||||
in_pp->binds[0].x = atof(row[6]);
|
||||
in_pp->binds[0].y = atof(row[7]);
|
||||
in_pp->binds[0].z = atof(row[8]);
|
||||
p_player_profile_struct->x = atof(row[0]);
|
||||
p_player_profile_struct->y = atof(row[1]);
|
||||
p_player_profile_struct->z = atof(row[2]);
|
||||
p_player_profile_struct->heading = atof(row[3]);
|
||||
p_player_profile_struct->zone_id = atoi(row[4]);
|
||||
p_player_profile_struct->binds[0].zoneId = atoi(row[5]);
|
||||
p_player_profile_struct->binds[0].x = atof(row[6]);
|
||||
p_player_profile_struct->binds[0].y = atof(row[7]);
|
||||
p_player_profile_struct->binds[0].z = atof(row[8]);
|
||||
}
|
||||
|
||||
if(in_pp->x == 0 && in_pp->y == 0 && in_pp->z == 0)
|
||||
database.GetSafePoints(in_pp->zone_id, 0, &in_pp->x, &in_pp->y, &in_pp->z);
|
||||
if (p_player_profile_struct->x == 0 && p_player_profile_struct->y == 0 && p_player_profile_struct->z == 0) {
|
||||
content_db.GetSafePoints(p_player_profile_struct->zone_id, 0, &p_player_profile_struct->x, &p_player_profile_struct->y, &p_player_profile_struct->z);
|
||||
}
|
||||
|
||||
if(in_pp->binds[0].x == 0 && in_pp->binds[0].y == 0 && in_pp->binds[0].z == 0)
|
||||
database.GetSafePoints(in_pp->binds[0].zoneId, 0, &in_pp->binds[0].x, &in_pp->binds[0].y, &in_pp->binds[0].z);
|
||||
if (p_player_profile_struct->binds[0].x == 0 && p_player_profile_struct->binds[0].y == 0 && p_player_profile_struct->binds[0].z == 0) {
|
||||
content_db.GetSafePoints(p_player_profile_struct->binds[0].zoneId, 0, &p_player_profile_struct->binds[0].x, &p_player_profile_struct->binds[0].y, &p_player_profile_struct->binds[0].z);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -783,4 +805,4 @@ bool WorldDatabase::GetCharSelInventory(uint32 account_id, char *name, EQEmu::In
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
}
|
||||
+8
-1
@@ -29,7 +29,7 @@ struct CharacterSelect_Struct;
|
||||
|
||||
class WorldDatabase : public SharedDatabase {
|
||||
public:
|
||||
bool GetStartZone(PlayerProfile_Struct* in_pp, CharCreate_Struct* in_cc, bool isTitanium);
|
||||
bool GetStartZone(PlayerProfile_Struct* p_player_profile_struct, CharCreate_Struct* p_char_create_struct, bool is_titanium);
|
||||
void GetCharSelectInfo(uint32 account_id, EQApplicationPacket **out_app, uint32 client_version_bit);
|
||||
int MoveCharacterToBind(int CharID, uint8 bindnum = 0);
|
||||
|
||||
@@ -38,6 +38,13 @@ public:
|
||||
|
||||
bool LoadCharacterCreateAllocations();
|
||||
bool LoadCharacterCreateCombos();
|
||||
|
||||
bool StoreCharacter(
|
||||
uint32 account_id,
|
||||
PlayerProfile_Struct *p_player_profile_struct,
|
||||
EQEmu::InventoryProfile *p_inventory_profile
|
||||
);
|
||||
|
||||
private:
|
||||
void SetTitaniumDefaultStartZone(PlayerProfile_Struct* in_pp, CharCreate_Struct* in_cc);
|
||||
void SetSoFDefaultStartZone(PlayerProfile_Struct* in_pp, CharCreate_Struct* in_cc);
|
||||
|
||||
Reference in New Issue
Block a user