THREE.TextureLoader()以意外和错误的方式运行。该类的load()函数多次尝试/加载相同的资产(即20次或更多次)。
下图显示了使用浏览器控制台的此行为:
用于加载和使用纹理的代码如下:
Element.prototype.createShaderMaterial = function (uniforms, vertexShader, fragmentShader) {
var loader = new THREE.TextureLoader();
uniforms.texture.value = loader.load(this.texture);
return new THREE.ShaderMaterial({
uniforms: uniforms,
vertexShader: vertexShader,
fragmentShader: fragmentShader,
wireframe: true
});
};
您还可以在此处找到实时预览:https://alexprut.github.io/earth-defender/ 和游戏代码:https://github.com/alexprut/earth-defender/tree/master/client/js
做错了什么?为什么多次加载相同的图像?
答案 0 :(得分:0)
事实是THREE.TextureLoader()
默认情况下不会缓存纹理,但我认为它应该,或者至少要求你不要这样做。
这意味着如果您有400个具有相同纹理的对象,则库将为相同的资产发出400 HTTP请求。
下面是一个简单的解决方案(Singleton模式/模块模式)缓存模块:
var TextureLoader = (function () {
var _instance = null;
var Loader = function () {
var _loader = new THREE.TextureLoader();
var _cache = [];
function _cachePush(elem, val) {
_cache.push({
element: elem,
value: val
});
}
function _cacheSearch(elem) {
for (var i = 0; i < _cache.length; i++) {
if (_cache[i].element === elem) {
return _cache[i].value;
}
}
return false;
}
function load(texture) {
var match = _cacheSearch(texture);
if (match) {
return match;
}
var val = _loader.load(texture);
_cachePush(texture, val);
return val;
}
return {
load: load
}
};
function getInstance() {
return (_instance) ? _instance : _instance = Loader();
}
return {
getInstance: getInstance
}
})();
使用和缓存需要调用的纹理:
TextureLoader.getInstance().load(texture);