1

我正在为 Android 开发 AndEngine 游戏。在我的游戏中,我必须每秒钟创建不同类型的 Tiles (AnimatedSprite)。我已经做到了。但我在比赛中感到抽搐和滞后。我认为这是由于频繁地分配和取消分配对象。所以我想在我的游戏中实现对象池模式。我当前用于创建 Tile 的代码:

public class TileFactory implements EntityFactory {

private static TileFactory tileFactory;

@Override
public AnimatedEntity createEntity(PlayLevelActivity mGameWorld, ResourceType type) {
    // TODO Auto-generated method stub
    ITiledTextureRegion textureRegion = ResourceManager.getTextureRegion(mGameWorld, type);;
    switch (type) {
        case STATIC_TILE:
            return new StaticTile(mGameWorld, 0, 0, textureRegion.getWidth(), textureRegion.getHeight(), 
                    BodyType.StaticBody, textureRegion, mGameWorld.getVertexBufferObjectManager());
        case DYNAMIC_TILE :
            return new DynamicTile(mGameWorld, 0, 0, textureRegion.getWidth(), textureRegion.getHeight(), 
                    BodyType.StaticBody, textureRegion, mGameWorld.getVertexBufferObjectManager());
        case DANGER_TILE:
            return new DangerTile(mGameWorld, 0, 0, textureRegion.getWidth(), textureRegion.getHeight(), 
                    BodyType.StaticBody, textureRegion, mGameWorld.getVertexBufferObjectManager());
        case FIRE_TILE:
            return new FireTile(mGameWorld, 0, 0, textureRegion.getWidth(), textureRegion.getHeight(), 
                    BodyType.StaticBody, textureRegion, mGameWorld.getVertexBufferObjectManager());
        case HIGH_JUMP_TILE:
            return new HighJumpTile(mGameWorld, 0, 0, textureRegion.getWidth(), textureRegion.getHeight(), 
                    BodyType.StaticBody, textureRegion, mGameWorld.getVertexBufferObjectManager());
        case RISK_TILE:
            return new RiskyTile(mGameWorld, 0, 0, textureRegion.getWidth(), textureRegion.getHeight(), 
                    BodyType.StaticBody, textureRegion, mGameWorld.getVertexBufferObjectManager());
        default :
            return null;
    }
}


    public static TileFactory getIntance() {
        if(tileFactory == null) {
            tileFactory = new TileFactory();
        }
        return tileFactory;
    }
}

我已经看到了一些在 AndEngine 中使用 ObjectPool 的示例,但它们仅适用于单一类型的实体。我有几种类型的实体要创建。任何指南如何将我当前的场景转换为 ObjecPool 之一?

静态瓷砖池类:

public class StaticTilePool extends GenericPool<StaticTile> {

PlayLevelActivity mGameWorld;
ITiledTextureRegion textureRegion;

public StaticTilePool(PlayLevelActivity mGameWorld) {
    this.mGameWorld = mGameWorld;
    textureRegion = ResourceManager.getTextureRegion(mGameWorld, ResourceType.STATIC_TILE);
}

/**
 * Called when a Tile is required but there isn't one in the pool
 */
@Override
protected StaticTile onAllocatePoolItem() {
    Log.d("count:", "count: " + getAvailableItemCount() + " ,    maximum count: " + getAvailableItemCountMaximum() + " ,    unrecycled count: " + getUnrecycledItemCount());

    return new StaticTile(mGameWorld, -100, -100, textureRegion.getWidth(), textureRegion.getHeight(), 
            BodyType.StaticBody, textureRegion, mGameWorld.getVertexBufferObjectManager());
}

/**
 * Called just before a Tile is returned to the caller, this is where you write your initialize code
 * i.e. set location, rotation, etc.
*/
@Override
protected void onHandleObtainItem(final StaticTile pItem) {
    pItem.reset();
    pItem.mBody.setAwake(false);
}


/**
 * Called when a Tile is sent to the pool
*/
@Override
protected void onHandleRecycleItem(final StaticTile pItem) {
    Log.d("onHandle recycle", "onhandle recycle oitem");
    pItem.mBody.setAwake(true);
    pItem.setVisible(false);
    pItem.setIgnoreUpdate(true);
}

}

4

1 回答 1

2

查看....

org.andengine.util.adt.pool.MultiPool

这正是你想要的。一个池子。您需要使用自己的自定义实现来扩展 MultiPool。这是我在项目中使用的示例。(我已经减少了多池中的池数量,但留得足够多,这样你就知道了。)

public class CritterPool extends MultiPool {
    private WorldActivity   mContext;

    public static enum TYPE {
        PROTOGUY, COW, MALE, SKELETON
    }

    public CritterPool(WorldActivity mContext) {
        super();
        this.mContext = mContext;
        this.registerPool(TYPE.PROTOGUY.ordinal(), new ProtoGuyPool(mContext));
        this.registerPool(TYPE.COW.ordinal(), new CowPool(mContext));
        this.registerPool(TYPE.MALE.ordinal(), new MalePool(mContext));
        this.registerPool(TYPE.SKELETON.ordinal(), new SkeletonPool(mContext));
    }

    public BaseCritter get(TYPE type) {
        return (BaseCritter) this.obtainPoolItem(type.ordinal());
    }

    public void recycle(BaseCritter critter) {
        this.recyclePoolItem(critter.getType().ordinal(), critter);
    }

}

所以现在,从外部,我创建了多池,然后我可以用我想要的任何类型的(在本例中为“小动物”)从池中调用 get(),无论是牛、骷髅等。

于 2013-02-22T01:41:48.140 回答