• There is NO official Otland's Discord server and NO official Otland's server list. The Otland's Staff does not manage any Discord server or server list. Moderators or administrator of any Discord server or server lists have NO connection to the Otland's Staff. Do not get scammed!

C++ TFS 1.2 [8.0] - canWalkthroughEx

Darius93

Premium User
Premium User
Joined
Oct 16, 2022
Messages
12
Reaction score
0
Hello, I use the distribution celohere.
And I'm having trouble finding the function responsible for checking whether the floor is free.
I want to make it so that the player can enter a monster that is a summon and has a yellow skull.

Can anyone help?

I Found tile.cpp

C++:
ReturnValue Tile::queryAdd(int32_t, const Thing& thing, uint32_t, uint32_t flags, Creature*) const
I guess this is the function.
Can someone help add/modify this code?

C++:
    if (const Creature* creature = thing.getCreature()) {
        const Monster* monster = creature->getMonster();
        if (monster && monster->isSummon()) {
         
            if (monster->getSkull() == SKULL_YELLOW) {
                return RETURNVALUE_NOERROR;
            }
        }
        return RETURNVALUE_NOTPOSSIBLE;
    }


C++:
ReturnValue Tile::queryAdd(int32_t, const Thing& thing, uint32_t, uint32_t flags, Creature*) const
{
    if (const Creature* creature = thing.getCreature()) {
        if (hasBitSet(FLAG_NOLIMIT, flags)) {
            return RETURNVALUE_NOERROR;
        }

        if (hasBitSet(FLAG_PATHFINDING, flags) && hasFlag(TILESTATE_FLOORCHANGE | TILESTATE_TELEPORT)) {
            return RETURNVALUE_NOTPOSSIBLE;
        }

        if (ground == nullptr) {
            return RETURNVALUE_NOTPOSSIBLE;
        }

        if (const Monster* monster = creature->getMonster()) {

            if (monster->getSkull() != SKULL_YELLOW && hasFlag(TILESTATE_PROTECTIONZONE | TILESTATE_FLOORCHANGE | TILESTATE_TELEPORT)) {
                return RETURNVALUE_NOTPOSSIBLE;
            }
        

            const CreatureVector* creatures = getCreatures();
            if (monster->canPushCreatures() && !monster->isSummon()) {
                if (creatures) {
                    for (Creature* tileCreature : *creatures) {
                        if (tileCreature->getPlayer() && tileCreature->getPlayer()->isInGhostMode()) {
                            continue;
                        }

                        const Monster* creatureMonster = tileCreature->getMonster();
                        if (!creatureMonster || !tileCreature->isPushable() ||
                                (creatureMonster->isSummon() && creatureMonster->getMaster()->getPlayer())) {
                            return RETURNVALUE_NOTPOSSIBLE;
                        }
                    }
                }
            } else if (creatures && !creatures->empty()) {
                for (const Creature* tileCreature : *creatures) {
                    if (!tileCreature->isInGhostMode()) {
                        return RETURNVALUE_NOTENOUGHROOM;
                    }
                }
            }

            if (hasFlag(TILESTATE_IMMOVABLEBLOCKSOLID)) {
                return RETURNVALUE_NOTPOSSIBLE;
            }

            if (hasBitSet(FLAG_PATHFINDING, flags) && hasFlag(TILESTATE_IMMOVABLENOFIELDBLOCKPATH)) {
                return RETURNVALUE_NOTPOSSIBLE;
            }

            if (hasFlag(TILESTATE_BLOCKSOLID) || (hasBitSet(FLAG_PATHFINDING, flags) && hasFlag(TILESTATE_NOFIELDBLOCKPATH))) {
                if (!(monster->canPushItems() || hasBitSet(FLAG_IGNOREBLOCKITEM, flags))) {
                    return RETURNVALUE_NOTPOSSIBLE;
                }
            }

            MagicField* field = getFieldItem();
            if (field && !field->isBlocking()) {
                CombatType_t combatType = field->getCombatType();

                //There is 3 options for a monster to enter a magic field
                //1) Monster is immune
                if (!monster->isImmune(combatType)) {
                    //1) Monster is "strong" enough to handle the damage
                    //2) Monster is already afflicated by this type of condition
                    if (hasBitSet(FLAG_IGNOREFIELDDAMAGE, flags)) {
                        if (!(monster->canPushItems() || monster->hasCondition(Combat::DamageToConditionType(combatType)))) {
                            return RETURNVALUE_NOTPOSSIBLE;
                        }
                    } else {
                        return RETURNVALUE_NOTPOSSIBLE;
                    }
                }
            }

            return RETURNVALUE_NOERROR;
        }

        const CreatureVector* creatures = getCreatures();
        if (const Player* player = creature->getPlayer()) {
            if (creatures && !creatures->empty() && !hasBitSet(FLAG_IGNOREBLOCKCREATURE, flags) && !player->isAccessPlayer()) {
                for (const Creature* tileCreature : *creatures) {
                    if (!tileCreature->isInGhostMode())
                        return RETURNVALUE_NOTPOSSIBLE;
                }
            }

            if (player->getParent() == nullptr && hasFlag(TILESTATE_NOLOGOUT)) {
                //player is trying to login to a "no logout" tile
                return RETURNVALUE_NOTPOSSIBLE;
            }

            const Tile* playerTile = player->getTile();
            if (playerTile && player->isPzLocked()) {
                if (!playerTile->hasFlag(TILESTATE_PVPZONE)) {
                    //player is trying to enter a pvp zone while being pz-locked
                    if (hasFlag(TILESTATE_PVPZONE)) {
                        return RETURNVALUE_PLAYERISPZLOCKEDENTERPVPZONE;
                    }
                } else if (!hasFlag(TILESTATE_PVPZONE)) {
                    // player is trying to leave a pvp zone while being pz-locked
                    return RETURNVALUE_PLAYERISPZLOCKEDLEAVEPVPZONE;
                }

                if ((!playerTile->hasFlag(TILESTATE_NOPVPZONE) && hasFlag(TILESTATE_NOPVPZONE)) ||
                    (!playerTile->hasFlag(TILESTATE_PROTECTIONZONE) && hasFlag(TILESTATE_PROTECTIONZONE))) {
                    // player is trying to enter a non-pvp/protection zone while being pz-locked
                    return RETURNVALUE_PLAYERISPZLOCKED;
                }
            }
        } else if (creatures && !creatures->empty() && !hasBitSet(FLAG_IGNOREBLOCKCREATURE, flags)) {
            for (const Creature* tileCreature : *creatures) {
                if (!tileCreature->isInGhostMode()) {
                    return RETURNVALUE_NOTENOUGHROOM;
                }
            }
        }

        if (!hasBitSet(FLAG_IGNOREBLOCKITEM, flags)) {
            //If the FLAG_IGNOREBLOCKITEM bit isn't set we dont have to iterate every single item
            if (hasFlag(TILESTATE_BLOCKSOLID)) {
                return RETURNVALUE_NOTENOUGHROOM;
            }
        } else {
            //FLAG_IGNOREBLOCKITEM is set
            if (ground) {
                const ItemType& iiType = Item::items[ground->getID()];
                if (iiType.blockSolid && (!iiType.moveable || ground->hasAttribute(ITEM_ATTRIBUTE_UNIQUEID))) {
                    return RETURNVALUE_NOTPOSSIBLE;
                }
            }

            if (const auto items = getItemList()) {
                for (const Item* item : *items) {
                    const ItemType& iiType = Item::items[item->getID()];
                    if (iiType.blockSolid && (!iiType.moveable || item->hasAttribute(ITEM_ATTRIBUTE_UNIQUEID))) {
                        return RETURNVALUE_NOTPOSSIBLE;
                    }
                }
            }
        }
    } else if (const Item* item = thing.getItem()) {
        const TileItemVector* items = getItemList();
        if (items && items->size() >= 0xFFFF) {
            return RETURNVALUE_NOTPOSSIBLE;
        }

        if (hasBitSet(FLAG_NOLIMIT, flags)) {
            return RETURNVALUE_NOERROR;
        }

        bool itemIsHangable = item->isHangable();
        if (ground == nullptr && !itemIsHangable) {
            return RETURNVALUE_NOTPOSSIBLE;
        }

        const CreatureVector* creatures = getCreatures();
        if (creatures && !creatures->empty() && item->isBlocking() && !hasBitSet(FLAG_IGNOREBLOCKCREATURE, flags)) {
            for (const Creature* tileCreature : *creatures) {
                if (!tileCreature->isInGhostMode()) {
                    return RETURNVALUE_NOTENOUGHROOM;
                }
            }
        }

        if (itemIsHangable && hasFlag(TILESTATE_SUPPORTS_HANGABLE)) {
            if (items) {
                for (const Item* tileItem : *items) {
                    if (tileItem->isHangable()) {
                        return RETURNVALUE_NEEDEXCHANGE;
                    }
                }
            }
        } else {
            if (ground) {
                const ItemType& iiType = Item::items[ground->getID()];
                if (iiType.blockSolid) {
                    if (!iiType.allowPickupable || item->isMagicField() || item->isBlocking()) {
                        if (!item->isPickupable()) {
                            return RETURNVALUE_NOTENOUGHROOM;
                        }

                        if (!iiType.hasHeight || iiType.pickupable || iiType.isBed()) {
                            return RETURNVALUE_NOTENOUGHROOM;
                        }
                    }
                }
            }

            if (items) {
                for (const Item* tileItem : *items) {
                    const ItemType& iiType = Item::items[tileItem->getID()];
                    if (!iiType.blockSolid) {
                        continue;
                    }

                    if (iiType.allowPickupable && !item->isMagicField() && !item->isBlocking()) {
                        continue;
                    }

                    if (!item->isPickupable()) {
                        return RETURNVALUE_NOTENOUGHROOM;
                    }

                    if (!iiType.hasHeight || iiType.pickupable || iiType.isBed()) {
                        return RETURNVALUE_NOTENOUGHROOM;
                    }
                }
            }
        }
    }
    return RETURNVALUE_NOERROR;
}
 
Last edited:
Back
Top