Commit dc22d6cf authored by fluorohydride's avatar fluorohydride

chain activity counter

parent fbd7df74
......@@ -1411,7 +1411,7 @@ effect* field::check_unique_onfield(card* pcard, uint8 controler) {
return 0;
}
void field::CheckCounter(card* pcard, int32 counter_type, int32 playerid) {
void field::check_card_counter(card* pcard, int32 counter_type, int32 playerid) {
auto& counter_map = (counter_type == 1) ? core.summon_counter :
(counter_type == 2) ? core.normalsummon_counter :
(counter_type == 3) ? core.spsummon_counter :
......@@ -1429,6 +1429,65 @@ void field::CheckCounter(card* pcard, int32 counter_type, int32 playerid) {
}
}
}
void field::check_card_counter(card_set* pcards, int32 counter_type, int32 playerid) {
auto& counter_map = (counter_type == 1) ? core.summon_counter :
(counter_type == 2) ? core.normalsummon_counter :
(counter_type == 3) ? core.spsummon_counter :
(counter_type == 4) ? core.flipsummon_counter : core.attack_counter;
for(auto iter = counter_map.begin();iter!=counter_map.end();++iter) {
auto& info = iter->second;
if(info.first) {
for(auto piter = pcards->begin(); piter != pcards->end(); ++piter) {
pduel->lua->add_param(*piter, PARAM_TYPE_CARD);
if(!pduel->lua->check_condition(info.first, 1)) {
if(playerid == 0)
info.second += 0x1;
else
info.second += 0x10000;
break;
}
}
}
}
}
void field::check_card_counter(card_vector* pcards, int32 counter_type, int32 playerid) {
auto& counter_map = (counter_type == 1) ? core.summon_counter :
(counter_type == 2) ? core.normalsummon_counter :
(counter_type == 3) ? core.spsummon_counter :
(counter_type == 4) ? core.flipsummon_counter : core.attack_counter;
for(auto iter = counter_map.begin();iter!=counter_map.end();++iter) {
auto& info = iter->second;
if(info.first) {
for(auto piter = pcards->begin(); piter != pcards->end(); ++piter) {
pduel->lua->add_param(*piter, PARAM_TYPE_CARD);
if(!pduel->lua->check_condition(info.first, 1)) {
if(playerid == 0)
info.second += 0x1;
else
info.second += 0x10000;
break;
}
}
}
}
}
void field::check_chain_counter(effect* peffect, int32 playerid, int32 chainid) {
for(auto iter = core.chain_counter.begin();iter != core.chain_counter.end(); ++iter) {
auto& info = iter->second;
if(info.first) {
pduel->lua->add_param(peffect, PARAM_TYPE_EFFECT);
pduel->lua->add_param(playerid, PARAM_TYPE_INT);
pduel->lua->add_param(chainid, PARAM_TYPE_INT);
if(!pduel->lua->check_condition(info.first, 3)) {
if(playerid == 0)
info.second += 0x1;
else
info.second += 0x10000;
break;
}
}
}
}
int32 field::check_lp_cost(uint8 playerid, uint32 lp) {
effect_set eset;
int32 val = lp;
......
......@@ -277,6 +277,7 @@ struct processor {
std::unordered_map<uint32, std::pair<uint32, uint32> > spsummon_counter;
std::unordered_map<uint32, std::pair<uint32, uint32> > flipsummon_counter;
std::unordered_map<uint32, std::pair<uint32, uint32> > attack_counter;
std::unordered_map<uint32, std::pair<uint32, uint32> > chain_counter;
};
class field {
public:
......@@ -356,7 +357,10 @@ public:
void add_unique_card(card* pcard);
void remove_unique_card(card* pcard);
effect* check_unique_onfield(card* pcard, uint8 controler);
void CheckCounter(card* pcard, int32 counter_type, int32 playerid);
void check_card_counter(card* pcard, int32 counter_type, int32 playerid);
void check_card_counter(card_set* pcards, int32 counter_type, int32 playerid);
void check_card_counter(card_vector* pcards, int32 counter_type, int32 playerid);
void check_chain_counter(effect* peffect, int32 playerid, int32 chainid);
int32 check_lp_cost(uint8 playerid, uint32 cost);
void save_lp_cost();
......
......@@ -3138,6 +3138,14 @@ int32 scriptlib::duel_add_custom_activity_counter(lua_State *L) {
pduel->game_field->core.attack_counter[counter_id] = std::make_pair(counter_filter, 0);
break;
}
case 6: break;
case 7: {
auto iter = pduel->game_field->core.chain_counter.find(counter_id);
if(iter != pduel->game_field->core.chain_counter.end())
break;
pduel->game_field->core.chain_counter[counter_id] = std::make_pair(counter_filter, 0);
break;
}
default:
break;
}
......@@ -3181,6 +3189,14 @@ int32 scriptlib::duel_get_custom_activity_count(lua_State *L) {
val = iter->second.second;
break;
}
case 6:
break;
case 7: {
auto iter = pduel->game_field->core.chain_counter.find(counter_id);
if(iter != pduel->game_field->core.chain_counter.end())
val = iter->second.second;
break;
}
default:
break;
}
......
......@@ -1407,8 +1407,8 @@ int32 field::summon(uint16 step, uint8 sumplayer, card * target, effect * proc,
pduel->write_buffer8(target->current.position);
core.summon_state_count[sumplayer]++;
core.normalsummon_state_count[sumplayer]++;
CheckCounter(target, 1, sumplayer);
CheckCounter(target, 2, sumplayer);
check_card_counter(target, 1, sumplayer);
check_card_counter(target, 2, sumplayer);
if (target->material_cards.size()) {
for (auto mit = target->material_cards.begin(); mit != target->material_cards.end(); ++mit)
raise_single_event(*mit, 0, EVENT_BE_PRE_MATERIAL, proc, REASON_SUMMON, sumplayer, sumplayer, 0);
......@@ -1539,7 +1539,7 @@ int32 field::flip_summon(uint16 step, uint8 sumplayer, card * target) {
target->fieldid = infos.field_id++;
core.phase_action = TRUE;
core.flipsummon_state_count[sumplayer]++;
CheckCounter(target, 4, sumplayer);
check_card_counter(target, 4, sumplayer);
pduel->write_buffer8(MSG_FLIPSUMMONING);
pduel->write_buffer32(target->data.code);
pduel->write_buffer8(target->current.controler);
......@@ -1771,7 +1771,7 @@ int32 field::mset(uint16 step, uint8 setplayer, card * target, effect * proc, ui
set_control(target, setplayer, 0, 0);
core.phase_action = TRUE;
core.normalsummon_state_count[setplayer]++;
CheckCounter(target, 2, setplayer);
check_card_counter(target, 2, setplayer);
target->set_status(STATUS_SUMMON_TURN, TRUE);
pduel->write_buffer8(MSG_SET);
pduel->write_buffer32(target->data.code);
......@@ -2035,7 +2035,7 @@ int32 field::special_summon_rule(uint16 step, uint8 sumplayer, card * target) {
target->current.reason_player = sumplayer;
target->summon_player = sumplayer;
core.spsummon_state_count[sumplayer]++;
CheckCounter(target, 3, sumplayer);
check_card_counter(target, 3, sumplayer);
break_effect();
return FALSE;
}
......@@ -2184,6 +2184,7 @@ int32 field::special_summon_rule(uint16 step, uint8 sumplayer, card * target) {
if(pgroup->container.size() == 0)
return TRUE;
core.phase_action = TRUE;
check_card_counter(&pgroup->container, 3, sumplayer);
pgroup->it = pgroup->container.begin();
return FALSE;
}
......@@ -2197,7 +2198,6 @@ int32 field::special_summon_rule(uint16 step, uint8 sumplayer, card * target) {
pcard->summon_player = sumplayer;
pcard->summon_info = (peffect->get_value(pcard) & 0xff00ffff) | SUMMON_TYPE_SPECIAL | ((uint32)pcard->current.location << 16);
move_to_field(pcard, sumplayer, sumplayer, LOCATION_MZONE, POS_FACEUP);
CheckCounter(pcard, 3, sumplayer);
return FALSE;
}
case 24: {
......@@ -2342,9 +2342,6 @@ int32 field::special_summon_step(uint16 step, group * targets, card * target) {
if(!targets)
core.special_summoning.insert(target);
target->enable_field_effect(FALSE);
core.spsummon_state_count[target->summon_player]++;
CheckCounter(target, 3, target->summon_player);
core.hint_timing[target->summon_player] |= TIMING_SPSUMMON;
move_to_field(target, target->summon_player, playerid, LOCATION_MZONE, positions);
return FALSE;
}
......@@ -2369,11 +2366,32 @@ int32 field::special_summon_step(uint16 step, group * targets, card * target) {
int32 field::special_summon(uint16 step, effect * reason_effect, uint8 reason_player, group * targets) {
switch(step) {
case 0: {
card_vector cv(targets->container.begin(), targets->container.end());
if(cv.size() > 1)
std::sort(cv.begin(), cv.end(), card::card_operation_sort);
for(auto cvit = cv.begin(); cvit != cv.end(); ++cvit)
add_process(PROCESSOR_SPSUMMON_STEP, 0, 0, targets, 0, (ptr)(*cvit));
card_vector cvs, cvo;
for(auto iter = targets->container.begin(); iter != targets->container.end(); ++iter) {
auto pcard = *iter;
if(pcard->summon_player == infos.turn_player)
cvs.push_back(pcard);
else
cvo.push_back(pcard);
}
if(!cvs.empty()) {
if(cvs.size() > 1)
std::sort(cvs.begin(), cvs.end(), card::card_operation_sort);
core.spsummon_state_count[infos.turn_player]++;
check_card_counter(&cvs, 3, infos.turn_player);
core.hint_timing[infos.turn_player] |= TIMING_SPSUMMON;
for(auto cvit = cvs.begin(); cvit != cvs.end(); ++cvit)
add_process(PROCESSOR_SPSUMMON_STEP, 0, 0, targets, 0, (ptr)(*cvit));
}
if(!cvo.empty()) {
if(cvo.size() > 1)
std::sort(cvo.begin(), cvo.end(), card::card_operation_sort);
core.spsummon_state_count[1 - infos.turn_player]++;
check_card_counter(&cvo, 3, 1 - infos.turn_player);
core.hint_timing[1 - infos.turn_player] |= TIMING_SPSUMMON;
for(auto cvit = cvo.begin(); cvit != cvo.end(); ++cvit)
add_process(PROCESSOR_SPSUMMON_STEP, 0, 0, targets, 0, (ptr)(*cvit));
}
return FALSE;
}
case 1: {
......
......@@ -4045,6 +4045,8 @@ int32 field::process_turn(uint16 step, uint8 turn_player) {
iter->second.second = 0;
for(auto iter=core.attack_counter.begin();iter!=core.attack_counter.end();++iter)
iter->second.second = 0;
for(auto iter=core.chain_counter.begin();iter!=core.attack_counter.end();++iter)
iter->second.second = 0;
infos.turn_id++;
infos.turn_player = turn_player;
pduel->write_buffer8(MSG_NEW_TURN);
......@@ -4356,6 +4358,7 @@ int32 field::add_chain(uint16 step) {
if((phandler->current.location == LOCATION_HAND))
clit->flag |= CHAIN_HAND_EFFECT;
core.current_chain.push_back(*clit);
check_chain_counter(peffect, clit->triggering_controler, clit->chain_count);
// triggered events which are not caused by RaiseEvent create relation with the handler
if(!(peffect->flag & EFFECT_FLAG_FIELD_ONLY) && (!(peffect->type & 0x2a0) || (peffect->code & EVENT_PHASE) == EVENT_PHASE)) {
peffect->handler->create_relation(peffect);
......
......@@ -22,19 +22,10 @@ function c24861088.initial_effect(c)
e2:SetTarget(c24861088.sptg)
e2:SetOperation(c24861088.spop)
c:RegisterEffect(e2)
if not c24861088.global_check then
c24861088.global_check=true
local ge1=Effect.CreateEffect(c)
ge1:SetType(EFFECT_TYPE_FIELD+EFFECT_TYPE_CONTINUOUS)
ge1:SetCode(EVENT_CHAIN_SOLVED)
ge1:SetOperation(c24861088.checkop)
Duel.RegisterEffect(ge1,0)
end
Duel.AddCustomActivityCounter(24861088,ACTIVITY_CHAIN,c24861088.chainfilter)
end
function c24861088.checkop(e,tp,eg,ep,ev,re,r,rp)
if not re:GetHandler():IsSetCard(0x70) then
Duel.RegisterFlagEffect(rp,24861089,RESET_PHASE+PHASE_END,0,1)
end
function c24861088.chainfilter(re,tp,cid)
return re:GetHandler():IsSetCard(0x70)
end
function c24861088.filter(c)
return c:IsSetCard(0x70) and not c:IsCode(24861088) and c:IsAbleToHand()
......@@ -59,7 +50,7 @@ function c24861088.spcon(e,tp,eg,ep,ev,re,r,rp)
and not Duel.IsExistingMatchingCard(c24861088.cfilter,tp,LOCATION_MZONE,0,1,nil)
end
function c24861088.spcost(e,tp,eg,ep,ev,re,r,rp,chk)
if chk==0 then return Duel.GetFlagEffect(tp,24861089)==0 end
if chk==0 then return Duel.GetCustomActivityCount(24861088,tp,ACTIVITY_CHAIN)==0 end
local e1=Effect.CreateEffect(e:GetHandler())
e1:SetType(EFFECT_TYPE_FIELD)
e1:SetProperty(EFFECT_FLAG_PLAYER_TARGET)
......
--混沌帝龍 -終焉の使者-
function c82301904.initial_effect(c)
c:EnableReviveLimit()
--special summon
--cannot special summon
local e1=Effect.CreateEffect(c)
e1:SetDescription(aux.Stringid(82301904,0))
e1:SetType(EFFECT_TYPE_FIELD)
e1:SetCode(EFFECT_SPSUMMON_PROC)
e1:SetProperty(EFFECT_FLAG_UNCOPYABLE)
e1:SetRange(LOCATION_HAND)
e1:SetCondition(c82301904.spcon)
e1:SetOperation(c82301904.spop)
e1:SetProperty(EFFECT_FLAG_CANNOT_DISABLE+EFFECT_FLAG_UNCOPYABLE)
e1:SetType(EFFECT_TYPE_SINGLE)
e1:SetCode(EFFECT_SPSUMMON_CONDITION)
c:RegisterEffect(e1)
--to grave
--special summon
local e2=Effect.CreateEffect(c)
e2:SetDescription(aux.Stringid(82301904,1))
e2:SetCategory(CATEGORY_TOGRAVE+CATEGORY_DAMAGE)
e2:SetType(EFFECT_TYPE_IGNITION)
e2:SetRange(LOCATION_MZONE)
e2:SetCost(c82301904.sgcost)
e2:SetTarget(c82301904.sgtg)
e2:SetOperation(c82301904.sgop)
e2:SetDescription(aux.Stringid(82301904,0))
e2:SetType(EFFECT_TYPE_FIELD)
e2:SetCode(EFFECT_SPSUMMON_PROC)
e2:SetProperty(EFFECT_FLAG_UNCOPYABLE)
e2:SetRange(LOCATION_HAND)
e2:SetCondition(c82301904.spcon)
e2:SetOperation(c82301904.spop)
c:RegisterEffect(e2)
--to grave
local e3=Effect.CreateEffect(c)
e3:SetDescription(aux.Stringid(82301904,1))
e3:SetCategory(CATEGORY_TOGRAVE+CATEGORY_DAMAGE)
e3:SetType(EFFECT_TYPE_IGNITION)
e3:SetRange(LOCATION_MZONE)
e3:SetCost(c82301904.sgcost)
e3:SetTarget(c82301904.sgtg)
e3:SetOperation(c82301904.sgop)
c:RegisterEffect(e3)
Duel.AddCustomActivityCounter(82301904,ACTIVITY_CHAIN,aux.FALSE)
end
function c82301904.spfilter(c,att)
return c:IsAttribute(att) and c:IsAbleToRemoveAsCost()
......@@ -41,8 +48,16 @@ function c82301904.spop(e,tp,eg,ep,ev,re,r,rp,c)
Duel.Remove(g1,POS_FACEUP,REASON_COST)
end
function c82301904.sgcost(e,tp,eg,ep,ev,re,r,rp,chk)
if chk==0 then return Duel.CheckLPCost(tp,1000)
else Duel.PayLPCost(tp,1000) end
if chk==0 then return Duel.CheckLPCost(tp,1000) and Duel.GetCustomActivityCount(82301904,tp,ACTIVITY_CHAIN)==0 end
Duel.PayLPCost(tp,1000)
local e1=Effect.CreateEffect(e:GetHandler())
e1:SetType(EFFECT_TYPE_FIELD)
e1:SetProperty(EFFECT_FLAG_PLAYER_TARGET)
e1:SetCode(EFFECT_CANNOT_ACTIVATE)
e1:SetTargetRange(1,0)
e1:SetValue(aux.FALSE)
e1:SetReset(RESET_PHASE+PHASE_END)
Duel.RegisterEffect(e1,tp)
end
function c82301904.sgtg(e,tp,eg,ep,ev,re,r,rp,chk)
if chk==0 then return true end
......@@ -50,11 +65,16 @@ function c82301904.sgtg(e,tp,eg,ep,ev,re,r,rp,chk)
Duel.SetOperationInfo(0,CATEGORY_TOGRAVE,g,g:GetCount(),0,0)
Duel.SetOperationInfo(0,CATEGORY_DAMAGE,0,0,1-tp,g:GetCount()*300)
end
function c82301904.sgfilter(c,p)
return c:IsLocation(LOCATION_GRAVE) and c:IsControler(p)
end
function c82301904.sgop(e,tp,eg,ep,ev,re,r,rp)
local g=Duel.GetFieldGroup(tp,0xe,0xe)
Duel.SendtoGrave(g,REASON_EFFECT)
local og=Duel.GetOperatedGroup()
local ct=og:FilterCount(Card.IsLocation,nil,LOCATION_GRAVE)
Duel.BreakEffect()
Duel.Damage(1-tp,ct*300,REASON_EFFECT)
local ct=og:FilterCount(c82301904.sgfilter,nil,1-tp)
if ct>0 then
Duel.BreakEffect()
Duel.Damage(1-tp,ct*300,REASON_EFFECT)
end
end
......@@ -666,9 +666,10 @@ DUEL_PSEUDO_SHUFFLE =0x10 --不洗牌
DUEL_TAG_MODE =0x20 --双打
DUEL_SIMPLE_AI =0x40 --AI
--
ACTIVITY_SUMMON =1
ACTIVITY_NORMALSUMMON =2
ACTIVITY_SPSUMMON =3
ACTIVITY_FLIPSUMMON =4
ACTIVITY_ATTACK =5
ACTIVITY_BATTLE_PHASE =6
ACTIVITY_SUMMON =1 --
ACTIVITY_NORMALSUMMON =2 --
ACTIVITY_SPSUMMON =3 --
ACTIVITY_FLIPSUMMON =4 --
ACTIVITY_ATTACK =5 -- only available in custom counter
ACTIVITY_BATTLE_PHASE =6 -- not available in custom counter
ACTIVITY_CHAIN =7 -- only available in custom counter
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment