Reputation: 655
I am trying to use the fetch
statement to load a local image and use it in my (three.js) application. The way it's set up now, I get an infinite loop and I don't know why.
It's a large application so I pulled the relevant fragment out here:
var mesh;
function fetch_img(filename) {
fetch(filename).then(function(response) {
if (response.ok) {
return response.blob();
}
throw new Error('Network response was an error.');
}).then(function(blob) {
mesh.material.map.image.src = URL.createObjectURL(blob);
mesh.material.map.needsUpdate = true;
}).catch(function(error) {
console.log('Fetch failed because: ' + error.message);
});
}
function start() {
var material = new THREE.MeshBasicMaterial({
map: new THREE.TextureLoader().load('loading.jpg', function(texture) {
mesh = new THREE.Mesh(geometry, material);
scene.add(mesh);
fetch_img('test1.jpg');
})
});
}
The idea being that I use a 'loading' image and then when the scene is created and that is loaded, I load the real image by calling fetch_img()
. Ultimately I'll be calling fetch_img()
from a number of places based on user input.
I expect it's something I've done wrong trying to understand JavaScript Promises - can someone point me in the right direction?
Upvotes: 0
Views: 201
Reputation: 8876
Here is what is happening:
Inside THREE.TextureLoader
, it's using THREE.ImageLoader
. THREE.ImageLoader
creates an img
element, and assigns an onload
event listener to it. It then sets the img.src
to the URL you provide it.
When you give the image.src
property a new value, that event gets fired, and goes to its handler, which is still assigned to the anonymous function you gave it in your THREE.TextureLoader
definition.
The rest is recusrively history.
To fix it, create a new image, assign the URL to its src
property, then replace the whole map.image
with the new image.
Upvotes: 2