예제 #1
0
파일: statdb.cpp 프로젝트: mekolat/ManaPlus
void StatDb::loadXmlFile(const std::string &fileName,
                         const SkipError skipError)
{
    XML::Document doc(fileName,
        UseVirtFs_true,
        skipError);
    XmlNodeConstPtrConst rootNode = doc.rootNode();

    if ((rootNode == nullptr) || !xmlNameEqual(rootNode, "stats"))
    {
        logger->log("StatDb: Error while loading %s!",
            fileName.c_str());
        if (skipError == SkipError_false)
            addDefaultStats();
        return;
    }

    for_each_xml_child_node(node, rootNode)
    {
        if (xmlNameEqual(node, "include"))
        {
            const std::string name = XML::getProperty(node, "name", "");
            if (!name.empty())
                loadXmlFile(name, skipError);
            continue;
        }
        else if (xmlNameEqual(node, "basic"))
        {
            loadBasicStats(node);
        }
        else if (xmlNameEqual(node, "extended"))
        {
            // TRANSLATORS: stats page name
            loadStats(node, _("Extended"));
        }
        else if (xmlNameEqual(node, "page"))
        {
            std::string page = XML::langProperty(node, "name", "");
            if (page.empty())
            {
                reportAlways("Page without name in stats.xml");
                page = "Unknown";
            }
            loadStats(node, page);
        }
    }
    if (skipError == SkipError_false)
    {
        if (mBasicStats.empty() &&
            mStats.empty())
        {
            reportAlways("StatDb: no stats found");
            addDefaultStats();
        }
    }
}
예제 #2
0
void MercenaryRecv::processMercenaryUpdate(Net::MessageIn &msg)
{
    const int sp = msg.readInt16("type");
    const int val = msg.readInt32("value");
    switch (sp)
    {
        setMercStat(Sp::ATK1, Attributes::MERC_ATK);
        setMercStat(Sp::MATK1, Attributes::MERC_MATK);
        setMercStat(Sp::HIT, Attributes::MERC_HIT);
        setMercStat(Sp::CRITICAL, Attributes::MERC_CRIT);
        setMercStat(Sp::DEF1, Attributes::MERC_DEF);
        setMercStat(Sp::MDEF1, Attributes::MERC_MDEF);
        setMercStat(Sp::MERCFLEE, Attributes::MERC_FLEE);
        setMercStat(Sp::ASPD, Attributes::MERC_ATTACK_DELAY);
        setMercStat(Sp::HP, Attributes::MERC_HP);
        setMercStat(Sp::MAXHP, Attributes::MERC_MAX_HP);
        setMercStat(Sp::SP, Attributes::MERC_MP);
        setMercStat(Sp::MAXSP, Attributes::MERC_MAX_MP);
        setMercStat(Sp::MERCKILLS, Attributes::MERC_KILLS);
        setMercStat(Sp::MERCFAITH, Attributes::MERC_FAITH);
        default:
            reportAlways("Unknown mercenary stat %d",
                sp);
            break;
    }
}
예제 #3
0
파일: statdb.cpp 프로젝트: mekolat/ManaPlus
static void loadBasicStats(XmlNodeConstPtr rootNode)
{
    const int maxAttr = static_cast<int>(Attributes::MAX_ATTRIBUTE);
    for_each_xml_child_node(node, rootNode)
    {
        if (xmlNameEqual(node, "stat"))
        {
            const std::string name = XML::getProperty(node, "name", "");
            const std::string attr = XML::getProperty(node, "attr", "");
            if (attr.empty() || AttributesEnum::find(attr) == false)
            {
                const int id = XML::getProperty(node, "id", 0);
                if (id <= 0 || id >= maxAttr)
                {
                    reportAlways("Wrong attr or id for basic "
                        "stat with name %s",
                        name.c_str());
                    continue;
                }
                const std::string tag = XML::getProperty(node, "tag", "");
                mBasicStats.push_back(BasicStat(static_cast<AttributesT>(id),
                    tag,
                    name));
            }
            else
            {
                const std::string tag = XML::getProperty(node, "tag", "");
                mBasicStats.push_back(BasicStat(AttributesEnum::get(attr),
                    tag,
                    name));
            }
        }
    }
}
예제 #4
0
CastingEffect::CastingEffect(const int skillId,
                             const int skillLevel,
                             const std::string &animation,
                             const int x,
                             const int y,
                             const int range) :
    Actor(),
    mSprite(animation.empty() ? nullptr :
        AnimatedSprite::load(paths.getStringValue("sprites") + animation)),
    mRectX((x - range) * mapTileSize),
    mRectY((y - range) * mapTileSize),
    mRectSize(range * mapTileSize * 2 + mapTileSize),
    mAnimationX(mRectX + (mRectSize - (mSprite ?
        mSprite->getWidth() : 0)) / 2),
    mAnimationY(mRectY + (mRectSize - (mSprite ?
        mSprite->getHeight() : 0)) / 2)
{
    mPixelX = x * mapTileSize;
    mPixelY = y * mapTileSize;
    mYDiff = range * mapTileSize + 31;
    if (!mSprite)
    {
        reportAlways("Skill %d/%d casting animation '%s' load failed",
            skillId,
            skillLevel,
            animation.c_str());
    }
}
예제 #5
0
파일: statdb.cpp 프로젝트: mekolat/ManaPlus
static void loadStats(XmlNodeConstPtr rootNode,
                      const std::string &page)
{
    const int maxAttr = static_cast<int>(Attributes::MAX_ATTRIBUTE);
    STD_VECTOR<BasicStat> &stats = mStats[page];
    mPages.push_back(page);
    for_each_xml_child_node(node, rootNode)
    {
        if (xmlNameEqual(node, "stat"))
        {
            const std::string name = XML::getProperty(node, "name", "");
            const std::string attr = XML::getProperty(node, "attr", "");
            if (attr.empty() || AttributesEnum::find(attr) == false)
            {
                const int id = XML::getProperty(node, "id", 0);
                if (id <= 0 || id >= maxAttr)
                {
                    reportAlways("Wrong attr or id for extended "
                        "stat with name %s",
                        name.c_str());
                    continue;
                }
                stats.push_back(BasicStat(static_cast<AttributesT>(id),
                    std::string(),
                    name));
            }
            else
            {
                stats.push_back(BasicStat(AttributesEnum::get(attr),
                    std::string(),
                    name));
            }
        }
    }
}
예제 #6
0
    static Resource *load(const void *const v)
    {
        if (!v)
            return nullptr;

        const AtlasLoader *const rl = static_cast<const AtlasLoader *const>(v);
        AtlasResource *const resource = AtlasManager::loadTextureAtlas(
            rl->name, *rl->files);
        if (!resource)
            reportAlways("Atlas creation error: %s", rl->name.c_str());
        return resource;
    }
