Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

EntityIndex #154

Closed
sschmid opened this issue Sep 6, 2016 · 6 comments
Closed

EntityIndex #154

sschmid opened this issue Sep 6, 2016 · 6 comments
Assignees
Milestone

Comments

@sschmid
Copy link
Owner

sschmid commented Sep 6, 2016

An EntityIndex can speed up retrieving entities dramatically. Entities can be indexed similar to a index in a database.
Instead of iterating over all entities with a e.g. a position and checking if pos == (1, 2), an EntityIndex can observe group(Position) and index entities already. Getting all entities with pos == (1, 2) is constant speed of Dictionary access (=> very fast).

EntityIndex allows multiple entities with same key (key can be e.g. position or name)
PrimaryIndex ensures there is only one entity for a given key.

@sschmid sschmid self-assigned this Sep 6, 2016
@sschmid sschmid added this to the 0.32.0 milestone Sep 6, 2016
@sschmid
Copy link
Owner Author

sschmid commented Sep 6, 2016

A code generator is planned for a future version. See #75

public const string PositionKey = "Position":

public static void AddEntityIndices(Pool pool) {
    // Position index, key type is IntVector2
    var entityIndex = new EntityIndex<IntVector2>(
        pool.GetGroup(Matcher.Position),
        (entity, component) => { // How to create a key based on entity and component
            var positionComponent = component as PositionComponent;
            return positionComponent != null
                ? positionComponent.value
                : entity.position.value;
        });

    pool.AddEntityIndex(
        PositionKey, // Any unique name
        entityIndex
    );
}
public static HashSet<Entity> GetEntitiesWithPosition(this Pool pool, IntVector2 position) {
    var index = (EntityIndex<IntVector2>)pool.GetEntityIndex(PositionKey);
    return index.GetEntities(position);
}
var entities = pool.GetEntitiesWithPosition(pos); // fast index access

@sschmid sschmid added ready and removed ready labels Sep 6, 2016
@sschmid sschmid closed this as completed Sep 6, 2016
@echeg
Copy link

echeg commented Sep 7, 2016

I try:

[Game]
public class CardComponent : IComponent
{
    public int Id;
    [IndexKey("CardT")]
    public TypeCard CardType; // want to integrate
    public Rarity CardRarity;
}

public class GameController : MonoBehaviour {
    void Start()
    {
       _pool = Pools.sharedInstance.game = Pools.CreateGamePool();
       AddEntityIndices(_pool);
   }

    public static void AddEntityIndices(Pool pool)
    {
        // Position index, key type is IntVector2
        var entityIndex = new EntityIndex<TypeCard>(
            pool.GetGroup(GameMatcher.Card), // Group to observe
            (entity, component) => ((CardComponent) component).CardType // How to create a key
            );

        // Add to pool by name
        pool.AddEntityIndex(
            GameComponentIds.Card.ToString(),
            entityIndex
        );
    }

And I get error on

(entity, component) => ((CardComponent) component).CardType // How to create a key

NullReferenceException: Object reference not set to an instance of an object
GameController.<AddEntityIndices>m__C (Entitas.Entity entity, IComponent component) (at Assets/Scripts/GameController.cs:45)

@sschmid
Copy link
Owner Author

sschmid commented Sep 7, 2016

I updated my previous comment. Try that

@echeg
Copy link

echeg commented Sep 7, 2016

Thanks all works fine!

@echeg
Copy link

echeg commented Sep 13, 2016

What you think about double indices?
Example:

public class CardComponent : IComponent
{
    public int Id;
    [IndexKey("CardTypeIndex")]
    public TypeCard CardType;
    [IndexKey("CardRarityIndex")]
    public Rarity CardRarity;
}

var entities = pool.GetEntitiesWithTypeAndRarity(TypeCard.solder, Rarity.Common);

Or indices from different components

Example

public class CardComponent : IComponent
{
    public int Id;
    [IndexKey("CardTypeIndex")]
    public TypeCard CardType;
    public Rarity CardRarity;
}
public class PlayerComponent : IComponent 
{
    [IndexKey("PlayerIndex")]
    public int Player;
}
var entities = pool.GetEntitiesWithTypeAndPlayer(TypeCard.solder, PlayerId);

@sschmid
Copy link
Owner Author

sschmid commented Sep 20, 2016

You can achieve sth like this already manually, but yeah, generating these things will be very handy

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
Archived in project
Development

No branches or pull requests

2 participants