1 /* 2 * Entreri, an entity-component framework in Java 3 * 4 * Copyright (c) 2013, Michael Ludwig 5 * All rights reserved. 6 * 7 * Redistribution and use in source and binary forms, with or without modification, 8 * are permitted provided that the following conditions are met: 9 * 10 * Redistributions of source code must retain the above copyright notice, 11 * this list of conditions and the following disclaimer. 12 * Redistributions in binary form must reproduce the above copyright notice, 13 * this list of conditions and the following disclaimer in the 14 * documentation and/or other materials provided with the distribution. 15 * 16 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND 17 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 18 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 19 * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR 20 * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 21 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 22 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON 23 * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 24 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 25 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 26 */ 27 package com.lhkbob.entreri; 28 29 import java.util.Iterator; 30 31 /** 32 * <p/> 33 * An Entity represents a collection of Components within an EntitySystem. Entities are 34 * created by calling {@link com.lhkbob.entreri.EntitySystem#addEntity()} or the similar 35 * function that takes another Entity as a template. 36 * <p/> 37 * Once created the Entity object will not change its identity. There are no flyweight 38 * entities, unlike components which do use that design pattern. 39 * <p/> 40 * Entity implements both {@link Ownable} and {@link Owner}. This can be used to create 41 * hierarchies of both components and entities that share a lifetime. When an entity is 42 * removed from the system, all of its owned objects are disowned. If any of them were 43 * entities or components, they are also removed from the system. 44 * 45 * @author Michael Ludwig 46 */ 47 public interface Entity extends Iterable<Component>, Comparable<Entity>, Ownable, Owner { 48 /** 49 * @return The unique (in the scope of the entity system) id of this entity 50 */ 51 public int getId(); 52 53 /** 54 * @return The owning EntitySystem of this entity 55 */ 56 public EntitySystem getEntitySystem(); 57 58 /** 59 * @return True if this Entity is still in its EntitySystem, or false if it has been 60 * removed 61 */ 62 public boolean isAlive(); 63 64 /** 65 * <p/> 66 * Get the Component instance of the given type that's attached to this Entity. A null 67 * value is returned if the component type has not been attached to the entity. 68 * 69 * @param <T> The parameterized type of ComponentData of the component 70 * @param componentType The given type 71 * 72 * @return The current Component of type T attached to this entity 73 * 74 * @throws NullPointerException if componentType is null 75 */ 76 public <T extends Component> T get(Class<T> componentType); 77 78 /** 79 * <p/> 80 * Add a new Component with a data type T to this Entity. If there already exists a 81 * component of type T, it is removed first, and a new one is instantiated. 82 * 83 * @param <T> The parameterized type of component being added 84 * @param componentType The component type 85 * 86 * @return A new component of type T 87 * 88 * @throws NullPointerException if componentId is null 89 */ 90 public <T extends Component> T add(Class<T> componentType); 91 92 /** 93 * <p/> 94 * Add a new Component with a of type T to this Entity, but the new component's state 95 * will be cloned from the given Component instance. The <var>toClone</var> instance 96 * must still be live. If there already exists a component of type T, it is removed 97 * first, and a new one is instantiated. 98 * <p/> 99 * The new component is initialized by cloning the property values from 100 * <var>toClone</var> into the values of the new component. 101 * 102 * @param <T> The parameterized type of component to add 103 * @param toClone The existing T to clone when attaching to this component 104 * 105 * @return A new component of type T 106 * 107 * @throws NullPointerException if toClone is null 108 * @throws IllegalStateException if toClone is not a live component instance 109 */ 110 public <T extends Component> T add(T toClone); 111 112 /** 113 * Get the canonical component instance of type <var>T</var> on this Entity. Unlike 114 * {@link #get(Class)}, this will add the component if it is not present. Thus, this 115 * is a convenience for getting the component, and adding it if the get returned 116 * null. 117 * 118 * @param type The class interface of the component to add 119 * @param <T> The parameterized type of component 120 * 121 * @return The component of type T, potentially new if it wasn't already on the 122 * entity 123 */ 124 public <T extends Component> T as(Class<T> type); 125 126 /** 127 * Check whether or not the a component of the given type is attached to this entity. 128 * This is a convenience for getting the component and then checking if it's null. 129 * 130 * @param type The component type to check for 131 * 132 * @return True if the entity currently has the attached type, in which case get() 133 * will return a non-null alive component 134 */ 135 public boolean has(Class<? extends Component> type); 136 137 /** 138 * <p/> 139 * Remove any attached Component with the data type from this Entity. True is returned 140 * if a component was removed, and false otherwise. If a component is removed, the 141 * component should no longer be used and it will return false from {@link 142 * Component#isAlive()}. 143 * <p/> 144 * When a Component is removed, it will set its owner to null, and disown all of its 145 * owned objects. If any of those owned objects are entities or components, they are 146 * removed from the system as well. 147 * 148 * @param componentType The component type 149 * 150 * @return True if a component was removed 151 * 152 * @throws NullPointerException if componentId is null 153 */ 154 public boolean remove(Class<? extends Component> componentType); 155 156 /** 157 * <p/> 158 * Return an iterator over the components currently attached to the Entity. The 159 * iterator supports the remove operation and will detach the component from the 160 * entity just like a call to {@link #remove(Class)}. 161 * <p/> 162 * Components reported by the iterator are not flyweight. 163 * 164 * @return An iterator over the entity's components 165 */ 166 @Override 167 public Iterator<Component> iterator(); 168 }