Converted ZC_REQ_EXCHANGE_ITEM&ZC_ACK_EXCHANGE_ITEM to struct (#8581)

---------

Co-authored-by: Lemongrass3110 <lemongrass@kstp.at>
Co-authored-by: Atemo <Atemo@users.noreply.github.com>
Co-authored-by: Aleos <aleos89@users.noreply.github.com>
This commit is contained in:
AoShinHo 2024-09-12 15:17:54 -03:00 committed by GitHub
parent 00c88167ce
commit ae0bb4929c
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
11 changed files with 132 additions and 100 deletions

View File

@ -56,7 +56,6 @@
#include "skill.hpp"
#include "status.hpp"
#include "storage.hpp"
#include "trade.hpp"
#include "unit.hpp"
#include "vending.hpp"
@ -4646,33 +4645,27 @@ void clif_leavechat(struct chat_data* cd, map_session_data* sd, bool flag)
/// Opens a trade request window from char 'name'.
/// 00e5 <nick>.24B (ZC_REQ_EXCHANGE_ITEM)
/// 01f4 <nick>.24B <charid>.L <baselvl>.W (ZC_REQ_EXCHANGE_ITEM2)
void clif_traderequest(map_session_data* sd, const char* name)
{
int fd = sd->fd;
/// 01f4 <nick>.24B <targetid>.L <baselvl>.W (ZC_REQ_EXCHANGE_ITEM2)
void clif_traderequest(map_session_data& sd, const char* name){
#if PACKETVER < 6
WFIFOHEAD(fd,packet_len(0xe5));
WFIFOW(fd,0) = 0xe5;
safestrncpy(WFIFOCP(fd,2), name, NAME_LENGTH);
WFIFOSET(fd,packet_len(0xe5));
#else
map_session_data* tsd = map_id2sd(sd->trade_partner);
if( !tsd ) return;
PACKET_ZC_REQ_EXCHANGE_ITEM p{};
WFIFOHEAD(fd,packet_len(0x1f4));
WFIFOW(fd,0) = 0x1f4;
safestrncpy(WFIFOCP(fd,2), name, NAME_LENGTH);
WFIFOL(fd,26) = tsd->status.char_id;
WFIFOW(fd,30) = tsd->status.base_level;
WFIFOSET(fd,packet_len(0x1f4));
p.packetType = HEADER_ZC_REQ_EXCHANGE_ITEM;
safestrncpy(p.requesterName, name, sizeof(p.requesterName));
#if PACKETVER > 6
p.targetId = sd.trade_partner.id; // Client generates a random char[5] with this info
p.targetLv = sd.trade_partner.lv;
#endif
clif_send(&p,sizeof(p),&sd.bl,SELF);
}
/// Reply to a trade-request.
/// 00e7 <result>.B (ZC_ACK_EXCHANGE_ITEM)
/// 01f5 <result>.B <charid>.L <baselvl>.W (ZC_ACK_EXCHANGE_ITEM2)
/// 01f5 <result>.B <targetid>.L <baselvl>.W (ZC_ACK_EXCHANGE_ITEM2)
/// result:
/// 0 = Char is too far
/// 1 = Character does not exist
@ -4680,23 +4673,19 @@ void clif_traderequest(map_session_data* sd, const char* name)
/// 3 = Accept
/// 4 = Cancel
/// 5 = Busy
void clif_tradestart(map_session_data* sd, uint8 type)
{
int fd = sd->fd;
map_session_data* tsd = map_id2sd(sd->trade_partner);
if( PACKETVER < 6 || !tsd ) {
WFIFOHEAD(fd,packet_len(0xe7));
WFIFOW(fd,0) = 0xe7;
WFIFOB(fd,2) = type;
WFIFOSET(fd,packet_len(0xe7));
} else {
WFIFOHEAD(fd,packet_len(0x1f5));
WFIFOW(fd,0) = 0x1f5;
WFIFOB(fd,2) = type;
WFIFOL(fd,3) = tsd->status.char_id;
WFIFOW(fd,7) = tsd->status.base_level;
WFIFOSET(fd,packet_len(0x1f5));
}
void clif_traderesponse( map_session_data& sd, e_ack_trade_response result ){
PACKET_ZC_ACK_EXCHANGE_ITEM p{};
p.packetType = HEADER_ZC_ACK_EXCHANGE_ITEM;
p.result = static_cast<decltype(p.result)>( result );
#if PACKETVER > 6
p.targetId = sd.trade_partner.id; // Client generates a random char[5] with this info
p.targetLv = sd.trade_partner.lv;
#endif
clif_send(&p,sizeof(p),&sd.bl,SELF);
}
@ -12338,13 +12327,8 @@ void clif_parse_TradeRequest(int fd,map_session_data *sd)
}
if (t_sd->state.mail_writing) {
int old = sd->trade_partner;
// Fake trading
sd->trade_partner = t_sd->status.account_id;
clif_tradestart(sd, 5);
// Restore old state
sd->trade_partner = old;
clif_traderesponse(*sd,TRADE_ACK_BUSY);
return;
}
@ -16191,7 +16175,7 @@ void clif_parse_Mail_beginwrite( int fd, map_session_data *sd ){
return;
}
if( sd->state.storage_flag || sd->state.mail_writing || sd->trade_partner ){
if( sd->state.storage_flag || sd->state.mail_writing || sd->state.trading ){
clif_send_Mail_beginwrite_ack(sd, name, false);
return;
}

View File

@ -14,6 +14,7 @@
#include "packets.hpp"
#include "script.hpp"
#include "trade.hpp"
struct Channel;
struct clan;
@ -905,8 +906,8 @@ void clif_parse_LoadEndAck(int fd,map_session_data *sd);
void clif_hotkeys_send(map_session_data *sd, int tab);
// trade
void clif_traderequest(map_session_data* sd, const char* name);
void clif_tradestart(map_session_data* sd, uint8 type);
void clif_traderequest(map_session_data& sd, const char* name);
void clif_traderesponse( map_session_data& sd, e_ack_trade_response result );
void clif_tradeadditem(map_session_data* sd, map_session_data* tsd, int index, int amount);
void clif_tradeitemok(map_session_data& sd, int index, e_exitem_add_result result);
void clif_tradedeal_lock( map_session_data& sd, bool who );

View File

@ -46,7 +46,6 @@
parseable_packet(0x0094,6,clif_parse_GetCharNameRequest,2);
parseable_packet(0x0096,-1,clif_parse_WisMessage,2,4,28);
parseable_packet(0x0099,-1,clif_parse_Broadcast,2,4);
packet(0x009a,-1);
parseable_packet(0x009b,5,clif_parse_ChangeDir,2,4);
packet( HEADER_ZC_ITEM_ENTRY, sizeof( struct PACKET_ZC_ITEM_ENTRY ) );
packet(0x009e,17);
@ -100,7 +99,6 @@
parseable_packet(0x00e4,6,clif_parse_TradeRequest,2);
packet(0x00e5,26);
parseable_packet(0x00e6,3,clif_parse_TradeAck,2);
packet(0x00e7,3);
parseable_packet(0x00e8,8,clif_parse_TradeAddItem,2,4);
packet(0x00ea,5);
parseable_packet(0x00eb,2,clif_parse_TradeOk,0);
@ -300,8 +298,6 @@
packet(0x01f1,-1);
packet(0x01f2,20);
packet(0x01f3,10);
packet(0x01f4,32);
packet(0x01f5,9);
packet(0x01f6,34);
parseable_packet(0x01f7,14,clif_parse_Adopt_reply,2,6,10);
packet(0x01f8,2);

View File

@ -963,7 +963,7 @@ bool guild_invite( map_session_data& sd, map_session_data* tsd ){
}
// Checking if there no other invitation pending
if( !battle_config.invite_request_check && ( tsd->party_invite > 0 || tsd->trade_partner || tsd->adopt_invite ) ){
if( !battle_config.invite_request_check && ( tsd->party_invite > 0 || tsd->state.trading || tsd->adopt_invite ) ){
clif_guild_inviteack( sd, 0 );
return false;
}

View File

@ -362,6 +362,38 @@ struct PACKET_ZC_ACK_OPEN_BANKING{
} __attribute__((packed));
DEFINE_PACKET_HEADER(ZC_ACK_OPEN_BANKING, 0x9b7)
#if PACKETVER > 6
struct PACKET_ZC_REQ_EXCHANGE_ITEM{
uint16 packetType;
char requesterName[NAME_LENGTH];
uint32 targetId;
uint16 targetLv;
} __attribute__((packed));
DEFINE_PACKET_HEADER(ZC_REQ_EXCHANGE_ITEM, 0x1f4)
#else
struct PACKET_ZC_REQ_EXCHANGE_ITEM{
uint16 packetType;
char requesterName[NAME_LENGTH];
} __attribute__((packed));
DEFINE_PACKET_HEADER(ZC_REQ_EXCHANGE_ITEM, 0x9a)
#endif
#if PACKETVER > 6
struct PACKET_ZC_ACK_EXCHANGE_ITEM{
uint16 packetType;
uint8 result;
uint32 targetId;
uint16 targetLv;
} __attribute__((packed));
DEFINE_PACKET_HEADER(ZC_ACK_EXCHANGE_ITEM, 0x1f5)
#else
struct PACKET_ZC_ACK_EXCHANGE_ITEM{
uint16 packetType;
uint8 result;
} __attribute__((packed));
DEFINE_PACKET_HEADER(ZC_ACK_EXCHANGE_ITEM, 0xe7)
#endif
struct PACKET_ZC_ACK_ADD_EXCHANGE_ITEM {
int16 packetType;
uint16 index;

View File

@ -446,7 +446,7 @@ bool party_invite( map_session_data& sd, map_session_data *tsd ){
return false;
}
if( !battle_config.invite_request_check && ( tsd->guild_invite > 0 || tsd->trade_partner || tsd->adopt_invite ) ){
if( !battle_config.invite_request_check && ( tsd->guild_invite > 0 || tsd->state.trading || tsd->adopt_invite ) ){
clif_party_invite_reply( sd, tsd->status.name, PARTY_REPLY_JOIN_OTHER_PARTY );
return false;
}

View File

@ -706,7 +706,11 @@ public:
int united_soul[MAX_UNITED_SOULS]; // Stores the account ID's of character's who's soul is united.
int servant_sign[MAX_SERVANT_SIGN]; // Stores the account ID's of character's with a servant sign.
int trade_partner;
struct{
uint32 id;
unsigned int lv;
}trade_partner;
struct s_deal {
struct s_item {
short index, amount;

View File

@ -1192,7 +1192,7 @@ int pet_select_egg(map_session_data *sd,short egg_index)
if(egg_index < 0 || egg_index >= MAX_INVENTORY)
return 0; //Forged packet!
if(sd->trade_partner) //The player have trade in progress.
if(sd->state.trading) //The player have trade in progress.
return 0;
std::shared_ptr<s_pet_db> pet = pet_db_search(sd->inventory.u.items_inventory[egg_index].nameid, PET_EGG);

View File

@ -38,54 +38,58 @@ void trade_traderequest(map_session_data *sd, map_session_data *target_sd)
}
if (target_sd == nullptr || sd == target_sd) {
clif_tradestart(sd, 1); // character does not exist
clif_traderesponse(*sd, TRADE_ACK_CHARNOTEXIST);
return;
}
if (target_sd->npc_id) { // Trade fails if you are using an NPC.
clif_tradestart(sd, 2);
clif_traderesponse(*sd, TRADE_ACK_FAILED);
return;
}
if (!battle_config.invite_request_check) {
if (target_sd->guild_invite > 0 || target_sd->party_invite > 0 || target_sd->adopt_invite) {
clif_tradestart(sd, 2);
clif_traderesponse(*sd, TRADE_ACK_FAILED);
return;
}
}
if ( sd->trade_partner != 0 ) { // If a character tries to trade to another one then cancel the previous one
map_session_data *previous_sd = map_id2sd(sd->trade_partner);
if ( sd->trade_partner.id != 0 ) { // If a character tries to trade to another one then cancel the previous one
map_session_data *previous_sd = map_id2sd(sd->trade_partner.id);
if( previous_sd != nullptr ){
previous_sd->trade_partner = 0;
previous_sd->trade_partner = {0,0};
clif_tradecancelled( *previous_sd );
} // Once cancelled then continue to the new one.
sd->trade_partner = 0;
sd->trade_partner = {0,0};
clif_tradecancelled( *sd );
}
if (target_sd->trade_partner != 0) {
clif_tradestart(sd, 2); // person is in another trade
if (target_sd->trade_partner.id != 0) {
clif_traderesponse(*sd, TRADE_ACK_FAILED); // person is in another trade
return;
}
if (!pc_can_give_items(sd) || !pc_can_give_items(target_sd)) { // check if both GMs are allowed to trade
clif_displaymessage(sd->fd, msg_txt(sd,246));
clif_tradestart(sd, 2); // GM is not allowed to trade
clif_traderesponse(*sd, TRADE_ACK_FAILED); // GM is not allowed to trade
return;
}
// Players can not request trade from far away, unless they are allowed to use @trade.
if (!pc_can_use_command(sd, "trade", COMMAND_ATCOMMAND) &&
(sd->bl.m != target_sd->bl.m || !check_distance_bl(&sd->bl, &target_sd->bl, TRADE_DISTANCE))) {
clif_tradestart(sd, 0); // too far
clif_traderesponse(*sd, TRADE_ACK_TOOFAR);
return ;
}
target_sd->trade_partner = sd->status.account_id;
sd->trade_partner = target_sd->status.account_id;
clif_traderequest(target_sd, sd->status.name);
target_sd->trade_partner.id = sd->status.account_id;
target_sd->trade_partner.lv = sd->status.base_level;
sd->trade_partner.id = target_sd->status.account_id;
sd->trade_partner.lv = target_sd->status.base_level;
clif_traderequest(*target_sd, sd->status.name);
}
@ -107,28 +111,28 @@ void trade_tradeack(map_session_data *sd, int type)
nullpo_retv(sd);
if (sd->state.trading || !sd->trade_partner)
if (sd->state.trading || !sd->trade_partner.id)
return; // Already trading or no partner set.
if ((tsd = map_id2sd(sd->trade_partner)) == nullptr) {
clif_tradestart(sd, 1); // Character does not exist
sd->trade_partner=0;
if ((tsd = map_id2sd(sd->trade_partner.id)) == nullptr) {
clif_traderesponse(*sd, TRADE_ACK_CHARNOTEXIST);
sd->trade_partner = {0,0};
return;
}
if (tsd->state.trading || tsd->trade_partner != sd->bl.id) {
clif_tradestart(sd, 2);
sd->trade_partner=0;
if (tsd->state.trading || tsd->trade_partner.id != sd->bl.id) {
clif_traderesponse(*sd, TRADE_ACK_FAILED);
sd->trade_partner = {0,0};
return; // Already trading or wrong partner.
}
if (type == 4) { // Cancel
clif_tradestart(tsd, type);
clif_tradestart(sd, type);
clif_traderesponse(*tsd, TRADE_ACK_CANCEL);
clif_traderesponse(*sd, TRADE_ACK_CANCEL);
sd->state.deal_locked = 0;
sd->trade_partner = 0;
sd->trade_partner = {0,0};
tsd->state.deal_locked = 0;
tsd->trade_partner = 0;
tsd->trade_partner = {0,0};
return;
}
@ -139,21 +143,21 @@ void trade_tradeack(map_session_data *sd, int type)
// Check here as well since the original character could had warped.
if (!pc_can_use_command(sd, "trade", COMMAND_ATCOMMAND) &&
(sd->bl.m != tsd->bl.m || !check_distance_bl(&sd->bl, &tsd->bl, TRADE_DISTANCE))) {
clif_tradestart(sd, 0); // too far
sd->trade_partner=0;
tsd->trade_partner = 0;
clif_traderesponse(*sd, TRADE_ACK_TOOFAR);
sd->trade_partner = {0,0};
tsd->trade_partner = {0,0};
return;
}
// Check if you can start trade.
if (sd->npc_id || sd->state.vending || sd->state.buyingstore || sd->state.storage_flag ||
tsd->npc_id || tsd->state.vending || tsd->state.buyingstore || tsd->state.storage_flag) { // Fail
clif_tradestart(sd, 2);
clif_tradestart(tsd, 2);
clif_traderesponse(*sd, TRADE_ACK_FAILED);
clif_traderesponse(*tsd, TRADE_ACK_FAILED);
sd->state.deal_locked = 0;
sd->trade_partner = 0;
sd->trade_partner = {0,0};
tsd->state.deal_locked = 0;
tsd->trade_partner = 0;
tsd->trade_partner = {0,0};
return;
}
@ -162,8 +166,8 @@ void trade_tradeack(map_session_data *sd, int type)
tsd->state.trading = 1;
memset(&sd->deal, 0, sizeof(sd->deal));
memset(&tsd->deal, 0, sizeof(tsd->deal));
clif_tradestart(tsd, type);
clif_tradestart(sd, type);
clif_traderesponse(*tsd, static_cast<e_ack_trade_response>( type ));
clif_traderesponse(*sd, static_cast<e_ack_trade_response>( type ));
}
/**
@ -356,7 +360,7 @@ void trade_tradeadditem(map_session_data *sd, short index, short amount)
if( !sd->state.trading || sd->state.deal_locked > 0 )
return; // Can't add stuff.
if( (target_sd = map_id2sd(sd->trade_partner)) == nullptr ) {
if( (target_sd = map_id2sd(sd->trade_partner.id)) == nullptr ) {
trade_tradecancel(sd);
return;
}
@ -453,7 +457,7 @@ void trade_tradeaddzeny(map_session_data* sd, int amount)
if( !sd->state.trading || sd->state.deal_locked > 0 )
return; //Can't add stuff.
if( (target_sd = map_id2sd(sd->trade_partner)) == nullptr ) {
if( (target_sd = map_id2sd(sd->trade_partner.id)) == nullptr ) {
trade_tradecancel(sd);
return;
}
@ -478,7 +482,7 @@ void trade_tradeok(map_session_data *sd)
if(sd->state.deal_locked || !sd->state.trading)
return;
if ((target_sd = map_id2sd(sd->trade_partner)) == nullptr) {
if ((target_sd = map_id2sd(sd->trade_partner.id)) == nullptr) {
trade_tradecancel(sd);
return;
}
@ -500,15 +504,15 @@ void trade_tradecancel(map_session_data *sd)
nullpo_retv(sd);
target_sd = map_id2sd(sd->trade_partner);
target_sd = map_id2sd(sd->trade_partner.id);
sd->state.isBoundTrading = 0;
if(!sd->state.trading) { // Not trade accepted
if( target_sd != nullptr ) {
target_sd->trade_partner = 0;
target_sd->trade_partner = {0,0};
clif_tradecancelled( *target_sd );
}
sd->trade_partner = 0;
sd->trade_partner = {0,0};
clif_tradecancelled( *sd );
return;
}
@ -529,7 +533,7 @@ void trade_tradecancel(map_session_data *sd)
sd->state.deal_locked = 0;
sd->state.trading = 0;
sd->trade_partner = 0;
sd->trade_partner = {0,0};
clif_tradecancelled( *sd );
if (!target_sd)
@ -549,7 +553,7 @@ void trade_tradecancel(map_session_data *sd)
}
target_sd->state.deal_locked = 0;
target_sd->trade_partner = 0;
target_sd->trade_partner = {0,0};
target_sd->state.trading = 0;
clif_tradecancelled( *target_sd );
}
@ -569,7 +573,7 @@ void trade_tradecommit(map_session_data *sd)
if (!sd->state.trading || !sd->state.deal_locked) //Locked should be 1 (pressed ok) before you can press trade.
return;
if ((tsd = map_id2sd(sd->trade_partner)) == nullptr) {
if ((tsd = map_id2sd(sd->trade_partner.id)) == nullptr) {
trade_tradecancel(sd);
return;
}
@ -642,12 +646,12 @@ void trade_tradecommit(map_session_data *sd)
}
sd->state.deal_locked = 0;
sd->trade_partner = 0;
sd->trade_partner = {0,0};
sd->state.trading = 0;
sd->state.isBoundTrading = 0;
tsd->state.deal_locked = 0;
tsd->trade_partner = 0;
tsd->trade_partner = {0,0};
tsd->state.trading = 0;
tsd->state.isBoundTrading = 0;

View File

@ -4,8 +4,19 @@
#ifndef TRADE_HPP
#define TRADE_HPP
#include <common/cbasetypes.hpp>
class map_session_data;
enum e_ack_trade_response : uint8 {
TRADE_ACK_TOOFAR = 0,
TRADE_ACK_CHARNOTEXIST,
TRADE_ACK_FAILED,
TRADE_ACK_ACCEPT,
TRADE_ACK_CANCEL,
TRADE_ACK_BUSY
};
void trade_traderequest(map_session_data *sd, map_session_data *target_sd);
void trade_tradeack(map_session_data *sd,int type);
void trade_tradeadditem(map_session_data *sd,short index,short amount);

View File

@ -3239,7 +3239,7 @@ int unit_remove_map_(struct block_list *bl, clr_type clrtype, const char* file,
if(sd->chatID)
chat_leavechat(sd,0);
if(sd->trade_partner)
if(sd->trade_partner.id > 0)
trade_tradecancel(sd);
searchstore_close(*sd);