Commit 7ac932e8 authored by whenmo's avatar whenmo Committed by GitHub

add some function

parent fffcc1e1
...@@ -1650,6 +1650,7 @@ function VgF.ToTrigger(g) ...@@ -1650,6 +1650,7 @@ function VgF.ToTrigger(g)
end end
return ct return ct
end end
--[[
---将卡片(组) g Call 到单位区。返回 Call 成功的数量 ---将卡片(组) g Call 到单位区。返回 Call 成功的数量
---@param g Card|Group 要Call的卡(片组) ---@param g Card|Group 要Call的卡(片组)
---@param calltyp number Call的方式,默认填0 ---@param calltyp number Call的方式,默认填0
...@@ -1657,7 +1658,6 @@ end ...@@ -1657,7 +1658,6 @@ end
---@param zone number|nil 指示要Call到的格子。<br>前列的R:17; 后列的R:14; 全部的R:31; V:32 ---@param zone number|nil 指示要Call到的格子。<br>前列的R:17; 后列的R:14; 全部的R:31; V:32
---@param callpos number|nil 表示形式 ---@param callpos number|nil 表示形式
---@return number Call 成功的数量 ---@return number Call 成功的数量
--[[
function VgF.Call(g, calltyp, p, zone, callpos) function VgF.Call(g, calltyp, p, zone, callpos)
g = VgF.ReturnGroup(g) g = VgF.ReturnGroup(g)
if #g == 0 then return 0 end if #g == 0 then return 0 end
...@@ -1709,4 +1709,363 @@ function VgF.Call(g, calltyp, p, zone, callpos) ...@@ -1709,4 +1709,363 @@ function VgF.Call(g, calltyp, p, zone, callpos)
end end
return Duel.SpecialSummonComplete() return Duel.SpecialSummonComplete()
end end
---将底下的卡片组一起送去 loc
function VgF.GetUnderGroup(g)
local og = Group.CreateGroup()
if #g == 0 then return og end
for c in VgF.Next(g) do
og = og + c:GetOverlayGroup()
end
return og
end
---用于效果的Operation。把卡片组 g,送去 loc,第三个参数开始为额外参数,内容与原函数相同。
---@param loc number 要送去的区域。不填则返回0。
---@param g Card|Group 要操作的卡|卡片组。
---@return number 具体操作的卡的数量
function VgF.Sendto(loc, g, ...)
local ex_params = {...}
local g = VgF.ReturnGroup(g)
if #g == 0 then return 0 end
local loc_table = {}
loc_table[LOCATION_DROP ] = VgF.ToDrop
loc_table[LOCATION_DECK ] = VgF.ToDeck
loc_table[LOCATION_HAND ] = VgF.ToHand
loc_table[LOCATION_BIND ] = VgF.Bind
loc_table[LOCATION_EXILE ] = VgF.Remove
loc_table[LOCATION_SOUL ] = VgF.ToSoul
loc_table[LOCATION_TRIGGER ] = VgF.ToTrigger
loc_table[LOCATION_MZONE ] = VgF.Call
if loc_table[loc] then
return loc_table[loc](g, ...)
-- loc = LOCATION_DAMAGE, LOCATION_ORDER, LOCATION_SPARE, LOCATION_GZONE, LOCATION_EMBLEM
elseif bit.band(loc, 0xf800) > 0 or loc == 0 then
local sg = VgF.GetUnderGroup(g)
Duel.Sendto(sg, ex_params[1], loc, ex_params[2], ex_params[3], ex_params[4])
Duel.Sendto(g, ex_params[1], loc, ex_params[2], ex_params[3], ex_params[4])
return #Duel.GetOperatedGroup()
end
return 0
end
--]]
------------------------------------------
--[[
---能量爆发
---@param val number 能量爆发的数量
---@param p number 能量爆发的玩家
---@param r number 原因
---@return number 实际被操作的数量
function VgF.EnergyBlast(val, p, r)
if type(val) ~= "number" then Debug.Message("VgF.EnergyBlast param val is not number") end
local g = Duel.GetMatchingGroup(Card.IsCode, p, LOCATION_EMBLEM, 0, nil, CARD_ENERGY)
g = VgF.GetCardsFromGroup(g, val)
return VgF.Sendto(0, g, p, POS_FACEUP, r)
end
---灵魂爆发
---@param val number 灵魂爆发的数量
---@param p number 灵魂爆发的玩家
---@param r number 原因
---@return number 实际被操作的数量
function VgF.SoulBlast(val, p, r)
if type(val) ~= "number" then Debug.Message("VgF.SoulBlast param val is not number") end
Duel.Hint(HINT_SELECTMSG, p, HINTMSG_REMOVEXYZ)
local g = VgF.GetSoulGroup(p):Select(p, val, val, nil)
return VgF.ToDrop(g, r)
end
---灵魂填充
---@param val number 灵魂填充的数量
---@param p number 灵魂爆发的玩家
---@param r number 原因
---@return number 实际被操作的数量
function VgF.SoulCharge(val, p, e)
if type(val) ~= "number" then Debug.Message("VgF.SoulCharge param val is not number") end
local g = Duel.GetDecktopGroup(p, val)
Duel.DisableShuffleCheck()
Duel.RaiseEvent(g, EVENT_CUSTOM + EVENT_OVERLAY_FILL, e, 0, p, p, val)
return VgF.ToSoul(g, VgF.GetVanguard(p))
end
---计数爆发
---@param val number 计数爆发的数量
---@return number 实际被操作的数量
function VgF.CounterBlast(val, p)
if type(val) ~= "number" then Debug.Message("VgF.CounterBlast param val is not number") end
Duel.Hint(HINT_SELECTMSG, p, HINTMSG_DAMAGE)
local g = Duel.SelectMatchingCard(p, Card.IsFaceup, p, LOCATION_DAMAGE, 0, val, val, nil)
return Duel.ChangePosition(g, POS_FACEDOWN_ATTACK)
end
---计数回充
---@param val number 计数回充的数量
---@return number 实际被操作的数量
function VgF.CounterCharge(val, p)
Duel.Hint(HINT_SELECTMSG, p, HINTMSG_POSCHANGE)
local g = Duel.SelectMatchingCard(p, Card.IsFaceup, p, LOCATION_DAMAGE, 0, val, val, nil)
return Duel.ChangePosition(g, POS_FACEUP_ATTACK)
end
-- 封装的cost函数
---用于多Cost。例如 VgF.CostAnd(vgf.CounterBlast(1), vgf.Discard(1))。
function VgF.CostAnd(...)
local funcs = {...}
return function(e, tp, eg, ep, ev, re, r, rp, chk)
for _, func in ipairs(funcs) do
if func(e, tp, eg, ep, ev, re, r, rp, chk) == false then
return false
end
end
return true
end
end
---【费用】[将 xx 横置]
---@param val number|nil 要横置的卡的数量,不填为横置这张卡,99则为不限张数改用卡片组条件控制
---@param f function|nil 要横置的卡的条件
---@return function 效果的Cost函数
function VgF.CostRest(val, f)
local rest_filter = function(c)
return c:IsCanChangePosition() and c:IsPosition(POS_FACEUP_ATTACK)
end
f = f or VgF.True
if not val then
-- 将这个单位横置
return function(e, tp, eg, ep, ev, re, r, rp, chk)
local c = e:GetHandler()
if chk == 0 then return rest_filter(c) end
Duel.ChangePosition(c, POS_FACEUP_DEFENSE)
end
elseif val ~= 99 then
-- 一般条件
f = function(c, tc)
return rest_filter(c) and f(c, tc)
end
return function(e, tp, eg, ep, ev, re, r, rp, chk)
local g = Duel.GetMatchingGroup(f, tp, LOCATION_MZONE + LOCATION_ORDER, 0, nil, e:GetHandler())
if chk == 0 then return #g > 0 end
Duel.Hint(HINT_SELECTMSG, tp, HINTMSG_REST)
g = g:Select(tp, val, val, nil)
Duel.ChangePosition(g, POS_FACEUP_DEFENSE)
end
end
-- 卡片组条件 (不限张数
-- ex : 将你其他的你希望的张数的后防者横置
-- ex : 将你的卡名均不同的3张含有「焰之巫女」的后防者横置
return function(e, tp, eg, ep, ev, re, r, rp, chk)
local g = Duel.GetMatchingGroup(rest_filter, tp, LOCATION_MZONE + LOCATION_ORDER, 0, nil)
if chk == 0 then return g:CheckSubGroup(f, 1, nil, e:GetHandler()) end
Duel.Hint(HINT_SELECTMSG, tp, HINTMSG_REST)
g = g:SelectSubGroup(tp, f, false, 1, #g, e:GetHandler())
Duel.ChangePosition(g, POS_FACEUP_DEFENSE)
end
end
---【费用】[将 xx 舍弃]
---@param val number|nil 要舍弃的卡的数量。不填则为舍弃这张卡,99则为不限张数改用卡片组条件控制
---@param f function|nil 要舍弃的卡的条件
---@return function 效果的Cost函数
function VgF.CostDiscard(val, f)
if not val then
-- 将这张卡舍弃
return function(e, tp, eg, ep, ev, re, r, rp, chk)
local c=e:GetHandler()
if chk==0 then return c:IsDiscardable() end
Duel.SendtoGrave(c, REASON_DISCARD + REASON_COST)
end
elseif val ~= 99 then
-- 一般条件
f = f or VgF.True
return function(e, tp, eg, ep, ev, re, r, rp, chk)
local c = e:GetHandler()
if chk == 0 then
if e:IsHasType(EFFECT_TYPE_ACTIVATE) then
VgF.AddMixCostGroupFrom(c, "LOCATION_HAND")
VgF.AddMixCostGroupTo(c, "LOCATION_DROP")
VgF.AddMixCostGroupFilter(c, f)
VgF.AddMixCostGroupCountMin(c, val)
VgF.AddMixCostGroupCountMax(c, val)
end
return VgF.IsExistingMatchingCard(f, tp, LOCATION_HAND, 0, val, nil, c)
end
Duel.DiscardHand(tp, f, val, val, REASON_DISCARD + REASON_COST, nil, c)
end
end
-- 卡片组条件 (不限张数
-- ex : 选择你的手牌中的等级合计在3以上的至少1张卡,舍弃
return function(e, tp, eg, ep, ev, re, r, rp, chk)
local c = e:GetHandler()
local g = Duel.GetFieldGroup(tp, LOCATION_HAND, 0)
if chk == 0 then
if e:IsHasType(EFFECT_TYPE_ACTIVATE) then
VgF.AddMixCostGroupFrom(c, "LOCATION_HAND")
VgF.AddMixCostGroupTo(c, "LOCATION_DROP")
VgF.AddMixCostGroupFilter(c, f)
VgF.AddMixCostGroupCountMin(c, val)
VgF.AddMixCostGroupCountMax(c, val)
end
return g:CheckSubGroup(f, 1, nil, c)
end
Duel.Hint(HINT_SELECTMSG, tp, HINTMSG_DISCARD)
g = g:SelectSubGroup(tp, f, false, 1, #g, c)
Duel.SendtoGrave(g, REASON_DISCARD + REASON_COST)
end
end
---【费用】[将 xx 退场]
---@param val number|nil 要退场的卡的数量。不填则为将这个单位退场,99则为不限张数改用卡片组条件控制
---@param f function|nil 要退场的卡的条件
---@return function 效果的Cost函数
function VgF.CostRetire(val, f)
if type(f) == "number" then
f = function(c) return c:IsCode(f) end
end
if not val then
-- 将这个单位退场
return function(e, tp, eg, ep, ev, re, r, rp, chk)
local c = e:GetHandler()
if chk == 0 then return c:IsAbleToGraveAsCost() end
VgF.ToDrop(c, REASON_COST)
end
elseif val ~= 99 then
-- 一般条件
f = function(c, tc)
return c:IsAbleToGraveAsCost() and f(c, tc)
end
return function(e, tp, eg, ep, ev, re, r, rp, chk)
local g = Duel.GetMatchingGroup(f, tp, LOCATION_MZONE, 0, nil, e:GetHandler())
if chk == 0 then return #g > 0 end
Duel.Hint(HINT_SELECTMSG, tp, HINTMSG_LEAVEFIELD)
g = g:Select(tp, val, val, nil)
VgF.ToDrop(c, REASON_COST)
end
end
-- 卡片组条件 (不限张数
-- ex : 将你的1张以上的你希望的张数的衍生物单位退场
return function(e, tp, eg, ep, ev, re, r, rp, chk)
local g = Duel.GetMatchingGroup(Card.IsAbleToGraveAsCost, tp, LOCATION_MZONE, 0, nil)
if chk == 0 then return g:CheckSubGroup(f, 1, nil, e:GetHandler()) end
Duel.Hint(HINT_SELECTMSG, tp, HINTMSG_LEAVEFIELD)
g = g:SelectSubGroup(tp, f, false, 1, #g, e:GetHandler())
VgF.ToDrop(c, REASON_COST)
end
end
---【费用】[将 xx 封锁]
---@param val number|nil 要封锁的卡的数量。不填则为将这个单位封锁,99则为不限张数改用卡片组条件控制
---@param f function|nil 要封锁的卡的条件
---@param pos number|nil 封锁的表示形式
---@return function 效果的Cost函数
function VgF.CostBind(val, f, pos)
if type(f) == "number" then
f = function(c) return c:IsCode(f) end
end
pos = pos or POS_FACEUP
local bind_loc = LOCATION_HAND + LOCATION_MZONE + LOCATION_SOUL + LOCATION_DROP
if not val then
-- 将这个单位封锁
return function(e, tp, eg, ep, ev, re, r, rp, chk)
local c = e:GetHandler()
if chk == 0 then return c:IsAbleToBindAsCost() end
VgF.Bind(c, pos, REASON_COST)
end
elseif val ~= 99 then
-- 一般条件
f = function(c, tc)
return c:IsAbleToBindAsCost() and f(c, tc)
end
return function(e, tp, eg, ep, ev, re, r, rp, chk)
local g = Duel.GetMatchingGroup(f, tp, bind_loc, 0, nil, e:GetHandler())
if chk == 0 then return #g > 0 end
Duel.Hint(HINT_SELECTMSG, tp, HINTMSG_BIND)
g = g:Select(tp, val, val, nil)
VgF.Bind(c, pos, REASON_COST)
end
end
-- 卡片组条件 (不限张数
-- ex : 将你的灵魂里的2张以上、至多4张的卡背面封锁
-- ex : 将你的1张以上的你希望的张数的灵魂里的卡封锁
return function(e, tp, eg, ep, ev, re, r, rp, chk)
local g = Duel.GetMatchingGroup(Card.IsAbleToBindAsCost, tp, bind_loc, 0, nil, e:GetHandler())
if chk == 0 then return g:CheckSubGroup(f, 1, nil, e:GetHandler()) end
Duel.Hint(HINT_SELECTMSG, tp, HINTMSG_BIND)
g = g:SelectSubGroup(tp, f, false, 1, #g, e:GetHandler())
VgF.Bind(c, pos, REASON_COST)
end
end
---【费用】[能量爆发val]
---@param val number 能量爆发的数量
---@return function 效果的Cost函数
function VgF.CostEnergyBlast(val)
if type(val) ~= "number" then Debug.Message("VgF.CostEnergyBlast param val is not number") end
return function(e, tp, eg, ep, ev, re, r, rp, chk)
local c = e:GetHandler()
if chk == 0 then
if e:IsHasType(EFFECT_TYPE_ACTIVATE) then
VgF.AddMixCostGroupFrom(c, "LOCATION_EMBLEM")
VgF.AddMixCostGroupTo(c, "0")
VgF.AddMixCostGroupFilter(c, function(tc) tc:IsCode(CARD_ENERGY) end)
VgF.AddMixCostGroupCountMin(c, val)
VgF.AddMixCostGroupCountMax(c, val)
end
return VgF.IsExistingMatchingCard(Card.IsCode, tp, LOCATION_EMBLEM, 0, val, nil, CARD_ENERGY)
end
VgF.EnergyBlast(val, tp, REASON_COST)
end
end
---【费用】[灵魂爆发val]
---@param val number 灵魂爆发的数量
---@return function 效果的Cost函数
function VgF.CostSoulBlast(val)
if type(val) ~= "number" then Debug.Message("VgF.CostSoulBlast param val is not number") end
return function(e, tp, eg, ep, ev, re, r, rp, chk)
local c = e:GetHandler()
if chk == 0 then
if e:IsHasType(EFFECT_TYPE_ACTIVATE) then
VgF.AddMixCostGroupFrom(c, "LOCATION_OVERLAY")
VgF.AddMixCostGroupTo(c, "LOCATION_DROP")
VgF.AddMixCostGroupFilter(c, nil)
VgF.AddMixCostGroupCountMin(c, val)
VgF.AddMixCostGroupCountMax(c, val)
end
return #VgF.GetSoulGroup(tp) >= val
end
VgF.SoulBlast(val, tp, REASON_COST)
end
end
---【费用】[灵魂填充val]
---@param val number 灵魂填充的数量
---@return function 效果的Cost函数
function VgF.CostSoulCharge(val)
if type(val) ~= "number" then Debug.Message("VgF.CostSoulCharge param val is not number") end
return function(e, tp, eg, ep, ev, re, r, rp, chk)
local c = e:GetHandler()
if chk == 0 then
if e:IsHasType(EFFECT_TYPE_ACTIVATE) then
VgF.AddMixCostGroupFrom(c, "LOCATION_DECK")
VgF.AddMixCostGroupTo(c, "LOCATION_OVERLAY")
VgF.AddMixCostGroupFilter(c, nil)
VgF.AddMixCostGroupCountMin(c, val)
VgF.AddMixCostGroupCountMax(c, val)
end
return Duel.GetFieldGroupCount(tp, LOCATION_DECK, 0) >= val
end
VgF.SoulCharge(val, tp, e)
end
end
---【费用】[计数爆发val]
---@param val number 计数爆发的数量
---@return function 效果的Cost函数
function VgF.CostCounterBlast(val)
if type(val) ~= "number" then Debug.Message("VgF.CostCounterBlast param val is not number") end
return function(e, tp, eg, ep, ev, re, r, rp, chk)
local c = e:GetHandler()
if chk == 0 then
if e:IsHasType(EFFECT_TYPE_ACTIVATE) then
VgF.AddMixCostGroupFrom(c, "LOCATION_DAMAGE")
VgF.AddMixCostGroupTo(c, "POSCHANGE")
VgF.AddMixCostGroupFilter(c, Card.IsFaceup)
VgF.AddMixCostGroupCountMin(c, val)
VgF.AddMixCostGroupCountMax(c, val)
end
return VgF.IsExistingMatchingCard(Card.IsFaceup, tp, LOCATION_DAMAGE, 0, val, nil)
end
VgF.CounterCharge(val, tp)
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