Fixes atcommands for PvP and GvG toggle

* Fixes atcommands pvpon, pvpoff, gvgon, and gvgoff to properly toggle the current map with the appropriate zone.
* Atcommand pvpon will assign the MAPTYPE_NOPENALTY_FREEPKZONE zone.
* Atcommand gvgon will assign the MAPTYPE_EVENT_GUILDWAR zone.
* Adds getMapZone() to return a map's zone.
* Adds setZone() to set a map's zone.
Thanks to @Atemo!
This commit is contained in:
aleos 2024-01-18 10:22:07 -05:00
parent d3ea299f53
commit fc3cc3c1c2
3 changed files with 78 additions and 26 deletions

View File

@ -1786,7 +1786,8 @@ ACMD_FUNC(pvpoff)
return -1;
}
map_setmapflag(sd->bl.m, MF_PVP, false);
map_setmapflag(sd->bl.m, MF_PVP, false); // Needed to remove battle and client settings.
map_zone_db.setZone(sd->bl.m, map_zone_db.getMapZone(sd->bl.m));
clif_displaymessage(fd, msg_txt(sd,31)); // PvP: Off.
return 0;
@ -1804,7 +1805,7 @@ ACMD_FUNC(pvpon)
return -1;
}
map_setmapflag(sd->bl.m, MF_PVP, true);
map_zone_db.setZone(sd->bl.m, MAPTYPE_NOPENALTY_FREEPKZONE);
clif_displaymessage(fd, msg_txt(sd,32)); // PvP: On.
@ -1823,7 +1824,9 @@ ACMD_FUNC(gvgoff)
return -1;
}
map_setmapflag(sd->bl.m, MF_GVG, false);
map_setmapflag(sd->bl.m, MF_GVG, false); // Needed to remove battle and client settings.
map_zone_db.setZone(sd->bl.m, map_zone_db.getMapZone(sd->bl.m));
clif_displaymessage(fd, msg_txt(sd,33)); // GvG: Off.
return 0;
@ -1841,7 +1844,8 @@ ACMD_FUNC(gvgon)
return -1;
}
map_setmapflag(sd->bl.m, MF_GVG, true);
map_zone_db.setZone(sd->bl.m, MAPTYPE_EVENT_GUILDWAR);
clif_displaymessage(fd, msg_txt(sd,34)); // GvG: On.
return 0;

View File

@ -510,26 +510,8 @@ void MapZoneDatabase::loadingFinished() {
// This allows for live modifications to the map without affecting the Map Zone DB.
for (const auto &zone : map_zone_db) {
for (const auto &map : zone.second->maps) {
map_data *mapdata = map_getmapdata(map);
if (mapdata == nullptr)
if (map_zone_db.setZone(map, static_cast<e_map_type>(zone.second->id)))
continue;
mapdata->zone = std::make_shared<s_map_zone_data>();
mapdata->zone->id = zone.second->id;
mapdata->zone->disabled_commands = zone.second->disabled_commands;
mapdata->zone->disabled_items = zone.second->disabled_items;
mapdata->zone->disabled_skills = zone.second->disabled_skills;
mapdata->zone->disabled_statuses = zone.second->disabled_statuses;
mapdata->zone->restricted_jobs = zone.second->restricted_jobs;
// Apply mapflags from Map Zone DB
for (const auto &flag : zone.second->mapflags) {
char flag_name[50] = {}, empty[1] = {};
if (map_getmapflag_name(static_cast<e_mapflag>(flag.first), flag_name))
npc_parse_mapflag(mapdata->name, empty, flag_name, const_cast<char *>(flag.second.c_str()), empty, empty, "MapZoneDatabase::loadingFinished");
}
}
}
@ -540,6 +522,70 @@ void MapZoneDatabase::loadingFinished() {
}
}
/**
* Get the zone to a map.
* @param map_id: Map ID
* @return e_map_type on success or MAPTYPE_UNUSED otherwise
*/
e_map_type MapZoneDatabase::getMapZone(int16 map_id) {
map_data *mapdata = map_getmapdata(map_id);
if (mapdata == nullptr) {
ShowError("MapZoneDatabase::getMapZone: Unknown map ID %d, skipping.\n", map_id);
return MAPTYPE_UNUSED;
}
for (const auto &zone : map_zone_db) {
if (util::vector_exists(zone.second->maps, map_id))
return static_cast<e_map_type>(zone.second->id);
}
return MAPTYPE_UNUSED;
}
/**
* Set the zone to a map.
* @param map_id: Map ID
* @param zone: Zone to set
* @return True on success or false otherwise
*/
bool MapZoneDatabase::setZone(int16 map_id, e_map_type zone) {
map_data *mapdata = map_getmapdata(map_id);
if (mapdata == nullptr) {
ShowError("MapZoneDatabase::setZone: Unknown map ID %d, skipping.\n", map_id);
return false;
}
auto zonedata = map_zone_db.find(zone);
if (zonedata == nullptr) {
ShowError("MapZoneDatabase::setZone: Unknown zone %d, skipping.\n", zone);
return false;
}
mapdata->zone = std::make_shared<s_map_zone_data>();
mapdata->zone->id = zonedata->id;
mapdata->zone->disabled_commands = zonedata->disabled_commands;
mapdata->zone->disabled_items = zonedata->disabled_items;
mapdata->zone->disabled_skills = zonedata->disabled_skills;
mapdata->zone->disabled_statuses = zonedata->disabled_statuses;
mapdata->zone->restricted_jobs = zonedata->restricted_jobs;
// Intialization and configuration-dependent adjustments of mapflags
map_flags_init();
// Apply mapflags from Map Zone DB
for (const auto &flag : zonedata->mapflags) {
char flag_name[50] = {}, empty[1] = {};
if (map_getmapflag_name(static_cast<e_mapflag>(flag.first), flag_name))
npc_parse_mapflag(mapdata->name, empty, flag_name, const_cast<char *>(flag.second.c_str()), empty, empty, "MapZoneDatabase::setZone");
}
return true;
}
MapZoneDatabase map_zone_db;
/**
@ -4292,9 +4338,6 @@ int map_readallmaps (void)
mapdata->channel = NULL;
}
// intialization and configuration-dependent adjustments of mapflags
map_flags_init();
if( !enable_grf ) {
// The cache isn't needed anymore, so free it. [Shinryo]
auto it = map_cache_buffer.begin();

View File

@ -50,6 +50,7 @@ struct npc_data;
struct item_data;
struct Channel;
enum sc_type : int16;
enum e_map_type : uint8_t;
struct map_data *map_getmapdata(int16 m);
#define msg_config_read(cfgName,isnew) map_msg_config_read(cfgName,isnew)
@ -900,6 +901,10 @@ public:
const std::string getDefaultLocation() override;
uint64 parseBodyNode(const ryml::NodeRef &node) override;
void loadingFinished() override;
// Others
e_map_type getMapZone(int16 map_id);
bool setZone(int16 map_id, e_map_type zone);
};
extern MapZoneDatabase map_zone_db;