c1_lua/lua/app/global/global_func.lua

1777 lines
45 KiB
Lua
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

local GFunc = {}
local EMPTY_TABLE = {}
local HASH_SEED = 31
local UINT_RANGE = 4294967296
local byte = string.byte
local DESIGN_RESOLUTION_WIDTH = CS.BF.GameConst.DESIGN_RESOLUTION_WIDTH
local DESIGN_RESOLUTION_HEIGHT = CS.BF.GameConst.DESIGN_RESOLUTION_HEIGHT
local UnityTime = CS.UnityEngine.Time
--获取unicode 字符串长度 和utf-8长度
function GFunc.getTextLen(str)
local byteLen = #str
local strLen = 0
local i = 1
local curByte
local byteCount = 1
while i <= byteLen do
curByte = byte(str, i)
byteCount = 1
if curByte > 0 and curByte <= 127 then
byteCount = 1
elseif curByte >= 192 and curByte < 223 then
byteCount = 2
elseif curByte >= 224 and curByte < 239 then
byteCount = 3
elseif curByte >= 240 and curByte <= 247 then
byteCount = 4
end
i = i + byteCount
strLen = strLen + 1
end
return strLen, i - 1
end
function GFunc.getTextLen2(str)
local byteLen = #str
local strLen = 0
local i = 1
local curByte
local byteCount = 1
while i <= byteLen do
curByte = byte(str, i)
byteCount = 1
if curByte > 0 and curByte <= 127 then
byteCount = 1
strLen = strLen + 1
elseif curByte >= 192 and curByte < 223 then
-- 中文算2个字节
byteCount = 2
strLen = strLen + 1
elseif curByte >= 224 and curByte < 239 then
byteCount = 3
strLen = strLen + 2
elseif curByte >= 240 and curByte <= 247 then
byteCount = 4
strLen = strLen + 1
end
i = i + byteCount
end
return strLen, i - 1
end
-- 判断字符串是不是全部都是空格,32是半角空格227是全角空格
function GFunc.getIsAllSpaceStr(str)
local result = true
local byteLen = #str
local i = 1
local curByte
local byteCount = 1
while i <= byteLen do
curByte = byte(str, i)
byteCount = 1
if curByte > 0 and curByte <= 127 then
byteCount = 1
if curByte ~= 32 then
result = false
break
end
elseif curByte >= 192 and curByte < 223 then
byteCount = 2
result = false
break
elseif curByte >= 224 and curByte < 239 then
byteCount = 3
if curByte ~= 227 then
result = false
break
end
elseif curByte >= 240 and curByte <= 247 then
byteCount = 4
result = false
break
else
result = false
break
end
i = i + byteCount
end
return result
end
function GFunc.num2Str(count, dec)
if count >= 99999999999 then -- 前端限制最大显示99999M
if dec then
return "99999.99M"
else
return "99999M"
end
elseif count >= 10000000 then
if dec then
count = math.floor((count*10^dec)/1000000)/(10^dec)
return count .. "M"
else
count = count // 1000000
return count .. "M"
end
elseif count >= 100000 then
if dec then
count = math.floor((count*10^dec)/1000)/(10^dec)
return count .. "K"
else
count = count // 1000
return count .. "K"
end
else
return GFunc.parseDedundantNumber(count)
end
end
-- 超过千位就缩写,目前只有公会奖励用到 1K-5K
function GFunc.num2Str2(count, dec)
if count >= 99999999999 then -- 前端限制最大显示99999M
if dec then
return "99999.99M"
else
return "99999M"
end
elseif count >= 1000000 then
if dec then
count = math.floor((count*10^dec)/1000000)/(10^dec)
return count .. "M"
else
count = count // 1000000
return count .. "M"
end
elseif count >= 1000 then
if dec then
count = math.floor((count*10^dec)/1000)/(10^dec)
return count .. "K"
else
count = count // 1000
return count .. "K"
end
else
return GFunc.parseDedundantNumber(count)
end
end
-- 与num2Str类似 但是上限扩大3位至99999B
function GFunc.num2Str3(count, dec)
if count >= 99999999999999 then -- 前端限制最大显示99999B
if dec then
return "99999.99B"
else
return "99999B"
end
elseif count >= 10000000000 then
if dec then
count = math.floor((count*10^dec)/1000000000)/(10^dec)
return count .. "B"
else
count = count // 1000000000
return count .. "B"
end
elseif count >= 10000000 then
if dec then
count = math.floor((count*10^dec)/1000000)/(10^dec)
return count .. "M"
else
count = count // 1000000
return count .. "M"
end
elseif count >= 100000 then
if dec then
count = math.floor((count*10^dec)/1000)/(10^dec)
return count .. "K"
else
count = count // 1000
return count .. "K"
end
else
return GFunc.parseDedundantNumber(count)
end
end
function GFunc.killDOTween(id, complete)
if complete == nil then
return CS.BF.Utils.KillDOTween(id)
else
return CS.BF.Utils.KillDOTween(id, complete)
end
end
function GFunc.setDOTweenTimeScale(id, timeScale)
CS.BF.Utils.SetDOTweenTimeScale(id, timeScale)
end
function GFunc.nameToLayer(name)
return CS.BF.Utils.NameToLayer(name)
end
-- BKDRHash
function GFunc.hash(str)
local h = 0
for i = 1, #str do
h = h * HASH_SEED + byte(str, i)
end
return h%UINT_RANGE
end
function GFunc.getScreenSize()
return CS.UnityEngine.Screen.width, CS.UnityEngine.Screen.height
end
function GFunc.parseDedundantNumber(num)
if num % 1 == 0 then
return math.ceil(num)
else
return num
end
end
function GFunc.openUrl(web)
CS.UnityEngine.Application.OpenURL(web)
end
function GFunc.getShader(shaderName)
return CS.UnityEngine.Shader.Find(shaderName)
end
function GFunc.subStringGetByteCount(str, index)
local curByte = byte(str, index)
local byteCount = 1
if curByte == nil then
byteCount = 0
elseif curByte > 240 then
byteCount = 4
elseif curByte > 225 then
byteCount = 3
elseif curByte > 192 then
byteCount = 2
end
return byteCount
end
function GFunc.subStringByCharCount(str, needCount)
local index = 1
local lastIndex = 1
local num = 0
while num < needCount and lastIndex ~= 0 do
lastIndex = GFunc.subStringGetByteCount(str, index)
index = index + lastIndex
num = num + 1
end
return string.sub(str,1, index - 1)
end
function GFunc.setLayer(gameObject, layerName)
local trans = gameObject.transform:GetComponentsInChildren(typeof(CS.UnityEngine.Transform))
local layer = GFunc.nameToLayer(layerName)
if trans then
local len = trans.Length
for i = 0, len - 1 do
trans[i].gameObject.layer = layer
end
end
end
-- 根据当前屏幕分辨率 计算偏差值
function GFunc.calculateFitSizeY()
local width, height = GFunc.getScreenSize()
local dif = 0
if width / height < DESIGN_RESOLUTION_WIDTH / DESIGN_RESOLUTION_HEIGHT then
dif = height / (width / DESIGN_RESOLUTION_WIDTH) - DESIGN_RESOLUTION_HEIGHT
end
return dif
end
-- 获得Expand模式下UI分辨率
function GFunc.getUIExpandScreenSize()
local width, height = GFunc.getScreenSize()
if width / height <= DESIGN_RESOLUTION_WIDTH / DESIGN_RESOLUTION_HEIGHT then
height = height * (DESIGN_RESOLUTION_WIDTH / width)
width = DESIGN_RESOLUTION_WIDTH
else
width = width * (DESIGN_RESOLUTION_HEIGHT / height)
height = DESIGN_RESOLUTION_HEIGHT
end
return width, height
end
function GFunc.checkNameValid(str, min, max)
local result = nil
if str == nil or str == "" then
--输入不能为空
return false
else
result = string.match(str, "/u{0020}") or string.match(str, "/u{3000}") or string.match(str, "/u{00A0}")
end
if result then
--非法字符
return false
end
local k, length = GFunc.getTextLen(str)
if length < min then
return false
elseif length > max then
return false
end
return true
end
function GFunc.showMessageBox(params)
local MessageBox = require "app/ui/common/message_box"
MessageBox:showMessageBox(params)
end
function GFunc.showCheatingBox(params)
local CheatMessageBox = require "app/ui/common/cheat_message_box"
CheatMessageBox:showCheatMessageBox(params)
end
function GFunc.hideCheatingBox()
local CheatMessageBox = require "app/ui/common/cheat_message_box"
CheatMessageBox:hideCheatMessageBox()
end
function GFunc.showToast(tab)
ModuleManager.ToastManager:showToast(tab)
end
function GFunc.UiRectTransformScreenPointToLocalPointInRectangle(go, x, y)
local uiCamera = UIManager:getUICameraComponent()
local anchoredPosition = CS.BF.Utils.RectTransformScreenPointToLocalPointInRectangle(go:getTransform(),
x, y, uiCamera)
return anchoredPosition
end
function GFunc.UiRectangleContainsScreenPoint(go, x, y)
local uiCamera = UIManager:getUICameraComponent()
return CS.BF.Utils.RectangleContainsScreenPoint(go:getTransform(), x, y, uiCamera)
end
function GFunc.getPerByW(ratio)
if ratio < 0 then
return math.ceil(ratio*0.01)
else
return math.floor(ratio*0.01)
end
end
function GFunc.getPerByW2(ratio)
if ratio < 0 then
return math.ceil(ratio*0.0001)
else
return math.floor(ratio*0.0001)
end
end
function GFunc.getPerByW3(ratio)
return ratio*0.0001
end
-- function GFunc.getRoundingNumByW(num)
-- if num <= 0 then
-- return 0
-- end
-- if num < 10000 then
-- return GFunc.getRoundingNumByW(num*100) // 100
-- end
-- local remainder = num%10000
-- if remainder < 5000 then
-- return num - remainder
-- elseif remainder > 5000 then
-- return num - remainder + 10000
-- else
-- local integer = (num - remainder)*0.0001
-- if integer%2 == 0 then
-- return num - remainder
-- else
-- return num - remainder + 10000
-- end
-- end
-- end
function GFunc.getPerStr(key, str)
if key == GConst.ATTR_TYPE.crit or
key == GConst.ATTR_TYPE.crit_time or
-- key == GConst.ATTR_TYPE.atk_range or
key == GConst.ATTR_TYPE.atkp_1 or
key == GConst.ATTR_TYPE.atkp_2 or
key == GConst.ATTR_TYPE.atkp_3 or
key == GConst.ATTR_TYPE.atkp_4 or
key == GConst.ATTR_TYPE.atkp_5 or
key == GConst.ATTR_TYPE.atkp_6 or
key == GConst.ATTR_TYPE.atkp_7 or
key == GConst.ATTR_TYPE.atkp_8 or
key == GConst.ATTR_TYPE.atkp_9 or
key == GConst.ATTR_TYPE.hpp_1 or
key == GConst.ATTR_TYPE.hpp_2 or
key == GConst.ATTR_TYPE.hpp_3 or
key == GConst.ATTR_TYPE.hpp_4 or
key == GConst.ATTR_TYPE.hpp_5 or
key == GConst.ATTR_TYPE.hpp_6 or
key == GConst.ATTR_TYPE.hpp_7 or
-- key == GConst.ATTR_TYPE.spdp or
key == GConst.ATTR_TYPE.gold_gain or
key == GConst.ATTR_TYPE.dmg_addition_skill or
key == GConst.ATTR_TYPE.dmg_addition_normal or
key == GConst.ATTR_TYPE.pickaxe_recover_spd or
key == GConst.ATTR_TYPE.mineral_gain or
key == GConst.ATTR_TYPE.research_spd or
key == GConst.ATTR_TYPE.dmg_addition or
key == GConst.ATTR_TYPE.dmg_addition_poicon or
-- key == GConst.ATTR_TYPE.atkp_0 or
key == GConst.ATTR_TYPE.airborne_damage or
-- key == GConst.ATTR_TYPE.skill_all_damage or
-- key == GConst.ATTR_TYPE.skill_1_damage or
-- key == GConst.ATTR_TYPE.skill_2_damage or
-- key == GConst.ATTR_TYPE.skill_3_damage or
-- key == GConst.ATTR_TYPE.attack_damage or
key == GConst.ATTR_TYPE.miss or
key == GConst.ATTR_TYPE.dmg_dec_all or
key == GConst.ATTR_TYPE.idle_income
then
str = str .. "%"
end
return str
end
function GFunc.getAttrName(key)
return I18N:getText("attr", key, "name")
end
function GFunc.getTimeStrWithMS(time)
local m = math.floor(time/60)
local s = time%60
return I18N:getGlobalText(I18N.GlobalConst.TIME_MS, string.format("%02d", m), string.format("%02d", s))
end
function GFunc.getTimeStrWithMS2(time)
local m = math.floor(time/60)
local s = time%60
return I18N:getGlobalText(I18N.GlobalConst.TIME_STR_MS, string.format("%02d", m), string.format("%02d", s))
end
function GFunc.getTimeStrWithHMS(time)
local h = math.floor(time/3600)
local m = math.floor((time%3600)/60)
local s = time%60
return I18N:getGlobalText(I18N.GlobalConst.TIME_HMS, string.format("%02d", h), string.format("%02d", m), string.format("%02d", s))
end
function GFunc.getTimeStrWithM2(time)
local m = time // 60
return I18N:getGlobalText(I18N.GlobalConst.TIME_STR_M, m)
end
function GFunc.getTimeStrWithHMS2(time)
local h = math.floor(time/3600)
local m = math.floor((time%3600)/60)
local s = time%60
return I18N:getGlobalText(I18N.GlobalConst.TIME_STR_HMS, h, m, s)
end
function GFunc.getTimeStrWithDH2(time)
local d = math.floor(time/86400)
local h = math.floor((time%86400)/3600)
return I18N:getGlobalText(I18N.GlobalConst.TIME_STR_DH, d, h)
end
function GFunc.getTimeStrWithD2(time)
local d = math.floor(time/86400)
return I18N:getGlobalText(I18N.GlobalConst.TIME_STR_D, d)
end
function GFunc.getTimeStrWithHM(time)
local h = math.floor(time/3600)
local m = math.floor((time%3600)/60)
return I18N:getGlobalText(I18N.GlobalConst.TIME_STR_HM, string.format("%02d", h), string.format("%02d", m))
end
function GFunc.getTimeStrWithHM2(time)
local h = math.floor(time/3600)
local m = math.floor((time%3600)/60)
return I18N:getGlobalText(I18N.GlobalConst.TIME_STR_HM, h, m)
end
function GFunc.getTimeStr(time)
if time > 86400 then
return GFunc.getTimeStrWithDH2(time)
else
return GFunc.getTimeStrWithHMS2(time)
end
end
function GFunc.getTimeStr2(time)
if time > 86400 then
return GFunc.getTimeStrWithD2(time)
else
return GFunc.getTimeStrWithHM2(time)
end
end
function GFunc.getTimeStr3(time)
if time >= 3600 then
return GFunc.getTimeStrWithHM(time)
else
return GFunc.getTimeStrWithMS2(time)
end
end
function GFunc.getAdaptScale(basePixel)
basePixel = basePixel or 0
local DESIGN_WIDTH = 720
local DESIGN_HEIGHT = 1280
local safeHeight = SafeAreaManager:getNotchScreenHeight()
local winSizeWidth, winSizeHeight = GFunc.getScreenSize()
local maxScale = math.max(DESIGN_WIDTH/winSizeWidth, DESIGN_HEIGHT/winSizeHeight)
local height = maxScale*winSizeHeight - basePixel - safeHeight
local scale = height/(DESIGN_HEIGHT - basePixel)
return scale
end
function GFunc.getConstIntValue(key)
local ConstCfg = ConfigManager:getConfig("const")
return math.floor(ConstCfg[key].value)
end
function GFunc.getConstValue(key)
local ConstCfg = ConfigManager:getConfig("const")
return ConstCfg[key] and ConstCfg[key].value or 0
end
function GFunc.getTargetAnchoredPosition(targetGo, parent)
local rectTransform = targetGo:getComponent(GConst.TYPEOF_UNITY_CLASS.RECTTRANSFORM)
local rect = rectTransform.rect
local localToWorldMatrix = rectTransform.localToWorldMatrix
local tarCornerMid = localToWorldMatrix:MultiplyPoint3x4(BF.Vector3((rect.xMax + rect.x) / 2, (rect.yMax + rect.y) / 2, 0))
local screenPos = UIManager:getUICameraComponent():WorldToScreenPoint(tarCornerMid)
local anchoredPosition = CS.BF.Utils.RectTransformScreenPointToLocalPointInRectangle(parent:getTransform(), screenPos.x, screenPos.y, UIManager:getUICameraComponent())
return anchoredPosition
end
function GFunc.getFormatPrice(rechargeId)
local cfg = ConfigManager:getConfig("recharge")[rechargeId]
if cfg == nil then
return GConst.EMPTY_STRING
end
-- 优先读取通过sdk获取的商品价格
local price = SDKManager:getProductPrice(cfg.payId)
if price and price ~= "" then
return price
end
-- sdk里查不到就读表
return cfg.price_str
end
function GFunc.setGrey(component, isGrey)
if isGrey then
component.color = GConst.COMPONENT_GREY_COLOR
else
component.color = GConst.COLOR.WHITE
end
end
function GFunc.checkBit(value, nbit)
if not value then
return false
end
local ret = value >> (nbit - 1)
if ret %2 == 1 then
return true
else
return false
end
end
function GFunc.showItemNotEnough(itemId)
local gemTextInfo = I18N:getConfig("item")[itemId]
Logger.printTable(gemTextInfo)
if gemTextInfo then
GFunc.showToast(I18N:getGlobalText(I18N.GlobalConst.ITEM_NOT_ENOUGH, gemTextInfo.name))
end
end
function GFunc.showJewelryNotEnough(itemId)
local gemTextInfo = I18N:getConfig("jewelry")[itemId]
if gemTextInfo then
GFunc.showToast(I18N:getGlobalText(I18N.GlobalConst.ITEM_NOT_ENOUGH, gemTextInfo.name))
end
end
function GFunc.checkCost(id, num, showToast, giftType)
if num <= 0 then
BIReport:postDataException(id, num, giftType)
-- return false
end
local count = DataManager.BagData.ItemData:getItemNumById(id)
if count < num then
if showToast then
GFunc.showItemNotEnough(id)
end
return false
else
return true
end
end
function GFunc.checkCostNum(id, num, giftType)
if num <= 0 then
BIReport:postDataException(id, num, giftType)
return false
end
return true
end
---- 获得奖励的统一接口
function GFunc.addRewards(rewards, itemGetType)
if rewards == nil then
return
end
if EDITOR_MODE then
if not itemGetType then
local params = {
content = "GFunc addRewards has no itemGetType",
boxType = GConst.MESSAGE_BOX_TYPE.MB_OK,
okText = I18N:getGlobalText(I18N.GlobalConst.BTN_TEXT_OK),
}
GFunc.showMessageBox(params)
Logger.log("GFunc addRewards has no itemGetType")
end
end
-- 用元表来判断此奖励是否领过了,避免重复领取
if getmetatable(rewards) then
return
end
setmetatable(rewards, EMPTY_TABLE)
-- 合并奖励
local newRewards = {}
GFunc.mergeRewards2(rewards, newRewards)
local runeList = {}
-- 根据类型type来添加奖励
for k, v in ipairs(newRewards) do
if v.type == GConst.REWARD_TYPE.ITEM then
DataManager.BagData.ItemData:addItem(v.item, itemGetType)
elseif v.type == GConst.REWARD_TYPE.EQUIP then
DataManager.BagData.EquipData:addEquipCountById(v.equip.id, v.equip.count, itemGetType)
end
end
ModuleManager.TaskManager:addTaskProgress(GConst.TaskConst.TASK_TYPE.X_RUNE_GOT, {runeList = runeList})
end
function GFunc.addCosts(costs, itemGetType)
if costs == nil then
return
end
-- 用元表来判断此消耗是否领过了,避免重复扣除
if getmetatable(costs) then
return
end
setmetatable(costs, EMPTY_TABLE)
for _, unitCost in ipairs(costs) do
if unitCost.type == GConst.REWARD_TYPE.ITEM then
DataManager.BagData.ItemData:addItemCost(unitCost.item, itemGetType)
end
end
end
-- 奖励排序 结构为后端结构
-- function GFunc.sortRewards(rewards)
-- rewards = rewards or {}
-- local maxType = 10
-- for i,v in ipairs(rewards) do
-- if v.type == GConst.REWARD_TYPE.ITEM then
-- rewards[i].sort = (maxType - v.type) * 1000000000 + (1000000000 - v.item.cfg_id)
-- elseif v.type == GConst.REWARD_TYPE.EQUIP then
-- local cfg = ConfigManager:getConfig("equip")[v.equip.id]
-- rewards[i].sort = (maxType - v.type) * 1000000000 + cfg.qlt*100000000 + v.equip.id
-- elseif v.type == GConst.REWARD_TYPE.JEWELRY then
-- rewards[i].sort = (maxType - v.type) * 1000000000 + (1000000000 - v.jewelry.cfg_id)
-- end
-- end
-- table.sort(rewards, function (a, b)
-- return a.sort > b.sort
-- end)
-- end
---- 奖励展示接口
function GFunc.showRewardBox(rewards, extParams, callback)
rewards = rewards or {}
local params = extParams or {}
local newRewards = {}
if not params.noMerge then
GFunc.mergeRewards2(rewards, newRewards)
else
newRewards = rewards
end
params.rewards = newRewards
params.callback = callback
ModuleManager.TipsManager:showRewardsBox(params)
end
function GFunc.mergeRewards2(rewards, newRewards)
local items = {}
for i,v in ipairs(rewards) do
if v.type == GConst.REWARD_TYPE.ITEM then
items[v.item.cfg_id] = (items[v.item.cfg_id] or 0) + v.item.count
elseif v.type == GConst.REWARD_TYPE.EQUIP then
table.insert(newRewards, v)
end
end
for k,v in pairs(items) do
table.insert(newRewards, {type = GConst.REWARD_TYPE.ITEM, item = {cfg_id = k, count = v}})
end
end
-- reward 结构为 type id num 配置中结构
function GFunc.mergeRewards(rewards)
local items = {}
local newRewards = {}
for i,v in ipairs(rewards) do
if v.type == GConst.REWARD_TYPE.ITEM then
items[v.id] = (items[v.id] or 0) + v.num
elseif v.type == GConst.REWARD_TYPE.EQUIP then
table.insert(newRewards, v)
elseif v.type == GConst.REWARD_TYPE.LEGACY then
table.insert(newRewards, v)
end
end
for k,v in pairs(items) do
table.insert(newRewards, {type = GConst.REWARD_TYPE.ITEM, id = k, num = v})
end
return newRewards
end
function GFunc.getRandomIndex(weightArr)
if #weightArr <= 0 then
return
end
local maxWeight = 0
for i, v in ipairs(weightArr) do
maxWeight = maxWeight + v
end
local randomWeight = math.random(1, maxWeight)
local idx
for i, v in ipairs(weightArr) do
if randomWeight <= v then
idx = i
break
else
randomWeight = randomWeight - v
end
end
return idx
end
-- function GFunc.getRewardsStr(rewards)
-- if rewards == nil then
-- return
-- end
-- local itemStr = ""
-- for k, v in ipairs(rewards) do
-- if v.type == GConst.REWARD_TYPE.ITEM then
-- itemStr = itemStr .. v.type .. "." .. v.item.cfg_id .. "." .. v.item.count
-- elseif v.type == GConst.REWARD_TYPE.EQUIP then
-- itemStr = itemStr .. v.type .. "." .. v.equip.id .. "." .. v.equip.eid
-- elseif v.type == GConst.REWARD_TYPE.JEWELRY then
-- itemStr = itemStr .. v.type .. "." .. v.jewelry.cfg_id .. "." .. v.jewelry.count
-- end
-- if k ~= #rewards then
-- itemStr = itemStr.. "|"
-- end
-- end
-- return itemStr
-- end
function GFunc.copyStr(str)
CS.UnityEngine.GUIUtility.systemCopyBuffer = str
end
function GFunc.getShakeSeq(obj, onlyKill, originScale, notForcerefresh)
originScale = originScale or 1
if obj.shakeSeq then
if notForcerefresh then
return obj.shakeSeq
end
obj.shakeSeq:Kill()
obj.shakeSeq = nil
end
obj:setLocalScale(originScale, originScale, originScale)
if onlyKill then
return
end
obj.shakeSeq = obj:createBindTweenSequence()
-- obj.shakeSeq:AppendCallback(obj:setLocalEulerAngles(0, 0, 15))
-- obj.shakeSeq:Append(obj:getTransform():DOLocalRotate(BF.Vector3(0, 0, -15), 0.2))
-- obj.shakeSeq:Append(obj:getTransform():DOLocalRotate(BF.Vector3(0, 0, 15), 0.2))
obj.shakeSeq:AppendInterval(2)
obj.shakeSeq:Append(obj:getTransform():DOScale(originScale * 1.12, 0.1))
obj.shakeSeq:Append(obj:getTransform():DOScale(originScale * 0.9, 0.11))
obj.shakeSeq:Append(obj:getTransform():DOScale(originScale * 1.1, 0.15))
obj.shakeSeq:Append(obj:getTransform():DOScale(originScale * 0.9, 0.2))
obj.shakeSeq:Append(obj:getTransform():DOScale(originScale * 1.05, 0.25))
obj.shakeSeq:Append(obj:getTransform():DOScale(originScale * 0.9, 0.3))
obj.shakeSeq:Append(obj:getTransform():DOScale(originScale * 1, 0.3))
obj.shakeSeq:Append(obj:getTransform():DOScale(originScale, 0.3))
obj.shakeSeq:SetLoops(-1)
return obj.shakeSeq
end
function GFunc.getShakeSeq2(obj, onlyKill, originScale, notForcerefresh)
originScale = originScale or 1
if obj.shakeSeq then
if not notForcerefresh then
return obj.shakeSeq
end
obj.shakeSeq:Kill()
obj.shakeSeq = nil
end
obj:setLocalScale(originScale, originScale, originScale)
if onlyKill then
return
end
obj.shakeSeq = obj:createBindTweenSequence()
-- obj.shakeSeq:AppendCallback(obj:setLocalEulerAngles(0, 0, 15))
-- obj.shakeSeq:Append(obj:getTransform():DOLocalRotate(BF.Vector3(0, 0, -15), 0.2))
-- obj.shakeSeq:Append(obj:getTransform():DOLocalRotate(BF.Vector3(0, 0, 15), 0.2))
obj.shakeSeq:AppendInterval(1)
obj.shakeSeq:Append(obj:getTransform():DOScale(originScale * 1.12, 0.1))
obj.shakeSeq:Append(obj:getTransform():DOScale(originScale * 0.9, 0.11))
obj.shakeSeq:Append(obj:getTransform():DOScale(originScale * 1.1, 0.15))
obj.shakeSeq:Append(obj:getTransform():DOScale(originScale * 0.9, 0.2))
obj.shakeSeq:Append(obj:getTransform():DOScale(originScale * 1.05, 0.25))
obj.shakeSeq:Append(obj:getTransform():DOScale(originScale * 0.9, 0.3))
obj.shakeSeq:Append(obj:getTransform():DOScale(originScale * 1, 0.3))
obj.shakeSeq:Append(obj:getTransform():DOScale(originScale, 0.3))
obj.shakeSeq:SetLoops(-1)
return obj.shakeSeq
end
function GFunc.getShakeSeqRotate(obj, onlyKill, notForcerefresh)
if obj.shakeSeq then
if notForcerefresh then
return obj.shakeSeq
end
obj.shakeSeq:Kill()
obj.shakeSeq = nil
obj:setLocalEulerAngles(0,0,0)
end
if onlyKill then
return
end
local objTrans = obj:getTransform()
obj.shakeSeq = obj:createBindTweenSequence()
obj.shakeSeq:AppendInterval(2)
local angle = 12
obj.shakeSeq:Append(objTrans:DORotate({x=0,y=0,z=angle},0.2))
obj.shakeSeq:Append(objTrans:DORotate({x=0,y=0,z=-angle},0.1))
obj.shakeSeq:Append(objTrans:DORotate({x=0,y=0,z=angle},0.1))
obj.shakeSeq:Append(objTrans:DORotate({x=0,y=0,z=-angle},0.07))
obj.shakeSeq:Append(objTrans:DORotate({x=0,y=0,z=angle},0.07))
obj.shakeSeq:Append(objTrans:DORotate({x=0,y=0,z=-angle},0.05))
obj.shakeSeq:SetLoops(-1)
return obj.shakeSeq
end
function GFunc.getScaleQueueAni(root, rewardList, listCell, callBack)
if root.aniSeq then
root.aniSeq:Kill()
root.aniSeq = nil
end
root.aniSeq = root:createBindTweenSequence()
local seq = root.aniSeq
local groupCell = {}
local index = 1
table.foreach(listCell, function(k, cell)
if groupCell[index] and #groupCell[index] >= 5 then
index = index + 1
end
if not groupCell[index] then
groupCell[index] = {}
end
table.insert(groupCell[index], cell)
end)
local rewardListTrans = rewardList:getTransform()
-- ani
table.foreach(groupCell, function(row, cells)
table.foreach(cells, function(k, cell)
local summonRewardCell = cell
local rewardType, id = summonRewardCell:getReward()
summonRewardCell:showMask()
local isNew = summonRewardCell:getIsFirstGet()
local rewardQlt = GFunc.getQuality(rewardType, id)
if rewardQlt and rewardQlt >= 4 and isNew then -- 紫色以上
seq:AppendInterval(0.4)
seq:AppendCallback(function() summonRewardCell:showReward() end)
--seq:Append(rewardListTrans:DOShakePosition(0.4, 14, 18, 90,true)) -- 轻幅度震动
seq:Append(rewardListTrans:DOShakePosition(1, 20, 18, 90,true)) -- 大力震动
else
seq:AppendCallback(function()
summonRewardCell:showReward()
end)
end
end)
seq:AppendInterval(0.1)
end)
seq:AppendCallback(function()
if callBack then
callBack()
end
end)
return seq
end
function GFunc.miningTipsMovePosY(obj, delay,callBack)
if obj.seq then
obj.seq:Kill()
obj.seq = nil
end
obj.seq = obj:createBindTweenSequence()
local trans = obj:getTransform()
local localPosY = trans.localPosition.y
local seq = obj.seq
seq:AppendInterval(delay)
seq:Append(trans:DOLocalMoveY(localPosY + 200, 1.2))
seq:AppendCallback(function()
obj:setActive(false)
if callBack then
callBack()
end
end)
end
function GFunc.dataEncrypt(data)
if not VersionCompatible:supportDataEncryptVersion() then
return data
end
local numStr = CS.Security.XXTEA.Encrypt(tostring(data), GConst.SECRET_KEY)
return numStr
end
function GFunc.dataDecrypt(data)
if not VersionCompatible:supportDataEncryptVersion() then
return data
end
local numStr = CS.Security.XXTEA.Decrypt(data, GConst.SECRET_KEY)
return tonumber(numStr)
end
function GFunc.getTickCount()
if not VersionCompatible:supportDataEncryptVersion() then
return 0
end
return math.floor(UnityTime.realtimeSinceStartup)
end
function GFunc.IsGotServerTime()
if not VersionCompatible:supportDataEncryptVersion() then
return true
end
if not CS.BF.BFMain.IsGotServerTime then
return false
end
return true
end
---得到展示奖励的图集名称图片资源id
function GFunc.getFrameRes(type, id)
if type == GConst.REWARD_TYPE.REWARD_NONE then
return
end
local qlt = 1
local atlasPath = ""
if type == GConst.REWARD_TYPE.ITEM then
local ItemCfg = ConfigManager:getConfig("item")
local config = ItemCfg[id]
if not config then
return
end
qlt = config.qlt
atlasPath = GConst.ATLAS_PATH.ICON_EQUIP
end
if type == GConst.REWARD_TYPE.EQUIP then
local equipCfg = ConfigManager:getConfig("equip")
local config = equipCfg[id]
if not config then
return
end
qlt = config.qlt
atlasPath = GConst.ATLAS_PATH.ICON_EQUIP
end
if type == GConst.REWARD_TYPE.RUNES then
local runeCfg = ConfigManager:getConfig("runes")
local config = runeCfg[id]
if not config then
return
end
qlt = config.qlt
atlasPath = GConst.ATLAS_PATH.ICON_RUNE
end
return atlasPath, GConst.HERO_FRAME[ GConst.QUALITY[qlt] ] or "frame_1", qlt
end
---得到展示奖励的图集名称图片资源id
function GFunc.getQuality(type, id)
if type == GConst.REWARD_TYPE.REWARD_NONE then
return
end
local qlt = 1
if type == GConst.REWARD_TYPE.ITEM then
local ItemCfg = ConfigManager:getConfig("item")
local config = ItemCfg[id]
if not config then
return
end
qlt = config.qlt
end
if type == GConst.REWARD_TYPE.EQUIP then
local equipCfg = ConfigManager:getConfig("equip")
local config = equipCfg[id]
if not config then
return
end
qlt = config.qlt
end
if type == GConst.REWARD_TYPE.LEGACY then
local equipCfg = ConfigManager:getConfig("legacy")
local config = equipCfg[id]
if not config then
return
end
qlt = config.qlt
end
if type == GConst.REWARD_TYPE.RUNES then
local runeCfg = ConfigManager:getConfig("runes")
local config = runeCfg[id]
if not config then
return
end
qlt = config.qlt
end
return qlt
end
---得到展示奖励的图集名称图片资源id
function GFunc.getRewardIconRes(type, id)
if type == GConst.REWARD_TYPE.REWARD_NONE then
return
end
if type == GConst.REWARD_TYPE.ITEM then
return GFunc.getIconRes(id)
end
if type == GConst.REWARD_TYPE.EQUIP then
return GFunc.getEquipIconRes(id)
end
if type == GConst.REWARD_TYPE.RUNES then
return GFunc.getRuneIconRes(id)
end
if type == GConst.REWARD_TYPE.LEGACY then
return GFunc.getLegacyIconRes(id)
end
end
function GFunc.getIconRes(itemId)
local ItemCfg = ConfigManager:getConfig("item")
local config = ItemCfg[itemId]
if not config then
return
end
return GConst.ATLAS_PATH.ICON_ITEM, tostring(config.icon)
end
function GFunc.getEquipIconRes(equipId)
local EquipCfg = ConfigManager:getConfig("equip")
local config = EquipCfg[equipId]
if not config then
return
end
return GConst.ATLAS_PATH.ICON_EQUIP, tostring(config.icon)
end
function GFunc.getRuneIconRes(runeId)
local runeCfg = ConfigManager:getConfig("runes")
local config = runeCfg[runeId]
if not config then
return
end
return GConst.ATLAS_PATH.ICON_RUNE, tostring(config.icon)
end
function GFunc.getLegacyIconRes(legacyId)
local legacyCfg = ConfigManager:getConfig("legacy")
local config = legacyCfg[legacyId]
if not config then
return
end
return GConst.ATLAS_PATH.ICON_LEGACY, tostring(config.icon)
end
---得到展示奖励的图集名称图片资源id
function GFunc.getRewardName(type, id)
if type == GConst.REWARD_TYPE.REWARD_NONE then
return
end
if type == GConst.REWARD_TYPE.ITEM then
return I18N:getText("item", id, "name")
end
if type == GConst.REWARD_TYPE.EQUIP then
return I18N:getText("equip", id, "desc")
end
if type == GConst.REWARD_TYPE.RUNES then
return I18N:getText("rune", id, "desc")
end
end
function GFunc.performDurationDelay(obj, delay, callback)
if obj.sequence then
obj.sequence:Kill()
obj.sequence = nil
end
local sequence = obj:createBindTweenSequence()
delay = delay or 0
delay = math.max(0, delay)
obj.sequence = sequence
sequence:AppendInterval(delay or 0)
sequence:OnComplete(callback)
return sequence
end
function GFunc.compareVersionThan(version1, version2, include)
if not version1 or not version2 then
return false
end
local versionStrs = string.split(version1, ".")
local versionNum1 = tonumber(versionStrs[1])
local versionNum2 = tonumber(versionStrs[2])
local versionNum3 = tonumber(versionStrs[3])
local versionStrs2 = string.split(version2, ".")
local versionNum21 = tonumber(versionStrs2[1])
local versionNum22 = tonumber(versionStrs2[2])
local versionNum23 = tonumber(versionStrs2[3])
if not versionNum1 or not versionNum2 or not versionNum3 or not versionNum21 or not versionNum22 or not versionNum23 then
return false
end
if versionNum1 > versionNum21 then
return true, true
elseif versionNum1 < versionNum21 then
return false
end
if versionNum2 > versionNum22 then
return true, true
elseif versionNum2 < versionNum22 then
return false
end
if versionNum3 > versionNum23 then
return true
elseif versionNum3 < versionNum23 then
return false
end
if include then
return true
end
return false
end
function GFunc.getFormatCfgRewards(rewards, onlyOne)
local cfgRewards = GFunc.getArray()
for _, reward in ipairs(rewards) do
local cfgReward = {
type = reward.type,
id = reward.id,
count = {
value = reward.count.value,
unit = reward.count.unit,
},
}
if onlyOne then
return cfgReward
else
table.insert(cfgRewards, reward)
end
end
return cfgRewards
end
function GFunc.getUpdateDataMap(fnName, dataName, dataMap, costs, rewards, fnArgs)
local params = {
fnName = fnName,
dataType = dataName,
data = dataMap,
costs = costs or GFunc.getArray(),
rewards = rewards or GFunc.getArray(),
fnArgs = fnArgs
}
return params
end
function GFunc.isShenhe()
return CS.BF.BFMain.IsShenhe
end
function GFunc.getArray()
local array = {}
setmetatable(array, {__jsontype = "array"})
return array
end
function GFunc.showProbability()
local language = I18N:getCurLanguage()
if language == "ko" or language == "ja" then
return true
end
return false
end
function GFunc.getTable(struct)
local t = {}
if struct then
for k, v in pairs(struct) do
if type(v) == "table" then
t[k] = GFunc.getTable(v)
else
t[k] = v
end
end
end
return t
end
function GFunc.formatTimeStep(timestep)
if timestep and timestep > 10000000000 then
timestep = timestep // 1000
end
return timestep
end
function GFunc.randomPos(idx, pos)
local posX, posY
if idx == 1 then
posX = math.random(-50, 0)
posY = math.random(0, 50)
elseif idx == 2 then
posX = math.random(0, 50)
posY = math.random(0, 50)
elseif idx == 3 then
posX = math.random(-50, 0)
posY = math.random(-50, 0)
elseif idx == 4 then
posX = math.random(0, 50)
posY = math.random(-50, 0)
else
posX = math.random(-50, 50)
posY = math.random(-50, 50)
end
return posX + pos.x, posY + pos.y
end
function GFunc.imgFly(flyImg, beginPos, endPos, callback)
if flyImg.aniSeq then
flyImg.aniSeq:Kill()
end
local scale = 0.5
flyImg:setAnchoredPosition(beginPos.x, beginPos.y)
flyImg:setVisible(true, 0.1)
local maxDis = 2000
local dis = BF.Vector2Distance(beginPos, endPos)
local time = dis/maxDis
local aniSeq = flyImg:createBindTweenSequence()
-- aniSeq:Append(flyImg:getTransform():DOScale(BF.Vector3(scale + 0.2, scale + 0.2, scale + 0.2), 0.1):SetEase(CS.DG.Tweening.Ease.InCubic))
aniSeq:Append(flyImg:getTransform():DOScale(BF.Vector3(scale, scale, scale), 0.04):SetEase(CS.DG.Tweening.Ease.InCubic))
-- aniSeq:AppendInterval(0.3)
aniSeq:Append(flyImg:getTransform():DOAnchorPos(endPos, time):SetEase(CS.DG.Tweening.Ease.InCubic))
aniSeq:Join(flyImg:getTransform():DOScale(BF.Vector3(0.1, 0.1, 0.1), time):SetEase(CS.DG.Tweening.Ease.InCubic))
aniSeq:AppendCallback(function()
flyImg:setVisible(false)
if callback then
callback()
end
end)
flyImg.aniSeq = aniSeq
end
function GFunc.doScaleFlyImg(img, callback)
if img.aniSeq then
img.aniSeq:Kill()
img:setLocalScale(1, 1, 1)
end
local transform = img:getTransform()
local localScale = transform.localScale
local scale = localScale.x
local aniSeq = img:createBindTweenSequence()
aniSeq:Append(img:getTransform():DOScale(BF.Vector3(scale + 0.1, scale + 0.1, scale + 0.1), 0.08):SetEase(CS.DG.Tweening.Ease.InCubic))
aniSeq:Append(img:getTransform():DOScale(BF.Vector3(scale - 0.08, scale - 0.08, scale - 0.08), 0.08):SetEase(CS.DG.Tweening.Ease.InCubic))
aniSeq:Append(img:getTransform():DOScale(BF.Vector3(scale, scale, scale), 0.08):SetEase(CS.DG.Tweening.Ease.InCubic))
aniSeq:AppendCallback(function()
if callback then
callback()
end
end)
img.aniSeq = aniSeq
end
function GFunc.doScaleQuickZoom(img,callback)
if img.aniSeq then
img.aniSeq:Kill()
end
local transform = img:getTransform()
local aniSeq = img:createBindTweenSequence()
aniSeq:Append(transform:DOScale(1.4, 0.1))
aniSeq:Append(transform:DOScale(1, 0.06))
aniSeq:AppendCallback(function()
if callback then
callback()
end
end)
img.aniSeq = aniSeq
end
-- colorType 1 白色, 2 黑色
function GFunc.setAdsSprite(img, isGrey, colorType)
if not img then
return
end
colorType = colorType or 1
local skip = DataManager.MallActData:skipAd()
local icon = ""
if colorType == 1 then
icon = skip and "common_ad_4" or "common_ad_3"
end
if colorType == 2 then
icon = skip and "common_ad_2" or "common_ad_1"
end
if isGrey then
icon = skip and "common_ad_6" or "common_ad_5"
end
img:setSprite(GConst.ATLAS_PATH.COMMON, icon)
--img:setSprite(GConst.ATLAS_PATH.COMMON, icon, function ()
-- img:getComponent(GConst.TYPEOF_UNITY_CLASS.UI_IMAGE):SetNativeSize()
--end)
end
function GFunc.getAdSprite()
local skip = DataManager.MallActData:skipAd()
return skip and "common_ad_4" or "common_ad_3"
end
function GFunc.centerImgAndTx(imgObj, txObj, spacing, offset)
spacing = spacing or 0
offset = offset or 0
local imgW = imgObj:getSizeDelta().x
local txW = txObj:getComponent(GConst.TYPEOF_UNITY_CLASS.UI_TEXT_MESH_PRO).preferredWidth
txObj:setSizeDeltaX(txW)
local w = (imgW + txW + spacing) / 2
imgObj:setAnchoredPositionX(imgW / 2 - w + offset)
txObj:setAnchoredPositionX(w - txW / 2 + offset)
end
function GFunc.centerTxAndTx(txObj1, txObj2, spacing)
spacing = spacing or 0
local txW = txObj1:getComponent(GConst.TYPEOF_UNITY_CLASS.UI_TEXT_MESH_PRO).preferredWidth
txObj1:setSizeDeltaX(txW)
local txW2 = txObj2:getComponent(GConst.TYPEOF_UNITY_CLASS.UI_TEXT_MESH_PRO).preferredWidth
txObj2:setSizeDeltaX(txW2)
local w = (txW2 + txW + spacing) / 2
txObj1:setAnchoredPositionX(txW / 2 - w)
txObj2:setAnchoredPositionX(w - txW2 / 2)
end
function GFunc.expandImgToFitTx(imgObj, txObj, spacing)
spacing = spacing or 0
local txW = txObj:getComponent(GConst.TYPEOF_UNITY_CLASS.UI_TEXT_MESH_PRO).preferredWidth
txObj:setSizeDeltaX(txW)
imgObj:setSizeDeltaX(txW + spacing * 2)
end
function GFunc.formatAdImg(adImg)
if DataManager.MonthlyData:skipAd() then
adImg:setSprite(GConst.ATLAS_PATH.COMMON, "common_ad_1")
else
adImg:setSprite(GConst.ATLAS_PATH.COMMON, "common_ad")
end
end
function GFunc.organizeCfg(cfgId, cfg)
local result = {}
result.cfgId = cfgId
result.cfg = cfg
return result
end
function GFunc.gemEnough(needNum,showToast) -- 钻石是否足够
return GFunc.checkCost(GConst.ItemConst.ITEM_ID_GEM, needNum, showToast) --判断不提示,点击才提示
end
function GFunc.getCostContentWithColor(key)
local cost = GFunc.getConstIntValue(key)
local content = "<color=#ed2929>"..cost.."</color>"
local bigNum = {
unit = 0,
value = cost
}
if GFunc.gemEnough(bigNum, false) then
content = tostring(cost)
end
return content
end
---设置图片和文本居中, 文本需要左右居中对齐
function GFunc.setMiddlePosX(txtObj, icon, bgImg)
local txtRectWidth = txtObj:getTransform().rect.width
local iconRectWidth = icon:getTransform().rect.width
local bgImgRectWidth = bgImg:getTransform().rect.width
local halfBgWidth = bgImgRectWidth * 0.5
-- 文本的宽度
local meshPro = txtObj:getComponent(GConst.TYPEOF_UNITY_CLASS.UI_TEXT_MESH_PRO)
local width = meshPro.preferredWidth
local txtMinWidth = math.max(width, txtRectWidth)
-- 以bg中心点为锚点时
-- 文本距离边界的距离
local txtPadding = halfBgWidth - txtMinWidth
txtPadding = txtPadding > 0 and txtPadding or 0
-- 图片距离边界距离
local iconPadding = halfBgWidth - iconRectWidth
iconPadding = iconPadding > 0 and iconPadding or 0
local maxPadding = math.max(txtPadding, iconPadding)
local minPadding = math.min(txtPadding, iconPadding)
local offset = (maxPadding - minPadding) * 0.5
if txtPadding > iconPadding then
txtObj:setAnchoredPositionX(txtMinWidth * 0.5 + offset)
icon:setAnchoredPositionX(-iconRectWidth * 0.5 + offset)
else
txtObj:setAnchoredPositionX(txtMinWidth * 0.5 - offset)
icon:setAnchoredPositionX(-iconRectWidth * 0.5 - offset)
end
end
---计算最小值
function GFunc.getCalcMinVal(arr)
local min = arr[1]
for i, v in ipairs(arr) do
if min > v then
min = v
end
end
return min
end
---计算最大值
function GFunc.getCalcMaxVal(arr)
local max = arr[1] or 0
for i, v in ipairs(arr) do
if max < v then
max = v
end
end
return max
end
function GFunc.getRewardTableByRewardList(rewardList)
local newRewards = {}
for _, reward in ipairs(rewardList) do
table.insert(newRewards, reward)
end
return newRewards
end
function GFunc.getRewardTableByReward(reward)
return GFunc.getRewardTable(reward.type, reward.id, reward.count)
end
function GFunc.getRewardTable(type, id, count)
if type == GConst.REWARD_TYPE.EQUIP then
return GFunc.getServerEquipRewardTable(id, count)
end
return {
type = type,
id = id,
count = {
unit = count.unit,
value = count.value,
}
}
end
function GFunc.getServerRuneRewardTable(id, level)
return {
type = GConst.REWARD_TYPE.RUNES,
rune = {
id = id,
level = level,
},
}
end
function GFunc.getServerEquipRewardTable(id, level, count)
local reward = {
type = GConst.REWARD_TYPE.EQUIP,
equip = {
id = id,
level = level,
count = count
},
}
return reward
end
function GFunc.checkTableValueSame(standardTable, compareTable, debug)
if type(standardTable) ~= "table" or type(compareTable) ~= "table" then
if debug and standardTable ~= compareTable then
Logger.logHighlight(standardTable)
end
return standardTable == compareTable
end
for k, v in pairs(standardTable) do
local v2 = compareTable[k]
if v2 == nil then
if debug then
Logger.logHighlight(k)
end
return false
end
if not GFunc.checkTableValueSame(v, v2, debug) then
return false
end
end
return true
end
-- 获取挖矿研究得到的属性加成
function GFunc.getMainHeroAttributeVal(key)
local mainEntity = DataManager.HeroData:getMainHeroEntity()
local allAttr = mainEntity:getAllAttr()
local result = allAttr[key]
return result
end
function GFunc.showCurrencyFlyAction(rewards, pos)
local flyPos = {}
if not pos then
pos = {x = 0, y = 0}
else
local sPoint = UIManager:getUICameraComponent():WorldToScreenPoint(pos)
pos = CS.BF.Utils.RectTransformScreenPointToLocalPointInRectangle(UIManager:getMainCanvasTransform(), sPoint.x, sPoint.y, UIManager:getUICameraComponent())
end
for i, reward in ipairs(rewards) do
if reward.type == GConst.REWARD_TYPE.ITEM then
local allPos = {}
for i = 1, 4 do
local posX, posY = GFunc.randomPos(i, pos)
allPos[i] = {x = posX, y = posY}
end
flyPos[reward.item.id] = allPos
end
end
UIManager:showCurrencyAction(flyPos)
end
function GFunc.getSkillEffectStr(id, lv)
local str = I18N:getText("skill", id, "desc")
local cfg = ConfigManager:getConfig("skill")[id]
local baseNum = cfg.string_num_base
local growNum = cfg.string_num_grow
local tab = {}
for i,v in ipairs(baseNum) do
table.insert(tab, baseNum[i] + (lv - 1)*growNum[i])
end
local idx = 0
str = string.gsub(str, '{%d+}', function (s)
idx = idx + 1
return tostring(tab[idx])
end)
return str
end
function GFunc.goTargetElasticityY(obj, onlyKill, offset, punchY, callBack)
if obj.shakeSeq then
obj.shakeSeq:Kill()
obj.shakeSeq = nil
end
if onlyKill then
return
end
local curPosY = obj:getAnchoredPositionY()
local objTrans = obj:getTransform()
obj.shakeSeq = obj:createBindTweenSequence()
obj.shakeSeq:Append(objTrans:DOLocalMoveY(curPosY - offset / 2,0.1))
obj.shakeSeq:Append(objTrans:DOLocalMoveY(curPosY + offset * 2 ,0.1))
obj.shakeSeq:Join(objTrans:DOPunchScale({x=0,y=punchY,z = 0},0.2, 6))
obj.shakeSeq:AppendCallback(function()
if callBack then
callBack()
end
end)
return obj.shakeSeq
end
function GFunc.goTargetPosXShake(obj, onlyKill, targetX, offset, callBack)
if obj.shakeSeq then
obj.shakeSeq:Kill()
obj.shakeSeq = nil
end
if onlyKill then
return
end
obj.shakeSeq = obj:createBindTweenSequence()
local objTrans = obj:getTransform()
local seq = obj.shakeSeq
seq:Append(objTrans:DOLocalMoveX(targetX,0.12))
seq:Append(objTrans:DOLocalMoveX(targetX + offset,0.1))
seq:Append(objTrans:DOLocalMoveX(targetX - offset / 3,0.05))
seq:Append(objTrans:DOLocalMoveX(targetX, 0.1))
seq:AppendCallback(function()
if callBack then
callBack()
end
end)
return obj.shakeSeq
end
function GFunc.getRewardId(reward)
if reward.id_for_nothing then
return CS.BF.Utils.GetRewardNumber(reward.id_for_nothing)
else
return reward.id
end
end
function GFunc.getRewardNum(reward)
if reward.num_for_nothing then
return CS.BF.Utils.GetRewardNumber(reward.num_for_nothing)
else
return reward.num
end
end
function GFunc.getRewardType(reward)
if reward.type_for_nothing then
return CS.BF.Utils.GetRewardNumber(reward.type_for_nothing)
else
return reward.type
end
end
--[[
设置tabLe只速 出现改写会抛出Lua error
用法locaL readOnlyCfg = GFunc.readOnlyTab(cfg) return readOnlyCfg
增加了防重置设置read_onLy的机制
Lua5.3支持 1) table库支持调用元方法所以table.remove table.insert也会抛出错误,
2)不用定义_ipairs 5.3 ipairs迭代器支持访问元方法__indexpairs迭代器next不支持故需要元方法_pairs
低版本Lua此网数不能完全按照预期工作
]]
function GFunc.readOnlyTab(inputTable)
local travelled_tables = {}
local function _read_only(tbl)
if not travelled_tables[tbl] then
local tbl_mt = getmetatable(tbl)
if not tbl_mt then
tbl_mt = {}
setmetatable(tbl, tbl_mt)
end
local proxy = tbl_mt._read_only__proxy
if not proxy then
proxy = {}
tbl_mt.__read_only_proxy = proxy
local proxy_mt = {
__index = tbl,
__newindex = function (t, k, v) error( "error write to a read-only table with key = " .. tostring(k)) end,
__pairs = function (t) return pairs(tbl) end,
-- __ipairs = function (t) return ipairs(tbl) end, 5.3版本不需要此方法
_len = function (t) return #tbl end,
__read_only_proxy = proxy
}
setmetatable(proxy, proxy_mt)
end
travelled_tables[tbl] = proxy
for k, v in pairs(tbl) do
if type(v) == "table" then
tbl[k] = _read_only(v)
end
end
end
return travelled_tables[tbl]
end
return _read_only(inputTable)
end
return GFunc