예제 #7
0
StatusEffect *StatusEffectDB::getStatusEffect(const int index,
                                              const Enable enabling)
{
    std::map<int, StatusEffect *> &effects
        = statusEffects[enabling == Enable_true];
    const std::map<int, StatusEffect *>::iterator it = effects.find(index);
    if (it != effects.end())
        return (*it).second;
    reportAlways("Missing status effect: %d",
        index);
    return nullptr;
}
예제 #8
0
void Inventory::setItem(const int index,
                        const int id,
                        const ItemTypeT type,
                        const int quantity,
                        const uint8_t refine,
                        const ItemColor color,
                        const Identified identified,
                        const Damaged damaged,
                        const Favorite favorite,
                        const Equipm equipment,
                        const Equipped equipped)
{
    if (index < 0 || index >= CAST_S32(mSize))
    {
        reportAlways("Warning: invalid inventory index: %d",
            index);
        return;
    }

    Item *const item1 = mItems[index];
    if ((item1 == nullptr) && id > 0)
    {
        Item *const item = new Item(id,
            type,
            quantity,
            refine,
            color,
            identified,
            damaged,
            favorite,
            equipment,
            equipped);
        item->setInvIndex(index);
        mItems[index] = item;
        mUsed++;
        distributeSlotsChangedEvent();
    }
    else if (id > 0 && (item1 != nullptr))
    {
        item1->setId(id, color);
        item1->setQuantity(quantity);
        item1->setRefine(refine);
        item1->setEquipment(equipment);
        item1->setIdentified(identified);
        item1->setDamaged(damaged);
        item1->setFavorite(favorite);
    }
    else if (item1 != nullptr)
    {
        removeItemAt(index);
    }
}
예제 #9
0
void OpenGLImageHelper::bindTexture(const GLuint texture)
{
    switch (mUseOpenGL)
    {
#ifdef ANDROID
        case RENDER_NORMAL_OPENGL:
        case RENDER_SAFE_OPENGL:
        case RENDER_MODERN_OPENGL:
        case RENDER_GLES2_OPENGL:
            break;
        case RENDER_GLES_OPENGL:
            MobileOpenGLGraphics::bindTexture(mTextureType, texture);
            break;
#elif defined(__native_client__)
        case RENDER_NORMAL_OPENGL:
        case RENDER_MODERN_OPENGL:
        case RENDER_GLES_OPENGL:
            break;
        case RENDER_SAFE_OPENGL:
            SafeOpenGLGraphics::bindTexture(mTextureType, texture);
            break;
        case RENDER_GLES2_OPENGL:
            MobileOpenGL2Graphics::bindTexture(mTextureType, texture);
            break;
#else  // ANDROID

        case RENDER_NORMAL_OPENGL:
            NormalOpenGLGraphics::bindTexture(mTextureType, texture);
            break;
        case RENDER_MODERN_OPENGL:
            ModernOpenGLGraphics::bindTexture(mTextureType, texture);
            break;
        case RENDER_SAFE_OPENGL:
            SafeOpenGLGraphics::bindTexture(mTextureType, texture);
            break;
        case RENDER_GLES_OPENGL:
            MobileOpenGLGraphics::bindTexture(mTextureType, texture);
            break;
        case RENDER_GLES2_OPENGL:
            MobileOpenGL2Graphics::bindTexture(mTextureType, texture);
            break;
#endif  // ANDROID

        case RENDER_SOFTWARE:
        case RENDER_SDL2_DEFAULT:
        case RENDER_NULL:
        case RENDER_LAST:
        default:
            reportAlways("Unknown OpenGL backend: %d", mUseOpenGL);
            break;
    }
}
예제 #10
0
void Inventory::setTag(const int index,
                       const int tag)
{
    if (index < 0 || index >= CAST_S32(mSize))
    {
        reportAlways("Warning: invalid inventory index: %d",
            index);
        return;
    }
    Item *const item1 = mItems[index];
    if (item1 != nullptr)
        item1->setTag(tag);
}
예제 #11
0
void Inventory::setOptions(const int index,
                           const ItemOptionsList *const options)
{
    if (index < 0 || index >= CAST_S32(mSize))
    {
        reportAlways("Warning: invalid inventory index: %d",
            index);
        return;
    }
    Item *const item1 = mItems[index];
    if (item1 != nullptr)
        item1->setOptions(options);
}
예제 #12
0
SDL_Surface *OpenGLImageHelper::convertSurface(SDL_Surface *tmpImage,
                                               int width, int height)
{
    if (!tmpImage)
        return nullptr;

#ifdef USE_SDL2
    SDL_SetSurfaceAlphaMod(tmpImage, SDL_ALPHA_OPAQUE);
#else  // USE_SDL2

    // Make sure the alpha channel is not used, but copied to destination
    SDL_SetAlpha(tmpImage, 0, SDL_ALPHA_OPAQUE);
#endif  // USE_SDL2

    // Determine 32-bit masks based on byte order
    uint32_t rmask, gmask, bmask, amask;
#if SDL_BYTEORDER == SDL_BIG_ENDIAN
    rmask = 0xff000000;
    gmask = 0x00ff0000;
    bmask = 0x0000ff00;
    amask = 0x000000ff;
#else  // SDL_BYTEORDER == SDL_BIG_ENDIAN

    rmask = 0x000000ff;
    gmask = 0x0000ff00;
    bmask = 0x00ff0000;
    amask = 0xff000000;
#endif  // SDL_BYTEORDER == SDL_BIG_ENDIAN

    if (tmpImage->format->BitsPerPixel != 32
        || rmask != tmpImage->format->Rmask
        || gmask != tmpImage->format->Gmask
        || amask != tmpImage->format->Amask)
    {
        SDL_Surface *oldImage = tmpImage;
#ifdef USE_SDL2
        SDL_SetSurfaceBlendMode(oldImage, SDL_BLENDMODE_NONE);
#endif  // USE_SDL2

        tmpImage = MSDL_CreateRGBSurface(SDL_SWSURFACE, width, height,
            32, rmask, gmask, bmask, amask);

        if (!tmpImage)
        {
            reportAlways("Error, image convert failed: out of memory");
            return nullptr;
        }
        SDL_BlitSurface(oldImage, nullptr, tmpImage, nullptr);
    }
    return tmpImage;
}
예제 #13
0
void Inventory::setCards(const int index,
                         const int *const cards,
                         const int size) const
{
    if (index < 0 || index >= CAST_S32(mSize))
    {
        reportAlways("Warning: invalid inventory index: %d",
            index);
        return;
    }

    Item *const item1 = mItems[index];
    if (item1 != nullptr)
        item1->setCards(cards, size);
}
예제 #14
0
Image *OpenGLImageHelper::load(SDL_RWops *const rw, Dye const &dye)
{
    SDL_Surface *const tmpImage = loadPng(rw);
    if (!tmpImage)
    {
        reportAlways("Error, image load failed: %s", IMG_GetError());
        return nullptr;
    }

    SDL_Surface *const surf = convertTo32Bit(tmpImage);
    MSDL_FreeSurface(tmpImage);
    if (!surf)
        return nullptr;

    uint32_t *pixels = static_cast<uint32_t *>(surf->pixels);
    const int type = dye.getType();

    switch (type)
    {
        case 1:
        {
            const DyePalette *const pal = dye.getSPalete();
            if (pal)
                pal->replaceSOGLColor(pixels, surf->w * surf->h);
            break;
        }
        case 2:
        {
            const DyePalette *const pal = dye.getAPalete();
            if (pal)
                pal->replaceAOGLColor(pixels, surf->w * surf->h);
            break;
        }
        case 0:
        default:
        {
            dye.normalOGLDye(pixels, surf->w * surf->h);
            break;
        }
    }

    Image *const image = loadSurface(surf);
    MSDL_FreeSurface(surf);
    return image;
}
예제 #15
0
Image *OpenGLImageHelper::glLoad(SDL_Surface *tmpImage,
                                 int width, int height)
{
    if (!tmpImage)
        return nullptr;

    BLOCK_START("OpenGLImageHelper::glLoad")
    // Flush current error flag.
    graphicsManager.getLastError();

    if (!width)
        width = tmpImage->w;
    if (!height)
        height = tmpImage->h;

    SDL_Surface *oldImage = tmpImage;
    tmpImage = convertSurfaceNormalize(tmpImage, width, height);
    if (!tmpImage)
        return nullptr;

    const int realWidth = tmpImage->w;
    const int realHeight = tmpImage->h;

    const GLuint texture = getNewTexture();
    bindTexture(texture);

    if (SDL_MUSTLOCK(tmpImage))
        SDL_LockSurface(tmpImage);

    if (mUseOpenGL != RENDER_MODERN_OPENGL &&
        mUseOpenGL != RENDER_GLES_OPENGL &&
        mUseOpenGL != RENDER_GLES2_OPENGL)
    {
        glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
    }

    if (!mUseTextureSampler)
    {
        if (mBlur)
        {
            mglTexParameteri(mTextureType, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
            mglTexParameteri(mTextureType, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
        }
        else
        {
            mglTexParameteri(mTextureType, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
            mglTexParameteri(mTextureType, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
        }
    }
#if !defined(ANDROID) && !defined(__native_client__)
    mglTexParameteri(mTextureType, GL_TEXTURE_MAX_LEVEL, 0);
#endif  // !defined(ANDROID) && !defined(__native_client__)

    mglTexImage2D(mTextureType, 0, mInternalTextureType,
        tmpImage->w, tmpImage->h,
        0, GL_RGBA, GL_UNSIGNED_BYTE, tmpImage->pixels);

#ifdef DEBUG_OPENGL
/*
    disabled for now, because debugger can't show it
    if (isGLNotNull(mglLabelObject))
    {
        const char *const text = "image text";
        mglLabelObject(GL_TEXTURE, texture, strlen(text), text);
    }
*/
#endif  // DEBUG_OPENGL

/*
    GLint compressed;
    glGetTexLevelParameteriv(mTextureType, 0,
        GL_TEXTURE_COMPRESSED_ARB, &compressed);
    if (compressed)
        logger->log("image compressed");
    else
        logger->log("image not compressed");
*/

#ifdef DEBUG_OPENGL_LEAKS
    textures_count ++;
#endif  // DEBUG_OPENGL_LEAKS

    if (SDL_MUSTLOCK(tmpImage))
        SDL_UnlockSurface(tmpImage);

    if (oldImage != tmpImage)
        MSDL_FreeSurface(tmpImage);

    GLenum error = graphicsManager.getLastError();
    if (error)
    {
        std::string errmsg = GraphicsManager::errorToString(error);
        reportAlways("Error: Image GL import failed: %s (%u)",
            errmsg.c_str(), error);
//        return nullptr;
    }

    BLOCK_END("OpenGLImageHelper::glLoad")
    return new Image(texture, width, height, realWidth, realHeight);
}
예제 #16
0
    for_each_xml_child_node(childNode, node)
    {
        if (!xmlTypeEqual(childNode, XML_ELEMENT_NODE))
            continue;

        if (xmlNameEqual(childNode, "button"))
        {
            const std::string name = XML::getProperty(childNode, "name", "");
            const std::string value = XML::getProperty(childNode, "value", "");
            if (value.empty())
                continue;

            NpcButtonInfo *const button = new NpcButtonInfo;
            button->x = XML::getIntProperty(
                childNode, "x", 0, 0, 10000);
            button->y = XML::getIntProperty(
                childNode, "y", 0, 0, 10000);
            button->name = name;
            button->value = value;
            button->image = XML::getProperty(childNode, "image", "");
            if (button->name.empty() && button->image.empty())
            {
                reportAlways("Error: npc button without name or image");
                delete button;
                continue;
            }
            button->imageWidth = XML::getIntProperty(
                childNode, "imageWidth", 16, 1, 1000);
            button->imageHeight = XML::getIntProperty(
                childNode, "imageHeight", 16, 1, 1000);
            dialog->menu.buttons.push_back(button);
        }
        else if (xmlNameEqual(childNode, "image"))
        {
            const std::string image = XML::getProperty(childNode, "image", "");
            if (image.empty())
            {
                reportAlways("Error: no image attribute found in image tag.");
                continue;
            }
            NpcImageInfo *const imageInfo = new NpcImageInfo;
            imageInfo->name = image;
            imageInfo->x = XML::getIntProperty(
                childNode, "x", 0, 0, 10000);
            imageInfo->y = XML::getIntProperty(
                childNode, "y", 0, 0, 10000);
            dialog->menu.images.push_back(imageInfo);
        }
        else if (xmlNameEqual(childNode, "text"))
        {
            const std::string text = XML::getProperty(childNode, "text", "");
            if (text.empty())
            {
                reportAlways("Error: no text attribute found in text tag.");
                continue;
            }
            NpcTextInfo *const textInfo = new NpcTextInfo;
            textInfo->text = text;
            textInfo->x = XML::getIntProperty(
                childNode, "x", 0, 0, 10000);
            textInfo->y = XML::getIntProperty(
                childNode, "y", 0, 0, 10000);
            textInfo->width = XML::getIntProperty(
                childNode, "width", 20, 10, 10000);
            textInfo->height = XML::getIntProperty(
                childNode, "height", 20, 10, 10000);
            dialog->menu.texts.push_back(textInfo);
        }
    }
예제 #17
0
ResourceManager::~ResourceManager()
{
    mDestruction = true;
    mResources.insert(mOrphanedResources.begin(), mOrphanedResources.end());

    // Release any remaining spritedefs first because they depend on image sets
    ResourceIterator iter = mResources.begin();

#ifdef DEBUG_LEAKS
#ifdef UNITTESTS
    bool status(false);
#endif  // UNITTESTS

    while (iter != mResources.end())
    {
        if (iter->second)
        {
            if (iter->second->getRefCount())
            {
                logger->log(std::string("ResourceLeak: ").append(
                    iter->second->getIdPath()).append(" (").append(
                    toString(iter->second->getRefCount())).append(")"));
#ifdef UNITTESTS
                status = true;
#endif  // UNITTESTS
            }
        }
        ++iter;
    }

#ifdef UNITTESTS
    if (status)
        reportAlways("Found leaked resources.");
#endif  // UNITTESTS

    iter = mResources.begin();
#endif  // DEBUG_LEAKS

    while (iter != mResources.end())
    {
#ifdef DEBUG_LEAKS
        if (iter->second && iter->second->getRefCount())
        {
            ++iter;
            continue;
        }
#endif  // DEBUG_LEAKS

        if (dynamic_cast<SpriteDef*>(iter->second))
        {
            cleanUp(iter->second);
            const ResourceIterator toErase = iter;
            ++iter;
            mResources.erase(toErase);
        }
        else
        {
            ++iter;
        }
    }

    // Release any remaining image sets first because they depend on images
    iter = mResources.begin();
    while (iter != mResources.end())
    {
#ifdef DEBUG_LEAKS
        if (iter->second && iter->second->getRefCount())
        {
            ++iter;
            continue;
        }
#endif  // DEBUG_LEAKS

        if (dynamic_cast<ImageSet*>(iter->second))
        {
            cleanUp(iter->second);
            const ResourceIterator toErase = iter;
            ++iter;
            mResources.erase(toErase);
        }
        else
        {
            ++iter;
        }
    }

    // Release remaining resources, logging the number of dangling references.
    iter = mResources.begin();
    while (iter != mResources.end())
    {
#ifdef DEBUG_LEAKS
        if (iter->second && iter->second->getRefCount())
        {
            ++iter;
            continue;
        }
#endif  // DEBUG_LEAKS

        if (iter->second)
        {
            cleanUp(iter->second);
            const ResourceIterator toErase = iter;
            ++iter;
            mResources.erase(toErase);
        }
        else
        {
            ++iter;
        }
    }
    clearDeleted();
    clearScheduled();
}
예제 #18
0
void PETDB::loadXmlFile(const std::string &fileName,
                        const SkipError skipError)
{
    XML::Document doc(fileName,
        UseResman_true,
        skipError);
    const XmlNodePtrConst rootNode = doc.rootNode();

    if (!rootNode || !xmlNameEqual(rootNode, "pets"))
    {
        logger->log("PET Database: Error while loading %s!",
            fileName.c_str());
        return;
    }

    // iterate <pet>s
    for_each_xml_child_node(petNode, rootNode)
    {
        if (xmlNameEqual(petNode, "include"))
        {
            const std::string name = XML::getProperty(petNode, "name", "");
            if (!name.empty())
                loadXmlFile(name, skipError);
            continue;
        }
        else if (!xmlNameEqual(petNode, "pet"))
        {
            continue;
        }

        const BeingTypeId id = fromInt(XML::getProperty(
            petNode, "id", -1), BeingTypeId);
        if (id == BeingTypeId_negOne)
        {
            reportAlways("PET Database: PET with missing ID in %s!",
                paths.getStringValue("petsFile").c_str());
            continue;
        }

        BeingInfo *currentInfo = nullptr;
        if (mPETInfos.find(id) != mPETInfos.end())
            currentInfo = mPETInfos[id];
        if (!currentInfo)
            currentInfo = new BeingInfo;

        currentInfo->setName(XML::langProperty(petNode,
            // TRANSLATORS: unknown info name
            "name", _("pet")));

        currentInfo->setTargetSelection(XML::getBoolProperty(petNode,
            "targetSelection", true));

        BeingCommon::readBasicAttributes(currentInfo, petNode, "talk");
        BeingCommon::readWalkingAttributes(currentInfo, petNode, 0);

        currentInfo->setDeadSortOffsetY(XML::getProperty(petNode,
            "deadSortOffsetY", 31));

        const std::string returnMessage = XML::langProperty(petNode,
            // TRANSLATORS: popup menu item
            // TRANSLATORS: pet return to egg
            "removeMessage", _("Return to egg"));
        currentInfo->setString(0, returnMessage);

        SpriteDisplay display;
        for_each_xml_child_node(spriteNode, petNode)
        {
            if (!XmlHaveChildContent(spriteNode))
                continue;

            if (xmlNameEqual(spriteNode, "sprite"))
            {
                SpriteReference *const currentSprite = new SpriteReference;
                currentSprite->sprite = XmlChildContent(spriteNode);
                currentSprite->variant =
                    XML::getProperty(spriteNode, "variant", 0);
                display.sprites.push_back(currentSprite);
            }
            else if (xmlNameEqual(spriteNode, "particlefx"))
            {
                std::string particlefx = XmlChildContent(spriteNode);
                display.particles.push_back(particlefx);
            }
        }

        currentInfo->setDisplay(display);

        mPETInfos[id] = currentInfo;
    }
}