问题场景
有个UIPanelA,里面有个英雄列表,每个英雄头像是异步加载出来,接口形如
game.resMgr:LoadAsync(imgAssetPath, function(imgAsset){
heroIcon.texture = imgAsset
})
界面打开后执行加载会导致一个问题,原来的默认图片不是当前英雄头像,会突然变成对应的英雄头像。
如果换成空的头像,美术会说,忽然变掉了,体验不好。
所以需要处理异步图片加载导致的这个图片突然变化的问题。
现有情况分析
项目里的Panel的Prefab资源加载也是使用的异步加载方式。
当Prefab加载后,资源加载对象会调用传入的回调方法,在回调方法里会调用Panel对象Init方法显示出Panel,在这里会处理业务逻辑,再去异步加载英雄头像。所以会导致图片忽然切换了。
处理方案
打开界面时提前处理业务,进行资源的预加载操作。这些资源加载也计入Panel资源的加载,当Panel的Prefab,Icon都加载完毕才调用Init方法显示Panel和处理业务逻辑。Icon资源在加载的后缓存到一个table里面,下次可直接取用,关闭Panel的时候可以做自动释放。
伪代码如下,loader和回调方法需要自行实现,这里就讲个思路 |^o^|
class Panel
function onCreate()
local iconCallback = function(assetPath, iconAsset)
resMap[assetPath] = iconAsset
end
loader:loadAsset(assetPath1, iconCallback)
loader:loadAsset(assetPath2, iconCallback)
loader:loadAsset(assetPath3, iconCallback)
...
loader:addOnCompleteCallback(completeCallback{
Init()
})
function Init()
loadImg(image1, assetPath1)
loadImg(image2, assetPath2)
loadImg(image3, assetPath3)
end
function loadImg(image, assetPath)
if resMap[assetPath] then
image.sprite = resMap[assetPath]
else
loader:loadAsync(assetPath, function(asset)
resMap[assetPath] = asset
image.sprite = asset
end)
end
end