When it comes to using threejs the texture loader can be used load external image assets in the form of image files such as PNG files. Once the images are loaded they can then bee used a as textures for the various maps of a material such as a color map, or emissive map just to name a few as the final object that is furnished is an instance of the Texture class.
If what I want is the raw Image object to use in some other situation that does not call for Texture objects I could use the Image loader, but I have found that it might be better to just use the image property of a Texture object. Speaking of the Image loader there are a number of loaders built into threejs itself and the texture loader is just one of them. There are also a number of official loaders in the examples folder that have to do with loading all kinds of external file formats used by various 3d model editing programs such as blender such as the DAE file loader as well. All of these work off of the base loader class of threejs that one will want to learn a thing or two about as there are certain things that will apply to all loaders based off of this class.
One of the draw backs of using the texture loader is that it is just a simple extension of the Image loader that will create a new instance of a Texture object. If I am in a situation in which I have some JSON data for a texture that I want to load and parse into a texture object then the texture loader is not much help. I could take a moment to create my own loader that extends from the base loader class that will do what i think the texture loader should do. However I have found that a better way to do what I want with texture data, as well as just about everything else that I care about would be to just use the object loader.
In these examples I am using an absolute path to a file that I am hosting locally with the system that I am using. I will not be getting into the specifics about the differences between absolute and relative paths here as that is a bit off topic. However if you do not know what I am taking about then you should read up more on the topic of absolute and relative paths as it is something that you should get solid sooner or later.
When I wrote this post and the examples for this post I was using r127 of threejs, and the last time I came around to doing some editing I was using r146 of the library and so the demos where updated to my style rules for r146. I have got into the habit of making sure I always make note of the version of threejs that I am using since there are always code breaking changes being made to the library.
In my test threejs repository on Github the source code examples that I am writing about here can be found. I am also parking the source code examples for my many other posts on threejs there as well.
I often like to start out my posts with a basic, simple, hello world type example of a threejs feature. So then for this section I will be starting out with just a few basic examples of the texture loader that mainly just involve loading a single image file, to create a single texture object. Nothing fancy involving loading many files, or getting to deep into a closely related topic of some kind here.
In the example I will be loading just a single image that will result in a single texture object. This single texture will then be used to create just a basic color map for an instance of the THREE.BasicMatreial. I will then be just creating and adding a cube to a scene object that will use this material, and not do anything fancy with the uv attribute of the geometry, or more than one material at this time. As such the end result will the whole of the texture being displayed on each of the faces of the cube.
In this example I just passed a string to a single image as the first argument, and I also passed just a single call back function that will fire when the loading of the file is done. So then there is the question of what to do when it comes to loading not just one file, but a few files. Also what if there is a problem loading one or more files? With that said there should be a way to set a callback that will fire when something goes wrong. So with that said I think I should get around to making at least a few more examples of this texture loader.
So then there is the topic of how to go about loading more that one texture in threejs as the texture loader by itself will just load one image at a time. There are a number of ways of doing this sort of thing, so I will want to have more than one example here.
For this example I pass an array of urls to my load texture collection helper, inside the body of this helper that is given the array of urls I call the promise all method and pass the array of urls as the first argument, but I call the map method off of the array of urls, and call by load texture helper for each url. I then pass each url to the load texture method which will return a promise object for each url using the texture loader for each image.
If all goes well the end result will be an array of textures that will be available in the next then function call of the promise returned by the load texture collection helper. However I think it is always a good idea to have something in place that will fire in the event that sometime goes wrong loading the files. For this example when there is a problem I just create a single cube that makes use of the normal material, rater than two cubes that use each of the textures with the basic material.
This is something that I put together pretty fast, and there are a lot of other features I might want to add when it comes to turning this into some kind of actual support library or something to that effect. However say you all ready have a great way to go about loading a whole bunch of image files just the way you like to, and you just want to create textures with those images that are loaded all ready. Well you do not have to use the texture loader, in that case the THREE.Texture constrictor can just be called and a reference to each image can be passed as the first argument for the texture constrictor.
Although the Promise all solution that I made a while back seems to work okay, these days I am more of the minbdset of using the THREE.Loading manager for this sort of thing.
When it comes to making use of the texture loader often I will want to abstract away code that I find myself using over and over again into a module form that I can then just like to and use for every new project in which I will want to load a few textures. The most primitive form of this kind of module would be something that I just call a load method and then give a base url and a list of files that I will like to load at that base url. This load method will then return a promise and the resolved object will be an object where every key is a file name, and every value is a texture made from that file.
Here I have a basic example of the load method of this module that is based off of the load many manager example above. Now that I abstracted away much of what was in that example, the code is now a lot cleaner.
That will be it for now on the texture loader at least for today, there is a lot more to write about when it comes to what to do with a texture after it is loader rather than just how to go about loading a texture. In this post I wanted to just stick to using an external image for a color map of a cube, but I did not get into the various other kinds of maps there are to work with in the basic material, as well as the many other materials that will work with light sources. However I guess getting into all of that would be a matter for another post.