Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

add pendulum summon functions #551

Open
wants to merge 6 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
38 changes: 36 additions & 2 deletions card.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2989,7 +2989,7 @@ void card::filter_spsummon_procedure(uint8 playerid, effect_set* peset, uint32 s
}
}
}
void card::filter_spsummon_procedure_g(uint8 playerid, effect_set* peset) {
void card::filter_spsummon_procedure_g(uint8 playerid, effect_set* peset, group* mg) {
auto pr = field_effect.equal_range(EFFECT_SPSUMMON_PROC_G);
for(auto eit = pr.first; eit != pr.second;) {
effect* peffect = eit->second;
Expand All @@ -3005,7 +3005,8 @@ void card::filter_spsummon_procedure_g(uint8 playerid, effect_set* peset) {
pduel->game_field->save_lp_cost();
pduel->lua->add_param(peffect, PARAM_TYPE_EFFECT);
pduel->lua->add_param(this, PARAM_TYPE_CARD);
if(pduel->lua->check_condition(peffect->condition, 2))
pduel->lua->add_param(mg, PARAM_TYPE_GROUP);
if(pduel->lua->check_condition(peffect->condition, 3))
peset->add_item(peffect);
pduel->game_field->restore_lp_cost();
pduel->game_field->core.reason_effect = oreason;
Expand Down Expand Up @@ -3215,6 +3216,39 @@ int32 card::is_tuner(card* scard) {
return TRUE;
return FALSE;
}
int32 card::is_pendulum_summon(uint8 playerid, group* mg) {
uint32 acttype = pduel->game_field->core.summon_action_type;
pduel->game_field->core.summon_action_type = SUMMON_IN_CHAIN;
auto pr = field_effect.equal_range(EFFECT_SPSUMMON_PROC_G);
for(auto eit = pr.first; eit != pr.second;) {
effect* peffect = eit->second;
++eit;
if(!peffect->is_available() || !peffect->check_count_limit(playerid))
continue;
if(current.controler != playerid && !peffect->is_flag(EFFECT_FLAG_BOTH_SIDE))
continue;
effect* oreason = pduel->game_field->core.reason_effect;
uint8 op = pduel->game_field->core.reason_player;
pduel->game_field->core.reason_effect = peffect;
pduel->game_field->core.reason_player = this->current.controler;
pduel->game_field->save_lp_cost();
pduel->lua->add_param(peffect, PARAM_TYPE_EFFECT);
pduel->lua->add_param(this, PARAM_TYPE_CARD);
pduel->lua->add_param(mg, PARAM_TYPE_GROUP);
if(pduel->lua->check_condition(peffect->condition, 3)) {
pduel->game_field->restore_lp_cost();
pduel->game_field->core.reason_effect = oreason;
pduel->game_field->core.reason_player = op;
pduel->game_field->core.summon_action_type = acttype;
return TRUE;
}
pduel->game_field->restore_lp_cost();
pduel->game_field->core.reason_effect = oreason;
pduel->game_field->core.reason_player = op;
}
pduel->game_field->core.summon_action_type = acttype;
return FALSE;
}
int32 card::check_unique_code(card* pcard) {
if(!unique_code)
return FALSE;
Expand Down
3 changes: 2 additions & 1 deletion card.h
Original file line number Diff line number Diff line change
Expand Up @@ -322,14 +322,15 @@ class card {
int32 filter_set_procedure(uint8 playerid, effect_set* eset, uint8 ignore_count, uint8 min_tribute, uint32 zone);
int32 check_set_procedure(effect* proc, uint8 playerid, uint8 ignore_count, uint8 min_tribute, uint32 zone);
void filter_spsummon_procedure(uint8 playerid, effect_set* eset, uint32 summon_type, material_info info = null_info);
void filter_spsummon_procedure_g(uint8 playerid, effect_set* eset);
void filter_spsummon_procedure_g(uint8 playerid, effect_set* eset, group* mg);
effect* is_affected_by_effect(int32 code);
effect* is_affected_by_effect(int32 code, card* target);
int32 fusion_check(group* fusion_m, card* cg, uint32 chkf, uint8 not_material);
void fusion_select(uint8 playerid, group* fusion_m, card* cg, uint32 chkf, uint8 not_material);
int32 check_fusion_substitute(card* fcard);
int32 is_not_tuner(card* scard);
int32 is_tuner(card* scard);
int32 is_pendulum_summon(uint8 playerid, group* mg);

int32 check_unique_code(card* pcard);
void get_unique_target(card_set* cset, int32 controler, card* icard = nullptr);
Expand Down
8 changes: 8 additions & 0 deletions field.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3271,6 +3271,14 @@ int32 field::is_player_can_spsummon_count(uint8 playerid, uint32 count) {
}
return check_spsummon_counter(playerid, count);
}
int32 field::is_player_can_pendulum_summon(uint8 playerid, group* mg) {
for(uint8 p = 0; p < 2; ++p) {
for(auto& pcard : player[p].list_szone)
if(pcard && pcard->current.pzone && pcard->is_pendulum_summon(playerid, mg))
return TRUE;
}
return FALSE;
}
int32 field::is_player_can_place_counter(uint8 playerid, card * pcard, uint16 countertype, uint16 count) {
effect_set eset;
filter_player_effect(playerid, EFFECT_CANNOT_PLACE_COUNTER, &eset);
Expand Down
6 changes: 6 additions & 0 deletions field.h
Original file line number Diff line number Diff line change
Expand Up @@ -285,13 +285,15 @@ struct processor {
card* limit_link_card{ nullptr };
int32 limit_link_minc{ 0 };
int32 limit_link_maxc{ 0 };
group* limit_pendulum{ nullptr };
uint8 not_material{ FALSE };
uint8 attack_cancelable{ FALSE };
uint8 attack_rollback{ FALSE };
uint8 effect_damage_step{ 0 };
int32 battle_damage[2]{};
int32 summon_count[2]{};
uint8 extra_summon[2]{};
uint8 default_pendulum_summon[2]{};
int32 spe_effect[2]{};
int32 duel_options{ 0 };
int32 duel_rule{ CURRENT_RULE }; //current rule: 5, Master Rule 2020
Expand All @@ -304,6 +306,7 @@ struct processor {
uint8 coin_result[MAX_COIN_COUNT]{};
int32 coin_count{ 0 };
bool is_target_ready{ false };
uint32 summon_action_type{ SUMMON_IN_IDLE };

uint8 to_bp{ FALSE };
uint8 to_m2{ FALSE };
Expand Down Expand Up @@ -484,6 +487,7 @@ class field {
int32 is_player_can_flipsummon(uint8 playerid, card* pcard);
int32 is_player_can_spsummon_monster(uint8 playerid, uint8 toplayer, uint8 sumpos, uint32 sumtype, card_data* pdata);
int32 is_player_can_spsummon_count(uint8 playerid, uint32 count);
int32 is_player_can_pendulum_summon(uint8 playerid, group* mg);
int32 is_player_can_release(uint8 playerid, card* pcard, uint32 reason);
int32 is_player_can_place_counter(uint8 playerid, card* pcard, uint16 countertype, uint16 count);
int32 is_player_can_remove_counter(uint8 playerid, card* pcard, uint8 s, uint8 o, uint16 countertype, uint16 count, uint32 reason);
Expand Down Expand Up @@ -594,6 +598,7 @@ class field {
int32 sset_g(uint16 step, uint8 setplayer, uint8 toplayer, group* ptarget, uint8 confirm, effect* reason_effect);
int32 special_summon_step(uint16 step, group* targets, card* target, uint32 zone);
int32 special_summon(uint16 step, effect* reason_effect, uint8 reason_player, group* targets, uint32 zone);
int32 pendulum_summon(uint16 step, uint8 playerid, group* mg);
int32 destroy_replace(uint16 step, group* targets, card* target, uint8 battle);
int32 destroy(uint16 step, group* targets, effect* reason_effect, uint32 reason, uint8 reason_player);
int32 release_replace(uint16 step, group* targets, card* target);
Expand Down Expand Up @@ -763,6 +768,7 @@ class field {
#define PROCESSOR_SSET 65
#define PROCESSOR_SPSUMMON_STEP 66
#define PROCESSOR_SSET_G 67
#define PROCESSOR_PENDULUM_SUMMON 68
#define PROCESSOR_DRAW 70
#define PROCESSOR_DAMAGE 71 //arg1: arguments, arg2: arguments, arg3: arguments
#define PROCESSOR_RECOVER 72 //arg1: arguments, arg2: arguments, arg3: arguments
Expand Down
72 changes: 72 additions & 0 deletions libduel.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -422,6 +422,25 @@ int32 scriptlib::duel_xyz_summon(lua_State *L) {
}
return lua_yield(L, 0);
}
int32 scriptlib::duel_pendulum_summon(lua_State *L) {
check_action_permission(L);
check_param_count(L, 2);
uint32 playerid = (uint32)lua_tointeger(L, 1);
if(playerid != 0 && playerid != 1)
return 0;
duel* pduel = interpreter::get_duel_info(L);
if(pduel->game_field->core.effect_damage_step)
return 0;
group* pendulum_group = nullptr;
if(!lua_isnil(L, 2)) {
check_param(L, PARAM_TYPE_GROUP, 2);
group* pgroup = *(group**)lua_touserdata(L, 2);
pendulum_group = pduel->new_group(pgroup->container);
pendulum_group->is_readonly = 1;
}
pduel->game_field->add_process(PROCESSOR_PENDULUM_SUMMON, 0, nullptr, pendulum_group, playerid, 0);
return lua_yield(L, 0);
}
int32 scriptlib::duel_link_summon(lua_State *L) {
check_action_permission(L);
check_param_count(L, 3);
Expand Down Expand Up @@ -3630,6 +3649,24 @@ int32 scriptlib::duel_remove_overlay_card(lua_State *L) {
return 1;
});
}
int32 scriptlib::duel_use_default_pendulum_summon(lua_State *L) {
check_action_permission(L);
check_param_count(L, 1);
int32 playerid = (int32)lua_tointeger(L, 1);
if(playerid != 0 && playerid != 1)
return 0;
duel* pduel = interpreter::get_duel_info(L);
pduel->game_field->core.default_pendulum_summon[playerid] = TRUE;
return 0;
}
int32 scriptlib::duel_is_summon_in_chain(lua_State *L) {
duel* pduel = interpreter::get_duel_info(L);
if(pduel->game_field->core.summon_action_type == SUMMON_IN_CHAIN)
lua_pushboolean(L, 1);
else
lua_pushboolean(L, 0);
return 1;
}
int32 scriptlib::duel_hint(lua_State * L) {
check_param_count(L, 3);
int32 htype = (int32)lua_tointeger(L, 1);
Expand Down Expand Up @@ -4347,6 +4384,22 @@ int32 scriptlib::duel_is_player_can_spsummon_count(lua_State * L) {
lua_pushboolean(L, pduel->game_field->is_player_can_spsummon_count(playerid, count));
return 1;
}
int32 scriptlib::duel_is_player_can_pendulum_summon(lua_State * L) {
check_param_count(L, 1);
int32 playerid = (int32)lua_tointeger(L, 1);
if(playerid != 0 && playerid != 1) {
lua_pushboolean(L, 0);
return 1;
}
group* mg = nullptr;
if(lua_gettop(L) >= 2 && !lua_isnil(L, 2)) {
check_param(L, PARAM_TYPE_GROUP, 2);
mg = *(group**) lua_touserdata(L, 2);
}
duel* pduel = interpreter::get_duel_info(L);
lua_pushboolean(L, pduel->game_field->is_player_can_pendulum_summon(playerid, mg));
return 1;
}
int32 scriptlib::duel_is_player_can_release(lua_State * L) {
check_param_count(L, 1);
int32 playerid = (int32)lua_tointeger(L, 1);
Expand Down Expand Up @@ -4457,6 +4510,20 @@ int32 scriptlib::duel_is_player_can_additional_summon(lua_State * L) {
lua_pushboolean(L, 0);
return 1;
}
int32 scriptlib::duel_is_player_default_pendulum_summoned(lua_State * L) {
check_param_count(L, 1);
int32 playerid = (int32)lua_tointeger(L, 1);
if(playerid != 0 && playerid != 1) {
lua_pushboolean(L, 0);
return 1;
}
duel* pduel = interpreter::get_duel_info(L);
if(pduel->game_field->core.default_pendulum_summon[playerid])
lua_pushboolean(L, 1);
else
lua_pushboolean(L, 0);
return 1;
}
int32 scriptlib::duel_is_chain_negatable(lua_State * L) {
check_param_count(L, 1);
lua_pushboolean(L, 1);
Expand Down Expand Up @@ -4745,6 +4812,7 @@ static const struct luaL_Reg duellib[] = {
{ "SpecialSummonRule", scriptlib::duel_special_summon_rule },
{ "SynchroSummon", scriptlib::duel_synchro_summon },
{ "XyzSummon", scriptlib::duel_xyz_summon },
{ "PendulumSummon", scriptlib::duel_pendulum_summon },
{ "LinkSummon", scriptlib::duel_link_summon },
{ "MSet", scriptlib::duel_setm },
{ "SSet", scriptlib::duel_sets },
Expand Down Expand Up @@ -4893,6 +4961,8 @@ static const struct luaL_Reg duellib[] = {
{ "GetOverlayCount", scriptlib::duel_get_overlay_count },
{ "CheckRemoveOverlayCard", scriptlib::duel_check_remove_overlay_card },
{ "RemoveOverlayCard", scriptlib::duel_remove_overlay_card },
{ "UseDefaultPendulumSummon", scriptlib::duel_use_default_pendulum_summon },
{ "IsSummonInChain", scriptlib::duel_is_summon_in_chain },
{ "Hint", scriptlib::duel_hint },
{ "HintSelection", scriptlib::duel_hint_selection },
{ "SelectEffectYesNo", scriptlib::duel_select_effect_yesno },
Expand Down Expand Up @@ -4927,12 +4997,14 @@ static const struct luaL_Reg duellib[] = {
{ "IsPlayerCanFlipSummon", scriptlib::duel_is_player_can_flipsummon },
{ "IsPlayerCanSpecialSummonMonster", scriptlib::duel_is_player_can_spsummon_monster },
{ "IsPlayerCanSpecialSummonCount", scriptlib::duel_is_player_can_spsummon_count },
{ "IsPlayerCanPendulumSummon", scriptlib::duel_is_player_can_pendulum_summon },
{ "IsPlayerCanRelease", scriptlib::duel_is_player_can_release },
{ "IsPlayerCanRemove", scriptlib::duel_is_player_can_remove },
{ "IsPlayerCanSendtoHand", scriptlib::duel_is_player_can_send_to_hand },
{ "IsPlayerCanSendtoGrave", scriptlib::duel_is_player_can_send_to_grave },
{ "IsPlayerCanSendtoDeck", scriptlib::duel_is_player_can_send_to_deck },
{ "IsPlayerCanAdditionalSummon", scriptlib::duel_is_player_can_additional_summon },
{ "IsPlayerDefaultPendulumSummoned", scriptlib::duel_is_player_default_pendulum_summoned },
{ "IsChainNegatable", scriptlib::duel_is_chain_negatable },
{ "IsChainDisablable", scriptlib::duel_is_chain_disablable },
{ "IsChainDisabled", scriptlib::duel_is_chain_disabled },
Expand Down
Loading