diff --git a/source/Items/ItemBed.h b/source/Items/ItemBed.h index b49df65a3..1b2c54cbd 100644 --- a/source/Items/ItemBed.h +++ b/source/Items/ItemBed.h @@ -7,8 +7,8 @@ class cItemBedHandler : public cItemHandler { public: - cItemBedHandler(int a_ItemID) - : cItemHandler(a_ItemID) + cItemBedHandler(int a_ItemType) + : cItemHandler(a_ItemType) { } diff --git a/source/Items/ItemBucket.h b/source/Items/ItemBucket.h index 21c9da2a9..3490300ae 100644 --- a/source/Items/ItemBucket.h +++ b/source/Items/ItemBucket.h @@ -3,92 +3,162 @@ #include "ItemHandler.h" #include "../World.h" +#include "../Simulator/FluidSimulator.h" +#include "../Blocks/BlockHandler.h" -class cItemBucketHandler : public cItemHandler + + + + +class cItemBucketHandler : + public cItemHandler { public: - cItemBucketHandler(int a_ItemID) - : cItemHandler(a_ItemID) + cItemBucketHandler(int a_ItemType) : + cItemHandler(a_ItemType) { } - virtual bool OnItemUse(cWorld *a_World, cPlayer *a_Player, cItem *a_Item, int a_X, int a_Y, int a_Z, char a_Dir) override + virtual bool OnItemUse(cWorld * a_World, cPlayer * a_Player, cItem * a_Item, int a_BlockX, int a_BlockY, int a_BlockZ, char a_Dir) override { - switch(m_ItemID) + switch (m_ItemType) { - case E_ITEM_BUCKET: + case E_ITEM_BUCKET: return ScoopUpFluid(a_World, a_Player, a_Item, a_BlockX, a_BlockY, a_BlockZ, a_Dir); + case E_ITEM_LAVA_BUCKET: return PlaceFluid (a_World, a_Player, a_Item, a_BlockX, a_BlockY, a_BlockZ, a_Dir, E_BLOCK_LAVA); + case E_ITEM_WATER_BUCKET: return PlaceFluid (a_World, a_Player, a_Item, a_BlockX, a_BlockY, a_BlockZ, a_Dir, E_BLOCK_WATER); + default: { - if (a_Dir >= 0) - { - AddDirection(a_X, a_Y, a_Z, a_Dir); - } - BLOCKTYPE ClickedBlock = a_World->GetBlock(a_X, a_Y, a_Z); - LOG("Bucket Clicked BlockID: %d", ClickedBlock); - ENUM_ITEM_ID NewItem = E_ITEM_EMPTY; - switch (ClickedBlock) - { - case E_BLOCK_WATER: - case E_BLOCK_STATIONARY_WATER: - { - NewItem = E_ITEM_WATER_BUCKET; - break; - } - case E_BLOCK_LAVA: - case E_BLOCK_STATIONARY_LAVA: - { - NewItem = E_ITEM_LAVA_BUCKET; - break; - } - } - cItem Item(a_Item->m_ItemID, 1); - if ( - (NewItem != E_ITEM_EMPTY) && - ( - ((a_Player->GetGameMode() == 1) || - a_Player->GetInventory().RemoveItem(Item)) - ) - ) - { - // Give New Bucket - cItem Item(NewItem, 1); - a_Player->GetInventory().AddItem(Item); - // Remove water / lava block - a_Player->GetWorld()->SetBlock(a_X, a_Y, a_Z, E_BLOCK_AIR, 0); - return true; - } + ASSERT(!"Unhandled ItemType"); + return false; + } + } + } + + + + bool ScoopUpFluid(cWorld * a_World, cPlayer * a_Player, cItem * a_Item, int a_BlockX, int a_BlockY, int a_BlockZ, char a_Dir) + { + if (a_Dir < 0) + { + return false; + } + AddDirection(a_BlockX, a_BlockY, a_BlockZ, a_Dir); + BLOCKTYPE ClickedBlock; + NIBBLETYPE ClickedMeta; + a_World->GetBlockTypeMeta(a_BlockX, a_BlockY, a_BlockZ, ClickedBlock, ClickedMeta); + LOGD("Bucket Clicked BlockType %d, meta %d", ClickedBlock, ClickedMeta); + if (ClickedMeta != 0) + { + // Not a source block + return false; + } + + if (a_Player->GetGameMode() == eGameMode_Creative) + { + // In creative mode don't modify the inventory, just remove the fluid: + a_World->SetBlock(a_BlockX, a_BlockY, a_BlockZ, E_BLOCK_AIR, 0); + return true; + } + + ENUM_ITEM_ID NewItem = E_ITEM_EMPTY; + switch (ClickedBlock) + { + case E_BLOCK_WATER: + case E_BLOCK_STATIONARY_WATER: + { + NewItem = E_ITEM_WATER_BUCKET; + break; + } + case E_BLOCK_LAVA: + case E_BLOCK_STATIONARY_LAVA: + { + NewItem = E_ITEM_LAVA_BUCKET; break; } - case E_ITEM_WATER_BUCKET: - case E_ITEM_LAVA_BUCKET: - { - BLOCKTYPE NewBlock = (m_ItemID == E_ITEM_LAVA_BUCKET) ? E_BLOCK_LAVA : E_BLOCK_WATER; - if (a_Dir >= 0) - { - AddDirection(a_X, a_Y, a_Z, a_Dir); - if (a_World->GetBlock(a_X, a_Y, a_Z) == E_BLOCK_AIR) - { - cItem Item(a_Item->m_ItemID, 1); - if ((a_Player->GetGameMode() == 1) || (a_Player->GetInventory().RemoveItem(Item))) - { - a_World->SetBlock(a_X, a_Y, a_Z, NewBlock, 0); + default: return false; + } + + // Remove the bucket from the inventory + cItem Item(a_Item->m_ItemType, 1); + if (!a_Player->GetInventory().RemoveItem(Item)) + { + LOG("Clicked with an empty bucket, but cannot remove one from the inventory? WTF?"); + ASSERT(!"Inventory bucket mismatch"); + return true; + } + + // Give new bucket, filled with fluid: + Item.m_ItemType = NewItem; + Item.m_ItemCount = 1; + a_Player->GetInventory().AddItem(Item); - if (a_Player->GetGameMode() == 1) - { - break; //No new Bucket for creative players - } - cItem Item(E_ITEM_BUCKET, 1); - a_Player->GetInventory().AddItem(Item); - return true; - } - } - } + // Remove water / lava block + a_Player->GetWorld()->SetBlock(a_BlockX, a_BlockY, a_BlockZ, E_BLOCK_AIR, 0); + return true; + } + + + bool PlaceFluid(cWorld * a_World, cPlayer * a_Player, cItem * a_Item, int a_BlockX, int a_BlockY, int a_BlockZ, char a_Dir, BLOCKTYPE a_FluidBlock) + { + if (a_Dir < 0) + { + return false; + } + + BLOCKTYPE CurrentBlock = a_World->GetBlock(a_BlockX, a_BlockY, a_BlockZ); + bool CanWashAway = cFluidSimulator::CanWashAway(CurrentBlock); + if (!CanWashAway) + { + // The block pointed at cannot be washed away, so put fluid on top of it / on its sides + AddDirection(a_BlockX, a_BlockY, a_BlockZ, a_Dir); + CurrentBlock = a_World->GetBlock(a_BlockX, a_BlockY, a_BlockZ); + } + if ( + !CanWashAway && + (CurrentBlock != E_BLOCK_AIR) && + (CurrentBlock != E_BLOCK_WATER) && + (CurrentBlock != E_BLOCK_STATIONARY_WATER) && + (CurrentBlock != E_BLOCK_LAVA) && + (CurrentBlock != E_BLOCK_STATIONARY_LAVA) + ) + { + // Cannot place water here + return false; + } + + if (a_Player->GetGameMode() != eGameMode_Creative) + { + // Remove fluid bucket, add empty bucket: + cItem Item(a_Item->m_ItemType, 1); + if (!a_Player->GetInventory().RemoveItem(Item)) + { + LOG("Clicked with a full bucket, but cannot remove one from the inventory? WTF?"); + ASSERT(!"Inventory bucket mismatch"); + return false; + } + Item.m_ItemType = E_ITEM_BUCKET; + Item.m_ItemCount = 1; + if (!a_Player->GetInventory().AddItem(Item)) + { + return false; + } + } + + // Wash away anything that was there prior to placing: + if (CanWashAway) + { + cBlockHandler * Handler = BlockHandler(CurrentBlock); + if (Handler->DoesDropOnUnsuitable()) + { + Handler->DropBlock(a_World, a_BlockX, a_BlockY, a_BlockZ); } - break; } - return false; + a_World->SetBlock(a_BlockX, a_BlockY, a_BlockZ, a_FluidBlock, 0); + + return true; } }; \ No newline at end of file diff --git a/source/Items/ItemCloth.h b/source/Items/ItemCloth.h index 5de064397..f6e2c1906 100644 --- a/source/Items/ItemCloth.h +++ b/source/Items/ItemCloth.h @@ -11,8 +11,8 @@ class cItemClothHandler : public cItemHandler { public: - cItemClothHandler(int a_ItemID) - : cItemHandler(a_ItemID) + cItemClothHandler(int a_ItemType) + : cItemHandler(a_ItemType) { } diff --git a/source/Items/ItemDoor.h b/source/Items/ItemDoor.h index 6e841333f..949ad833a 100644 --- a/source/Items/ItemDoor.h +++ b/source/Items/ItemDoor.h @@ -7,8 +7,8 @@ class cItemDoorHandler : public cItemHandler { public: - cItemDoorHandler(int a_ItemID) - : cItemHandler(a_ItemID) + cItemDoorHandler(int a_ItemType) + : cItemHandler(a_ItemType) { } @@ -20,7 +20,7 @@ public: virtual BLOCKTYPE GetBlockType() override { - return (m_ItemID == E_ITEM_WOODEN_DOOR) ? E_BLOCK_WOODEN_DOOR : E_BLOCK_IRON_DOOR; + return (m_ItemType == E_ITEM_WOODEN_DOOR) ? E_BLOCK_WOODEN_DOOR : E_BLOCK_IRON_DOOR; } }; \ No newline at end of file diff --git a/source/Items/ItemDye.h b/source/Items/ItemDye.h index 16e850719..28512c74d 100644 --- a/source/Items/ItemDye.h +++ b/source/Items/ItemDye.h @@ -13,23 +13,23 @@ class cItemDyeHandler : public cItemHandler { public: - cItemDyeHandler(int a_ItemID) - : cItemHandler(a_ItemID) + cItemDyeHandler(int a_ItemType) + : cItemHandler(a_ItemType) { } - virtual bool OnItemUse(cWorld *a_World, cPlayer *a_Player, cItem *a_Item, int a_X, int a_Y, int a_Z, char a_Dir) override + virtual bool OnItemUse(cWorld * a_World, cPlayer * a_Player, cItem * a_Item, int a_BlockX, int a_BlockY, int a_BlockZ, char a_Dir) override { // TODO: Handle coloring the sheep, too (OnItemUseOnEntity maybe) // Handle growing the plants: if (a_Item->m_ItemHealth == E_META_DYE_WHITE) { - if (a_World->GrowRipePlant(a_X, a_Y, a_Z, true)) + if (a_World->GrowRipePlant(a_BlockX, a_BlockY, a_BlockZ, true)) { - if (a_Player->GetGameMode() == eGameMode_Survival) + if (a_Player->GetGameMode() != eGameMode_Creative) { - cItem Item(a_Item->m_ItemID, 1, a_Item->m_ItemHealth); + cItem Item(a_Item->m_ItemType, 1, a_Item->m_ItemHealth); a_Player->GetInventory().RemoveItem(Item); return true; } diff --git a/source/Items/ItemFood.h b/source/Items/ItemFood.h index 6e5a27d5d..8faed1d05 100644 --- a/source/Items/ItemFood.h +++ b/source/Items/ItemFood.h @@ -7,8 +7,8 @@ class cItemFoodHandler : public cItemHandler { public: - cItemFoodHandler(int a_ItemID) - : cItemHandler(a_ItemID) + cItemFoodHandler(int a_ItemType) + : cItemHandler(a_ItemType) { } @@ -19,7 +19,7 @@ public: virtual FoodInfo GetFoodInfo() override { - switch(m_ItemID) + switch(m_ItemType) { case E_ITEM_BREAD: return FoodInfo(5, 6.f); diff --git a/source/Items/ItemHandler.cpp b/source/Items/ItemHandler.cpp index af050eabd..021794f84 100644 --- a/source/Items/ItemHandler.cpp +++ b/source/Items/ItemHandler.cpp @@ -42,44 +42,44 @@ cItemHandler * cItemHandler::m_ItemHandler[2266]; -cItemHandler *cItemHandler::GetItemHandler(int a_ItemID) +cItemHandler *cItemHandler::GetItemHandler(int a_ItemType) { - if(a_ItemID < 0) a_ItemID = 0; + if(a_ItemType < 0) a_ItemType = 0; if(!m_HandlerInitialized) { //We have to initialize memset(m_ItemHandler, 0, sizeof(m_ItemHandler)); m_HandlerInitialized = true; } - if(m_ItemHandler[a_ItemID]) - return m_ItemHandler[a_ItemID]; - m_ItemHandler[a_ItemID] = CreateItemHandler(a_ItemID); - return m_ItemHandler[a_ItemID]; + if(m_ItemHandler[a_ItemType]) + return m_ItemHandler[a_ItemType]; + m_ItemHandler[a_ItemType] = CreateItemHandler(a_ItemType); + return m_ItemHandler[a_ItemType]; } -cItemHandler *cItemHandler::CreateItemHandler(int a_ItemID) +cItemHandler *cItemHandler::CreateItemHandler(int a_ItemType) { - switch(a_ItemID) + switch(a_ItemType) { - default: return new cItemHandler(a_ItemID); + default: return new cItemHandler(a_ItemType); // Single item per handler, alphabetically sorted: - case E_ITEM_BED: return new cItemBedHandler(a_ItemID); - case E_ITEM_DYE: return new cItemDyeHandler(a_ItemID); - case E_ITEM_FLINT_AND_STEEL: return new cItemLighterHandler(a_ItemID); - case E_ITEM_LEAVES: return new cItemLeavesHandler(a_ItemID); - case E_ITEM_REDSTONE_DUST: return new cItemRedstoneDustHandler(a_ItemID); - case E_ITEM_REDSTONE_REPEATER: return new cItemRedstoneRepeaterHandler(a_ItemID); - case E_ITEM_SAPLING: return new cItemSaplingHandler(a_ItemID); - case E_ITEM_SHEARS: return new cItemShearsHandler(a_ItemID); - case E_ITEM_SIGN: return new cItemSignHandler(a_ItemID); - case E_ITEM_SPAWN_EGG: return new cItemSpawnEggHandler(a_ItemID); - case E_ITEM_SUGARCANE: return new cItemSugarcaneHandler(a_ItemID); - case E_ITEM_WOOL: return new cItemClothHandler(a_ItemID); + case E_ITEM_BED: return new cItemBedHandler(a_ItemType); + case E_ITEM_DYE: return new cItemDyeHandler(a_ItemType); + case E_ITEM_FLINT_AND_STEEL: return new cItemLighterHandler(a_ItemType); + case E_ITEM_LEAVES: return new cItemLeavesHandler(a_ItemType); + case E_ITEM_REDSTONE_DUST: return new cItemRedstoneDustHandler(a_ItemType); + case E_ITEM_REDSTONE_REPEATER: return new cItemRedstoneRepeaterHandler(a_ItemType); + case E_ITEM_SAPLING: return new cItemSaplingHandler(a_ItemType); + case E_ITEM_SHEARS: return new cItemShearsHandler(a_ItemType); + case E_ITEM_SIGN: return new cItemSignHandler(a_ItemType); + case E_ITEM_SPAWN_EGG: return new cItemSpawnEggHandler(a_ItemType); + case E_ITEM_SUGARCANE: return new cItemSugarcaneHandler(a_ItemType); + case E_ITEM_WOOL: return new cItemClothHandler(a_ItemType); case E_ITEM_WOODEN_HOE: case E_ITEM_STONE_HOE: @@ -87,7 +87,7 @@ cItemHandler *cItemHandler::CreateItemHandler(int a_ItemID) case E_ITEM_GOLD_HOE: case E_ITEM_DIAMOND_HOE: { - return new cItemHoeHandler(a_ItemID); + return new cItemHoeHandler(a_ItemType); } case E_ITEM_WOODEN_PICKAXE: @@ -96,7 +96,7 @@ cItemHandler *cItemHandler::CreateItemHandler(int a_ItemID) case E_ITEM_GOLD_PICKAXE: case E_ITEM_DIAMOND_PICKAXE: { - return new cItemPickaxeHandler(a_ItemID); + return new cItemPickaxeHandler(a_ItemType); } case E_ITEM_WOODEN_SHOVEL: @@ -105,7 +105,7 @@ cItemHandler *cItemHandler::CreateItemHandler(int a_ItemID) case E_ITEM_GOLD_SHOVEL: case E_ITEM_DIAMOND_SHOVEL: { - return new cItemShovelHandler(a_ItemID); + return new cItemShovelHandler(a_ItemType); } case E_ITEM_WOODEN_SWORD: @@ -114,39 +114,39 @@ cItemHandler *cItemHandler::CreateItemHandler(int a_ItemID) case E_ITEM_GOLD_SWORD: case E_ITEM_DIAMOND_SWORD: { - return new cItemSwordHandler(a_ItemID); + return new cItemSwordHandler(a_ItemType); } case E_ITEM_STONE_SLAB: case E_ITEM_WOODEN_SLAB: { - return new cItemSlabHandler(a_ItemID); + return new cItemSlabHandler(a_ItemType); } case E_ITEM_LOG: case E_ITEM_PLANKS: { - return new cItemWoodHandler(a_ItemID); + return new cItemWoodHandler(a_ItemType); } case E_ITEM_BUCKET: case E_ITEM_WATER_BUCKET: case E_ITEM_LAVA_BUCKET: { - return new cItemBucketHandler(a_ItemID); + return new cItemBucketHandler(a_ItemType); } case E_ITEM_PUMPKIN_SEEDS: case E_ITEM_MELON_SEEDS: case E_ITEM_SEEDS: { - return new cItemSeedsHandler(a_ItemID); + return new cItemSeedsHandler(a_ItemType); } case E_ITEM_IRON_DOOR: case E_ITEM_WOODEN_DOOR: { - return new cItemDoorHandler(a_ItemID); + return new cItemDoorHandler(a_ItemType); } // Food: @@ -166,7 +166,7 @@ cItemHandler *cItemHandler::CreateItemHandler(int a_ItemID) case E_ITEM_ROTTEN_FLESH: case E_ITEM_SPIDER_EYE: { - return new cItemFoodHandler(a_ItemID); + return new cItemFoodHandler(a_ItemType); } } } @@ -188,16 +188,16 @@ void cItemHandler::Deinit() -cItemHandler::cItemHandler(int a_ItemID) +cItemHandler::cItemHandler(int a_ItemType) { - m_ItemID = a_ItemID; + m_ItemType = a_ItemType; } -bool cItemHandler::OnItemUse(cWorld *a_World, cPlayer *a_Player, cItem *a_Item, int a_X, int a_Y, int a_Z, char a_Dir) +bool cItemHandler::OnItemUse(cWorld * a_World, cPlayer * a_Player, cItem * a_Item, int a_BlockX, int a_BlockY, int a_BlockZ, char a_Dir) { return false; } @@ -206,7 +206,7 @@ bool cItemHandler::OnItemUse(cWorld *a_World, cPlayer *a_Player, cItem *a_Item, -bool cItemHandler::OnDiggingBlock(cWorld *a_World, cPlayer *a_Player, cItem *a_Item, int a_X, int a_Y, int a_Z, char a_Dir) +bool cItemHandler::OnDiggingBlock(cWorld * a_World, cPlayer * a_Player, cItem * a_Item, int a_BlockX, int a_BlockY, int a_BlockZ, char a_Dir) { return false; } @@ -246,13 +246,13 @@ void cItemHandler::OnFoodEaten(cWorld *a_World, cPlayer *a_Player, cItem *a_Item char cItemHandler::GetMaxStackSize(void) { - if (m_ItemID < 256) + if (m_ItemType < 256) { // All blocks can stack up to 64 return 64; } - switch (m_ItemID) + switch (m_ItemType) { case E_ITEM_APPLE: return 64; case E_ITEM_ARROW: return 64; @@ -291,14 +291,14 @@ char cItemHandler::GetMaxStackSize(void) bool cItemHandler::IsTool() { return - (m_ItemID >= 256 && m_ItemID <= 259) - || (m_ItemID == 261) - || (m_ItemID >= 267 && m_ItemID <= 279) - || (m_ItemID >= 283 && m_ItemID <= 286) - || (m_ItemID >= 290 && m_ItemID <= 294) - || (m_ItemID >= 256 && m_ItemID <= 259) - || (m_ItemID == 325) - || (m_ItemID == 346); + (m_ItemType >= 256 && m_ItemType <= 259) + || (m_ItemType == 261) + || (m_ItemType >= 267 && m_ItemType <= 279) + || (m_ItemType >= 283 && m_ItemType <= 286) + || (m_ItemType >= 290 && m_ItemType <= 294) + || (m_ItemType >= 256 && m_ItemType <= 259) + || (m_ItemType == 325) + || (m_ItemType == 346); } @@ -308,15 +308,15 @@ bool cItemHandler::IsTool() bool cItemHandler::IsFood() { return - (m_ItemID == 260) - || (m_ItemID == 282) - || (m_ItemID == 297) - || (m_ItemID >= 319 && m_ItemID <= 320) - || (m_ItemID == 335) - || (m_ItemID >= 349 && m_ItemID <= 350) - || (m_ItemID == 357) - || (m_ItemID == 360) - || (m_ItemID >= 363 && m_ItemID <= 366); + (m_ItemType == 260) + || (m_ItemType == 282) + || (m_ItemType == 297) + || (m_ItemType >= 319 && m_ItemType <= 320) + || (m_ItemType == 335) + || (m_ItemType >= 349 && m_ItemType <= 350) + || (m_ItemType == 357) + || (m_ItemType == 360) + || (m_ItemType >= 363 && m_ItemType <= 366); } @@ -325,7 +325,7 @@ bool cItemHandler::IsFood() bool cItemHandler::IsPlaceable() { - return m_ItemID >= 1 && m_ItemID <= 136; + return m_ItemType >= 1 && m_ItemType <= 136; } @@ -343,16 +343,16 @@ bool cItemHandler::CanHarvestBlock(BLOCKTYPE a_BlockType) BLOCKTYPE cItemHandler::GetBlockType() { - ASSERT(m_ItemID < 256); // Items with IDs above 255 should all be handled by specific handlers + ASSERT(m_ItemType < 256); // Items with IDs above 255 should all be handled by specific handlers #ifdef _DEBUG - if (m_ItemID > 256) + if (m_ItemType > 256) { - LOGERROR("Item %d has no valid block!", m_ItemID); + LOGERROR("Item %d has no valid block!", m_ItemType); } #endif // _DEBUG - return (BLOCKTYPE) m_ItemID; + return (BLOCKTYPE) m_ItemType; } @@ -368,14 +368,14 @@ NIBBLETYPE cItemHandler::GetBlockMeta(short a_ItemDamage) -void cItemHandler::PlaceBlock(cWorld *a_World, cPlayer *a_Player, cItem *a_Item, int a_X, int a_Y, int a_Z, char a_Dir) +void cItemHandler::PlaceBlock(cWorld *a_World, cPlayer *a_Player, cItem *a_Item, int a_BlockX, int a_BlockY, int a_BlockZ, char a_Dir) { BLOCKTYPE Block = GetBlockType(); cBlockHandler *Handler = cBlockHandler::GetBlockHandler(Block); - Handler->PlaceBlock(a_World, a_Player, GetBlockMeta(a_Item->m_ItemHealth), a_X, a_Y, a_Z, a_Dir); + Handler->PlaceBlock(a_World, a_Player, GetBlockMeta(a_Item->m_ItemHealth), a_BlockX, a_BlockY, a_BlockZ, a_Dir); if(a_Player->GetGameMode() == eGameMode_Survival) { - cItem Item(a_Item->m_ItemID, 1); + cItem Item(a_Item->m_ItemType, 1); a_Player->GetInventory().RemoveItem(Item); } } diff --git a/source/Items/ItemHandler.h b/source/Items/ItemHandler.h index 23aa0448d..dfd5739af 100644 --- a/source/Items/ItemHandler.h +++ b/source/Items/ItemHandler.h @@ -17,9 +17,9 @@ class cPlayer; class cItemHandler { public: - cItemHandler(int a_ItemID); + cItemHandler(int a_ItemType); // Called when the player tries to use the item. Return false to make the item unusable. DEFAULT: False - virtual bool OnItemUse(cWorld *a_World, cPlayer *a_Player, cItem *a_Item, int a_X, int a_Y, int a_Z, char a_Dir); //eg for fishing or hoes + virtual bool OnItemUse(cWorld *a_World, cPlayer *a_Player, cItem *a_Item, int a_BlockX, int a_BlockY, int a_BlockZ, char a_Dir); //eg for fishing or hoes // Called while the player diggs a block using this item virtual bool OnDiggingBlock(cWorld * a_World, cPlayer * a_Player, cItem * a_HeldItem, int a_BlockX, int a_BlockY, int a_BlockZ, char a_BlockFace); // Called when the player destroys a block using this item. This also calls the drop function for the destroyed block @@ -50,7 +50,7 @@ public: virtual bool EatItem(cPlayer *a_Player, cItem *a_Item); // Places the current block and removes the item from the player inventory - virtual void PlaceBlock(cWorld *a_World, cPlayer *a_Player, cItem *a_Item, int a_X, int a_Y, int a_Z, char a_Dir); + virtual void PlaceBlock(cWorld *a_World, cPlayer *a_Player, cItem *a_Item, int a_BlockX, int a_BlockY, int a_BlockZ, char a_Dir); // Indicates if this item is a tool virtual bool IsTool(); @@ -66,18 +66,18 @@ public: // Returns whether this tool/item can harvest a specific block (e.g. wooden pickaxe can harvest stone, but wood canīt) DEFAULT: False virtual bool CanHarvestBlock(BLOCKTYPE a_BlockType); - static cItemHandler *GetItemHandler(int a_ItemID); + static cItemHandler *GetItemHandler(int a_ItemType); static void Deinit(); protected: - int m_ItemID; - static cItemHandler *CreateItemHandler(int m_ItemID); + int m_ItemType; + static cItemHandler *CreateItemHandler(int m_ItemType); static cItemHandler *m_ItemHandler[2266]; static bool m_HandlerInitialized; //used to detect if the itemhandlers are initialized }; //Short function -inline cItemHandler *ItemHandler(int a_ItemID) { return cItemHandler::GetItemHandler(a_ItemID); } \ No newline at end of file +inline cItemHandler *ItemHandler(int a_ItemType) { return cItemHandler::GetItemHandler(a_ItemType); } diff --git a/source/Items/ItemHoe.h b/source/Items/ItemHoe.h index e7ea9135c..bd39b7287 100644 --- a/source/Items/ItemHoe.h +++ b/source/Items/ItemHoe.h @@ -8,19 +8,19 @@ class cItemHoeHandler : public cItemHandler { public: - cItemHoeHandler(int a_ItemID) - : cItemHandler(a_ItemID) + cItemHoeHandler(int a_ItemType) + : cItemHandler(a_ItemType) { } - virtual bool OnItemUse(cWorld *a_World, cPlayer *a_Player, cItem *a_Item, int a_X, int a_Y, int a_Z, char a_Dir) override + virtual bool OnItemUse(cWorld *a_World, cPlayer *a_Player, cItem *a_Item, int a_BlockX, int a_BlockY, int a_BlockZ, char a_Dir) override { - BLOCKTYPE Block = a_World->GetBlock(a_X, a_Y, a_Z); + BLOCKTYPE Block = a_World->GetBlock(a_BlockX, a_BlockY, a_BlockZ); - if(Block == E_BLOCK_DIRT || Block == E_BLOCK_GRASS) + if ((Block == E_BLOCK_DIRT) || (Block == E_BLOCK_GRASS)) { - a_World->FastSetBlock(a_X, a_Y, a_Z, E_BLOCK_FARMLAND, 0); + a_World->FastSetBlock(a_BlockX, a_BlockY, a_BlockZ, E_BLOCK_FARMLAND, 0); a_Player->UseEquippedItem(); return true; diff --git a/source/Items/ItemLeaves.h b/source/Items/ItemLeaves.h index f96adb0b8..053bf6fb0 100644 --- a/source/Items/ItemLeaves.h +++ b/source/Items/ItemLeaves.h @@ -11,8 +11,8 @@ class cItemLeavesHandler : public cItemHandler { public: - cItemLeavesHandler(int a_ItemID) - : cItemHandler(a_ItemID) + cItemLeavesHandler(int a_ItemType) + : cItemHandler(a_ItemType) { } diff --git a/source/Items/ItemLighter.h b/source/Items/ItemLighter.h index 92279aafa..afa6c4fd5 100644 --- a/source/Items/ItemLighter.h +++ b/source/Items/ItemLighter.h @@ -7,19 +7,24 @@ class cItemLighterHandler : public cItemHandler { public: - cItemLighterHandler(int a_ItemID) - : cItemHandler(a_ItemID) + cItemLighterHandler(int a_ItemType) + : cItemHandler(a_ItemType) { } - virtual bool OnItemUse(cWorld *a_World, cPlayer *a_Player, cItem *a_Item, int a_X, int a_Y, int a_Z, char a_Dir) override + virtual bool OnItemUse(cWorld *a_World, cPlayer *a_Player, cItem *a_Item, int a_BlockX, int a_BlockY, int a_BlockZ, char a_Dir) override { + if (a_Dir < 0) + { + return false; + } + a_Player->UseEquippedItem(); - AddDirection(a_X, a_Y, a_Z, a_Dir); + AddDirection(a_BlockX, a_BlockY, a_BlockZ, a_Dir); - a_World->SetBlock(a_X, a_Y, a_Z, E_BLOCK_FIRE, 0); //0 -> new fire TODO: Make Firesimulator use this + a_World->SetBlock(a_BlockX, a_BlockY, a_BlockZ, E_BLOCK_FIRE, 0); //0 -> new fire TODO: Make Firesimulator use this return false; } diff --git a/source/Items/ItemPickaxe.h b/source/Items/ItemPickaxe.h index 68a55470a..4f513d2bc 100644 --- a/source/Items/ItemPickaxe.h +++ b/source/Items/ItemPickaxe.h @@ -8,15 +8,15 @@ class cItemPickaxeHandler : public cItemHandler { public: - cItemPickaxeHandler(int a_ItemID) - : cItemHandler(a_ItemID) + cItemPickaxeHandler(int a_ItemType) + : cItemHandler(a_ItemType) { } char PickaxeLevel() { - switch(m_ItemID) + switch(m_ItemType) { case E_ITEM_WOODEN_PICKAXE: case E_ITEM_GOLD_PICKAXE: diff --git a/source/Items/ItemRedstoneDust.h b/source/Items/ItemRedstoneDust.h index 1ce316d9e..69e57bab2 100644 --- a/source/Items/ItemRedstoneDust.h +++ b/source/Items/ItemRedstoneDust.h @@ -10,8 +10,8 @@ class cItemRedstoneDustHandler : public cItemHandler { public: - cItemRedstoneDustHandler(int a_ItemID) - : cItemHandler(a_ItemID) + cItemRedstoneDustHandler(int a_ItemType) + : cItemHandler(a_ItemType) { } diff --git a/source/Items/ItemRedstoneRepeater.h b/source/Items/ItemRedstoneRepeater.h index c31c2af53..b55ebc52e 100644 --- a/source/Items/ItemRedstoneRepeater.h +++ b/source/Items/ItemRedstoneRepeater.h @@ -10,8 +10,8 @@ class cItemRedstoneRepeaterHandler : public cItemHandler { public: - cItemRedstoneRepeaterHandler(int a_ItemID) - : cItemHandler(a_ItemID) + cItemRedstoneRepeaterHandler(int a_ItemType) + : cItemHandler(a_ItemType) { } diff --git a/source/Items/ItemSapling.h b/source/Items/ItemSapling.h index b0c223f29..ed635d265 100644 --- a/source/Items/ItemSapling.h +++ b/source/Items/ItemSapling.h @@ -10,8 +10,8 @@ class cItemSaplingHandler : public cItemHandler { public: - cItemSaplingHandler(int a_ItemID) - : cItemHandler(a_ItemID) + cItemSaplingHandler(int a_ItemType) + : cItemHandler(a_ItemType) { } diff --git a/source/Items/ItemSeeds.h b/source/Items/ItemSeeds.h index 3eb9d6e86..f013af3be 100644 --- a/source/Items/ItemSeeds.h +++ b/source/Items/ItemSeeds.h @@ -12,8 +12,8 @@ class cItemSeedsHandler : public cItemHandler { public: - cItemSeedsHandler(int a_ItemID) - : cItemHandler(a_ItemID) + cItemSeedsHandler(int a_ItemType) + : cItemHandler(a_ItemType) { } @@ -25,7 +25,7 @@ public: virtual BLOCKTYPE GetBlockType() override { - switch(m_ItemID) + switch(m_ItemType) { case E_ITEM_SEEDS: return E_BLOCK_CROPS; case E_ITEM_MELON_SEEDS: return E_BLOCK_MELON_STEM; @@ -39,18 +39,27 @@ public: return 0; //Not grown yet } - virtual void PlaceBlock(cWorld *a_World, cPlayer *a_Player, cItem *a_Item, int a_X, int a_Y, int a_Z, char a_Dir) override + + virtual void PlaceBlock(cWorld *a_World, cPlayer *a_Player, cItem *a_Item, int a_BlockX, int a_BlockY, int a_BlockZ, char a_Dir) override { - int X = a_X, - Y = a_Y, - Z = a_Z; + if (a_Dir != BLOCK_FACE_TOP) + { + // Only allow planting seeds from the top side of the block + return; + } + + int X = a_BlockX; + int Y = a_BlockY; + int Z = a_BlockZ; AddDirection(X, Y, Z, a_Dir, true); - if(a_World->GetBlock(X, Y, Z) != E_BLOCK_FARMLAND) + if (a_World->GetBlock(X, Y, Z) != E_BLOCK_FARMLAND) + { return; + } - return cItemHandler::PlaceBlock(a_World, a_Player, a_Item, a_X, a_Y, a_Z, a_Dir); + return cItemHandler::PlaceBlock(a_World, a_Player, a_Item, a_BlockX, a_BlockY, a_BlockZ, a_Dir); } } ; diff --git a/source/Items/ItemShears.h b/source/Items/ItemShears.h index 7e2ad61fe..743cbeaec 100644 --- a/source/Items/ItemShears.h +++ b/source/Items/ItemShears.h @@ -5,38 +5,59 @@ #include "../World.h" #include "../Player.h" -class cItemShearsHandler : public cItemHandler + + + + +class cItemShearsHandler : + public cItemHandler { public: - cItemShearsHandler(int a_ItemID) - : cItemHandler(a_ItemID) + cItemShearsHandler(int a_ItemType) : + cItemHandler(a_ItemType) { - } - virtual bool IsTool() override + + + virtual bool IsTool(void) override { return true; } - virtual bool OnDiggingBlock(cWorld *a_World, cPlayer *a_Player, cItem *a_Item, int a_X, int a_Y, int a_Z, char a_Dir) override + + + virtual bool OnDiggingBlock(cWorld *a_World, cPlayer *a_Player, cItem *a_Item, int a_BlockX, int a_BlockY, int a_BlockZ, char a_Dir) override { - BLOCKTYPE Block = a_World->GetBlock(a_X, a_Y, a_Z); - if(Block == E_BLOCK_LEAVES) + BLOCKTYPE Block = a_World->GetBlock(a_BlockX, a_BlockY, a_BlockZ); + if (Block == E_BLOCK_LEAVES) { cItems Drops; - Drops.push_back(cItem(E_ITEM_LEAVES, 1, a_World->GetBlockMeta(a_X, a_Y, a_Z))); - a_World->SpawnItemPickups(Drops, a_X, a_Y, a_Z); + Drops.push_back(cItem(E_ITEM_LEAVES, 1, a_World->GetBlockMeta(a_BlockX, a_BlockY, a_BlockZ))); + a_World->SpawnItemPickups(Drops, a_BlockX, a_BlockY, a_BlockZ); - a_World->SetBlock(a_X, a_Y, a_Z, E_BLOCK_AIR, 0); + a_World->SetBlock(a_BlockX, a_BlockY, a_BlockZ, E_BLOCK_AIR, 0); a_Player->UseEquippedItem(); return true; } + // TODO: cobweb, vines return false; } virtual bool CanHarvestBlock(BLOCKTYPE a_BlockType) override { - return a_BlockType == E_BLOCK_COBWEB - || a_BlockType == E_BLOCK_VINES; + switch (a_BlockType) + { + case E_BLOCK_COBWEB: + case E_BLOCK_VINES: + case E_BLOCK_LEAVES: + { + return true; + } + } // switch (a_BlockType + return false; } -}; \ No newline at end of file +} ; + + + + diff --git a/source/Items/ItemShovel.h b/source/Items/ItemShovel.h index f07820f8f..b1260311e 100644 --- a/source/Items/ItemShovel.h +++ b/source/Items/ItemShovel.h @@ -14,20 +14,20 @@ class cItemShovelHandler : public cItemHandler { public: - cItemShovelHandler(int a_ItemID) - : cItemHandler(a_ItemID) + cItemShovelHandler(int a_ItemType) + : cItemHandler(a_ItemType) { } - virtual bool OnDiggingBlock(cWorld *a_World, cPlayer *a_Player, cItem *a_Item, int a_X, int a_Y, int a_Z, char a_Dir) override + virtual bool OnDiggingBlock(cWorld *a_World, cPlayer *a_Player, cItem *a_Item, int a_BlockX, int a_BlockY, int a_BlockZ, char a_Dir) override { - BLOCKTYPE Block = a_World->GetBlock(a_X, a_Y, a_Z); - if(Block == E_BLOCK_SNOW) + BLOCKTYPE Block = a_World->GetBlock(a_BlockX, a_BlockY, a_BlockZ); + if (Block == E_BLOCK_SNOW) { - BlockHandler(Block)->DropBlock(a_World, a_X, a_Y, a_Z); + BlockHandler(Block)->DropBlock(a_World, a_BlockX, a_BlockY, a_BlockZ); - a_World->SetBlock(a_X, a_Y, a_Z, E_BLOCK_AIR, 0); + a_World->SetBlock(a_BlockX, a_BlockY, a_BlockZ, E_BLOCK_AIR, 0); a_Player->UseEquippedItem(); return true; } @@ -36,6 +36,6 @@ public: virtual bool CanHarvestBlock(BLOCKTYPE a_BlockType) override { - return a_BlockType == E_BLOCK_SNOW; + return (a_BlockType == E_BLOCK_SNOW); } }; \ No newline at end of file diff --git a/source/Items/ItemSign.h b/source/Items/ItemSign.h index a0c6aaa9c..b5593a010 100644 --- a/source/Items/ItemSign.h +++ b/source/Items/ItemSign.h @@ -7,8 +7,8 @@ class cItemSignHandler : public cItemHandler { public: - cItemSignHandler(int a_ItemID) - : cItemHandler(a_ItemID) + cItemSignHandler(int a_ItemType) + : cItemHandler(a_ItemType) { } diff --git a/source/Items/ItemSlab.h b/source/Items/ItemSlab.h index 0bab038a2..36779138b 100644 --- a/source/Items/ItemSlab.h +++ b/source/Items/ItemSlab.h @@ -11,28 +11,28 @@ class cItemSlabHandler : public cItemHandler { public: - cItemSlabHandler(int a_ItemID) - : cItemHandler(a_ItemID) + cItemSlabHandler(int a_ItemType) + : cItemHandler(a_ItemType) { } - virtual bool OnItemUse(cWorld * a_World, cPlayer * a_Player, cItem * a_Item, int a_X, int a_Y, int a_Z, char a_Dir) override + virtual bool OnItemUse(cWorld * a_World, cPlayer * a_Player, cItem * a_Item, int a_BlockX, int a_BlockY, int a_BlockZ, char a_Dir) override { BLOCKTYPE Block; NIBBLETYPE Meta; - a_World->GetBlockTypeMeta(a_X, a_Y, a_Z, Block, Meta); + a_World->GetBlockTypeMeta(a_BlockX, a_BlockY, a_BlockZ, Block, Meta); if ( - (a_Dir == 0 || a_Dir == 1) // Only when clicking on top or on bottom of the block - && (Block == E_BLOCK_WOODEN_SLAB || Block == E_BLOCK_STONE_SLAB) // It is a slab - && (Block == a_Item->m_ItemID) // Same slab + ((a_Dir == 0) || (a_Dir == 1)) // Only when clicking on top or on bottom of the block + && ((Block == E_BLOCK_WOODEN_SLAB) || (Block == E_BLOCK_STONE_SLAB)) // It is a slab + && (Block == a_Item->m_ItemType) // Same slab && ((Meta & 0x7) == (a_Item->m_ItemHealth & 0x7))) // Same Texture { - cItem Item(a_Item->m_ItemID, 1); + cItem Item(a_Item->m_ItemType, 1); if (a_Player->GetInventory().RemoveItem(Item)) { - a_World->SetBlock(a_X, a_Y, a_Z, Block - 1, Meta); //Block - 1 simple hack to save one if statement + a_World->SetBlock(a_BlockX, a_BlockY, a_BlockZ, Block - 1, Meta); // Block - 1 simple hack to save one if statement return true; } } diff --git a/source/Items/ItemSpawnEgg.h b/source/Items/ItemSpawnEgg.h index 76b742328..fb040c6ea 100644 --- a/source/Items/ItemSpawnEgg.h +++ b/source/Items/ItemSpawnEgg.h @@ -30,25 +30,25 @@ class cItemSpawnEggHandler : public cItemHandler { public: - cItemSpawnEggHandler(int a_ItemID) : - cItemHandler(a_ItemID) + cItemSpawnEggHandler(int a_ItemType) : + cItemHandler(a_ItemType) { } - virtual bool OnItemUse(cWorld * a_World, cPlayer * a_Player, cItem * a_Item, int a_X, int a_Y, int a_Z, char a_Dir) override + virtual bool OnItemUse(cWorld * a_World, cPlayer * a_Player, cItem * a_Item, int a_BlockX, int a_BlockY, int a_BlockZ, char a_Dir) override { if (a_Dir < 0) { return false; } - AddDirection(a_X, a_Y, a_Z, a_Dir); + AddDirection(a_BlockX, a_BlockY, a_BlockZ, a_Dir); if (a_Dir == BLOCK_FACE_BOTTOM) { - a_Y--; + a_BlockY--; } cMonster * Monster = NULL; @@ -56,7 +56,7 @@ public: Monster = new cZombie(); Monster->Initialize(a_World); - Monster->TeleportTo(a_X + 0.5, a_Y, a_Z + 0.5); + Monster->TeleportTo(a_BlockX + 0.5, a_BlockY, a_BlockZ + 0.5); a_World->BroadcastSpawn(*Monster); a_Player->UseEquippedItem(); diff --git a/source/Items/ItemSugarcane.h b/source/Items/ItemSugarcane.h index 4fdf43428..60b6ff262 100644 --- a/source/Items/ItemSugarcane.h +++ b/source/Items/ItemSugarcane.h @@ -12,8 +12,8 @@ class cItemSugarcaneHandler : public cItemHandler { public: - cItemSugarcaneHandler(int a_ItemID) - : cItemHandler(a_ItemID) + cItemSugarcaneHandler(int a_ItemType) + : cItemHandler(a_ItemType) { } diff --git a/source/Items/ItemSword.h b/source/Items/ItemSword.h index 4eec4c5a0..327c39a40 100644 --- a/source/Items/ItemSword.h +++ b/source/Items/ItemSword.h @@ -8,8 +8,8 @@ class cItemSwordHandler : public cItemHandler { public: - cItemSwordHandler(int a_ItemID) - : cItemHandler(a_ItemID) + cItemSwordHandler(int a_ItemType) + : cItemHandler(a_ItemType) { } diff --git a/source/Items/ItemWood.h b/source/Items/ItemWood.h index d6f66d1c5..5304ec316 100644 --- a/source/Items/ItemWood.h +++ b/source/Items/ItemWood.h @@ -11,8 +11,8 @@ class cItemWoodHandler : public cItemHandler { public: - cItemWoodHandler(int a_ItemID) - : cItemHandler(a_ItemID) + cItemWoodHandler(int a_ItemType) + : cItemHandler(a_ItemType) { } } ; diff --git a/source/Simulator/FluidSimulator.cpp b/source/Simulator/FluidSimulator.cpp index 2ade2ba11..cec208d94 100644 --- a/source/Simulator/FluidSimulator.cpp +++ b/source/Simulator/FluidSimulator.cpp @@ -32,15 +32,19 @@ bool cFluidSimulator::CanWashAway(BLOCKTYPE a_BlockType) { switch (a_BlockType) { - case E_BLOCK_YELLOW_FLOWER: - case E_BLOCK_RED_ROSE: - case E_BLOCK_RED_MUSHROOM: case E_BLOCK_BROWN_MUSHROOM: case E_BLOCK_CACTUS: - case E_BLOCK_TORCH: + case E_BLOCK_DEAD_BUSH: + case E_BLOCK_RAIL: case E_BLOCK_REDSTONE_TORCH_OFF: case E_BLOCK_REDSTONE_TORCH_ON: - case E_BLOCK_RAIL: + case E_BLOCK_REDSTONE_WIRE: + case E_BLOCK_RED_MUSHROOM: + case E_BLOCK_RED_ROSE: + case E_BLOCK_SNOW: + case E_BLOCK_TALL_GRASS: + case E_BLOCK_TORCH: + case E_BLOCK_YELLOW_FLOWER: { return true; }