I'm a doctor, not a mechanic

Legacy:Object Pool

From Unreal Wiki, The Unreal Engine Documentation Site
Jump to: navigation, search

UT2003 Object Pool[edit]

Overview[edit]

The object pool allows you to dynamically assign and create objects during the game. A main use is that of allocating textures during the game as they are needed rather than creating all of them beforehand. This method is far easier and more versatile than manually creating all the files you may possibly need. There are of coures many other uses for the object pool but for this example I will use textures.

Allocating Objects[edit]

When you allocate an object the game will first check if any existing objects of that type are available for use and if not, will create a new one to be used. Allocating an object is a simple process, here is an example using a shader.

var Shader Shader1;
 
Shader1 = Shader(Level.ObjectPool.AllocateObject(class'Shader'));

That will first check the object pool for any existing Shader objects in the pool. If one is found it will be removed from the pool and returned as the reference. If none are available it will create a new Shader and return that instead.

Freeing Objects[edit]

Since most uses of the object pool are temporary you need to free up an object once you are done using it. This will add the object to the object pool for later use. This too is a simple process.

Level.ObjectPool.FreeObject(Shader1);

That line will add Shader1 back into the object pool where it can be re-allocated later as needed.

Important Notes[edit]

While the object pool is very simple and powerful there are several things you should be aware of.

You should clear any references to an object before you free it and place it back into the object pool.[edit]

var Shader Shader1;
var ConstantColor Fader1;
 
Fader1 = ConstantColor(Level.ObjectPool.AllocateObject(class'ConstantColor'));
Shader1 = Shader(Level.ObjectPool.AllocateObject(class'Shader'));
 
Shader1.Opacity = Fader1;
 
//code here
 
Level.ObjectPool.FreeObject(Fader1);
Level.ObjectPool.FreeObject(Shader1);

Note that after allocating the Shader and ConstantColor I assign Fader1 as the opacity value for Shader1. I must be careful how I free these objects up once I am done with them. The code above is incorrect. You cannot properly free Fader1 because it is in use and referenced by Shader1. Although not necessarily required it is generally a good idea to manually clear the reference as well to ensure that no problems occur. Therefore the proper way to free these objects would be as follows.

Shader1.Opacity = None;
Level.ObjectPool.FreeObject(Shader1);
Level.ObjectPool.FreeObject(Fader1);

As I said this is not necessarily required but it should be done anyways to ensure maximum compatibility and avoid any possible problems. Even though problems relating to this seem rare we are dealing with objects not actors and any problems tend to cause a GPF crash so you are most likely better safe than sorry.

Properties of an object are not reset to default when placed in the object pool but instead remain intact.[edit]

var Shader Shader1;
 
Shader1 = Shader(Level.ObjectPool.AllocateObject(class'Shader'));
Shader1.TwoSided = True;
 
Level.ObjectPool.FreeObject(Shader1);

In that example we allocate a Shader, set the TwoSided variable to true, then free the Shader and place it back into the object pool. This creates a huge problem. When you free Shader1 the TwoSided variable is not reset but remains as you left it. The next person to allocate a Shader may now get one that has TwoSided set to true. This is not the default value so if they do not expect this it can cause major compatibility problems. Although you can reset the variables yourself before you free the object this only works for your code and there is no garuntee that other scripts also running will be as courteous. As you can imagine the lack of consistency with the objects you allocate can cause a great deal of problems. While you could manually set every variable of an object each time you allocate it there is a far more easy and effective solution to this problem. Instead of directly allocating the class you want create a custom subclass.

class MyTwoSidedShader extends Shader;
 
defaultproperties
{
	TwoSided=True
}

By using class'MyTwoSidedShader' instead of simply class'Shader' you ensure that nobody will be using objects of this type except you. Now you can assume with a reasonable amount of safety that the properties of these objects will not be changed unless you yourself change them. You can also save time, effort and performance by using default properties instead of having to manually set the variables every time you allocate the object. Overall it is a far cleaner and more compatible way of using the object pool.