2351 lines
79 KiB
Lua
2351 lines
79 KiB
Lua
local UIUtils = {}
|
||
|
||
function UIUtils.initLuaCustomConfig(self)
|
||
self.luaCustomConfig = self.luaCustomConfig or self.transform:GetComponent("LuaCustomConfig")
|
||
if not self.luaCustomConfig then
|
||
return
|
||
end
|
||
|
||
self.config = {}
|
||
|
||
self.config.HasValue = function(_, key)
|
||
local flag = self.luaCustomConfig.itemDict:TryGetValue(key)
|
||
if not flag then
|
||
return false
|
||
end
|
||
return true
|
||
end
|
||
|
||
if UNITY_EDITOR and CS.Beyond.DebugDefines.realTimeLuaCustomConfig then
|
||
|
||
setmetatable(self.config, {
|
||
__index = function(_, key)
|
||
local flag, item = self.luaCustomConfig.itemDict:TryGetValue(key)
|
||
if flag then
|
||
|
||
local valueType = CS.Beyond.Lua.LuaCustomConfig.ValueType
|
||
if item.valueType == valueType.Bool then
|
||
return item.boolValue
|
||
elseif item.valueType == valueType.Int then
|
||
return item.intValue
|
||
elseif item.valueType == valueType.Float then
|
||
return item.floatValue
|
||
elseif item.valueType == valueType.String then
|
||
return item.stringValue
|
||
elseif item.valueType == valueType.Vector2 then
|
||
return item.vector2Value
|
||
elseif item.valueType == valueType.Vector3 then
|
||
return item.vector3Value
|
||
elseif item.valueType == valueType.Vector4 then
|
||
return item.vector4Value
|
||
elseif item.valueType == valueType.Color then
|
||
return item.colorValue
|
||
elseif item.valueType == valueType.Lua then
|
||
return lume.dostring("return " .. item.luaValue)
|
||
elseif item.valueType == valueType.FMODEvent then
|
||
return item.fmodEventValue
|
||
elseif item.valueType == valueType.GameObject then
|
||
return item.gameObjectValue
|
||
elseif item.valueType == valueType.RectTransform then
|
||
return item.rectTransformValue
|
||
elseif item.valueType == valueType.AnimationCurve then
|
||
return item.curveValue
|
||
elseif item.valueType == valueType.LayerMask then
|
||
return item.layerMaskValue
|
||
elseif item.valueType == valueType.Material then
|
||
return item.material
|
||
elseif item.valueType == valueType.Enum then
|
||
local exception = string.format(
|
||
"return CS.%s.__CastFrom(%d)",
|
||
item.enumTypeFullName,
|
||
item.enumValue
|
||
)
|
||
local enumValue = lume.dostring(exception)
|
||
return enumValue
|
||
end
|
||
end
|
||
logger.error("无法获取 LuaCustomConfig 配置项", key)
|
||
end
|
||
})
|
||
else
|
||
|
||
local componentConfig = {}
|
||
self.luaCustomConfig:InitConfigTable(componentConfig)
|
||
setmetatable(self.config, {
|
||
__index = function(_, key)
|
||
local componentValue = componentConfig[key]
|
||
if componentValue ~= nil then
|
||
|
||
return componentValue
|
||
end
|
||
|
||
logger.error("无法获取 LuaCustomConfig 配置项", key)
|
||
end
|
||
})
|
||
end
|
||
|
||
getmetatable(self.config).__newindex = function()
|
||
logger.error("请在面板上配置 LuaCustomConfig,勿在代码中修改 view.config 中的值!")
|
||
end
|
||
end
|
||
|
||
function UIUtils.genCachedCellFunction(list, onMiss)
|
||
onMiss = onMiss or function(obj)
|
||
return Utils.wrapLuaNode(obj)
|
||
end
|
||
|
||
local cache = {}
|
||
local getCell = function(object)
|
||
local cell = cache[object]
|
||
if not cell then
|
||
cell = onMiss(object)
|
||
cache[object] = cell
|
||
end
|
||
return cell
|
||
end
|
||
|
||
|
||
return function(object)
|
||
if not object then
|
||
return
|
||
end
|
||
if type(object) == "number" then
|
||
if not list then
|
||
logger.error("genCachedCellFunction fail", list)
|
||
return
|
||
end
|
||
local luaIndex = object
|
||
|
||
object = list:Get(CSIndex(luaIndex))
|
||
end
|
||
if object then
|
||
return getCell(object)
|
||
end
|
||
end
|
||
end
|
||
|
||
function UIUtils.addChild(parent, prefab, keepScale)
|
||
if not prefab or IsNull(prefab.gameObject) then
|
||
logger.error("Invalid prefab", parent.transform:PathFromRoot())
|
||
end
|
||
local item = {}
|
||
item.gameObject = CSUtils.CreateObject(prefab.gameObject, parent.gameObject)
|
||
item.transform = item.gameObject.transform:GetComponent("RectTransform")
|
||
if not keepScale then
|
||
item.transform.localScale = Vector3.one
|
||
end
|
||
return item
|
||
end
|
||
|
||
local UIListCacheClass = require_ex("Common/Utils/UI/UIListCache").UIListCache
|
||
|
||
|
||
function UIUtils.genCellCache(itemTemplate, wrapFunction, parent)
|
||
return UIListCacheClass(itemTemplate, wrapFunction, parent)
|
||
end
|
||
|
||
local UIGoCacheClass = require_ex("Common/Utils/UI/UIGoCache").UIGoCache
|
||
|
||
|
||
function UIUtils.genGoCache(goTemplate, wrapFunction, parent)
|
||
return UIGoCacheClass(goTemplate, wrapFunction, parent)
|
||
end
|
||
|
||
function UIUtils.getStandardScreenX(x)
|
||
return x / Screen.width * UIConst.CANVAS_DEFAULT_WIDTH
|
||
end
|
||
|
||
function UIUtils.getStandardScreenY(y)
|
||
return y / Screen.height * UIConst.CANVAS_DEFAULT_HEIGHT
|
||
end
|
||
|
||
function UIUtils.getNormalizedScreenX(x)
|
||
return x / Screen.width
|
||
end
|
||
|
||
function UIUtils.getNormalizedScreenY(y)
|
||
return y / Screen.height
|
||
end
|
||
|
||
function UIUtils.isInputEventScopeValid(scope)
|
||
scope = scope or Types.EInputBindingScope.IncludeStandalone
|
||
local isValid
|
||
if scope == Types.EInputBindingScope.EditorOnly then
|
||
isValid = UNITY_EDITOR
|
||
elseif scope == Types.EInputBindingScope.IncludeDev then
|
||
isValid = UNITY_EDITOR or DEVELOPMENT_BUILD
|
||
elseif scope == Types.EInputBindingScope.IncludeStandalone then
|
||
isValid = UNITY_EDITOR or DEVELOPMENT_BUILD or UNITY_STANDALONE
|
||
end
|
||
return isValid
|
||
end
|
||
|
||
function UIUtils.bindInputPlayerAction(actionId, callback, groupId)
|
||
return InputManagerInst:CreateBinding(actionId, callback, groupId)
|
||
end
|
||
|
||
|
||
|
||
|
||
|
||
function UIUtils.bindInputEvent(key, action, modifyKeys, timing, groupId)
|
||
return InputManagerInst:CreateBinding(key, modifyKeys or "", timing or InputTimingType.OnClick, action, groupId or UIManager.persistentInputBindingKey)
|
||
end
|
||
|
||
|
||
function UIUtils.setAsNaviTarget(targetSelectable)
|
||
InputManagerInst.controllerNaviManager:SetTarget(targetSelectable)
|
||
end
|
||
|
||
|
||
|
||
function UIUtils.setAsNaviTargetInSilentModeIfNecessary(targetNaviGroup, targetSelectable)
|
||
InputManagerInst.controllerNaviManager:SetTargetInSilentModeIfNecessary(targetNaviGroup, targetSelectable)
|
||
end
|
||
|
||
|
||
|
||
function UIUtils.changeAndTrySetNaviBindingType(naviGroup, naviBindingType)
|
||
InputManagerInst.controllerNaviManager:ChangeAndTrySetNaviBindingType(naviGroup, naviBindingType)
|
||
end
|
||
|
||
|
||
|
||
|
||
function UIUtils.initUIDragHelper(uiDragItem, info)
|
||
if uiDragItem.luaTable then
|
||
local dragHelper = uiDragItem.luaTable[1]
|
||
dragHelper:RefreshInfo(info)
|
||
return dragHelper
|
||
else
|
||
local DragHelperClass = require_ex("Common/Utils/UI/UIDragHelper")
|
||
return DragHelperClass(uiDragItem, info)
|
||
end
|
||
end
|
||
|
||
|
||
function UIUtils.initUIDropHelper(uiDropItem, info)
|
||
if uiDropItem.luaTable then
|
||
local dropHelper = uiDropItem.luaTable[1]
|
||
if BEYOND_DEBUG_COMMAND then
|
||
|
||
|
||
if not dropHelper or type(dropHelper) ~= "userdata" then
|
||
logger.error("InValid dropHelper", uiDropItem.luaTable, uiDropItem.transform:PathFromRoot())
|
||
end
|
||
end
|
||
dropHelper:RefreshInfo(info)
|
||
return dropHelper
|
||
else
|
||
local DropHelperClass = require_ex("Common/Utils/UI/UIDropHelper")
|
||
return DropHelperClass(uiDropItem, info)
|
||
end
|
||
end
|
||
|
||
|
||
function UIUtils.isTypeDropValid(dragHelper, acceptTypes)
|
||
local isSourceValid = not acceptTypes.sources or lume.find(acceptTypes.sources, dragHelper.source)
|
||
if not isSourceValid then
|
||
return false
|
||
end
|
||
local isTypeValid = not acceptTypes.types or lume.find(acceptTypes.types, dragHelper.type)
|
||
if not isTypeValid then
|
||
return false
|
||
end
|
||
return true
|
||
end
|
||
|
||
function UIUtils.playItemDragAudio(itemId)
|
||
local res, audioData = Tables.audioItemDragAndDrop:TryGetValue(itemId)
|
||
if res and not string.isEmpty(audioData.audioDrag) then
|
||
AudioAdapter.PostEvent(audioData.audioDrag)
|
||
return
|
||
end
|
||
local _, itemData = Tables.itemTable:TryGetValue(itemId)
|
||
if itemData then
|
||
local audioTypeData = Tables.audioItemTypeDragAndDrop[itemData.showingType]
|
||
if audioTypeData ~= nil and not string.isEmpty(audioTypeData.audioDrag) then
|
||
AudioAdapter.PostEvent(audioTypeData.audioDrag)
|
||
end
|
||
end
|
||
end
|
||
|
||
function UIUtils.playItemDropAudio(itemId)
|
||
if string.isEmpty(itemId) then
|
||
return
|
||
end
|
||
local res, audioData = Tables.audioItemDragAndDrop:TryGetValue(itemId)
|
||
if res and not string.isEmpty(audioData.audioDrop) then
|
||
AudioAdapter.PostEvent(audioData.audioDrop)
|
||
return
|
||
end
|
||
local _, itemData = Tables.itemTable:TryGetValue(itemId)
|
||
if itemData then
|
||
local audioTypeData = Tables.audioItemTypeDragAndDrop[itemData.showingType]
|
||
if audioTypeData ~= nil and not string.isEmpty(audioTypeData.audioDrop) then
|
||
AudioAdapter.PostEvent(audioTypeData.audioDrop)
|
||
end
|
||
end
|
||
end
|
||
|
||
|
||
|
||
|
||
function UIUtils.screenPointToUI(screenPos, uiCamera, canvasRect)
|
||
canvasRect = canvasRect or UIManager.uiCanvasRect
|
||
local isInside, uiPos = Unity.RectTransformUtility.ScreenPointToLocalPointInRectangle(canvasRect, screenPos, uiCamera)
|
||
return uiPos, isInside
|
||
end
|
||
|
||
function UIUtils.objectPosToUI(pos, uiCamera, canvasRect)
|
||
local screenPos = CameraManager.mainCamera:WorldToScreenPoint(pos)
|
||
if screenPos.z < 0 then
|
||
screenPos.x = -screenPos.x
|
||
screenPos.y = -screenPos.y
|
||
end
|
||
return UIUtils.screenPointToUI(Vector2(screenPos.x, screenPos.y), uiCamera, canvasRect)
|
||
end
|
||
|
||
function UIUtils.getUIRectOfRectTransform(rectTransform, uiCamera)
|
||
|
||
local rect = CSUtils.RectTransformToScreenRect(rectTransform, uiCamera)
|
||
rect.y = Screen.height - rect.yMax
|
||
local canvasRect = UIManager.uiCanvasRect.rect
|
||
local scaleX = canvasRect.width / Screen.width
|
||
local scaleY = canvasRect.height / Screen.height
|
||
return Unity.Rect(rect.x * scaleX, rect.y * scaleY, rect.size.x * scaleX, rect.size.y * scaleY)
|
||
end
|
||
|
||
function UIUtils.addRectSizeKeepCenter(rect, addWidth, addHeight)
|
||
local center = rect.center
|
||
rect.size = rect.size + Vector2(addWidth or 0, addHeight or 0)
|
||
rect.center = center
|
||
return rect
|
||
end
|
||
|
||
|
||
function UIUtils.getSpritePath(path, name)
|
||
if name then
|
||
|
||
path = path .. "/" .. name
|
||
end
|
||
return UIConst.UI_SPRITE_PATH:format(path)
|
||
end
|
||
|
||
function UIUtils.getSpriteDevPath(path, name)
|
||
if name then
|
||
|
||
path = path .. "/" .. name
|
||
end
|
||
return UIConst.UI_SPRITE_DEV_PATH:format(path)
|
||
end
|
||
|
||
|
||
|
||
function UIUtils.isScreenPosInRectTransform(pos, rectTransform, uiCamera)
|
||
return CS.Beyond.UI.UIUtils.IsScreenPosInRectTransform(pos, rectTransform, uiCamera)
|
||
end
|
||
|
||
|
||
function UIUtils.getTransformScreenRect(transform, uiCamera)
|
||
local bounds = CSUtils.GetRectTransformBounds(transform)
|
||
local min = bounds.min
|
||
local size = bounds.size
|
||
if uiCamera then
|
||
min = uiCamera:WorldToScreenPoint(min)
|
||
local max = uiCamera:WorldToScreenPoint(bounds.max)
|
||
size = max - min
|
||
end
|
||
return Unity.Rect(min.x, Screen.height - (min.y + size.y), size.x, size.y)
|
||
end
|
||
|
||
|
||
function UIUtils.getRectTransformCenterPosition(rectTransform)
|
||
return CSUtils.GetRectTransformCenterPosition(rectTransform)
|
||
end
|
||
|
||
|
||
|
||
|
||
|
||
|
||
function UIUtils.updateTipsPosition(contentRectTrans, targetTransform, canvasRectTrans, uiCamera, posType, padding, xOffset)
|
||
if IsNull(targetTransform) then
|
||
contentRectTrans.anchoredPosition = Vector2.zero
|
||
return
|
||
end
|
||
local targetScreenRect = UIUtils.getTransformScreenRect(targetTransform, uiCamera)
|
||
UIUtils.updateTipsPositionWithScreenRect(contentRectTrans, targetScreenRect, canvasRectTrans, uiCamera, posType, padding, xOffset)
|
||
end
|
||
|
||
|
||
function UIUtils.updateTipsPositionWithScreenRect(contentRectTrans, targetScreenRect, canvasRectTrans, uiCamera, posType, padding, xOffset)
|
||
posType = posType or UIConst.UI_TIPS_POS_TYPE.RightDown
|
||
LayoutRebuilder.ForceRebuildLayoutImmediate(contentRectTrans)
|
||
if BEYOND_DEBUG then
|
||
if contentRectTrans.pivot ~= Vector2(0.5, 0.5) then
|
||
logger.error(string.format("Tips位置计算错误: [%s] 的锚点不在中心", contentRectTrans:PathFromRoot()))
|
||
end
|
||
end
|
||
local width = contentRectTrans.rect.width
|
||
local height = contentRectTrans.rect.height
|
||
local canvasSize = canvasRectTrans.rect.size
|
||
local oriScreenSize = Vector2(Screen.width, Screen.height)
|
||
local xRation = oriScreenSize.x / canvasSize.x
|
||
local yRation = oriScreenSize.y / canvasSize.y
|
||
local widthInScreen = width * xRation
|
||
local heightInScreen = height * yRation
|
||
local halfHeightInScreen = heightInScreen / 2
|
||
local halfWidthInScreen = widthInScreen / 2
|
||
|
||
padding = padding or {}
|
||
|
||
local paddingTop = (padding.top or 0) * yRation
|
||
local paddingLeft = (padding.left or 0) * xRation
|
||
local paddingRight = (padding.right or 0) * xRation
|
||
local paddingBottom = (padding.bottom or 0) * yRation
|
||
|
||
local screenSize = Vector2(oriScreenSize.x - (paddingLeft + paddingRight), oriScreenSize.y - (paddingTop + paddingBottom))
|
||
targetScreenRect.x = targetScreenRect.x - paddingLeft
|
||
targetScreenRect.y = targetScreenRect.y - paddingTop
|
||
|
||
|
||
local screenPos = Vector2(0, 0)
|
||
|
||
|
||
local finalXPos, finalYPos
|
||
|
||
|
||
if posType == UIConst.UI_TIPS_POS_TYPE.MidBottom then
|
||
|
||
local verticalSpaceEnough = true
|
||
local downHeight = screenSize.y - targetScreenRect.yMax
|
||
if downHeight >= heightInScreen then
|
||
screenPos.y = targetScreenRect.yMax + halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Bottom
|
||
else
|
||
local upHeightEnough = targetScreenRect.yMin >= heightInScreen
|
||
if upHeightEnough then
|
||
screenPos.y = targetScreenRect.yMin - halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Top
|
||
else
|
||
screenPos.y = targetScreenRect.center.y
|
||
verticalSpaceEnough = false
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Mid
|
||
end
|
||
end
|
||
|
||
local rightWidth = screenSize.x - targetScreenRect.xMax
|
||
local leftWidth = targetScreenRect.xMin
|
||
if verticalSpaceEnough then
|
||
if rightWidth >= halfWidthInScreen and leftWidth >= halfWidthInScreen then
|
||
|
||
screenPos.x = targetScreenRect.center.x
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Mid
|
||
else
|
||
if leftWidth < halfWidthInScreen then
|
||
|
||
screenPos.x = targetScreenRect.center.x + halfWidthInScreen - leftWidth
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Right
|
||
else
|
||
|
||
screenPos.x = targetScreenRect.center.x - (halfWidthInScreen - rightWidth)
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Left
|
||
end
|
||
end
|
||
else
|
||
if leftWidth >= widthInScreen then
|
||
screenPos.x = targetScreenRect.xMin - halfWidthInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Left
|
||
else
|
||
screenPos.x = targetScreenRect.xMax + halfWidthInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Right
|
||
end
|
||
end
|
||
elseif posType == UIConst.UI_TIPS_POS_TYPE.LeftTop then
|
||
|
||
local downHeight = screenSize.y - targetScreenRect.yMin
|
||
if downHeight >= heightInScreen then
|
||
screenPos.y = targetScreenRect.yMin + halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Bottom
|
||
else
|
||
screenPos.y = screenSize.y - halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Top
|
||
end
|
||
|
||
|
||
local leftWidth = targetScreenRect.xMin
|
||
if leftWidth >= widthInScreen then
|
||
screenPos.x = targetScreenRect.xMin - halfWidthInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Left
|
||
else
|
||
screenPos.x = 0
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Left
|
||
end
|
||
elseif posType == UIConst.UI_TIPS_POS_TYPE.LeftTopOrRightTop then
|
||
|
||
local downHeight = screenSize.y - targetScreenRect.yMin
|
||
if downHeight >= heightInScreen then
|
||
screenPos.y = targetScreenRect.yMin + halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Bottom
|
||
else
|
||
screenPos.y = screenSize.y - halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Top
|
||
end
|
||
|
||
|
||
local leftWidth = targetScreenRect.xMin
|
||
if leftWidth >= widthInScreen then
|
||
screenPos.x = targetScreenRect.xMin - halfWidthInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Left
|
||
else
|
||
screenPos.x = targetScreenRect.xMax + halfWidthInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Right
|
||
end
|
||
elseif posType == UIConst.UI_TIPS_POS_TYPE.RightTopOrLeftTop then
|
||
|
||
local downHeight = screenSize.y - targetScreenRect.yMin
|
||
if downHeight >= heightInScreen then
|
||
screenPos.y = targetScreenRect.yMin + halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Bottom
|
||
else
|
||
screenPos.y = screenSize.y - halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Top
|
||
end
|
||
|
||
|
||
local rightWidth = screenSize.x - targetScreenRect.xMax
|
||
if rightWidth >= widthInScreen then
|
||
screenPos.x = targetScreenRect.xMax + halfWidthInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Right
|
||
else
|
||
screenPos.x = targetScreenRect.xMin - halfWidthInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Left
|
||
end
|
||
elseif posType == UIConst.UI_TIPS_POS_TYPE.RightTop then
|
||
|
||
local downHeight = screenSize.y - targetScreenRect.yMin
|
||
if downHeight >= heightInScreen then
|
||
screenPos.y = targetScreenRect.yMin + halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Bottom
|
||
else
|
||
screenPos.y = screenSize.y - halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Top
|
||
end
|
||
|
||
|
||
local rightWidth = screenSize.x - targetScreenRect.xMax
|
||
if rightWidth >= widthInScreen then
|
||
screenPos.x = targetScreenRect.xMax + halfWidthInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Right
|
||
else
|
||
screenPos.x = screenSize.x - halfWidthInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Left
|
||
end
|
||
elseif posType == UIConst.UI_TIPS_POS_TYPE.RightDown then
|
||
|
||
local downHeight = screenSize.y - targetScreenRect.yMax
|
||
if downHeight >= heightInScreen then
|
||
screenPos.y = targetScreenRect.yMax + halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Bottom
|
||
else
|
||
local upHeight = targetScreenRect.yMin
|
||
if upHeight >= downHeight then
|
||
|
||
screenPos.y = targetScreenRect.yMin - halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Top
|
||
else
|
||
screenPos.y = screenSize.y - halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Bottom
|
||
end
|
||
end
|
||
|
||
|
||
local rightWidth = screenSize.x - targetScreenRect.xMax
|
||
if rightWidth >= widthInScreen then
|
||
screenPos.x = targetScreenRect.xMax + halfWidthInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Right
|
||
else
|
||
local leftWidth = targetScreenRect.xMin
|
||
if leftWidth >= widthInScreen then
|
||
screenPos.x = targetScreenRect.xMin - halfWidthInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Left
|
||
else
|
||
screenPos.x = screenSize.x - halfWidthInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Right
|
||
end
|
||
end
|
||
elseif posType == UIConst.UI_TIPS_POS_TYPE.LeftDown then
|
||
|
||
local downHeight = screenSize.y - targetScreenRect.yMax
|
||
if downHeight >= heightInScreen then
|
||
screenPos.y = targetScreenRect.yMax + halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Bottom
|
||
else
|
||
local upHeight = targetScreenRect.yMin
|
||
if upHeight >= downHeight then
|
||
|
||
screenPos.y = targetScreenRect.yMin - halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Top
|
||
else
|
||
screenPos.y = screenSize.y - halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Bottom
|
||
end
|
||
end
|
||
|
||
|
||
local leftWidth = targetScreenRect.xMin
|
||
if leftWidth >= widthInScreen then
|
||
screenPos.x = targetScreenRect.xMin - halfWidthInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Left
|
||
else
|
||
screenPos.x = 0
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Left
|
||
end
|
||
elseif posType == UIConst.UI_TIPS_POS_TYPE.MidTop then
|
||
|
||
if targetScreenRect.yMin >= heightInScreen then
|
||
screenPos.y = targetScreenRect.yMin - halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Top
|
||
else
|
||
local downHeight = screenSize.y - targetScreenRect.yMax
|
||
if downHeight >= heightInScreen then
|
||
screenPos.y = targetScreenRect.yMax + halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Bottom
|
||
else
|
||
screenPos.y = halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Top
|
||
end
|
||
end
|
||
|
||
|
||
screenPos.x = targetScreenRect.center.x
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Mid
|
||
elseif posType == UIConst.UI_TIPS_POS_TYPE.LeftMid then
|
||
|
||
local downHeight = screenSize.y - targetScreenRect.center.y
|
||
if downHeight >= heightInScreen then
|
||
screenPos.y = targetScreenRect.center.y
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Mid
|
||
else
|
||
screenPos.y = screenSize.y - halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Top
|
||
end
|
||
|
||
|
||
local leftWidth = targetScreenRect.xMin
|
||
if leftWidth >= widthInScreen then
|
||
screenPos.x = targetScreenRect.xMin - halfWidthInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Left
|
||
else
|
||
screenPos.x = 0
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Left
|
||
end
|
||
elseif posType == UIConst.UI_TIPS_POS_TYPE.RightMid then
|
||
|
||
local downHeight = screenSize.y - targetScreenRect.center.y
|
||
if downHeight >= heightInScreen then
|
||
screenPos.y = targetScreenRect.center.y
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Mid
|
||
else
|
||
screenPos.y = screenSize.y - halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Top
|
||
end
|
||
|
||
|
||
local rightWidth = screenSize.x - targetScreenRect.xMax
|
||
if rightWidth >= widthInScreen then
|
||
screenPos.x = targetScreenRect.xMax + halfWidthInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Right
|
||
else
|
||
screenPos.x = screenSize.x - halfWidthInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Right
|
||
end
|
||
elseif posType == UIConst.UI_TIPS_POS_TYPE.GuideTips then
|
||
local outDistance = UIConst.UI_GUIDE_OUT_OF_SCREEN_DISTANCE
|
||
if targetScreenRect.xMin < -outDistance or targetScreenRect.xMax - screenSize.x > outDistance or
|
||
targetScreenRect.yMin < -outDistance or targetScreenRect.yMax - screenSize.y > outDistance then
|
||
|
||
screenPos.x = targetScreenRect.x
|
||
screenPos.y = targetScreenRect.y
|
||
screenPos = screenPos - oriScreenSize / 2
|
||
screenPos.y = -screenPos.y
|
||
local canvasPos = Vector2(screenPos.x / xRation, screenPos.y / yRation)
|
||
contentRectTrans.anchoredPosition = canvasPos
|
||
return targetScreenRect.xMin < 0 and UIConst.UI_TIPS_X_POS_TYPE.Left or UIConst.UI_TIPS_X_POS_TYPE.Right,
|
||
targetScreenRect.yMin < 0 and UIConst.UI_TIPS_Y_POS_TYPE.Top or UIConst.UI_TIPS_Y_POS_TYPE.Bottom
|
||
end
|
||
|
||
|
||
local downHeight = screenSize.y - targetScreenRect.yMin
|
||
if downHeight >= heightInScreen then
|
||
screenPos.y = targetScreenRect.yMin + halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Bottom
|
||
else
|
||
screenPos.y = screenSize.y - halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Top
|
||
end
|
||
|
||
|
||
local leftWidth = targetScreenRect.xMin
|
||
if leftWidth >= widthInScreen then
|
||
screenPos.x = targetScreenRect.xMin - halfWidthInScreen - xOffset
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Left
|
||
else
|
||
local rightWidth = screenSize.x - targetScreenRect.xMax
|
||
if rightWidth >= widthInScreen then
|
||
screenPos.x = targetScreenRect.xMax + halfWidthInScreen + xOffset
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Right
|
||
else
|
||
|
||
screenPos.x = targetScreenRect.center.x
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Mid
|
||
if targetScreenRect.yMin >= (screenSize.y - targetScreenRect.yMax) then
|
||
screenPos.y = targetScreenRect.yMin - halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Top
|
||
else
|
||
screenPos.y = targetScreenRect.yMax + halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Bottom
|
||
end
|
||
end
|
||
end
|
||
elseif posType == UIConst.UI_TIPS_POS_TYPE.FacTopViewOption then
|
||
if targetScreenRect.center.y >= screenSize.y then
|
||
screenPos.x = targetScreenRect.center.x
|
||
screenPos.y = targetScreenRect.yMin - halfHeightInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Mid
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Top
|
||
elseif targetScreenRect.center.y <= 0 then
|
||
screenPos.x = targetScreenRect.center.x
|
||
screenPos.y = targetScreenRect.yMax + halfHeightInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Mid
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Bottom
|
||
else
|
||
|
||
local downHeight = screenSize.y - targetScreenRect.center.y
|
||
if downHeight >= heightInScreen then
|
||
screenPos.y = targetScreenRect.center.y
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Mid
|
||
else
|
||
screenPos.y = screenSize.y - halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Top
|
||
end
|
||
|
||
local rightWidth = screenSize.x - targetScreenRect.xMax
|
||
if rightWidth >= widthInScreen then
|
||
screenPos.x = targetScreenRect.xMax + halfWidthInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Right
|
||
else
|
||
screenPos.x = screenSize.x - halfWidthInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Right
|
||
end
|
||
end
|
||
elseif posType == UIConst.UI_TIPS_POS_TYPE.FacTopViewBuildActionIcons then
|
||
if targetScreenRect.yMin >= heightInScreen then
|
||
screenPos.y = targetScreenRect.yMin - halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Top
|
||
else
|
||
screenPos.y = targetScreenRect.yMax + halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Bottom
|
||
end
|
||
screenPos.x = targetScreenRect.center.x
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Mid
|
||
elseif posType == UIConst.UI_TIPS_POS_TYPE.FacSmartAlertTop then
|
||
screenPos.y = targetScreenRect.yMin - halfHeightInScreen
|
||
screenPos.x = targetScreenRect.center.x
|
||
elseif posType == UIConst.UI_TIPS_POS_TYPE.AdaptiveRightTop then
|
||
|
||
local downHeight = screenSize.y - targetScreenRect.yMin
|
||
if downHeight >= heightInScreen then
|
||
screenPos.y = targetScreenRect.yMin + halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Bottom
|
||
else
|
||
screenPos.y = screenSize.y - halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Top
|
||
end
|
||
|
||
|
||
local rightWidth = screenSize.x - targetScreenRect.xMax
|
||
if rightWidth >= widthInScreen then
|
||
screenPos.x = targetScreenRect.xMax + halfWidthInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Right
|
||
else
|
||
|
||
screenPos.x = targetScreenRect.xMin - halfWidthInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Left
|
||
end
|
||
elseif posType == UIConst.UI_TIPS_POS_TYPE.DailyAbsentRightTop then
|
||
|
||
if targetScreenRect.yMin >= heightInScreen then
|
||
screenPos.y = targetScreenRect.yMax - halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Top
|
||
else
|
||
screenPos.y = targetScreenRect.yMin + halfHeightInScreen
|
||
finalYPos = UIConst.UI_TIPS_Y_POS_TYPE.Bottom
|
||
end
|
||
|
||
|
||
local rightWidth = screenSize.x - targetScreenRect.xMax
|
||
if rightWidth >= widthInScreen then
|
||
screenPos.x = targetScreenRect.xMax + halfWidthInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Right
|
||
else
|
||
|
||
screenPos.x = targetScreenRect.xMin - halfWidthInScreen
|
||
finalXPos = UIConst.UI_TIPS_X_POS_TYPE.Left
|
||
end
|
||
end
|
||
|
||
|
||
screenPos.x = lume.clamp(screenPos.x, halfWidthInScreen, screenSize.x - halfWidthInScreen) + paddingLeft
|
||
screenPos.y = lume.clamp(screenPos.y, halfHeightInScreen, screenSize.y - halfHeightInScreen) + paddingTop
|
||
|
||
screenPos = screenPos - oriScreenSize / 2
|
||
screenPos.y = -screenPos.y
|
||
|
||
|
||
local canvasPos = Vector2(screenPos.x / xRation, screenPos.y / yRation)
|
||
contentRectTrans.anchoredPosition = canvasPos
|
||
return finalXPos, finalYPos
|
||
end
|
||
|
||
|
||
|
||
function UIUtils.rectTransToPadding(rectTransform)
|
||
local anchoredPos = rectTransform.anchoredPosition
|
||
local size = rectTransform.rect.size
|
||
local parentSize = rectTransform.parent.rect.size
|
||
local left = (parentSize.x - size.x) / 2 + anchoredPos.x
|
||
local right = (parentSize.x - size.x) / 2 - anchoredPos.x
|
||
local top = (parentSize.y - size.y) / 2 - anchoredPos.y
|
||
local bottom = (parentSize.y - size.y) / 2 + anchoredPos.y
|
||
return {
|
||
top = top,
|
||
left = left,
|
||
right = right,
|
||
bottom = bottom,
|
||
}
|
||
end
|
||
|
||
function UIUtils.screenPosToWorldPos(x, y, yPlane)
|
||
local ray = CameraManager.mainCamera:ScreenPointToRay(Vector3(x, y, 0))
|
||
local length = (yPlane - ray.origin.y) / ray.direction.y
|
||
local worldPos = ray.origin + ray.direction * length
|
||
return worldPos
|
||
end
|
||
|
||
function UIUtils.changeAlpha(target, a)
|
||
local color = target.color
|
||
color.a = a
|
||
target.color = color
|
||
end
|
||
|
||
function UIUtils.changeColorExceptAlpha(target, color)
|
||
local a = target.color.a
|
||
color.a = a
|
||
target.color = color
|
||
end
|
||
|
||
function UIUtils.isPosInScreen(worldPos, camera, xFrame, yFrame)
|
||
xFrame = xFrame or 0
|
||
yFrame = yFrame or 0
|
||
local xMin = xFrame
|
||
local xMax = Screen.width - xFrame
|
||
local yMin = yFrame
|
||
local yMax = Screen.height - yFrame
|
||
|
||
camera = camera or CameraManager.mainCamera
|
||
local pos = camera:WorldToScreenPoint(worldPos)
|
||
return pos.x >= xMin and pos.y >= yMin and pos.z >= 0 and pos.x <= xMax and pos.y <= yMax, pos
|
||
end
|
||
|
||
function UIUtils.getRemainingText(t)
|
||
local hour = math.floor(t / 3600)
|
||
t = t % 3600
|
||
local min = math.floor(t / 60)
|
||
t = math.floor(t % 60)
|
||
return string.format("%02d:%02d:%02d", hour, min, t)
|
||
end
|
||
|
||
function UIUtils.getRemainingTextToMinute(t)
|
||
local min = math.floor(t / 60)
|
||
t = math.floor(t % 60)
|
||
return string.format("%02d:%02d", min, t)
|
||
end
|
||
|
||
function UIUtils.getItemRarity(itemId)
|
||
local data = Tables.itemTable:GetValue(itemId)
|
||
return data.rarity
|
||
end
|
||
|
||
function UIUtils.getItemUseDesc(itemId)
|
||
return CS.Beyond.Gameplay.TacticalItemUtil.GetUseItemDesc(itemId)
|
||
end
|
||
|
||
function UIUtils.getItemEquippedDesc(itemId)
|
||
return CS.Beyond.Gameplay.TacticalItemUtil.GetEquipItemDesc(itemId)
|
||
end
|
||
|
||
function UIUtils.getItemEquippedExtraDesc(itemId)
|
||
return CS.Beyond.Gameplay.TacticalItemUtil.GetEquipItemExtraDesc(itemId)
|
||
end
|
||
|
||
function UIUtils.getItemRarityColor(rarity)
|
||
local rarityColorStr = Tables.rarityColorTable[rarity]
|
||
return UIUtils.getColorByString(rarityColorStr.color)
|
||
end
|
||
|
||
function UIUtils.getCharRarityColor(rarity)
|
||
return UIUtils.getItemRarityColor(rarity)
|
||
end
|
||
|
||
function UIUtils.getColorByString(strColor, a)
|
||
local r = 0
|
||
local g = 0
|
||
local b = 0
|
||
a = a or 255
|
||
if string.len(strColor) == 6 then
|
||
local strR = string.sub(strColor, 1, 2)
|
||
local strG = string.sub(strColor, 3, 4)
|
||
local strB = string.sub(strColor, 5, 6)
|
||
r = tonumber(strR, 16)
|
||
g = tonumber(strG, 16)
|
||
b = tonumber(strB, 16)
|
||
end
|
||
if string.len(strColor) == 8 then
|
||
local strR = string.sub(strColor, 1, 2)
|
||
local strG = string.sub(strColor, 3, 4)
|
||
local strB = string.sub(strColor, 5, 6)
|
||
local strA = string.sub(strColor, 7, 8)
|
||
r = tonumber(strR, 16)
|
||
g = tonumber(strG, 16)
|
||
b = tonumber(strB, 16)
|
||
a = tonumber(strA, 16)
|
||
end
|
||
local color = CS.UnityEngine.Color(r / 255, g / 255, b / 255, a / 255)
|
||
return color
|
||
end
|
||
|
||
function UIUtils.setSpecialFillAmount(img, percent, minMaxVector2)
|
||
img.fillAmount = percent * (minMaxVector2.y - minMaxVector2.x) + minMaxVector2.x
|
||
end
|
||
|
||
function UIUtils.checkInputValid(value)
|
||
|
||
return true
|
||
|
||
end
|
||
|
||
function UIUtils.getStringLength(str)
|
||
return CS.Beyond.I18n.I18nUtils.GetStringLength(str)
|
||
end
|
||
|
||
function UIUtils.getNumString(num, isPrice)
|
||
if isPrice and num < 100000 then
|
||
return string.format("%d", num)
|
||
end
|
||
local curLang = CS.Beyond.I18n.I18nUtils.curEnvLang
|
||
local isChineseStyleLang = curLang == GEnums.EnvLang.CN
|
||
if isChineseStyleLang then
|
||
local wan = num / 10000
|
||
if wan < 1 then
|
||
return string.format("%d", num)
|
||
end
|
||
if wan < 10000 then
|
||
return UIUtils._getNumAbbrStr(wan, Language.LUA_NUM_UNIT_WAN, isPrice)
|
||
end
|
||
local yi = wan / 10000
|
||
return UIUtils._getNumAbbrStr(yi, Language.LUA_NUM_UNIT_YI, isPrice)
|
||
else
|
||
local m = num / 1000 / 1000
|
||
local k = num / 1000
|
||
if m >= 1 then
|
||
return UIUtils._getNumAbbrStr(m, Language.LUA_NUM_UNIT_MILLION, isPrice)
|
||
elseif k >= 1 then
|
||
return UIUtils._getNumAbbrStr(k, Language.LUA_NUM_UNIT_THOUSAND, isPrice)
|
||
else
|
||
return string.format("%d", num)
|
||
end
|
||
end
|
||
end
|
||
|
||
function UIUtils._getNumAbbrStr(num, text, isCeiling)
|
||
local carryFunc = function(x)
|
||
|
||
return isCeiling and math.ceil(x - 1e-10) or math.floor(x + 1e-10)
|
||
end
|
||
|
||
|
||
if num < 100 then
|
||
if num < 10 then
|
||
|
||
if carryFunc(num * 100) % 10 > 0 then
|
||
return string.format("%.2f%s", carryFunc(num * 100) / 100, text)
|
||
elseif math.floor(num * 10) % 10 > 0 then
|
||
return string.format("%.1f%s", carryFunc(num * 10) / 10, text)
|
||
end
|
||
else
|
||
|
||
if carryFunc(num * 10) % 10 > 0 then
|
||
return string.format("%.1f%s", carryFunc(num * 10) / 10, text)
|
||
end
|
||
end
|
||
end
|
||
|
||
return string.format("%d%s", carryFunc(num), text)
|
||
end
|
||
|
||
|
||
function UIUtils.ceilToTenthStr(num)
|
||
return string.format("%.1f", math.ceil(num * 10 - 1e-6) * 0.1)
|
||
end
|
||
|
||
|
||
function UIUtils.floorToTenthStr(num)
|
||
return string.format("%.1f", math.floor(num * 10 + 1e-6) * 0.1)
|
||
end
|
||
|
||
local ROMAN_VAL = { 1000, 900, 500, 400, 100, 90, 50, 40, 10, 9, 5, 4, 1}
|
||
local ROMAN_SYM = { "M", "CM", "D", "CD", "C", "XC", "L", "XL", "X", "IX", "V", "IV", "I"}
|
||
|
||
|
||
|
||
|
||
function UIUtils.intToRoman(num)
|
||
local roman = ""
|
||
for i = 1, #ROMAN_VAL do
|
||
while num >= ROMAN_VAL[i] do
|
||
num = num - ROMAN_VAL[i]
|
||
roman = roman .. ROMAN_SYM[i]
|
||
end
|
||
end
|
||
return roman
|
||
end
|
||
|
||
function UIUtils.setSizeDeltaX(rect, value)
|
||
local size = rect.sizeDelta
|
||
size.x = value
|
||
rect.sizeDelta = size
|
||
end
|
||
|
||
function UIUtils.setSizeDeltaY(rect, value)
|
||
local size = rect.sizeDelta
|
||
size.y = value
|
||
rect.sizeDelta = size
|
||
end
|
||
|
||
function UIUtils.mapScreenPosToEllipseEdge (screenPos, ellipseXRadius, ellipseYRadius)
|
||
local x = screenPos.x
|
||
local y = screenPos.y
|
||
|
||
local angle = math.atan(y, x)
|
||
local k = y / x
|
||
local uiPos = Vector2.zero
|
||
local a = ellipseXRadius
|
||
local b = ellipseYRadius
|
||
uiPos.x = a * b / math.sqrt(b * b + a * a * k * k)
|
||
if x < 0 then
|
||
uiPos.x = -uiPos.x
|
||
end
|
||
uiPos.y = uiPos.x * k
|
||
|
||
if uiPos.magnitude < screenPos.magnitude then
|
||
return uiPos, math.deg(angle), true
|
||
end
|
||
|
||
return screenPos, math.deg(angle), false
|
||
end
|
||
|
||
function UIUtils.resolveOriginalText(text)
|
||
return CS.Beyond.Gameplay.GameplayUIUtils.ResolveOriginalText(text)
|
||
end
|
||
|
||
function UIUtils.resolveTextCinematic(text)
|
||
local cfg = {
|
||
playerName = true,
|
||
gender = true,
|
||
}
|
||
return UIUtils.resolveText(text, cfg)
|
||
end
|
||
|
||
|
||
|
||
function UIUtils.resolveText(text, cfg)
|
||
return CS.Beyond.Gameplay.GameplayUIUtils.ResolveText(text, cfg.playerName, cfg.gender)
|
||
end
|
||
|
||
function UIUtils.resolveTextPlayerName(text)
|
||
return CS.Beyond.Gameplay.GameplayUIUtils.ResolveTextPlayerName(text)
|
||
end
|
||
|
||
function UIUtils.resolveTextGender(text)
|
||
return CS.Beyond.Gameplay.GameplayUIUtils.ResolveTextGender(text)
|
||
end
|
||
|
||
function UIUtils.genDynamicBlackScreenMaskData(systemName, fadeInTime, fadeOutTime, fadeInCallback)
|
||
local maskData = CS.Beyond.Gameplay.UICommonMaskData()
|
||
maskData.fadeInTime = fadeInTime
|
||
maskData.fadeBeforeTime = 0
|
||
maskData.fadeOutTime = fadeOutTime
|
||
if fadeInCallback ~= nil then
|
||
maskData.fadeInCallback = function()
|
||
fadeInCallback()
|
||
end
|
||
end
|
||
|
||
if BEYOND_DEBUG or BEYOND_DEBUG_COMMAND then
|
||
maskData.extraData = CS.Beyond.Gameplay.CommonMaskExtraData()
|
||
maskData.extraData.desc = systemName
|
||
end
|
||
|
||
return maskData
|
||
end
|
||
|
||
function UIUtils.genDynamicBlackScreenMaskDataWithWaitTime(systemName, fadeInTime, fadeOutTime, fadeWaitTime, fadeInCallback)
|
||
local maskData = CS.Beyond.Gameplay.UICommonMaskData()
|
||
maskData.fadeInTime = fadeInTime
|
||
maskData.fadeBeforeTime = 0
|
||
maskData.fadeWaitTime = fadeWaitTime
|
||
maskData.fadeOutTime = fadeOutTime
|
||
if fadeInCallback ~= nil then
|
||
maskData.fadeInCallback = function()
|
||
fadeInCallback()
|
||
end
|
||
end
|
||
|
||
if BEYOND_DEBUG or BEYOND_DEBUG_COMMAND then
|
||
maskData.extraData = CS.Beyond.Gameplay.CommonMaskExtraData()
|
||
maskData.extraData.desc = systemName
|
||
end
|
||
|
||
return maskData
|
||
end
|
||
|
||
local rewardItemRarityEffectNames = {
|
||
[1] = "normaGlow",
|
||
[2] = "greenGlow",
|
||
[3] = "blueGlow",
|
||
[4] = "purpleGlow",
|
||
[5] = "goldGlow",
|
||
}
|
||
function UIUtils.setRewardItemRarityGlow(cell, rarity)
|
||
local count = #rewardItemRarityEffectNames
|
||
rarity = math.min(count, rarity)
|
||
for k = 1, count do
|
||
local name = rewardItemRarityEffectNames[k]
|
||
cell.view[name].gameObject:SetActiveIfNecessary(k == rarity)
|
||
end
|
||
end
|
||
|
||
function UIUtils.getItemTypeName(itemId)
|
||
local itemCfg = Tables.itemTable:GetValue(itemId)
|
||
local itemTypeCfg = Tables.itemTypeTable:GetValue(itemCfg.type:GetHashCode())
|
||
local defaultTypeName = itemTypeCfg.name
|
||
|
||
if itemCfg.type == GEnums.ItemType.Weapon then
|
||
local weaponCfg = Tables.weaponBasicTable:GetValue(itemId)
|
||
if not weaponCfg then
|
||
return defaultTypeName
|
||
end
|
||
|
||
local weaponTypeInt = weaponCfg.weaponType:ToInt()
|
||
local weaponTypeName = Language[string.format("LUA_WEAPON_TYPE_%d", weaponTypeInt)]
|
||
return weaponTypeName
|
||
end
|
||
|
||
|
||
if itemCfg.type == GEnums.ItemType.Equip then
|
||
local _, equipBasicCfg = Tables.equipTable:TryGetValue(itemId)
|
||
if not equipBasicCfg then
|
||
return defaultTypeName
|
||
end
|
||
|
||
local equipTemplateId = itemId
|
||
local _, equipTemplate = Tables.equipTable:TryGetValue(equipTemplateId)
|
||
if not equipTemplate then
|
||
return defaultTypeName
|
||
end
|
||
|
||
local equipType = equipTemplate.partType
|
||
local equipTypeName = Language[UIConst.CHAR_INFO_EQUIP_TYPE_TILE_PREFIX .. LuaIndex(equipType:ToInt())]
|
||
return equipTypeName
|
||
end
|
||
|
||
return defaultTypeName
|
||
end
|
||
|
||
function UIUtils.displayItemBasicInfos(view, loader, itemId, instId)
|
||
local data = Tables.itemTable:GetValue(itemId)
|
||
local itemType = data.type
|
||
|
||
if view.itemNameTxt then
|
||
view.itemNameTxt.text = UIUtils.getItemName(itemId, instId)
|
||
end
|
||
|
||
if view.itemIcon then
|
||
view.itemIcon:InitItemIcon(itemId, true, instId)
|
||
end
|
||
|
||
if view.itemTypeTxt then
|
||
local itemTypeName = UIUtils.getItemTypeName(itemId)
|
||
view.itemTypeTxt.text = itemTypeName
|
||
end
|
||
if view.rarityLine then
|
||
UIUtils.setItemRarityImage(view.rarityLine, data.rarity)
|
||
end
|
||
end
|
||
|
||
function UIUtils.getItemName(itemId, instId)
|
||
local data = Tables.itemTable:GetValue(itemId)
|
||
if not instId then
|
||
return data.name
|
||
end
|
||
|
||
if data.type == GEnums.ItemType.WeaponGem then
|
||
local leadTermId = CharInfoUtils.getGemLeadSkillTermId(instId)
|
||
if not leadTermId then
|
||
return data.name
|
||
end
|
||
|
||
local leadTermCfg = Tables.gemTable:GetValue(leadTermId)
|
||
return string.format(Language.LUA_ITEM_COMPOSITE_NAME, data.name, leadTermCfg.tagName)
|
||
end
|
||
|
||
return data.name
|
||
end
|
||
|
||
function UIUtils.checkIfReachAdventureLv(needLv)
|
||
local adventureLevelData = GameInstance.player.adventure.adventureLevelData
|
||
return adventureLevelData.lv >= needLv
|
||
end
|
||
|
||
function UIUtils.displayCommercialItemInfo(view, loader, itemId, instId)
|
||
local itemData = Tables.itemTable[itemId]
|
||
if itemData.type == GEnums.ItemType.GemLockedTermBox then
|
||
|
||
view.stateCtrl:SetState("GemLockedTermBox")
|
||
|
||
local tipsGemWidget = view.tipsGemAttributeNode
|
||
tipsGemWidget:InitTipsGemAttributeNode()
|
||
tipsGemWidget:RefreshView(itemId)
|
||
end
|
||
end
|
||
|
||
function UIUtils.displayWeaponInfo(view, loader, itemId, instId)
|
||
local itemData = Tables.itemTable[itemId]
|
||
|
||
local weaponInstData = instId and CharInfoUtils.getWeaponByInstId(instId)
|
||
view.starGroup:InitStarGroup(itemData.rarity)
|
||
view.potentialStar:InitWeaponPotentialStar(weaponInstData and weaponInstData.refineLv or 0)
|
||
view.weaponGemSlimNode:InitWeaponGemSlimNode(weaponInstData and weaponInstData.attachedGemInstId or 0)
|
||
if weaponInstData then
|
||
view.tipWeaponLevelNode:InitTipWeaponLevelNode(itemId, instId)
|
||
view.weaponAttributeNode:InitWeaponAttributeNode(instId, weaponInstData.attachedGemInstId)
|
||
view.weaponSkillNode:InitWeaponSkillNode(instId)
|
||
else
|
||
local hasValue
|
||
|
||
local weaponBasicData
|
||
|
||
local weaponBreakThroughDetailList
|
||
local initMaxLevel, breakThroughCount, maxBreakthroughLevel = 0, 0, 0
|
||
hasValue, weaponBasicData = Tables.weaponBasicTable:TryGetValue(itemId)
|
||
if hasValue then
|
||
hasValue, weaponBreakThroughDetailList = Tables.weaponBreakThroughTemplateTable:TryGetValue(weaponBasicData.breakthroughTemplateId)
|
||
if hasValue then
|
||
breakThroughCount = #weaponBreakThroughDetailList.list
|
||
if breakThroughCount > 1 then
|
||
initMaxLevel = weaponBreakThroughDetailList.list[1].breakthroughLv
|
||
maxBreakthroughLevel = breakThroughCount - 1
|
||
end
|
||
end
|
||
end
|
||
view.tipWeaponLevelNode:InitTipWeaponLevelNodeNoInst(1, initMaxLevel, 0, maxBreakthroughLevel)
|
||
view.weaponAttributeNode:InitWeaponAttributeNodeByTemplateId(itemId)
|
||
view.weaponSkillNode:InitWeaponSkillNodeByTemplateId(itemId, 0, 0, false)
|
||
end
|
||
|
||
if view.equippedNode then
|
||
if instId and instId > 0 then
|
||
view.equippedNode:InitEquipNodeByWeaponInstId(instId)
|
||
else
|
||
view.equippedNode.gameObject:SetActive(false)
|
||
end
|
||
if view.equippedSpace then
|
||
view.equippedSpace.gameObject:SetActive(view.equippedNode.gameObject.activeSelf)
|
||
end
|
||
end
|
||
end
|
||
|
||
function UIUtils.displayEquipInfo(view, loader, itemId, instId)
|
||
local equipCfg = Tables.equipTable[itemId]
|
||
view.equipLvTxt.text = equipCfg.minWearLv
|
||
view.equipSuitNode:InitEquipSuitNode(itemId)
|
||
local hasInst = CharInfoUtils.getEquipByInstId(instId) ~= nil
|
||
if hasInst then
|
||
view.weaponAttributeNode:InitEquipAttributeNode(instId)
|
||
else
|
||
view.weaponAttributeNode:InitEquipAttributeNodeByTemplateId(itemId)
|
||
end
|
||
if view.equippedNode then
|
||
if hasInst then
|
||
view.equippedNode:InitEquippedNodeByEquipInstId(instId)
|
||
else
|
||
view.equippedNode.gameObject:SetActive(false)
|
||
end
|
||
if view.equippedSpace then
|
||
view.equippedSpace.gameObject:SetActive(view.equippedNode.gameObject.activeSelf)
|
||
end
|
||
end
|
||
end
|
||
|
||
function UIUtils.displayWeaponGemInfo(view, loader, itemId, instId)
|
||
view.gemSkillNode:InitGemSkillNode(instId)
|
||
if view.equippedNode then
|
||
if instId and instId > 0 then
|
||
view.equippedNode:InitEquippedNodeByGemInstId(instId)
|
||
else
|
||
view.equippedNode.gameObject:SetActive(false)
|
||
end
|
||
end
|
||
if view.domainTagNode then
|
||
local domainId
|
||
local isInst = instId and instId > 0
|
||
if isInst then
|
||
local gemInst = CharInfoUtils.getGemByInstId(instId)
|
||
if gemInst then
|
||
domainId = gemInst.domainId
|
||
end
|
||
end
|
||
view.domainTagNode:InitDomainTagNode(domainId)
|
||
end
|
||
end
|
||
|
||
function UIUtils.displayGiftItemTags(view, itemId)
|
||
local _, giftData = Tables.giftItemTable:TryGetValue(itemId)
|
||
if not giftData or #giftData.tagList == 0 then
|
||
view.gameObject:SetActive(false)
|
||
return
|
||
end
|
||
view.gameObject:SetActive(true)
|
||
view.tagCellCache = view.tagCellCache or UIUtils.genCellCache(view.tagCell)
|
||
view.tagCellCache:Refresh(#giftData.tagList, function(cell, index)
|
||
local tagId = giftData.tagList[CSIndex(index)]
|
||
local _, tagData = Tables.tagDataTable:TryGetValue(tagId)
|
||
if tagData then
|
||
cell.nameTxt.text = tagData.tagName
|
||
end
|
||
end)
|
||
end
|
||
|
||
function UIUtils.checkText(text, errHint)
|
||
if string.isEmpty(text) then
|
||
return errHint
|
||
end
|
||
return text
|
||
end
|
||
|
||
|
||
|
||
|
||
|
||
function UIUtils.getShortLeftTime(leftSec)
|
||
if leftSec < Const.SEC_PER_MIN then
|
||
return string.format(Language.TIME_FORMAT_MIN, 0)
|
||
elseif leftSec < Const.SEC_PER_HOUR then
|
||
return string.format(Language.TIME_FORMAT_MIN, math.floor(leftSec / Const.SEC_PER_MIN))
|
||
elseif leftSec < Const.SEC_PER_DAY then
|
||
return string.format(Language.TIME_FORMAT_HOUR, math.floor(leftSec / Const.SEC_PER_HOUR))
|
||
else
|
||
return string.format(Language.TIME_FORMAT_DAY, math.floor(leftSec / Const.SEC_PER_DAY))
|
||
end
|
||
end
|
||
|
||
|
||
function UIUtils.getSecondsLeftTime(leftSec)
|
||
if leftSec < 0 then
|
||
leftSec = 0
|
||
end
|
||
leftSec = math.floor(leftSec)
|
||
return string.format(Language.TIME_FORMAT_SEC, leftSec)
|
||
end
|
||
|
||
|
||
|
||
|
||
|
||
|
||
function UIUtils.getFullLeftTime(leftSec)
|
||
if leftSec < 0 then
|
||
leftSec = 0
|
||
end
|
||
local days = math.floor(leftSec / Const.SEC_PER_DAY)
|
||
local hours = math.floor((leftSec % Const.SEC_PER_DAY) / Const.SEC_PER_HOUR)
|
||
local minutes = math.floor((leftSec % Const.SEC_PER_HOUR) / Const.SEC_PER_MIN)
|
||
if days >= 1 then
|
||
return string.format(Language.TIME_FORMAT_DAY_HOUR_MIN, days, hours, minutes)
|
||
end
|
||
return UIUtils.getLeftTime(leftSec)
|
||
end
|
||
|
||
|
||
|
||
|
||
|
||
function UIUtils.getLeftTime(leftSec)
|
||
if leftSec < Const.SEC_PER_MIN then
|
||
return string.format(Language.TIME_FORMAT_MIN, 0)
|
||
elseif leftSec < Const.SEC_PER_HOUR then
|
||
return string.format(Language.TIME_FORMAT_MIN, math.floor(leftSec / Const.SEC_PER_MIN))
|
||
elseif leftSec < Const.SEC_PER_DAY then
|
||
local hourTime = math.floor(leftSec / Const.SEC_PER_HOUR)
|
||
local minTime = math.floor((leftSec % Const.SEC_PER_HOUR) / Const.SEC_PER_MIN)
|
||
return string.format(Language.TIME_FORMAT_HOUR_MIN, hourTime, minTime)
|
||
else
|
||
local dayTime = math.floor(leftSec / Const.SEC_PER_DAY)
|
||
local hourTime = math.floor((leftSec % Const.SEC_PER_DAY) / Const.SEC_PER_HOUR)
|
||
return string.format(Language.TIME_FORMAT_DAY_HOUR, dayTime, hourTime)
|
||
end
|
||
end
|
||
|
||
|
||
|
||
|
||
function UIUtils.getLeftTimeToSecond(leftSec)
|
||
leftSec = lume.round(leftSec)
|
||
if leftSec <= Const.SEC_PER_HOUR then
|
||
local format = Language.TIME_FORMAT_ONE_COLON
|
||
return string.format(format, math.floor(leftSec / Const.SEC_PER_MIN), math.fmod(leftSec, Const.SEC_PER_MIN))
|
||
else
|
||
local hourTime = math.floor(leftSec / Const.SEC_PER_HOUR)
|
||
local minTime = math.floor((leftSec % Const.SEC_PER_HOUR) / Const.SEC_PER_MIN)
|
||
local secTime = math.fmod((leftSec % Const.SEC_PER_HOUR), Const.SEC_PER_MIN)
|
||
local format = Language.TIME_FORMAT_TWO_COLON
|
||
return string.format(format, hourTime, minTime, secTime)
|
||
end
|
||
end
|
||
|
||
function UIUtils.setItemSprite(img, id, self, isBig)
|
||
local data = Tables.itemTable:GetValue(id)
|
||
local sprite
|
||
if isBig then
|
||
img:LoadSprite(UIConst.UI_SPRITE_ITEM_BIG, data.iconId)
|
||
end
|
||
if not sprite then
|
||
img:LoadSprite(UIConst.UI_SPRITE_ITEM, data.iconId)
|
||
end
|
||
end
|
||
|
||
function UIUtils.tryGetTagList(itemId, itemType)
|
||
if not itemType then
|
||
local itemData = Tables.itemTable[itemId]
|
||
itemType = itemData.type
|
||
end
|
||
|
||
if itemType == GEnums.ItemType.NormalBuilding or itemType == GEnums.ItemType.FuncBuilding then
|
||
local machineId = FactoryUtils.getItemBuildingId(itemId)
|
||
local succ, machineId2TagIdData = Tables.factoryMachineId2tagIdsTable:TryGetValue(machineId)
|
||
if not succ then
|
||
return false
|
||
end
|
||
return true, machineId2TagIdData.tagIds
|
||
end
|
||
|
||
local succ, ingredientId2TagIdData = Tables.factoryResourceItemId2TagIdTable:TryGetValue(itemId)
|
||
if not succ then
|
||
return false
|
||
end
|
||
|
||
local tagIds = {}
|
||
local count = 0
|
||
local facCore = GameInstance.player.remoteFactory.core
|
||
for craftId, tagId in pairs(ingredientId2TagIdData.craftId2TagId) do
|
||
if facCore:IsFormulaVisible(craftId) then
|
||
if not lume.find(tagIds, tagId) then
|
||
tagIds[count] = tagId
|
||
count = count + 1
|
||
end
|
||
end
|
||
end
|
||
|
||
if count == 0 then
|
||
return false
|
||
end
|
||
tagIds.Count = count
|
||
return true, tagIds
|
||
end
|
||
|
||
|
||
|
||
function UIUtils.getTrackerColorByMissionImportance(t)
|
||
return DataManager.worldSetting.missionIconColor[t]
|
||
end
|
||
|
||
|
||
function UIUtils.getNumTextByLanguage(num)
|
||
return Language[string.format("LUA_NUM_%d", num)]
|
||
end
|
||
|
||
function UIUtils.setFacBuffColorText(uiText, text, isBuff)
|
||
local colorStr = UIConst.FAC_BUILDING_DEBUFF_COLOR_STR
|
||
if isBuff then
|
||
colorStr = UIConst.FAC_BUILDING_BUFF_COLOR_STR
|
||
end
|
||
uiText.text = string.format(UIConst.COLOR_STRING_FORMAT,
|
||
colorStr, text)
|
||
end
|
||
|
||
function UIUtils.childrenArrayActive(root, activeCount)
|
||
local childrenCount = root.transform.childCount
|
||
for i = 0, childrenCount - 1 do
|
||
local child = root.transform:GetChild(i)
|
||
child.gameObject:SetActive(i < activeCount)
|
||
end
|
||
end
|
||
|
||
function UIUtils.useItemOnTip(itemId)
|
||
if GameInstance.playerController.mainCharacter == nil or
|
||
GameInstance.playerController.mainCharacter:HasTag(CS.Beyond.Gameplay.PredefinedTag.ForbiddenUsingItem) then
|
||
Notify(MessageConst.SHOW_TOAST, Language.LUA_ITEM_BAR_TAG_FORBIDDEN)
|
||
return false
|
||
end
|
||
if GameInstance.mode:IsItemForbidden(itemId) then
|
||
Notify(MessageConst.SHOW_TOAST, Language.LUA_ITEM_BAR_TOAST_GAME_MODE_FORBID)
|
||
return false
|
||
end
|
||
local useItemData = Tables.useItemTable:GetValue(itemId)
|
||
if useItemData.uiType == GEnums.ItemUseUiType.SingleHeal or
|
||
useItemData.uiType == GEnums.ItemUseUiType.AllHeal or
|
||
useItemData.uiType == GEnums.ItemUseUiType.Revive or
|
||
useItemData.uiType == GEnums.ItemUseUiType.Alive or
|
||
useItemData.uiType == GEnums.ItemUseUiType.SingleUsp or
|
||
useItemData.uiType == GEnums.ItemUseUiType.AllUsp then
|
||
UIManager:Open(PanelId.TacticalItem, { itemId = itemId })
|
||
return true
|
||
elseif useItemData.uiType == GEnums.ItemUseUiType.Throw then
|
||
if GameInstance.player.inventory:UseItem(Utils.getCurrentScope(), itemId) then
|
||
return true
|
||
end
|
||
end
|
||
return false
|
||
end
|
||
|
||
function UIUtils.lineLog(title, sep)
|
||
local lines = {
|
||
string.format("====== %s ======", title)
|
||
}
|
||
sep = sep or " :: "
|
||
return function(...)
|
||
local t = {...}
|
||
local st = {}
|
||
for _, v in ipairs(t) do
|
||
st[#st + 1] = tostring(v)
|
||
end
|
||
local line = table.concat(st, sep)
|
||
if not line:isEmpty() then
|
||
table.insert(lines, line)
|
||
else
|
||
logger.error(table.concat(lines, "\n"))
|
||
end
|
||
end
|
||
end
|
||
|
||
function UIUtils.parseAllRecipedAsInput(itemId)
|
||
|
||
end
|
||
|
||
function UIUtils.getCellNums(width, space, cellWidthList)
|
||
local nums = {}
|
||
local count = #cellWidthList
|
||
local curWidth = 0
|
||
local curCellNum = 0
|
||
for i = 1, count do
|
||
local cellWidth = cellWidthList[i]
|
||
if curWidth == 0 then
|
||
curWidth = cellWidth
|
||
else
|
||
curWidth = curWidth + cellWidth + space
|
||
end
|
||
|
||
if curWidth > width then
|
||
local num = i - curCellNum - 1
|
||
table.insert(nums, num)
|
||
curCellNum = i - 1
|
||
curWidth = cellWidth
|
||
end
|
||
end
|
||
|
||
if count > curCellNum then
|
||
table.insert(nums, count - curCellNum)
|
||
end
|
||
|
||
return nums
|
||
end
|
||
|
||
function UIUtils.setItemStorageCountText(storageCountNode, itemId, needCount, ignoreInSafeZone)
|
||
local inventory = GameInstance.player.inventory
|
||
local itemData = Tables.itemTable[itemId]
|
||
local isMoneyType = inventory:IsMoneyType(itemData.type)
|
||
local valuableDepotType = itemData.valuableTabType
|
||
local isValuableItem = valuableDepotType ~= GEnums.ItemValuableDepotType.Factory
|
||
local count, bagCount, _ = Utils.getItemCount(itemId, ignoreInSafeZone, true)
|
||
if ignoreInSafeZone or Utils.isInSafeZone() or isMoneyType or isValuableItem then
|
||
storageCountNode:InitStorageNode(count, needCount, true)
|
||
else
|
||
storageCountNode:InitStorageNode(bagCount, needCount, false)
|
||
end
|
||
end
|
||
|
||
function UIUtils.setNoEnoughCountColor(countStr)
|
||
UIUtils.setCountColor(countStr, true)
|
||
end
|
||
|
||
function UIUtils.setCountColor(countStr, isLack)
|
||
if isLack then
|
||
return string.format(UIConst.COLOR_STRING_FORMAT, UIConst.COUNT_NOT_ENOUGH_COLOR_STR, countStr)
|
||
else
|
||
return countStr
|
||
end
|
||
end
|
||
|
||
function UIUtils.setCountColorByCustomColor(countStr, isLack, customLackColorStr)
|
||
if isLack then
|
||
local color = string.isEmpty(customLackColorStr) and UIConst.COUNT_NOT_ENOUGH_COLOR_STR or customLackColorStr
|
||
return string.format(UIConst.COLOR_STRING_FORMAT, color, countStr)
|
||
else
|
||
return countStr
|
||
end
|
||
end
|
||
|
||
function UIUtils.PlayAnimationAndToggleActive(animationWrapper, isOn, callback)
|
||
animationWrapper:ClearTween(false)
|
||
if animationWrapper.gameObject.activeSelf == isOn then
|
||
if isOn then
|
||
|
||
animationWrapper:SampleToInAnimationEnd()
|
||
end
|
||
if callback then
|
||
callback()
|
||
end
|
||
return
|
||
end
|
||
|
||
if isOn then
|
||
animationWrapper.gameObject:SetActive(true)
|
||
animationWrapper:PlayInAnimation(callback)
|
||
else
|
||
animationWrapper:PlayOutAnimation(function()
|
||
if animationWrapper and animationWrapper.gameObject then
|
||
animationWrapper.gameObject:SetActiveIfNecessary(false)
|
||
end
|
||
if callback then
|
||
callback()
|
||
end
|
||
end)
|
||
end
|
||
end
|
||
|
||
function UIUtils.inTimeline()
|
||
local inTimeline = GameWorld.cutsceneManager.isMainTimelinePlaying
|
||
return inTimeline
|
||
end
|
||
|
||
function UIUtils.inCG()
|
||
local inCG = VideoManager.isPlayingFMV
|
||
return inCG
|
||
end
|
||
|
||
function UIUtils.inDialog()
|
||
local inDialog = GameWorld.dialogManager.isPlaying
|
||
return inDialog
|
||
end
|
||
|
||
function UIUtils.inCinematic()
|
||
return UIUtils.inCG() or UIUtils.inTimeline() or UIUtils.inDialog()
|
||
end
|
||
|
||
function UIUtils.inDungeon()
|
||
return GameInstance.dungeonManager.inDungeon
|
||
end
|
||
|
||
function UIUtils.IsPhaseLevelOnTop()
|
||
return PhaseManager:GetTopPhaseId() == PhaseId.Level
|
||
end
|
||
|
||
|
||
function UIUtils.usingBlockTransition()
|
||
local BlockGlitchTransition = require_ex("UI/Panels/BlockGlitchTransition/BlockGlitchTransitionCtrl")
|
||
return BlockGlitchTransition.BlockGlitchTransitionCtrl.s_renderTexture ~= nil
|
||
end
|
||
|
||
function UIUtils.getTextShowDuration(text, tSpeed)
|
||
local speed = tSpeed or 1
|
||
local duration = I18nUtils.GetTextShowDuration(text)
|
||
return duration / speed
|
||
end
|
||
|
||
function UIUtils.removePattern(str, pattern)
|
||
local result = ""
|
||
for match in string.gmatch(str, pattern) do
|
||
local cleaned = string.gsub(match, "{.*}", "")
|
||
result = result .. cleaned
|
||
end
|
||
if string.isEmpty(result) then
|
||
result = str
|
||
end
|
||
return result
|
||
end
|
||
|
||
function UIUtils.loadSprite(loader, path, name)
|
||
local fullPath = UIUtils.getSpritePath(path, name)
|
||
if BEYOND_DEBUG then
|
||
|
||
local fullDevPath = UIUtils.getSpriteDevPath(path, name)
|
||
if ResourceManager.CheckExists(fullDevPath) then
|
||
fullPath = fullDevPath
|
||
end
|
||
end
|
||
local pathHash = __beyond_calculate_ab_path_hash(fullPath)
|
||
if not ResourceManager.CheckExistsWithStringPathHash(pathHash) then
|
||
|
||
logger.error("资源不存在", fullPath, pathHash)
|
||
return nil
|
||
end
|
||
local sprite = loader:LoadSprite(fullPath)
|
||
return sprite
|
||
end
|
||
|
||
function UIUtils.getPuzzleColorByColorType(colorType)
|
||
local colorStr = UIConst.MINI_PUZZLE_GAME_ECOLOR_STR[colorType]
|
||
colorStr = string.isEmpty(colorStr) and "FF00FF" or colorStr
|
||
return UIUtils.getColorByString(colorStr)
|
||
end
|
||
|
||
function UIUtils.calcPivotVecByData(data, puzzleCellSize, puzzleCellPadding)
|
||
|
||
local centerCell = data.originBlocks[0]
|
||
local xMax = centerCell.x
|
||
local xMin = centerCell.x
|
||
local yMax = centerCell.y
|
||
local yMin = centerCell.y
|
||
for _, originBlock in pairs(data.originBlocks) do
|
||
xMax = math.max(xMax, originBlock.x)
|
||
xMin = math.min(xMin, originBlock.x)
|
||
yMax = math.max(yMax, originBlock.y)
|
||
yMin = math.min(yMin, originBlock.y)
|
||
end
|
||
|
||
local width = (xMax - xMin + 1) * (puzzleCellSize + 2 * puzzleCellPadding)
|
||
local height = (yMax - yMin + 1) * (puzzleCellSize + 2 * puzzleCellPadding)
|
||
local centerX = ((centerCell.x - xMin) * 2 + 1) * (puzzleCellSize / 2 + puzzleCellPadding)
|
||
local centerY = ((centerCell.y - yMin) * 2 + 1) * (puzzleCellSize / 2 + puzzleCellPadding)
|
||
return Vector2(centerX / width, centerY / height)
|
||
end
|
||
|
||
function UIUtils.splitItem(slotIndex)
|
||
local toSlot = GameInstance.player.inventory.itemBag:GetOrFallback(Utils.getCurrentScope()):GetFirstEmptySlotIndex()
|
||
if toSlot < 0 then
|
||
Notify(MessageConst.SHOW_TOAST, Language.LUA_ITEM_TIPS_TOAST_1)
|
||
return
|
||
end
|
||
UIManager:Open(PanelId.ItemSplit, {
|
||
slotIndex = slotIndex,
|
||
})
|
||
end
|
||
|
||
function UIUtils.getRewardFirstItem(rewardId)
|
||
|
||
local rewardTableData = Tables.rewardTable[rewardId]
|
||
return rewardTableData.itemBundles[0]
|
||
end
|
||
|
||
function UIUtils.getSoilRewardFirstItem(rewardId)
|
||
|
||
local rewardTableData = Tables.rewardSoilTable[rewardId]
|
||
return rewardTableData.itemBundles[0]
|
||
end
|
||
|
||
function UIUtils.getRewardItems(rewardId, items)
|
||
|
||
local _, rewardTableData = Tables.rewardTable:TryGetValue(rewardId)
|
||
items = items or {}
|
||
if rewardTableData then
|
||
|
||
for _, v in pairs(rewardTableData.itemBundles) do
|
||
table.insert(items, v)
|
||
end
|
||
else
|
||
logger.error("RewardTable表数据缺失!reward id:" .. rewardId)
|
||
end
|
||
return items
|
||
end
|
||
|
||
|
||
function UIUtils.getRewardItemsMergeSameId(rewardId, items)
|
||
local _, rewardTableData = Tables.rewardTable:TryGetValue(rewardId)
|
||
items = items or {}
|
||
if rewardTableData then
|
||
|
||
for _, v in pairs(rewardTableData.itemBundles) do
|
||
local found = false
|
||
|
||
for i, existingItem in ipairs(items) do
|
||
if existingItem.id == v.id then
|
||
local mergedItem = {
|
||
id = v.id,
|
||
count = existingItem.count + v.count
|
||
}
|
||
items[i] = mergedItem
|
||
found = true
|
||
break
|
||
end
|
||
end
|
||
if not found then
|
||
table.insert(items, {
|
||
id = v.id,
|
||
count = v.count,
|
||
})
|
||
end
|
||
end
|
||
else
|
||
logger.error("RewardTable表数据缺失!reward id:" .. rewardId)
|
||
end
|
||
return items
|
||
end
|
||
|
||
function UIUtils.getMonsterIconByMonsterId(monsterId)
|
||
return string.format("Assets/Beyond/DynamicAssets/Gameplay/UI/Sprites/Wiki/MonsterImage/%s.png", monsterId)
|
||
end
|
||
|
||
function UIUtils.getParentCenterAnchoredPosition(rectTransform)
|
||
local position = Vector2.zero
|
||
if rectTransform == nil then
|
||
return position
|
||
end
|
||
|
||
if rectTransform.parent == nil then
|
||
return position
|
||
end
|
||
|
||
local parentRectTransform = rectTransform.parent:GetComponent("RectTransform")
|
||
if parentRectTransform == nil then
|
||
return position
|
||
end
|
||
|
||
local anChorOffset = Vector2(
|
||
parentRectTransform.rect.width * (0.5 - rectTransform.anchorMin.x),
|
||
parentRectTransform.rect.height * (0.5 - rectTransform.anchorMin.y)
|
||
)
|
||
|
||
local pivotOffset = Vector2(
|
||
rectTransform.rect.width * (rectTransform.pivot.x - 0.5),
|
||
rectTransform.rect.height * (rectTransform.pivot.y - 0.5)
|
||
);
|
||
|
||
return anChorOffset + pivotOffset;
|
||
end
|
||
|
||
function UIUtils.getRomanNumberText(number)
|
||
if number < 1 or number > 10 then
|
||
return ""
|
||
end
|
||
return Language[string.format("ui_common_roman_num_%d", number)]
|
||
end
|
||
|
||
function UIUtils.setItemRarityImage(img, rarity)
|
||
local rarityColor = UIUtils.getItemRarityColor(rarity)
|
||
img.color = rarityColor
|
||
end
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
function UIUtils.getEnemyInfoByIdAndLevel(enemyId, enemyLevel)
|
||
local hasEnemyCfg, enemyCfg = Tables.enemyTable:TryGetValue(enemyId)
|
||
local hasEnemyDisplayInfoCfg, enemyDisplayInfoCfg = Tables.enemyDisplayInfoTable:TryGetValue(enemyId)
|
||
|
||
if not hasEnemyCfg and not hasEnemyDisplayInfoCfg then
|
||
logger.error(string.format("敌人表和敌人展示信息表中都找不到enemyId:%s。", enemyId))
|
||
return
|
||
end
|
||
|
||
|
||
local enemyTemplateId = hasEnemyCfg and enemyCfg.templateId or (hasEnemyDisplayInfoCfg and enemyDisplayInfoCfg.templateId)
|
||
local hasEnemyTemplateDisplayCfg, enemyTemplateDisplayCfg = Tables.enemyTemplateDisplayInfoTable:TryGetValue(enemyTemplateId)
|
||
if not hasEnemyTemplateDisplayCfg then
|
||
logger.error(string.format("敌人模板展示信息表中都找不到enemyTemplateId:%s,enemyId:%s。", enemyTemplateId, enemyId))
|
||
return
|
||
end
|
||
|
||
local enemyInfo = {}
|
||
|
||
enemyInfo.name = (hasEnemyDisplayInfoCfg and not string.isEmpty(enemyDisplayInfoCfg.name)) and
|
||
enemyDisplayInfoCfg.name or enemyTemplateDisplayCfg.name
|
||
enemyInfo.desc = (hasEnemyDisplayInfoCfg and not string.isEmpty(enemyDisplayInfoCfg.description)) and
|
||
enemyDisplayInfoCfg.description or enemyTemplateDisplayCfg.description
|
||
enemyInfo.level = enemyLevel
|
||
enemyInfo.templateId = enemyTemplateId
|
||
|
||
enemyInfo.ability = {}
|
||
|
||
local abilityIds = (hasEnemyDisplayInfoCfg and enemyDisplayInfoCfg.abilityDescIds.Count > 0) and
|
||
enemyDisplayInfoCfg.abilityDescIds or enemyTemplateDisplayCfg.abilityDescIds
|
||
for _, abilityId in pairs(abilityIds) do
|
||
local abilityDescCfg = Tables.enemyAbilityDescTable[abilityId]
|
||
table.insert(enemyInfo.ability, {
|
||
abilityId = abilityDescCfg.abilityId,
|
||
name = abilityDescCfg.name,
|
||
description = abilityDescCfg.description,
|
||
})
|
||
end
|
||
|
||
return enemyInfo
|
||
end
|
||
|
||
|
||
|
||
|
||
|
||
function UIUtils.isItemTypeForbidden(dungeonId, itemType)
|
||
local _, subGameInstData = DataManager.subGameInstDataTable:TryGetValue(dungeonId)
|
||
if not subGameInstData then
|
||
return false
|
||
end
|
||
|
||
local _, gameModeData = DataManager.gameModeTable:TryGetData(subGameInstData.modeId)
|
||
if not gameModeData then
|
||
return false
|
||
end
|
||
|
||
if not gameModeData.functionSettings then
|
||
return false
|
||
end
|
||
|
||
for index, functionSetting in cs_pairs(gameModeData.functionSettings) do
|
||
if functionSetting.modeFuncType == GEnums.GameModeFuncType.ForbidUseItemType then
|
||
local funcParams = functionSetting.funcParams
|
||
if funcParams and funcParams.itemTypes and
|
||
funcParams.itemTypes:Contains(itemType) then
|
||
return true
|
||
end
|
||
end
|
||
end
|
||
|
||
return false
|
||
end
|
||
|
||
|
||
function UIUtils.convertRewardItemBundlesToDataList(itemBundles, isIncremental)
|
||
local rewardItemDataList = {}
|
||
|
||
if itemBundles == nil or itemBundles.Count == 0 then
|
||
return rewardItemDataList
|
||
end
|
||
|
||
for index = 0, itemBundles.Count - 1 do
|
||
local rewardItem = itemBundles[index]
|
||
local itemId = rewardItem.id
|
||
local success, itemData = Tables.itemTable:TryGetValue(itemId)
|
||
if success then
|
||
table.insert(rewardItemDataList, {
|
||
id = itemId,
|
||
count = rewardItem.count,
|
||
rarity = itemData.rarity,
|
||
sortId1 = itemData.sortId1,
|
||
sortId2 = itemData.sortId2,
|
||
})
|
||
end
|
||
end
|
||
|
||
table.sort(rewardItemDataList, Utils.genSortFunction({ "rarity", "sortId1", "sortId2", "id" }, isIncremental))
|
||
|
||
return rewardItemDataList
|
||
end
|
||
|
||
|
||
|
||
function UIUtils.getMobileHudPanelMaxHeight(panelHeight, minHudHeight, maxHudHeight)
|
||
|
||
|
||
local minSupHeight = CS.Beyond.UI.UIConst.STANDARD_VERTICAL_RESOLUTION
|
||
|
||
local maxSupHeight = CS.Beyond.UI.UIConst.STANDARD_HORIZONTAL_RESOLUTION
|
||
|
||
local realHeight = lume.clamp(panelHeight, minSupHeight, maxSupHeight)
|
||
local realMaxHeight = (realHeight - minSupHeight) / (maxSupHeight - minSupHeight) *
|
||
(maxHudHeight - minHudHeight) + minHudHeight
|
||
|
||
return realMaxHeight
|
||
end
|
||
|
||
|
||
function UIUtils.commonAdaptHudTrack(view, config)
|
||
local layoutGroup = view.verticalLayoutGroup
|
||
local padding = layoutGroup.padding.vertical
|
||
local spacing = layoutGroup.spacing
|
||
local diffY = config.DIFF_HEIGHT or 0
|
||
LayoutRebuilder.ForceRebuildLayoutImmediate(view.rectTransform)
|
||
LayoutRebuilder.ForceRebuildLayoutImmediate(view.objectiveContent)
|
||
|
||
local hasVaryingNode = view.varyingNode.gameObject.activeInHierarchy
|
||
local varyingHeight = hasVaryingNode and view.varyingNode.rect.height + spacing or 0
|
||
local contentHeight = view.objectiveContent.rect.height + spacing + (hasVaryingNode and 0 or diffY)
|
||
local realMainHeight = padding + view.headNode.rect.height + contentHeight + varyingHeight
|
||
local width = view.rectTransform.rect.width
|
||
|
||
|
||
local rectHeight = realMainHeight
|
||
local canScrollContent = false
|
||
if DeviceInfo.usingTouch then
|
||
|
||
|
||
local minSupHeight = CS.Beyond.UI.UIConst.STANDARD_VERTICAL_RESOLUTION
|
||
|
||
local maxSupHeight = CS.Beyond.UI.UIConst.STANDARD_HORIZONTAL_RESOLUTION
|
||
|
||
local realHeight = lume.clamp(view.rectTransform.rect.height, minSupHeight, maxSupHeight)
|
||
local realMaxHeight = (realHeight - minSupHeight) / (maxSupHeight - minSupHeight) *
|
||
(config.MAX_MAIN_RECT_HEIGHT_FOR_MOBILE - config.MIN_MAIN_RECT_HEIGHT_FOR_MOBILE) +
|
||
config.MIN_MAIN_RECT_HEIGHT_FOR_MOBILE
|
||
|
||
rectHeight = math.min(realMainHeight, realMaxHeight)
|
||
canScrollContent = realMainHeight > realMaxHeight
|
||
end
|
||
|
||
view.rectTransform.sizeDelta = Vector2(width, rectHeight)
|
||
view.contentScrollView.enabled = canScrollContent
|
||
view.arrowBottomNode.gameObject:SetActiveIfNecessary(canScrollContent)
|
||
|
||
if canScrollContent then
|
||
view.contentScrollView:ScrollTo(Vector2(0, -1), true)
|
||
end
|
||
|
||
return canScrollContent
|
||
end
|
||
|
||
|
||
function UIUtils.commonAdaptHudTrackV2(view, config, canFoldThresholdOffsetY)
|
||
local layoutGroup = view.verticalLayoutGroup
|
||
local padding = layoutGroup.padding.vertical
|
||
local spacing = layoutGroup.spacing
|
||
local canFoldThresholdOffsetY = canFoldThresholdOffsetY or 0
|
||
LayoutRebuilder.ForceRebuildLayoutImmediate(view.rectTransform)
|
||
LayoutRebuilder.ForceRebuildLayoutImmediate(view.objectiveContent)
|
||
|
||
local contentHeight = view.objectiveContent.rect.height + spacing
|
||
local realMainHeight = padding + view.headNode.rect.height + contentHeight
|
||
|
||
|
||
local rectFoldHeight = realMainHeight
|
||
local rectUnfoldHeight = realMainHeight
|
||
local scrollState = UIConst.TRACK_HUD_SCROLL_STATE.AlwaysCantScroll
|
||
local ignoreScrollMask = false
|
||
if DeviceInfo.usingTouch then
|
||
local canFoldThresholdForMobile = config.CAN_FOLD_THRESHOLD_FOR_MOBILE + canFoldThresholdOffsetY
|
||
|
||
|
||
|
||
local minSupHeight = CS.Beyond.UI.UIConst.STANDARD_VERTICAL_RESOLUTION
|
||
|
||
local maxSupHeight = CS.Beyond.UI.UIConst.STANDARD_HORIZONTAL_RESOLUTION
|
||
|
||
local realCanvasHeight = lume.clamp(view.rectTransform.rect.height, minSupHeight, maxSupHeight)
|
||
local maxTrackHudHeight = realCanvasHeight - UIConst.ON_TRACK_HUD_CONST_HEIGHT -
|
||
realCanvasHeight * UIConst.JOYSTICK_IN_SCREEN_HEIGHT_PROPORTION * (1 - UIConst.TRACK_HUD_UNFOLD_OCCLUSION_JOYSTICK_PROPORTION)
|
||
+ canFoldThresholdOffsetY
|
||
|
||
if realMainHeight <= canFoldThresholdForMobile then
|
||
scrollState = UIConst.TRACK_HUD_SCROLL_STATE.AlwaysCantScroll
|
||
rectFoldHeight = realMainHeight
|
||
rectUnfoldHeight = realMainHeight
|
||
ignoreScrollMask = false
|
||
elseif realMainHeight <= canFoldThresholdForMobile + config.CAN_FOLD_THRESHOLD_FOR_MOBILE_OFFSET then
|
||
scrollState = UIConst.TRACK_HUD_SCROLL_STATE.AlwaysCantScroll
|
||
rectFoldHeight = canFoldThresholdForMobile
|
||
rectUnfoldHeight = realMainHeight
|
||
ignoreScrollMask = true
|
||
elseif realMainHeight <= maxTrackHudHeight then
|
||
scrollState = UIConst.TRACK_HUD_SCROLL_STATE.CanScrollWhenFold
|
||
rectFoldHeight = canFoldThresholdForMobile
|
||
rectUnfoldHeight = realMainHeight
|
||
ignoreScrollMask = false
|
||
else
|
||
scrollState = UIConst.TRACK_HUD_SCROLL_STATE.AlwaysCanScroll
|
||
rectFoldHeight = canFoldThresholdForMobile
|
||
rectUnfoldHeight = maxTrackHudHeight
|
||
ignoreScrollMask = false
|
||
end
|
||
end
|
||
|
||
return ignoreScrollMask, scrollState, rectFoldHeight, rectUnfoldHeight
|
||
end
|
||
|
||
function UIUtils.getMovingItemMode()
|
||
local mode
|
||
if UIUtils.isBatchMovingItem() then
|
||
mode = CS.Proto.ITEM_MOVE_MODE.BatchItemId
|
||
elseif UIUtils.isQuickMovingItem() then
|
||
mode = CS.Proto.ITEM_MOVE_MODE.Grid
|
||
elseif UIUtils.isQuickMovingHalfItem() then
|
||
mode = CS.Proto.ITEM_MOVE_MODE.HalfGrid
|
||
end
|
||
return mode
|
||
end
|
||
|
||
function UIUtils.isBatchMovingItem()
|
||
return Input.GetKey(Unity.KeyCode.LeftControl) or Input.GetKey(Unity.KeyCode.RightControl)
|
||
end
|
||
|
||
function UIUtils.isQuickMovingItem()
|
||
return Input.GetKey(Unity.KeyCode.LeftShift) or Input.GetKey(Unity.KeyCode.RightShift)
|
||
end
|
||
|
||
function UIUtils.isQuickMovingHalfItem()
|
||
return Input.GetKey(Unity.KeyCode.LeftAlt) or Input.GetKey(Unity.KeyCode.RightAlt)
|
||
end
|
||
|
||
function UIUtils.getSettlementEnhanceEffectDesc(enhanceMoneyProduceSpeedRate, enhanceMoneyProfitRate, enhanceExpProfitRate)
|
||
local effectStr = ""
|
||
|
||
if enhanceMoneyProduceSpeedRate ~= 0 then
|
||
effectStr = string.format(Language.LUA_SETTLEMENT_ENHANCE_MONEY_PRODUCE_SPEED, enhanceMoneyProduceSpeedRate) .. "\n"
|
||
end
|
||
|
||
if enhanceMoneyProfitRate ~= 0 then
|
||
effectStr = effectStr .. string.format(Language.LUA_SETTLEMENT_ENHANCE_MONEY_PROFIT, enhanceMoneyProfitRate) .. "\n"
|
||
end
|
||
|
||
if enhanceExpProfitRate ~= 0 then
|
||
effectStr = effectStr .. string.format(Language.LUA_SETTLEMENT_ENHANCE_EXP_PROFIT, enhanceExpProfitRate)
|
||
end
|
||
return effectStr
|
||
end
|
||
|
||
|
||
function UIUtils.showItemSideTips(itemCell, tipsPosType, tipsPosTransform)
|
||
local posInfo
|
||
if DeviceInfo.usingController then
|
||
posInfo = {
|
||
tipsPosType = tipsPosType or UIConst.UI_TIPS_POS_TYPE.RightDown,
|
||
tipsPosTransform = tipsPosTransform or itemCell.transform,
|
||
isSideTips = true,
|
||
}
|
||
end
|
||
itemCell:ShowTips(posInfo)
|
||
end
|
||
|
||
|
||
|
||
|
||
function UIUtils.bindHyperlinkPopup(bindTarget, hyperlinkUITextGroupId, inputGroupId, actionId)
|
||
if string.isEmpty(actionId) then
|
||
actionId = "hyperlink_show_popup"
|
||
end
|
||
local bindId = UIUtils.bindInputPlayerAction(actionId, function()
|
||
Notify(MessageConst.SHOW_HYPERLINK_POPUP_BY_GROUP_ID, hyperlinkUITextGroupId)
|
||
end, inputGroupId)
|
||
local curValid = CS.Beyond.UI.UIText.IsHyperlinkUITextGroupDisplayable(hyperlinkUITextGroupId)
|
||
InputManagerInst:ToggleBinding(bindId, curValid)
|
||
MessageManager:Register(MessageConst.HYPERLINK_UITEXT_GROUP_DISPLAYABLE_CHANGE, function(args)
|
||
local groupId, isValid = unpack(args)
|
||
if groupId == hyperlinkUITextGroupId then
|
||
InputManagerInst:ToggleBinding(bindId, isValid)
|
||
logger.info("[Hyperlink] bind displayable change :", isValid)
|
||
end
|
||
end, bindTarget)
|
||
end
|
||
|
||
|
||
function UIUtils.bindControllerCamZoom(groupId)
|
||
local inId = UIUtils.bindInputPlayerAction("cam_zoom_in_ct", function()
|
||
Utils.zoomCamera(4)
|
||
end, groupId)
|
||
local outId = UIUtils.bindInputPlayerAction("cam_zoom_out_ct", function()
|
||
Utils.zoomCamera(-4)
|
||
end, groupId)
|
||
return inId, outId
|
||
end
|
||
|
||
function UIUtils.setTabIcons(cell, iconPath, iconName)
|
||
cell.selectedIcon:LoadSprite(iconPath, iconName)
|
||
cell.defaultIcon:LoadSprite(iconPath, iconName .. "_shadow")
|
||
end
|
||
|
||
function UIUtils.setTabIconsWithFullPath(cell, iconPath)
|
||
cell.selectedIcon:LoadSprite(iconPath)
|
||
cell.defaultIcon:LoadSprite(iconPath .. "_shadow")
|
||
end
|
||
|
||
function UIUtils.hideItemTipsOnLoseFocus(isFocused)
|
||
if not isFocused then
|
||
Notify(MessageConst.HIDE_ITEM_TIPS)
|
||
end
|
||
end
|
||
|
||
|
||
|
||
|
||
|
||
function UIUtils.waitMsgExecute(msg, msgGroupKey, callback)
|
||
local registerKey
|
||
registerKey = MessageManager:Register(msg, function(msgArg)
|
||
if not callback(msgArg) then
|
||
MessageManager:Unregister(registerKey)
|
||
Notify(MessageConst.ON_WAIT_MSG_EXECUTE_COMPLETE, registerKey)
|
||
end
|
||
end, msgGroupKey)
|
||
return registerKey
|
||
end
|
||
|
||
|
||
function UIUtils.isBattleControllerModifyKeyChanged()
|
||
return CS.Beyond.GameSetting.gamepadCacheSkillCombo
|
||
end
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
function UIUtils.updateStaminaNode(node, staminaInfo)
|
||
node.descStaminaTxt.text = string.isEmpty(staminaInfo.descStamina) and Language["ui_dungeon_details_ap_refresh"] or
|
||
staminaInfo.descStamina
|
||
|
||
local costStamina = staminaInfo.costStamina
|
||
local isLack = GameInstance.player.inventory.curStamina < costStamina
|
||
node.costStaminaTxt.text = UIUtils.setCountColor(costStamina, isLack)
|
||
|
||
local delStamina = staminaInfo.delStamina
|
||
local hasDelStamina = delStamina ~= nil and type(delStamina) == "number"
|
||
node.delStaminaTxt.text = hasDelStamina and delStamina or 0
|
||
node.delStaminaTxt.gameObject:SetActive(hasDelStamina)
|
||
end
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
|
||
function UIUtils.initSearchInput(inputField, initInfo)
|
||
if inputField == nil or initInfo == nil then
|
||
return
|
||
end
|
||
|
||
if initInfo.characterLimit ~= nil then
|
||
inputField.characterLimit = initInfo.characterLimit
|
||
else
|
||
inputField.characterLimit = UIConst.INPUT_FIELD_NAME_CHARACTER_LIMIT
|
||
end
|
||
|
||
if initInfo.clearBtn ~= nil then
|
||
initInfo.clearBtn.gameObject:SetActive(not string.isEmpty(inputField.text))
|
||
end
|
||
|
||
inputField.onValueChanged:RemoveAllListeners()
|
||
inputField.onValueChanged:AddListener(function(str)
|
||
if initInfo.clearBtn ~= nil then
|
||
local isPsController = Utils.checkIsPSDevice()
|
||
if isPsController then
|
||
|
||
initInfo.clearBtn.gameObject:SetActive(false)
|
||
else
|
||
initInfo.clearBtn.gameObject:SetActive(not string.isEmpty(str))
|
||
end
|
||
end
|
||
|
||
if initInfo.onInputValueChanged ~= nil then
|
||
initInfo.onInputValueChanged(str)
|
||
end
|
||
end)
|
||
|
||
|
||
if initInfo.onInputSubmit ~= nil then
|
||
inputField.onSubmit:RemoveAllListeners()
|
||
inputField.onSubmit:AddListener(function(newText)
|
||
if Utils.checkIsPSDevice() then
|
||
return
|
||
end
|
||
initInfo.onInputSubmit(newText)
|
||
end)
|
||
end
|
||
|
||
|
||
inputField.onFocused:RemoveAllListeners()
|
||
inputField.onFocused:AddListener(function()
|
||
local isPsController = Utils.checkIsPSDevice()
|
||
if initInfo.clearBtn ~= nil and isPsController then
|
||
initInfo.clearBtn.gameObject:SetActive(false)
|
||
end
|
||
|
||
if initInfo.onInputFocused ~= nil then
|
||
initInfo.onInputFocused()
|
||
end
|
||
end)
|
||
|
||
|
||
inputField.onEndEdit:RemoveAllListeners()
|
||
inputField.onEndEdit:AddListener(function(newText)
|
||
local isPsController = Utils.checkIsPSDevice()
|
||
if initInfo.clearBtn ~= nil and isPsController then
|
||
initInfo.clearBtn.gameObject:SetActive(not string.isEmpty(inputField.text))
|
||
end
|
||
|
||
if initInfo.onInputEndEdit ~= nil then
|
||
initInfo.onInputEndEdit(newText)
|
||
end
|
||
end)
|
||
|
||
|
||
if initInfo.clearBtn ~= nil and initInfo.onClearClick ~= nil then
|
||
initInfo.clearBtn.onClick:RemoveAllListeners()
|
||
initInfo.clearBtn.onClick:AddListener(function()
|
||
initInfo.onClearClick()
|
||
CS.UnityEngine.EventSystems.EventSystem.current:SetSelectedGameObject(inputField.gameObject);
|
||
end)
|
||
end
|
||
|
||
|
||
if initInfo.searchBtn ~= nil and initInfo.onSearchClick ~= nil then
|
||
initInfo.searchBtn.onClick:RemoveAllListeners()
|
||
initInfo.searchBtn.onClick:AddListener(function()
|
||
initInfo.onSearchClick()
|
||
end)
|
||
end
|
||
end
|
||
|
||
|
||
function UIUtils.getUIVideoFullPath(path)
|
||
if string.isEmpty(path) then
|
||
return false
|
||
end
|
||
return CS.Beyond.Gameplay.View.VideoManager.TryGetVideoPlayFullPath('UI/' .. path)
|
||
end
|
||
|
||
|
||
function UIUtils.inDungeonOrFocusMode()
|
||
return GameInstance.dungeonManager.inDungeon or FocusModeUtils.isInFocusMode
|
||
end
|
||
|
||
function UIUtils.isUIGOActive(go)
|
||
return go.activeInHierarchy and go.layer ~= UIConst.HIDE_LAYER
|
||
end
|
||
|
||
|
||
_G.UIUtils = UIUtils
|
||
return UIUtils
|