• 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!
  • 2026 staff recruitment is open! Check it out and consider applying!

C++ Dual wield attackValue

Paulix

Active Member
Joined
Sep 13, 2012
Messages
151
Solutions
8
Reaction score
36
When I use the function onGetPlayerMinMaxValues, the attackValue param is returning only the attack of the left weapon equipped. My server has dual wield working, but I think I would need to chance this block to make it returns right + left attack.


LUA:
        case COMBAT_FORMULA_SKILL: {
            //onGetPlayerMinMaxValues(player, level, attackSkill, attackValue, attackFactor)
            Item* tool = player->getWeapon();
            const Weapon* weapon = g_weapons->getWeapon(tool);
            Item* item = nullptr;

            int32_t attackValue = 7;
            if (weapon) {
                attackValue = tool->getAttack();
                if (tool->getWeaponType() == WEAPON_AMMO) {
                    item = player->getWeapon(true);
                    if (item) {
                        attackValue += item->getAttack();
                    }
                }

                damage.secondary.type = weapon->getElementType();
                damage.secondary.value = weapon->getElementDamage(player, nullptr, tool);
            }

            lua_pushnumber(L, player->getLevel());
            lua_pushnumber(L, player->getWeaponSkill(item ? item : tool));
            lua_pushnumber(L, attackValue);
            lua_pushnumber(L, player->getAttackFactor());
            parameters += 4;
            break;
        }

does anyone know how i can add the right weapon validation and sum to the attackValue return?
I tried a few things with IA, but didn't work
 
You can use player->getWeapon(CONST_SLOT_LEFT, false) to get the left weapon item and player->getWeapon(CONST_SLOT_RIGHT, false) to get the right weapon item.
 
here is what I tried


LUA:
case COMBAT_FORMULA_SKILL: {

    Item* left = player->getWeapon(CONST_SLOT_LEFT, false);
    Item* right = player->getWeapon(CONST_SLOT_RIGHT, false);
    const Weapon* lweapon = g_weapons->getWeapon(left);
    const Weapon* rweapon = g_weapons->getWeapon(right);
    Item* itemleft = nullptr;
    Item* itemright = nullptr;
    Item* primaryWeapon = left ? left : right;

    int32_t attackValue = 7;

    if (lweapon) {
        attackValue += left->getAttack();
        if (lweapon->getWeaponType() == WEAPON_AMMO) {
            itemleft = player->getWeapon(CONST_SLOT_LEFT, true);
            if (itemleft) {
                attackValue += itemleft->getAttack();
            }
        }
    }
    if (rweapon) {
        attackValue += right->getAttack();
        if (rweapon->getWeaponType() == WEAPON_AMMO) {
            itemright = player->getWeapon(CONST_SLOT_RIGHT, true);
            if (itemright) {
                attackValue += itemright->getAttack();
            }
        }
    }

    lua_pushnumber(L, player->getLevel());
    lua_pushnumber(L, player->getWeaponSkill(itemleft ? itemleft : (itemright ? itemright : primaryWeapon)));
    lua_pushnumber(L, attackValue);
    lua_pushnumber(L, player->getAttackFactor());
    parameters += 4;
    break;
}

but it is still not working, only the damage from left hand returns when called
 
This should work if your Player::getWeapon()'s code is the same as in base TFS.
Can you show your code of both variants of that method? (i.e. with and without the ignoreAmmo parameter)

Also, just to make sure, did you remember to compile the server?

Edit: Well, currently it adds 7 to the total attack so that should be fixed, but generally the code as it stands should consider both weapons' attack values.
 
it was returning 7 atk when no weapons, 1 weapon attack when using one weapon, and the same attack of using only 1 weapon when dual wielding... asked copilot to check for errors, it didn't find anything

here is my weapons


LUA:
Item* Player::getWeapon(slots_t slot, bool ignoreAmmo) const
{
    Item* item = inventory[slot];
    if (!item) {
        return nullptr;
    }

    WeaponType_t weaponType = item->getWeaponType();
    if (weaponType == WEAPON_NONE || weaponType == WEAPON_SHIELD || weaponType == WEAPON_AMMO) {
        return nullptr;
    }

    if (!ignoreAmmo && weaponType == WEAPON_DISTANCE) {
        const ItemType& it = Item::items[item->getID()];
        if (it.ammoType != AMMO_NONE) {
            Item* ammoItem = inventory[CONST_SLOT_AMMO];
            if (!ammoItem || ammoItem->getAmmoType() != it.ammoType) {
                return nullptr;
            }
            item = ammoItem;
        }
    }
    return item;
}

Item* Player::getWeapon(bool ignoreAmmo/* = false*/) const
{
  /* If player is dual wielding, we already assured he has weapons in both hands. */
  if (isDualWielding()) {
      return getWeapon(getAttackHand(), ignoreAmmo);
  }

    Item* item = getWeapon(CONST_SLOT_LEFT, ignoreAmmo);
    if (item) {
        return item;
    }

    item = getWeapon(CONST_SLOT_RIGHT, ignoreAmmo);
    if (item) {
        return item;
    }
    return nullptr;
}
 
Hmm, I don't see anything that could be causing this.
I'd try either attaching debugger to see what's up or if you don't know how to do that, you could add these statements temporarily:
C++:
if (lweapon == nullptr)
    std::cout << "lweapon is null" << std::endl;
else
    std::cout << "left->getAttack() = " << left->getAttack() << std::endl;

if (rweapon == nullptr)
    std::cout << "rweapon is null" << std::endl;
else
    std::cout << "right->getAttack() = " << right->getAttack() << std::endl;
 
Back
Top