Merge remote-tracking branch 'queatz/mmb10'
authorPerttu Ahola <celeron55@gmail.com>
Tue, 30 Aug 2011 11:24:23 +0000 (14:24 +0300)
committerPerttu Ahola <celeron55@gmail.com>
Tue, 30 Aug 2011 11:24:23 +0000 (14:24 +0300)
src/content_nodemeta.cpp
src/content_nodemeta.h
src/guiMainMenu.cpp
src/inventory.cpp
src/inventory.h
src/server.cpp

index 433e6d04b23e372138eaee5f33d945fd295d00b9..d29eea6616ec1361f6220be2b35f19af1d808975 100644 (file)
@@ -182,19 +182,45 @@ std::string FurnaceNodeMetadata::infoText()
                assert(src_list);
                const InventoryItem *src_item = src_list->getItem(0);
 
-               if(src_item)
+               if(src_item) {
+                       InventoryList *dst_list = m_inventory->getList("dst");
+                       if(!dst_list->roomForCookedItem(src_item))
+                               return "Furnace is overloaded";
                        return "Furnace is out of fuel";
+               }
                else
                        return "Furnace is inactive";
        }
        else
        {
-               std::string s = "Furnace is active (";
-               s += itos(m_fuel_time/m_fuel_totaltime*100);
-               s += "%)";
+               std::string s = "Furnace is active";
+               // Do this so it doesn't always show (0%) for weak fuel
+               if(m_fuel_totaltime > 3) {
+                       s += " (";
+                       s += itos(m_fuel_time/m_fuel_totaltime*100);
+                       s += "%)";
+               }
                return s;
        }
 }
+bool FurnaceNodeMetadata::nodeRemovalDisabled()
+{
+       /*
+               Disable removal if furnace is not empty
+       */
+       InventoryList *list[3] = {m_inventory->getList("src"),
+       m_inventory->getList("dst"), m_inventory->getList("fuel")};
+       
+       for(int i = 0; i < 3; i++) {
+               if(list[i] == NULL)
+                       continue;
+               if(list[i]->getUsedSlots() == 0)
+                       continue;
+               return true;
+       }
+       return false;
+       
+}
 void FurnaceNodeMetadata::inventoryModified()
 {
        dstream<<"Furnace inventory modification callback"<<std::endl;
@@ -221,9 +247,14 @@ bool FurnaceNodeMetadata::step(float dtime)
                assert(src_list);
                const InventoryItem *src_item = src_list->getItem(0);
                
+               bool room_available = false;
+               
+               if(src_item && src_item->isCookable())
+                       room_available = dst_list->roomForCookedItem(src_item);
+               
                // Start only if there are free slots in dst, so that it can
                // accomodate any result item
-               if(dst_list->getFreeSlots() > 0 && src_item && src_item->isCookable())
+               if(room_available)
                {
                        m_src_totaltime = 3;
                }
@@ -252,13 +283,18 @@ bool FurnaceNodeMetadata::step(float dtime)
                                m_src_totaltime = 0;
                        }
                        changed = true;
-                       continue;
+                       
+                       // Fall through if the fuel item was used up this step
+                       if(m_fuel_time < m_fuel_totaltime)
+                               continue;
                }
                
                /*
-                       If there is no source item or source item is not cookable, stop loop.
+                       If there is no source item or source item is not cookable,
+                       or furnace became overloaded, stop loop.
                */
-               if(src_item == NULL || m_src_totaltime < 0.001)
+               if((m_fuel_time < m_fuel_totaltime || dst_list->roomForCookedItem(src_item) == false)
+                       && (src_item == NULL || m_src_totaltime < 0.001))
                {
                        m_step_accumulator = 0;
                        break;
index 84c3aed9d030ae76a9989d64c0706ccbc6b51bc7..50decd91081782242808797e4fb42041bbc37e66 100644 (file)
@@ -76,6 +76,7 @@ public:
        virtual Inventory* getInventory() {return m_inventory;}
        virtual void inventoryModified();
        virtual bool step(float dtime);
+       virtual bool nodeRemovalDisabled();
        virtual std::string getInventoryDrawSpecString();
 
 private:
index 2d5bd151acadd87fcb84f0f436e076fb2a1f90b1..fde71e4bc0d3b6c1d3a45eaca3286dcd51632822 100644 (file)
@@ -196,6 +196,8 @@ void GUIMainMenu::regenerateGui(v2u32 screensize)
                gui::IGUIEditBox *e =
                Environment->addEditBox(L"", rect, true, this, 264);
                e->setPasswordBox(true);
+               if(text_name != L"" && text_address != L"")
+                       Environment->setFocus(e);
 
        }
        changeCtype("");
