Understanding AndEngine entities
The AndEngine game engine follows the entity-component model. The entity-component design is very common in a lot of game engines today, and for a good reason. It's easy to use, it's modular, and it is extremely useful in the sense that all game objects can be traced back to the single, most basic Entity
object. The entity-component model can be thought of as the "entity" portion referring to the most basic level of the game engine's object system. The Entity
class handles only the most basic data that our game objects rely on, such as position, rotation, color, attaching and detaching to and from the scene, and more. The "component" portion refers to the modular subtypes of the Entity class, such as the Scene
, Sprite
, Text
, ParticleSystem
, Rectangle
, Mesh
, and every other object which can be placed within our game. The components are meant to handle more specific tasks, while the entity is meant to act as a base foundation that all components will rely on.
How to do it...
To start with the absolute most basic Entity
method, we will attach an Entity
object to a Scene
object:
Creating and attaching an Entity
object to the Scene
object requires only the following two lines of code:
Entity layer = new Entity(); mScene.attachChild(layer);
How it works…
The two lines of code given here allow us to create and attach a basic Entity
object to our Scene
object. An Entity
object that is defined as seen in the How to do it... section of this recipe will most commonly be used as a layer. The purpose of a layer will be discussed in the coming paragraphs.
Entities are very important when developing games. In AndEngine, the fact of the matter is that all objects displayed on our scenes are derived from entities (including the Scene
object itself!). In most cases, we can assume that the entity is either a visually displayed object such as a Sprite
, Text
, or Rectangle
object on the scene, or a layer, such as the Scene
object. Seeing as how broad the Entity
class is, we're going to talk about each of the two uses for entities as if they were separate objects.
The first and arguably most important aspect of an entity is the layering capabilities. A layer is a very simple concept in game design; however, due to the amount of entities games tend to support during gameplay, things can quickly become confusing when first getting to know them. We must think of a layer as an object which has one parent and an unlimited amount of children unless otherwise defined. As the name suggests, the purpose of a layer is to apply our various entity objects on our scene in an organized fashion, which fortunately also gives us the ability to perform one action on the layer that will affect all of its children in unison, for example, repositioning and applying certain entity modifiers. We can assume that if we have a background, a mid-ground, and a foreground, that our game will have three separate layers. These three layers would appear in a specific order depending on the order they are attached to the scene, as if stacking pieces of paper on top of each other. The last piece of paper added to the stack will appear in front of the rest if we were to look down on that stack of paper. The same rule applies for Entity
objects attached to a Scene
object; this is shown in the following image:
The previous image depicts a basic game scene consisting of three Entity
object layers. Each of the three layers has a specific purpose, which is to store all relative entities in terms of depth. The first layer applied to the scene is the background layer, including a sprite, which contains a blue sky and a sun. The second layer applied to the scene is the mid-ground layer. On this layer, we would find objects which are relative to the player, including the landscape the player walks on, collectable items, enemies, and more. Lastly, we have the foreground layer, used to display the front-most entities on the device's display. In the figure shown, the foreground layer is used to display the user interface, which includes a button, and two Text
objects.
Let's take another look at what a scene might look like with layers with child entities attached to it:
This figure shows how a scene would display entities on the screen in terms of depth/layering. At the bottom of the figure, we've got the device's display. We can see that Background Layer is attached to the Scene first, then Player Layer is attached. This means that the entities attached to the background will be displayed behind the Player Layer children. Keeping this in mind, the rule applies to the child entities as well. The first child attached to the layer will appear behind any subsequently attached object as far as depth goes.
Finally, one last vital topic relating to general AndEngine entities is Entity composition. One thing we should go over before moving on is the fact that children inherit parent values! This is an area where many new AndEngine developers run into issues when setting up multiple layers in their games. Everything from skew, scale, position, rotation, visibility, and more are all taken into account by child entities when their parent's properties change. Take a look at the following figure, which displays the entity's position composition in AndEngine:
First of all, we should know that in AndEngine's anchor center branch, coordinate systems start in the bottom-left corner of an entity. Increasing the x value will move the entity position to the right, and increasing the y value will move the entity position upward. Decreasing x/y values will have the opposite affect. With this in mind, we can see that the bigger rectangle which is attached to the Scene has its position set to coordinates (6, 6) on the Scene. Since the smaller rectangle is attached to the bigger rectangle, rather than its coordinate system being relative to the Scene, it is actually using the large rectangle's coordinate system. This means that the small rectangle's anchor center position will rest directly on position (0, 0) of the large rectangle's coordinate system. As we can see in the previous image, the (0, 0) position on the large rectangle's coordinate system is its bottom-left corner.
Note
The main difference between the older AndEngine branches and AndEngine's newest anchor center branch is the fact that positioning an entity no longer means we are setting the upper-left corner of an entity to a position on the coordinate system. Rather, the entity's center-point will be placed at the defined position, also seen in the previous figure.
There's more...
The Entity
object in AndEngine includes many different methods which affect many aspects of the entity. These methods play a vital role in shaping the overall characteristics of Entity
objects regardless of the entity's subtype. It is a good idea to get to know how to manipulate entities in order to take full control over how the entities appear, react, store information, and much more. Use the following list to familiarize yourself with some of the most important methods of the Entity
object, paired with their corresponding getter methods. Methods missing from this list will be covered in more detail in this and the following chapters:
setVisible(pBoolean)
andisVisible()
: This method can be used to set whether or not the entity is visible on the scene. Setting these methods totrue
will allow the entity to render, setting them tofalse
will disable rendering.setChildrenVisible(pBoolean)
andisChildrenVisible()
: Similar to thesetVisible(pBoolean)
method, except that it defines the visibility of the calling entity's children and not itself.setCullingEnabled(pBoolean)
andisCullingEnabled()
: Entity culling can be a very promising performance optimization technique. See Disabling rendering with entity culling in Chapter 8, Maximizing Performance, for more details.collidesWith(pOtherEntity)
: This method is used to detect when the entity that is calling this method collides, or overlaps, with theEntity
object supplied as this method's parameter. If the entities are colliding, this method returnstrue
.setIgnoreUpdate(pBoolean)
andisIgnoreUpdate()
: Ignoring entity updates can provide noticeable performance improvements. See Ignoring entity updates in Chapter 8, Maximizing Performance, for more details.setChildrenIgnoreUpdate(pBoolean)
andisChildrenIgnoreUpdate()
: Similar to thesetIgnoreUpdate(pBoolean)
method, except that it only affects the calling entity's children and not itself.getRootEntity()
: This method will iterate through the entity's parent until it reaches the root parent. Once the root parent is found, this method will return the rootEntity
object; in most cases, the root being our game'sScene
object.setTag(pInt)
andgetTag()
: This method can be used for storing an integer value within an entity. Typically used for setting up identification values to entities.setParent(pEntity)
andhasParent()
: Sets the parent entity to the entity calling this method. ThehasParent()
method returns atrue
orfalse
value depending on whether or not the calling entity has a parent.setZIndex(pInt)
andgetZIndex()
: Set theZ
index of the calling entity. Entities with a greater value will appear in front of entities with a lesser value. By default, all entities have aZ
index of0
, meaning that they simply appear in the order they are attached. See the followingsortChildren()
method for more details.sortChildren()
: This method must be called on the parent of an entity or group of entities which have had theirZ
index modified before changes take effect on the screen.setPosition(pX, pY)
orsetPosition(pEntity)
: This method can be used to set the position of an entity to specific x/y values, or it can be used to set to another entity's position. Additionally, we can use thesetX(pX)
andsetY(pY)
methods to make changes to only a single axis position.getX()
andgetY()
: These methods are used to obtain the position of an entity in local coordinates; that is, relation to its parent.setWidth(pWidth)
andsetHeight(pHeight)
orsetSize(pWidth, pHeight)
: These methods can be used to set the width and height of the calling entity. Additionally, we can use thegetWidth()
andgetHeight()
methods, which return their respective values in as a float datatype.setAnchorCenter(pAnchorCenterX, pAnchorCenterY)
: This method can be used to set the anchor center of the entity. The anchor center is the position within anEntity
object that it will rotate around, skew from, and scale from. Additionally, modifying the anchor center values will relocate the entity's "positioning" anchor from the default center-point. For example, if we move the anchor center position to the upper-left corner of an entity, callingsetPosition(0,0)
would place the entity's upper-left corner to position(0,0)
.setColor(pRed, pGreen, pBlue)
andgetColor()
: This method can be used to set the color of an entity, from values ranging from0.0f
for no color through to1.0f
for full color.setUserData(pObject)
andgetUserData(
)
: These two methods are incredibly useful when developing games with AndEngine. They allow us to store an object of our choice within the entity and modify it or retrieve it at any point in time. One possibility for user data storage would be to determine what type of weapon a player's character is holding. Use these methods to the fullest!