minecraft-pi-reborn/mods/src/cake/cake.cpp

242 lines
6.3 KiB
C++
Raw Normal View History

#include <libreborn/libreborn.h>
#include <symbols/minecraft.h>
#include <mods/feature/feature.h>
#include <mods/init/init.h>
#include <mods/misc/misc.h>
#include <mods/bucket/bucket.h>
2024-11-08 07:34:58 +00:00
#include <mods/extend/extend.h>
2024-04-02 23:22:01 +00:00
static Tile *cake = nullptr;
#define CAKE_LEN 0.0625F
// Description
static std::string Cake_getDescriptionId(__attribute__((unused)) Tile *tile) {
return "tile.cake";
}
// Textures
2024-09-21 01:30:47 +00:00
static int Cake_getTexture2(__attribute__((unused)) Tile *tile, const int face, __attribute__((unused)) int data) {
if (face == 1) {
// Top texture
return 121;
} else if (face == 0) {
// Bottom texture
return 124;
}
// Side texture
return 122;
}
2024-09-21 01:30:47 +00:00
static int Cake_getTexture3(__attribute__((unused)) Tile *tile, LevelSource *level, int x, int y, int z, const int face) {
// Eaten face
if (face == 3) {
2024-09-21 01:30:47 +00:00
const int data = level->getData(x, y, z);
if (data != 0 && data < 6) {
// Sliced texture
return 123;
}
}
// Normal
return Cake_getTexture2(tile, face, 0);
}
// Rendering
static bool Cake_isSolidRender(__attribute__((unused)) Tile *tile) {
// Stop it from turning other blocks invisable
return 0;
}
static int Cake_getRenderLayer(__attribute__((unused)) Tile *tile) {
// Stop weird transparency issues
return 1;
}
static bool Cake_isCubeShaped(__attribute__((unused)) Tile *tile) {
return false;
}
// Size
static void Cake_updateDefaultShape(Tile *tile) {
// Set the default shape
2024-05-15 09:02:19 +00:00
tile->setShape(
CAKE_LEN, 0.0, CAKE_LEN,
1.0 - CAKE_LEN, 0.5, 1.0 - CAKE_LEN
);
}
static AABB *Cake_getAABB(Tile *tile, Level *level, int x, int y, int z) {
// Get the size of the slices
2024-05-15 09:02:19 +00:00
int data = level->getData(x, y, z);
if (data >= 6) data = 0;
2024-09-21 01:30:47 +00:00
const float slice_size = (1.0 / 7.0) * (float) data;
// Corner 1
AABB *aabb = &tile->aabb;
aabb->x1 = (float) x + CAKE_LEN;
aabb->y1 = (float) y;
aabb->z1 = (float) z + CAKE_LEN;
// Corner 2
aabb->x2 = (float) x + (1.0 - CAKE_LEN);
aabb->y2 = (float) y + 0.5;
aabb->z2 = (float) z + (1.0 - CAKE_LEN) - slice_size;
return aabb;
}
static void Cake_updateShape(Tile *tile, LevelSource *level, int x, int y, int z) {
// Set cake
2024-05-15 09:02:19 +00:00
int data = level->getData(x, y, z);
if (data >= 6) data = 0;
// Get slice amount
2024-09-21 01:30:47 +00:00
const float slice_size = (1.0 / 7.0) * (float) data;
2024-05-15 09:02:19 +00:00
tile->setShape(
CAKE_LEN, 0.0, CAKE_LEN,
1.0 - CAKE_LEN, 0.5, (1.0 - CAKE_LEN) - slice_size
);
}
// Eating
static int Cake_use(__attribute__((unused)) Tile *tile, Level *level, int x, int y, int z, Player *player) {
// Eat
2024-05-15 09:02:19 +00:00
player->foodData.eat(3);
// Set the new tile
2024-07-14 09:06:27 +00:00
const int data = level->getData(x, y, z);
if (data >= 5) {
// Remove the cake, it has been completely gobbled up
2024-05-15 09:02:19 +00:00
level->setTileAndData(x, y, z, 0, 0);
} else {
// Remove a slice
2024-05-15 09:02:19 +00:00
level->setTileAndData(x, y, z, 92, data + 1);
}
return 1;
}
// Makes the cakes
static void make_cake() {
// Construct
2024-09-21 01:30:47 +00:00
cake = Tile::allocate();
ALLOC_CHECK(cake);
int texture = 122;
2024-05-17 06:52:55 +00:00
cake->constructor(92, texture, Material::dirt);
cake->texture = texture;
// Set VTable
2024-11-08 07:34:58 +00:00
cake->vtable = extend_dup_vtable(Tile_vtable::base);
ALLOC_CHECK(cake->vtable);
// Set shape
2024-05-15 09:02:19 +00:00
cake->setShape(
CAKE_LEN, 0.0, CAKE_LEN,
1.0 - CAKE_LEN, 0.5, 1.0 - CAKE_LEN
);
// Modify functions
cake->vtable->getDescriptionId = Cake_getDescriptionId;
cake->vtable->getTexture3 = Cake_getTexture3;
cake->vtable->getTexture2 = Cake_getTexture2;
cake->vtable->isSolidRender = Cake_isSolidRender;
cake->vtable->getRenderLayer = Cake_getRenderLayer;
cake->vtable->isCubeShaped = Cake_isCubeShaped;
cake->vtable->updateShape = Cake_updateShape;
cake->vtable->updateDefaultShape = Cake_updateDefaultShape;
cake->vtable->getAABB = Cake_getAABB;
cake->vtable->use = Cake_use;
// Init
2024-05-15 09:02:19 +00:00
cake->init();
cake->setDestroyTime(1.0f);
cake->setExplodeable(20.0f);
cake->category = 4;
std::string name = "Cake";
2024-07-15 07:05:05 +00:00
cake->setDescriptionId(name);
}
2024-05-18 22:58:39 +00:00
static void Tile_initTiles_injection() {
make_cake();
}
// Add cake to creative inventory
static void Inventory_setupDefault_FillingContainer_addItem_call_injection(FillingContainer *filling_container) {
ItemInstance *cake_instance = new ItemInstance;
ALLOC_CHECK(cake_instance);
cake_instance->count = 255;
cake_instance->auxiliary = 0;
cake_instance->id = 92;
2024-05-15 09:02:19 +00:00
filling_container->addItem(cake_instance);
}
// Recipe (only when buckets are enabled)
static void Recipes_injection(Recipes *recipes) {
// Sugar
2024-09-21 01:30:47 +00:00
constexpr Recipes_Type sugar = {
.item = nullptr,
.tile = nullptr,
.instance = {
.count = 1,
.id = 353,
.auxiliary = 0
},
.letter = 's'
};
// Wheat
2024-09-21 01:30:47 +00:00
constexpr Recipes_Type wheat = {
.item = nullptr,
.tile = nullptr,
.instance = {
.count = 1,
.id = 296,
.auxiliary = 0
},
.letter = 'w'
};
// Eggs
2024-09-21 01:30:47 +00:00
constexpr Recipes_Type eggs = {
.item = nullptr,
.tile = nullptr,
.instance = {
.count = 1,
.id = 344,
.auxiliary = 0
},
.letter = 'e'
};
// Milk
2024-09-21 01:30:47 +00:00
constexpr Recipes_Type milk = {
.item = nullptr,
.tile = nullptr,
.instance = {
.count = 1,
.id = 325,
.auxiliary = 1
},
.letter = 'm'
};
// Cake
ItemInstance cake_item = {
.count = 1,
.id = 92,
.auxiliary = 0
};
// Add
std::string line1 = "mmm";
std::string line2 = "ses";
std::string line3 = "www";
2024-07-15 07:05:05 +00:00
std::vector ingredients = {milk, sugar, wheat, eggs};
recipes->addShapedRecipe_3(cake_item, line1, line2, line3, ingredients);
}
void init_cake() {
// Add cakes
if (feature_has("Add Cake", server_enabled)) {
misc_run_on_tiles_setup(Tile_initTiles_injection);
misc_run_on_creative_inventory_setup(Inventory_setupDefault_FillingContainer_addItem_call_injection);
if (buckets_enabled) {
// The recipe needs milk buckets
misc_run_on_recipes_setup(Recipes_injection);
}
}
}