Exemplo n.º 1
0
int32_t
PListViewInvoke(void *pobject, void *in, void *out, void *extraData)
{
	if (!pobject || !in || !out)
		return B_ERROR;
	
	PView *parent = static_cast<PView*>(pobject);
	if (!parent)
		return B_BAD_TYPE;
	
	BListView *backend = (BListView*)parent->GetView();
	
	PArgs *args = static_cast<PArgs*>(in);
	int32 what;
	if (args->FindInt32("message", &what) != B_OK)
		what = -1;
	
	if (backend->Window())
		backend->Window()->Lock();
	
	if (what >= 0)
	{
		BMessage invMsg(what);
		backend->Invoke(&invMsg);
	}
	else	
		backend->Invoke();
	
	if (backend->Window())
		backend->Window()->Unlock();
	
	return B_OK;
}
Exemplo n.º 2
0
status_t
PListView::SetProperty(const char *name, PValue *value, const int32 &index)
{
	if (!name || !value)
		return B_ERROR;
	
	BString str(name);
	PProperty *prop = FindProperty(name,index);
	if (!prop)
		return B_NAME_NOT_FOUND;
	
	if (FlagsForProperty(prop) & PROPERTY_READ_ONLY)
		return B_READ_ONLY;
	
	BListView *backend = (BListView*)fView;
	
	BoolValue boolval;
	CharValue charval;
	ColorValue colorval;
	FloatValue floatval;
	IntValue intval;
	PointValue pointval;
	RectValue rectval;
	StringValue stringval;
	
	status_t status = prop->SetValue(value);
	if (status != B_OK)
		return status;

	if (backend->Window())
		backend->Window()->Lock();

	else if (str.ICompare("SelectionMessage") == 0)
	{
		BMessage selMsg(*intval.value);
		backend->SetSelectionMessage(&selMsg);
	}
	else if (str.ICompare("InvocationMessage") == 0)
	{
		BMessage invMsg(*intval.value);
		backend->SetInvocationMessage(&invMsg);
	}
	else if (str.ICompare("SelectionType") == 0)
	{
		prop->GetValue(&intval);
		backend->SetListType((list_view_type)*intval.value);
	}
	else
	{
		if (backend->Window())
			backend->Window()->Unlock();

		return PView::SetProperty(name, value, index);
	}

	if (backend->Window())
		backend->Window()->Unlock();

	return prop->GetValue(value);
}
Exemplo n.º 3
0
unsigned Inventory::removeFromSlot(unsigned slot, unsigned amount)
{
    InventoryData::iterator it = mPoss->inventory.find(slot);

    // When the given slot doesn't exist, we can't remove anything
    if (it == mPoss->inventory.end())
        return amount;

    LOG_DEBUG("Inventory: Request Removal of " << amount << " item(s) in slot: "
              << slot << " for character: '"
              << mCharacter->getComponent<BeingComponent>()->getName() << "'.");

    MessageOut invMsg(GPMSG_INVENTORY);
    // Check if an item of the same id exists elsewhere in the inventory
    bool exists = false;
    for (InventoryData::const_iterator it2 = mPoss->inventory.begin(),
         it2_end = mPoss->inventory.end();
         it2 != it2_end; ++it2)
    {
        if (it2->second.itemId == it->second.itemId
                && it->first != it2->first)
        {
            exists = true;
            break;
        }
    }

    // We check whether it's the last slot where we can find that item id.
    bool lastSlotOfItemRemaining = false;
    if (!exists && it->second.itemId)
        lastSlotOfItemRemaining = true;

    unsigned sub = std::min(amount, it->second.amount);
    amount -= sub;
    it->second.amount -= sub;
    invMsg.writeInt16(it->first);
    if (it->second.amount)
    {
        invMsg.writeInt16(it->second.itemId);
        invMsg.writeInt16(it->second.amount);
    }
    else
    {
        invMsg.writeInt16(0);

        // The item(s) was(were) the last one(s) in the inventory.
        if (lastSlotOfItemRemaining)
        {
            if (ItemClass *ic = itemManager->getItem(it->second.itemId))
                ic->useTrigger(mCharacter, ITT_LEAVE_INVY);
        }
        mPoss->inventory.erase(it);
    }

    if (invMsg.getLength() > 2)
        gameHandler->sendTo(mCharacter, invMsg);

    return amount;
}
Exemplo n.º 4
0
unsigned Inventory::move(unsigned slot1, unsigned slot2,
                             unsigned amount)
{
    LOG_DEBUG(amount << " item(s) requested to move from: " << slot1 << " to "
              << slot2 << " for character: '"
              << mCharacter->getComponent<BeingComponent>()->getName() << "'.");

    if (!amount || slot1 == slot2 || slot2 >= INVENTORY_SLOTS)
        return amount;

    InventoryData::iterator it1 = mPoss->inventory.find(slot1),
                            it2 = mPoss->inventory.find(slot2),
                            inv_end = mPoss->inventory.end();

    if (it1 == inv_end)
        return amount;

    MessageOut invMsg(GPMSG_INVENTORY);

    unsigned nb = std::min(amount, it1->second.amount);
    if (it2 == inv_end)
    {
        // Slot2 does not yet exist.
        mPoss->inventory[slot2].itemId = it1->second.itemId;
        nb = std::min(itemManager->getItem(it1->second.itemId)->getMaxPerSlot(),
                      nb);

        mPoss->inventory[slot2].amount = nb;
        it1->second.amount -= nb;
        amount -= nb;

        //Save the itemId in case of deletion of the iterator
        unsigned itemId = it1->second.itemId;
        invMsg.writeInt16(slot1);                  // Slot
        if (it1->second.amount)
        {
            invMsg.writeInt16(it1->second.itemId); // Item Id
            invMsg.writeInt16(it1->second.amount); // Amount
            LOG_DEBUG("Left " << amount << " item(s) id:"
                      << it1->second.itemId << " into slot: " << slot1);
        }
        else
        {
            invMsg.writeInt16(0);
            mPoss->inventory.erase(it1);
            LOG_DEBUG("Slot: " << slot1 << " is now empty.");
        }
        invMsg.writeInt16(slot2);                  // Slot
        invMsg.writeInt16(itemId);     // Item Id (same as slot 1)
        invMsg.writeInt16(nb);                     // Amount
        LOG_DEBUG("Slot: " << slot2 << " has now " << nb << " of item id: "
                  << itemId);
    }
    else
    {
        // Slot2 exists.
        if (it2->second.itemId != it1->second.itemId)
         {
            // Swap items when they are of a different type
            // and when all the amount of slot 1 is moving onto slot 2.
            if (amount >= it1->second.amount)
            {
                unsigned itemId = it1->second.itemId;
                unsigned amount = it1->second.amount;
                it1->second.itemId = it2->second.itemId;
                it1->second.amount = it2->second.amount;
                it2->second.itemId = itemId;
                it2->second.amount = amount;

                // Sending swapped slots.
                invMsg.writeInt16(slot1);
                invMsg.writeInt16(it1->second.itemId);
                invMsg.writeInt16(it1->second.amount);
                invMsg.writeInt16(slot2);
                invMsg.writeInt16(it2->second.itemId);
                invMsg.writeInt16(it2->second.amount);
                LOG_DEBUG("Swapping items in slots " << slot1
                          << " and " << slot2);
            }
            else
            {
                // Cannot partially stack items of a different type.
                LOG_DEBUG("Cannot move " << amount << " item(s) from slot "
                          << slot1 << " to " << slot2);
                return amount;
            }
        }
        else // Same item type on slot 2.
        {
            // Number of items moving
            nb = std::min(itemManager->getItem(
                              it1->second.itemId)->getMaxPerSlot()
                              - it2->second.amount, nb);

            // If nothing can move, we can abort
            if (!nb)
                return amount;

            it1->second.amount -= nb;
            it2->second.amount += nb;
            amount -= nb;

            invMsg.writeInt16(slot1);                  // Slot
            if (it1->second.amount)
            {
                invMsg.writeInt16(it1->second.itemId); // Item Id
                invMsg.writeInt16(it1->second.amount); // Amount
            }
            else
            {
                invMsg.writeInt16(0);
                mPoss->inventory.erase(it1);
            }
            invMsg.writeInt16(slot2);                  // Slot
            invMsg.writeInt16(it2->second.itemId);     // Item Id
            invMsg.writeInt16(it2->second.amount);     // Amount
        }
    }

    if (invMsg.getLength() > 2)
        gameHandler->sendTo(mCharacter, invMsg);

    return amount;
}
Exemplo n.º 5
0
unsigned Inventory::remove(unsigned itemId, unsigned amount)
{
    if (!itemId || !amount)
        return amount;

    LOG_DEBUG("Inventory: Request remove of " << amount << " item(s) id: "
              << itemId << " for character: '"
              << mCharacter->getComponent<BeingComponent>()->getName()
              << "'.");

    MessageOut invMsg(GPMSG_INVENTORY);
    bool triggerLeaveInventory = true;
    for (InventoryData::iterator it = mPoss->inventory.begin();
         it != mPoss->inventory.end();)
    {
        LOG_DEBUG("Remove: Treating slot id: " << it->first);
        if (it->second.itemId == itemId)
        {
            if (amount)
            {
                unsigned sub = std::min(amount, it->second.amount);
                amount -= sub;
                it->second.amount -= sub;
                invMsg.writeInt16(it->first);
                if (it->second.amount)
                {
                    invMsg.writeInt16(it->second.itemId);
                    invMsg.writeInt16(it->second.amount);
                    // Some still exist, and we have none left to remove, so
                    // no need to run leave invy triggers.
                    if (!amount)
                        triggerLeaveInventory = false;
                    LOG_DEBUG("Slot id: " << it->first << " has now "
                              << it->second.amount << "item(s).");
                }
                else
                {
                    invMsg.writeInt16(0);
                    // Ensure the slot is set empty.
                    LOG_DEBUG("Slot id: " << it->first << " is now empty.");
                    mPoss->inventory.erase(it++);
                    continue;
                }
            }
            else
            {
                // We found an instance of them existing and have none left to
                // remove, so no need to run leave invy triggers.
                triggerLeaveInventory = false;
            }
        }
        ++it;
    }

    if (triggerLeaveInventory)
        itemManager->getItem(itemId)->useTrigger(mCharacter, ITT_LEAVE_INVY);

    if (invMsg.getLength() > 2)
        gameHandler->sendTo(mCharacter, invMsg);

    return amount;
}
Exemplo n.º 6
0
unsigned Inventory::insert(unsigned itemId, unsigned amount)
{
    if (!itemId || !amount)
        return 0;

    MessageOut invMsg(GPMSG_INVENTORY);
    ItemClass *item = itemManager->getItem(itemId);
    if (!item) {
        LOG_ERROR("Inventory: Trying to insert invalid item id " << itemId
                  << " (amount: " << amount << ")");
        return amount;
    }
    unsigned maxPerSlot = item->getMaxPerSlot();

    LOG_DEBUG("Inventory: Inserting " << amount << " item(s) Id: " << itemId
              << " for character '"
              << mCharacter->getComponent<BeingComponent>()->getName() << "'.");

    InventoryData::iterator it, it_end = mPoss->inventory.end();
    // Add to slots with existing items of this type first.
    for (it = mPoss->inventory.begin(); it != it_end; ++it)
    {
        if (it->second.itemId == itemId)
        {
            // If the slot is full, try the next slot
            if (it->second.amount >= maxPerSlot)
                continue;

            // Add everything that'll fit to the stack
            unsigned short spaceLeft = maxPerSlot - it->second.amount;
            if (spaceLeft >= amount)
            {
                it->second.amount += amount;
                amount = 0;
                LOG_DEBUG("Everything inserted at slot id: " << it->first);
            }
            else
            {
                it->second.amount += spaceLeft;
                amount -= spaceLeft;
                LOG_DEBUG(spaceLeft << " item(s) inserted at slot id: "
                          << it->first);
            }

            invMsg.writeInt16(it->first);
            invMsg.writeInt16(itemId);
            invMsg.writeInt16(it->second.amount);
            if (!amount)
                break;
        }
    }

    int slot = 0;
    // We still have some left, so add to blank slots.
    for (it = mPoss->inventory.begin();; ++it)
    {
        if (!amount)
            break;
        int lim = (it == it_end) ? INVENTORY_SLOTS : it->first;
        while (amount && slot < lim)
        {
            int additions = std::min(amount, maxPerSlot);
            mPoss->inventory[slot].itemId = itemId;
            mPoss->inventory[slot].amount = additions;
            amount -= additions;
            LOG_DEBUG(additions << " item(s) inserted at slot id: " << slot);
            invMsg.writeInt16(slot++); // Last read, so also increment
            invMsg.writeInt16(itemId);
            invMsg.writeInt16(additions);
        }
        ++slot; // Skip the slot that the iterator points to
        if (it == it_end)
            break;
    }

    item->useTrigger(mCharacter, ITT_IN_INVY);

    // Send that first, before checking potential removals
    if (invMsg.getLength() > 2)
        gameHandler->sendTo(mCharacter, invMsg);

    return amount;
}