Commit 2ecb3ab8 authored by Vury Leo's avatar Vury Leo

tuning 白の枢機竜

parent 70ab2010
......@@ -30,7 +30,7 @@ function s.initial_effect(c)
end,
})
},
mat_filter=s.mat_filter,
matfilter=s.matfilter,
fgoalcheck=s.fgoalcheck,
})
--material limit
......@@ -96,7 +96,7 @@ function s.fgoalcheck(mg)
return hand>=1 and field>=1
end
function s.mat_filter(mc,tc)
function s.matfilter(mc,tc)
return mc:IsLocation(LOCATION_HAND) or mc:IsControler(tc:GetControler()) and mc:IsOnField()
end
......
......@@ -2,13 +2,31 @@
local s,id,o=GetID()
function s.initial_effect(c)
c:EnableReviveLimit()
-- aux.AddFusionProcFunRep(c,s.ffilter,2,true)
Fusion.AddFusionProcedure(c,{
slots={
Fusion.Slot.Group({
min=2,
max=2,
unique_by=function(mc) return { mc:GetCode(),mc:GetFusionCode() } end,
--- @param mc Card
unique_by=function(mc)
local function dedup_represent(code)
if code==78734254 then
return 17955766
elseif code==13857930 then
return 17732278
end
return code
end
local code=dedup_represent(mc:GetCode())
local res={code}
--- Add Fusion Tag names
for _,eff in ipairs({mc:IsHasEffect(EFFECT_ADD_FUSION_CODE)}) do
local fusion_tag_code=eff:GetValue()
assert(type(fusion_tag_code)=='number')
table.insert(res,dedup_represent(fusion_tag_code))
end
return res
end,
has_same={
function(mc,tc) return mc:GetFusionAttribute(tc:GetOwner()) end,
function(mc) return mc:GetRace() end,
......@@ -34,14 +52,6 @@ function s.initial_effect(c)
e2:SetOperation(s.operation)
c:RegisterEffect(e2)
end
function s.matchfilter(c,attr,race)
return c:IsFusionAttribute(attr) and c:IsRace(race)
end
function s.ffilter(c,fc,sub,mg,sg)
return not sg or sg:FilterCount(aux.TRUE,c)==0
or (sg:IsExists(s.matchfilter,#sg-1,c,c:GetFusionAttribute(),c:GetRace())
and not sg:IsExists(Card.IsFusionCode,1,c,c:GetFusionCode()))
end
function s.target(e,tp,eg,ep,ev,re,r,rp,chk)
if chk==0 then return Duel.IsPlayerCanDraw(tp,1) end
Duel.SetTargetPlayer(tp)
......
......@@ -3475,14 +3475,14 @@ function Fusion.AddFusionProcedure(c, opts)
end
---@param allow_extras boolean whether to allow extra materials for checking propose
function Fusion.BasicCondition(tc,slots,mat_filter,fgoalcheck,allow_extras,selected)
function Fusion.BasicCondition(tc,slots,matfilter,fgoalcheck,allow_extras,selected)
return function(e,g,gc,chkf)
if not g then return false end
-- Collect cards and apply global mat_filter
-- Collect cards and apply global matfilter
local cards={}
for c in aux.Next(g) do
if not mat_filter or mat_filter(c,tc) then
if not matfilter or matfilter(c,tc) then
table.insert(cards,c)
end
end
......@@ -3506,7 +3506,7 @@ function Fusion.BasicCondition(tc,slots,mat_filter,fgoalcheck,allow_extras,selec
end
-- Prepare locked flags for substitute materials
local locked = {}
local locked={}
if Fusion.LockedCodes then
for _, code in ipairs(Fusion.LockedCodes) do
for i,slot in ipairs(single_slots) do
......@@ -3531,7 +3531,7 @@ function Fusion.BasicCondition(tc,slots,mat_filter,fgoalcheck,allow_extras,selec
end
end
-- 5) DFS assign single‐slots
-- DFS assign single‐slots
local used={}
local sub_count=0
local function dfs_singles(i)
......@@ -3630,13 +3630,15 @@ function Fusion.StrictGroup(e,leftovers,mg_base,grp,tc,fgoalcheck,chkf)
return false
end
-- has_same on full matched
if grp.has_same and not Fusion.CheckHasSame(grp,Group.FromCards(table.unpack(matched)),e) then
if grp.has_same and not Fusion.CheckHasSame(grp,matched,e) then
Debug.Message("rejected by has_same")
return false
end
-- unique_by on full matched
if grp.unique_by then
local matcher=Fusion.UniqueByMatching(grp.unique_by,#matched)
if not matcher(matched) then
Debug.Message("rejected by unique_by")
return false
end
end
......@@ -3655,6 +3657,7 @@ function Fusion.SearchGroup(e,leftovers,mg_base,grp,tc,fgoalcheck,chkf)
table.insert(matched,c)
end
end
if #matched<grp.min then
return false
end
......@@ -3666,24 +3669,25 @@ function Fusion.SearchGroup(e,leftovers,mg_base,grp,tc,fgoalcheck,chkf)
return false
end
end
local comb={}
local function dfs(start,depth)
-- If we have at least grp.min cards, test this subset immediately
if depth>=grp.min then
-- build subset group and merged material group
local subG=Group.FromCards(table.unpack(comb,1,depth))
local sub_g_arr={table.unpack(comb,1,depth)}
local subG=Group.FromCards(table.unpack(sub_g_arr))
local mg_tmp=mg_base:Clone()
mg_tmp:Merge(subG)
-- has_same check
local ok_same=not grp.has_same or Fusion.CheckHasSame(grp,subG,e)
local ok_same=not grp.has_same or Fusion.CheckHasSame(grp,sub_g_arr,e)
-- unique_by check
local ok_unique=true
if grp.unique_by then
local matcher=Fusion.UniqueByMatching(grp.unique_by,depth)
ok_unique=matcher(comb)
local matcher=Fusion.UniqueByMatching(grp.unique_by,#sub_g_arr)
ok_unique=matcher(sub_g_arr)
end
-- final fusion checks
if ok_same and ok_unique and Fusion.FinalCheck(e,mg_tmp,tc,fgoalcheck,chkf) then
......@@ -3718,9 +3722,7 @@ end
-- Shared has_same checker (bitmask or key‐list)
function Fusion.CheckHasSame(grp,group_obj,e)
local cards={}
for c in aux.Next(group_obj) do table.insert(cards,c) end
function Fusion.CheckHasSame(grp,cards,e)
for _,fn in ipairs(grp.has_same) do
local v0=fn(cards[1],e:GetHandler())
if type(v0)=="number" then
......@@ -4001,7 +4003,7 @@ end
--- @param slots table[] your slot definitions
--- @param tc Card the Fusion monster (for substitutes)
--- @return boolean true if ∃ a mapping + completion path
function Fusion.CanCompleteFromMappings(e,sel,eg,slots,mat_filter,fgoalcheck,tc,gc,chkf)
function Fusion.CanCompleteFromMappings(e,sel,eg,slots,matfilter,fgoalcheck,tc,gc,chkf)
-- arrayify sel so we can refer by index
local cards_sel={}
for c in aux.Next(sel) do
......@@ -4071,23 +4073,23 @@ function Fusion.CanCompleteFromMappings(e,sel,eg,slots,mat_filter,fgoalcheck,tc,
for i,slot in ipairs(slots) do
if slot.group then
local need=group_need[i] or 0
-- if this slot has a unique_by, wrap its filter to exclude collided keys
local new_filter=slot.group.filter
if slot.group.unique_by then
local used_keys=Fusion.ExtractUsedKeys(cards_sel,mapping,i,slot.group.unique_by)
new_filter=Fusion.MakeExcludeFilter(new_filter,slot.group.unique_by,used_keys)
-- only if there is at least one already‐selected card for this slot…
local has_sel=false
for _,mapped_i in pairs(mapping) do
if mapped_i==i then
has_sel=true
break
end
end
-- if this slot has a has_same, wrap its filter to include only sames
if slot.group.has_same then
-- only if there is at least one already‐selected card for this slot…
local has_sel=false
for _,mapped_i in pairs(mapping) do
if mapped_i==i then
has_sel=true
break
end
if has_sel then
-- if this slot has a unique_by, wrap its filter to exclude collided keys
if slot.group.unique_by then
local used_keys=Fusion.ExtractUsedKeys(cards_sel,mapping,i,slot.group.unique_by)
new_filter=Fusion.MakeExcludeFilter(new_filter,slot.group.unique_by,used_keys)
end
if has_sel then
-- if this slot has a has_same, wrap its filter to include only sames
if slot.group.has_same then
-- precompute, for each fn in has_same, the overlap of already-mapped cards
local used_overlap={} -- fn → (number mask) or (table of keys)
for _,fn in ipairs(slot.group.has_same) do
......@@ -4152,8 +4154,8 @@ function Fusion.CanCompleteFromMappings(e,sel,eg,slots,mat_filter,fgoalcheck,tc,
min=need,
max=slot.group.max-slot.group.min+need,
filter=new_filter,
unique_by=slot.unique_by,
has_same=slot.has_same,
unique_by=slot.group.unique_by,
has_same=slot.group.has_same,
}
})
end
......@@ -4177,7 +4179,7 @@ function Fusion.CanCompleteFromMappings(e,sel,eg,slots,mat_filter,fgoalcheck,tc,
end
-- delegate to FusionCondition (allow_extras=true)
local search_cond=Fusion.BasicCondition(tc,rem_slots,mat_filter,fgoalcheck,true,sel)
local search_cond=Fusion.BasicCondition(tc,rem_slots,matfilter,fgoalcheck,true,sel)
if search_cond(e,rem_pool,gc,chkf) then
Fusion.LockedCodes=old_locked
return true
......@@ -4215,7 +4217,6 @@ function Fusion.UniqueByMatching(key_func,min_needed)
table.insert(card_keys[idx],id)
end
end
-- quick reject if fewer distinct keys exist than needed
if next_key_id<min_needed then
return false
......@@ -4300,14 +4301,14 @@ function Fusion.BuildPatterns(opts)
for _, v in ipairs(opts.variants) do
table.insert(patterns,{
slots=v.slots,
mat_filter=v.mat_filter,
matfilter=v.matfilter,
fgoalcheck=v.fgoalcheck or aux.TRUE,
})
end
else
table.insert(patterns,{
slots=opts.slots,
mat_filter=opts.mat_filter,
matfilter=opts.matfilter,
fgoalcheck=opts.fgoalcheck or aux.TRUE,
})
end
......@@ -4331,7 +4332,7 @@ function Fusion.MultiCondition(tc,patterns,allow_extras)
end
end
if ok then
local cond=Fusion.BasicCondition(tc,pat.slots,pat.mat_filter,pat.fgoalcheck,allow_extras,selected)
local cond=Fusion.BasicCondition(tc,pat.slots,pat.matfilter,pat.fgoalcheck,allow_extras,selected)
if cond(e,g,gc,chkf) then
return true
end
......@@ -4409,7 +4410,7 @@ function Fusion.MultiOperation(tc,patterns)
sg:AddCard(mc)
-- completion test against active patterns
for _,pat in ipairs(active_patterns) do
if Fusion.CanCompleteFromMappings(e,sg,eg,pat.slots,pat.mat_filter,pat.fgoalcheck,tc,gc,chkf) then
if Fusion.CanCompleteFromMappings(e,sg,eg,pat.slots,pat.matfilter,pat.fgoalcheck,tc,gc,chkf) then
addable:AddCard(mc)
break
end
......@@ -4480,11 +4481,11 @@ function Fusion.FusionCondition(tc,patterns)
-- attempt “search mode” on each pattern
for _,pat in ipairs(patterns) do
if Fusion.CanCompleteFromMappings(e,selected,g,pat.slots,pat.mat_filter,pat.fgoalcheck or aux.TRUE,tc,gc,chkf)
then
if Fusion.CanCompleteFromMappings(e,selected,g,pat.slots,pat.matfilter,pat.fgoalcheck or aux.TRUE,tc,gc,chkf) then
return true
end
end
return false
end
end
......
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