@@ -212,7 +214,7 @@ void GUIMainMenu::regenerateGui(v2u32 screensize)
                rect += topleft_client + v2s32(160, 100);
                gui::IGUIElement *e = 
                Environment->addEditBox(text_address.c_str(), rect, true, this, GUI_ID_ADDRESS_INPUT);
-               if(text_name != L"")
+               if(text_name != L"" && text_address == L"")
                        Environment->setFocus(e);
        }
        {
index 1ee63819dc344137240f0e2fa0816dcbe780e45f..62aedb536aee407b4309706c8b4b8c1b2c36c3aa 100644 (file)
@@ -549,7 +549,7 @@ InventoryItem * InventoryList::addItem(u32 i, InventoryItem *newitem)
        }
 }
 
-bool InventoryList::itemFits(u32 i, InventoryItem *newitem)
+bool InventoryList::itemFits(const u32 i, const InventoryItem *newitem)
 {
        // If it is an empty position, it's an easy job.
        const InventoryItem *to_item = getItem(i);
@@ -558,11 +558,11 @@ bool InventoryList::itemFits(u32 i, InventoryItem *newitem)
                return true;
        }
        
-       // If not addable, return the item
+       // If not addable, fail
        if(newitem->addableTo(to_item) == false)
                return false;
        
-       // If the item fits fully in the slot, add counter and delete it
+       // If the item fits fully in the slot, pass
        if(newitem->getCount() <= to_item->freeSpace())
        {
                return true;
@@ -571,6 +571,24 @@ bool InventoryList::itemFits(u32 i, InventoryItem *newitem)
        return false;
 }
 
+bool InventoryList::roomForItem(const InventoryItem *item)
+{
+       for(u32 i=0; i<m_items.size(); i++)
+               if(itemFits(i, item))
+                       return true;
+       return false;
+}
+
+bool InventoryList::roomForCookedItem(const InventoryItem *item)
+{
+       const InventoryItem *cook = item->createCookResult();
+       if(!cook)
+               return false;
+       bool room = roomForItem(cook);
+       delete cook;
+       return room;
+}
+
 InventoryItem * InventoryList::takeItem(u32 i, u32 count)
 {
        if(count == 0)
index 9c2027a5303e874d23a92d88f69c6cb2301b5012..b19a365c8ee1b71266835eaca6d0dab3bc7a5d1d 100644 (file)
@@ -490,7 +490,13 @@ public:
        InventoryItem * addItem(u32 i, InventoryItem *newitem);
 
        // Checks whether the item could be added to the given slot
-       bool itemFits(u32 i, InventoryItem *newitem);
+       bool itemFits(const u32 i, const InventoryItem *newitem);
+
+       // Checks whether there is room for a given item
+       bool roomForItem(const InventoryItem *item);
+
+       // Checks whether there is room for a given item aftr it has been cooked
+       bool roomForCookedItem(const InventoryItem *item);
 
        // Takes some items from a slot.
        // If there are not enough, takes as many as it can.
index a8eb68c55a95cc5d1fb9d1dd4f1424404d9cc32c..14d8942cb0cf6a4a4b5091b8c70923ae207e248a 100644 (file)
@@ -2446,7 +2446,7 @@ void Server::ProcessData(u8 *data, u32 datasize, u16 peer_id)
                                        if(g_settings.getBool("creative_mode") == false)
                                        {
                                                // Skip if inventory has no free space
-                                               if(ilist->getUsedSlots() == ilist->getSize())
+                                               if(ilist->roomForItem(item) == false)
                                                {
                                                        dout_server<<"Player inventory has no free space"<<std::endl;
                                                        return;
@@ -3198,6 +3198,9 @@ void Server::ProcessData(u8 *data, u32 datasize, u16 peer_id)
                                                mlist->addItem(item1);
                                        }
                                }
+                               // Disallow moving items if not allowed to build
+                               else if((getPlayerPrivs(player) & PRIV_BUILD) == 0)
+                                       return;
                        }
                        
                        if(disable_action == false)