feat: added HalfStairsCubeStair and HalfStairsStepStair

This commit is contained in:
Adrien1106 2024-06-18 14:56:46 +02:00
parent 3bf9fc2268
commit 6f8304d638
21 changed files with 948 additions and 217 deletions

View File

@ -41,7 +41,7 @@ public class ReFramed implements ModInitializer {
CUBE,
SMALL_CUBE, SMALL_CUBES_STEP,
STAIR, STAIRS_CUBE,
HALF_STAIR, HALF_STAIRS_SLAB, HALF_STAIRS_STAIR,
HALF_STAIR, HALF_STAIRS_SLAB, HALF_STAIRS_STAIR, HALF_STAIRS_CUBE_STAIR, HALF_STAIRS_STEP_STAIR,
SLAB, SLABS_CUBE, SLABS_STAIR, SLABS_OUTER_STAIR, SLABS_INNER_STAIR,
STEP, STEPS_SLAB, STEPS_CROSS,
LAYER,
@ -70,6 +70,8 @@ public class ReFramed implements ModInitializer {
HALF_STAIR = registerBlock("half_stair" , new ReFramedHalfStairBlock(cp(Blocks.OAK_STAIRS)));
HALF_STAIRS_SLAB = registerBlock("half_stairs_slab" , new ReFramedHalfStairsSlabBlock(cp(Blocks.OAK_STAIRS)));
HALF_STAIRS_STAIR = registerBlock("half_stairs_stair" , new ReFramedHalfStairsStairBlock(cp(Blocks.OAK_STAIRS)));
HALF_STAIRS_CUBE_STAIR = registerBlock("half_stairs_cube_stair" , new ReFramedHalfStairsCubeStairBlock(cp(Blocks.OAK_STAIRS)));
HALF_STAIRS_STEP_STAIR = registerBlock("half_stairs_step_stair" , new ReFramedHalfStairsStepStairBlock(cp(Blocks.OAK_STAIRS)));
LAYER = registerBlock("layer" , new ReFramedLayerBlock(cp(Blocks.OAK_SLAB)));
SLAB = registerBlock("slab" , new ReFramedSlabBlock(cp(Blocks.OAK_SLAB)));
SLABS_CUBE = registerBlock("slabs_cube" , new ReFramedSlabsCubeBlock(cp(Blocks.OAK_SLAB)));
@ -95,6 +97,7 @@ public class ReFramed implements ModInitializer {
BLUEPRINT = registerItem("blueprint" , new ReFramedBlueprintItem(new Item.Settings()));
BLUEPRINT_WRITTEN = registerItem("blueprint_written" , new ReFramedBlueprintWrittenItem(new Item.Settings().maxCount(1)));
REFRAMED_BLOCK_ENTITY = Registry.register(Registries.BLOCK_ENTITY_TYPE, id("camo"),
FabricBlockEntityTypeBuilder.create(
(pos, state) -> new ReFramedEntity(REFRAMED_BLOCK_ENTITY, pos, state),

View File

@ -45,38 +45,35 @@ public class ReFramedHalfStairBlock extends WaterloggableReFramedBlock {
@Override
@SuppressWarnings("deprecation")
public boolean canReplace(BlockState state, ItemPlacementContext context) {
if (context.getPlayer() == null) return false;
Direction dir = state.get(CORNER).getDirection(state.get(CORNER_FACE));
return !(
context.getPlayer().isSneaking()
if (context.getPlayer() == null
|| context.getPlayer().isSneaking()
|| !(context.getStack().getItem() instanceof BlockItem block_item)
|| (
!(
block_item.getBlock() == this
&& ReFramed.HALF_STAIRS_STAIR
.matchesShape(
) return false;
// allow replacing with slab, step, small cube and half stair
Block block = block_item.getBlock();
Corner corner = state.get(CORNER);
Direction dir = corner.getDirection(state.get(CORNER_FACE));
if (block == this || block == ReFramed.STEP)
return ReFramed.HALF_STAIRS_STAIR.matchesShape(
context.getHitPos(),
context.getBlockPos(),
ReFramed.HALF_STAIRS_STAIR.getDefaultState()
.with(EDGE, state.get(CORNER).getEdge(dir)),
ReFramed.HALF_STAIRS_STAIR.getDefaultState().with(EDGE, corner.getEdge(dir)),
dir.getDirection() == Direction.AxisDirection.POSITIVE ? 1 : 2
)
)
&& !(
block_item.getBlock() == ReFramed.SMALL_CUBE
&& BlockHelper.cursorMatchesFace(
ReFramed.SMALL_CUBE.getOutlineShape(
ReFramed.SMALL_CUBE.getDefaultState()
.with(CORNER, state.get(CORNER).getOpposite(state.get(CORNER_FACE))),
context.getWorld(),
context.getBlockPos(),
ShapeContext.absent()
),
BlockHelper.getRelativePos(context.getHitPos(), context.getBlockPos())
)
)
)
);
if (block == ReFramed.SMALL_CUBE)
return ReFramed.SMALL_CUBE.matchesShape(
context.getHitPos(),
context.getBlockPos(),
ReFramed.SMALL_CUBE.getDefaultState().with(CORNER, corner.change(dir))
) || ReFramed.SMALL_CUBE.matchesShape(
context.getHitPos(),
context.getBlockPos(),
ReFramed.SMALL_CUBE.getDefaultState().with(CORNER, corner.getOpposite(dir))
);
return false;
}
@Override
@ -94,7 +91,7 @@ public class ReFramedHalfStairBlock extends WaterloggableReFramedBlock {
return ReFramed.HALF_STAIRS_STAIR.getDefaultState()
.with(EDGE, current_state.get(CORNER).getEdge(current_state.get(CORNER).getDirection(current_state.get(CORNER_FACE))))
.with(WATERLOGGED, current_state.get(WATERLOGGED));
else if (current_state.isOf(ReFramed.SLAB)) {
if (current_state.isOf(ReFramed.SLAB)) {
Corner corner = BlockHelper.getPlacementCorner(ctx);
Direction face = current_state.get(FACING);
if (!corner.hasDirection(face)) corner = corner.change(face.getOpposite());
@ -134,7 +131,10 @@ public class ReFramedHalfStairBlock extends WaterloggableReFramedBlock {
@Override
public Map<Integer, Integer> getThemeMap(BlockState state, BlockState new_state) {
if (new_state.isOf(ReFramed.HALF_STAIRS_SLAB)) return Map.of(1, 1);
if (new_state.isOf(ReFramed.HALF_STAIRS_SLAB)
|| new_state.isOf(ReFramed.HALF_STAIRS_CUBE_STAIR)
|| new_state.isOf(ReFramed.HALF_STAIRS_STEP_STAIR)
) return Map.of(1, 1);
if (new_state.isOf(ReFramed.HALF_STAIRS_STAIR))
return Map.of(
1,

View File

@ -0,0 +1,48 @@
package fr.adrien1106.reframed.block;
import fr.adrien1106.reframed.util.blocks.Corner;
import fr.adrien1106.reframed.util.blocks.Edge;
import fr.adrien1106.reframed.util.blocks.StairShape;
import net.minecraft.block.BlockState;
import net.minecraft.block.ShapeContext;
import net.minecraft.util.math.BlockPos;
import net.minecraft.util.math.Direction;
import net.minecraft.util.shape.VoxelShape;
import net.minecraft.world.BlockView;
import static fr.adrien1106.reframed.block.ReFramedHalfStairBlock.getHalfStairShape;
import static fr.adrien1106.reframed.block.ReFramedSmallCubeBlock.getSmallCubeShape;
import static fr.adrien1106.reframed.block.ReFramedStairBlock.getStairShape;
import static fr.adrien1106.reframed.util.blocks.BlockProperties.CORNER;
import static fr.adrien1106.reframed.util.blocks.BlockProperties.CORNER_FACE;
public class ReFramedHalfStairsCubeStairBlock extends CornerDoubleReFramedBlock {
public ReFramedHalfStairsCubeStairBlock(Settings settings) {
super(settings);
}
@Override
public VoxelShape getOutlineShape(BlockState state, BlockView world, BlockPos pos, ShapeContext context) {
Corner corner = state.get(CORNER);
Direction face = corner.getDirection(state.get(CORNER_FACE));
Edge edge = corner.getEdge(face);
return getStairShape(
edge,
face.getDirection() == Direction.AxisDirection.POSITIVE
? StairShape.OUTER_LEFT
: StairShape.OUTER_RIGHT
);
}
@Override
public VoxelShape getShape(BlockState state, int i) {
Corner corner = state.get(CORNER);
Direction face = corner.getDirection(state.get(CORNER_FACE));
if (i == 2) corner = corner.change(face);
return i == 2
? getSmallCubeShape(corner)
: getHalfStairShape(corner, state.get(CORNER_FACE));
}
}

View File

@ -0,0 +1,76 @@
package fr.adrien1106.reframed.block;
import fr.adrien1106.reframed.util.blocks.BlockHelper;
import fr.adrien1106.reframed.util.blocks.Corner;
import fr.adrien1106.reframed.util.blocks.Edge;
import fr.adrien1106.reframed.util.blocks.StairShape;
import net.minecraft.block.Block;
import net.minecraft.block.BlockState;
import net.minecraft.block.ShapeContext;
import net.minecraft.item.ItemPlacementContext;
import net.minecraft.state.StateManager;
import net.minecraft.util.math.BlockPos;
import net.minecraft.util.math.Direction;
import net.minecraft.util.shape.VoxelShape;
import net.minecraft.world.BlockView;
import org.jetbrains.annotations.Nullable;
import static fr.adrien1106.reframed.block.ReFramedHalfStairBlock.getHalfStairShape;
import static fr.adrien1106.reframed.block.ReFramedStairBlock.getStairShape;
import static fr.adrien1106.reframed.block.ReFramedStepBlock.getStepShape;
import static fr.adrien1106.reframed.util.blocks.BlockProperties.*;
public class ReFramedHalfStairsStepStairBlock extends CornerDoubleReFramedBlock {
public ReFramedHalfStairsStepStairBlock(Settings settings) {
super(settings);
setDefaultState(getDefaultState().with(CORNER_FEATURE, 0));
}
@Override
protected void appendProperties(StateManager.Builder<Block, BlockState> builder) {
super.appendProperties(builder.add(CORNER_FEATURE));
}
@Override
public @Nullable BlockState getPlacementState(ItemPlacementContext ctx) {
BlockState state = super.getPlacementState(ctx);
Corner corner = state.get(CORNER);
int face_index = state.get(CORNER_FACE);
Direction face = corner.getDirection(face_index);
face = BlockHelper.getPlacementEdge(ctx).getOtherDirection(face);
int feature_index = corner.getDirectionIndex(face);
return state.with(CORNER_FEATURE, feature_index > face_index ? feature_index - 1 : feature_index);
}
@Override
public VoxelShape getOutlineShape(BlockState state, BlockView world, BlockPos pos, ShapeContext context) {
Corner corner = state.get(CORNER);
int feature_index = state.get(CORNER_FEATURE), face_index = state.get(CORNER_FACE);
Direction feature_face = corner.getDirection(feature_index >= face_index ? feature_index + 1 : feature_index);
Direction face = corner.getDirection(face_index);
Edge edge = Edge.getByDirections(feature_face, face);
return getStairShape(
edge,
corner.getOtherDirection(edge).getDirection() == Direction.AxisDirection.POSITIVE
? edge.getDirectionIndex(face) == 0
? StairShape.FIRST_OUTER_LEFT
: StairShape.SECOND_OUTER_LEFT
: edge.getDirectionIndex(face) == 0
? StairShape.FIRST_OUTER_RIGHT
: StairShape.SECOND_OUTER_RIGHT
);
}
@Override
public VoxelShape getShape(BlockState state, int i) {
Corner corner = state.get(CORNER);
int feature_index = state.get(CORNER_FEATURE), face_index = state.get(CORNER_FACE);
Direction feature_face = corner.getDirection(feature_index >= face_index ? feature_index + 1 : feature_index);
Direction face = corner.getDirection(face_index);
return i == 2
? getStepShape(Edge.getByDirections(face.getOpposite(), feature_face))
: getHalfStairShape(corner, face_index);
}
}

View File

@ -49,10 +49,11 @@ public class ReFramedSlabBlock extends WaterloggableReFramedBlock {
) return false;
// allow replacing with slab, step, small cube and half stair
if (block_item.getBlock() != this
&& block_item.getBlock() != ReFramed.STEP
&& block_item.getBlock() != ReFramed.SMALL_CUBE
&& block_item.getBlock() != ReFramed.HALF_STAIR
Block block = block_item.getBlock();
if (block != this
&& block != ReFramed.STEP
&& block != ReFramed.SMALL_CUBE
&& block != ReFramed.HALF_STAIR
) return false;
// check if the player is clicking on the inner part of the block

View File

@ -96,12 +96,20 @@ public class ReFramedSmallCubeBlock extends WaterloggableReFramedBlock {
public @Nullable BlockState getPlacementState(ItemPlacementContext ctx) {
BlockPos pos = ctx.getBlockPos();
BlockState current_state = ctx.getWorld().getBlockState(pos);
if (current_state.isOf(ReFramed.HALF_STAIR))
return ReFramed.HALF_STAIRS_SLAB.getDefaultState()
if (current_state.isOf(ReFramed.HALF_STAIR)) {
BlockState new_state;
Direction face = current_state.get(CORNER).getDirection(current_state.get(CORNER_FACE));
if (matchesShape(
ctx.getHitPos(), pos,
getDefaultState().with(CORNER, current_state.get(CORNER).change(face))
)) new_state = ReFramed.HALF_STAIRS_CUBE_STAIR.getDefaultState();
else new_state = ReFramed.HALF_STAIRS_SLAB.getDefaultState();
return new_state
.with(CORNER, current_state.get(CORNER))
.with(CORNER_FACE, current_state.get(CORNER_FACE))
.with(WATERLOGGED, current_state.get(WATERLOGGED));
}
if (current_state.isOf(this)) {
Vec3d hit = ctx.getHitPos();
@ -120,7 +128,9 @@ public class ReFramedSmallCubeBlock extends WaterloggableReFramedBlock {
corner.getSecondDirection().getDirection() == Direction.AxisDirection.POSITIVE ? 1 : 2
)) return state;
return state.with(EDGE, corner.getEdge(corner.getThirdDirection()));
} else if (current_state.isOf(ReFramed.SLAB)) {
}
if (current_state.isOf(ReFramed.SLAB)) {
Corner corner = BlockHelper.getPlacementCorner(ctx);
Direction face = current_state.get(FACING);
if (!corner.hasDirection(face)) corner = corner.change(face.getOpposite());

View File

@ -3,6 +3,7 @@ package fr.adrien1106.reframed.block;
import fr.adrien1106.reframed.ReFramed;
import fr.adrien1106.reframed.util.VoxelHelper;
import fr.adrien1106.reframed.util.blocks.BlockHelper;
import fr.adrien1106.reframed.util.blocks.Corner;
import fr.adrien1106.reframed.util.blocks.Edge;
import net.minecraft.block.Block;
import net.minecraft.block.BlockState;
@ -48,27 +49,17 @@ public class ReFramedStepBlock extends WaterloggableReFramedBlock {
|| !(context.getStack().getItem() instanceof BlockItem block_item)
) return false;
Edge edge = state.get(EDGE);
Block block = block_item.getBlock();
// allow replacing with stair
if (block_item.getBlock() == ReFramed.STAIR)
return ReFramed.STAIRS_CUBE
.matchesShape(
context.getHitPos(),
context.getBlockPos(),
ReFramed.STAIRS_CUBE.getDefaultState().with(EDGE, edge.opposite()),
1
);
if (block != this && block != ReFramed.STAIR) return false;
if (block_item.getBlock() == this)
Edge edge = state.get(EDGE);
return ReFramed.STAIR
.matchesShape(
context.getHitPos(),
context.getBlockPos(),
ReFramed.STAIR.getDefaultState()
.with(EDGE, edge.opposite())
ReFramed.STAIRS_CUBE.getDefaultState().with(EDGE, edge.opposite())
);
return false;
}
@Nullable
@ -76,6 +67,7 @@ public class ReFramedStepBlock extends WaterloggableReFramedBlock {
public BlockState getPlacementState(ItemPlacementContext ctx) {
BlockPos pos = ctx.getBlockPos();
BlockState current_state = ctx.getWorld().getBlockState(pos);
if (current_state.isOf(ReFramed.STAIR))
return ReFramed.STAIRS_CUBE.getDefaultState()
.with(EDGE, current_state.get(EDGE))
@ -105,7 +97,9 @@ public class ReFramedStepBlock extends WaterloggableReFramedBlock {
return ReFramed.STEPS_CROSS.getDefaultState()
.with(EDGE, edge)
.with(WATERLOGGED, current_state.get(WATERLOGGED));
} else if (current_state.isOf(ReFramed.SLAB)) {
}
if (current_state.isOf(ReFramed.SLAB)) {
Direction facing = current_state.get(FACING);
Edge edge;
@ -120,6 +114,26 @@ public class ReFramedStepBlock extends WaterloggableReFramedBlock {
}
if (current_state.isOf(ReFramed.HALF_STAIR)) {
Corner corner = current_state.get(CORNER);
int face_index = current_state.get(CORNER_FACE), feature_index;
Direction face = corner.getDirection(current_state.get(CORNER_FACE));
Direction side = ctx.getSide().getOpposite();
if (side.getAxis() == face.getAxis())
side = BlockHelper.getPlacementEdge(ctx).getOtherDirection(face == side ? face : face.getOpposite());
if (side.getAxis() != face.getAxis() && !corner.hasDirection(side))
side = corner.getOtherDirection(Edge.getByDirections(face, side.getOpposite()));
feature_index = corner.getDirectionIndex(side);
return ReFramed.HALF_STAIRS_STEP_STAIR.getDefaultState()
.with(CORNER, corner)
.with(CORNER_FACE, face_index)
.with(CORNER_FEATURE, feature_index > face_index ? feature_index - 1 : feature_index)
.with(WATERLOGGED, current_state.get(WATERLOGGED));
}
return super.getPlacementState(ctx).with(EDGE, BlockHelper.getPlacementEdge(ctx));
}

View File

@ -155,6 +155,14 @@ public class ReFramedClient implements ClientModInitializer {
HELPER.addReFramedModel("slabs_inner_stair_side" , HELPER.autoDouble(ReFramed.id("block/slabs_stair/inner/side/slab"), ReFramed.id("block/slabs_stair/inner/side/half_stair")));
// SLABS OUTER STAIR
HELPER.addReFramedModel("steps_cross" , HELPER.autoDouble(ReFramed.id("block/step/down"), ReFramed.id("block/step/cross")));
// HALF STAIRS CUBE STAIR
HELPER.addReFramedModel("half_stairs_cube_stair" , HELPER.autoDouble(ReFramed.id("block/half_stair/base"), ReFramed.id("block/half_stair/stair/cube")));
HELPER.addReFramedModel("half_stairs_cube_stair_side" , HELPER.autoDouble(ReFramed.id("block/half_stair/base_side"), ReFramed.id("block/half_stair/stair/cube_side")));
// HALF STAIRS STEP STAIR
HELPER.addReFramedModel("half_stairs_step_stair_1" , HELPER.autoDouble(ReFramed.id("block/half_stair/base"), ReFramed.id("block/half_stair/stair/step_1")));
HELPER.addReFramedModel("half_stairs_step_stair_side_1", HELPER.autoDouble(ReFramed.id("block/half_stair/base_side"), ReFramed.id("block/half_stair/stair/step_side_1")));
HELPER.addReFramedModel("half_stairs_step_stair_2" , HELPER.autoDouble(ReFramed.id("block/half_stair/base"), ReFramed.id("block/half_stair/stair/step_2")));
HELPER.addReFramedModel("half_stairs_step_stair_side_2", HELPER.autoDouble(ReFramed.id("block/half_stair/base_side"), ReFramed.id("block/half_stair/stair/step_side_2")));
// item model assignments (in lieu of models/item/___.json)
@ -185,6 +193,8 @@ public class ReFramedClient implements ClientModInitializer {
HELPER.assignItemModel("slabs_outer_stair" , ReFramed.SLABS_OUTER_STAIR);
HELPER.assignItemModel("slabs_inner_stair" , ReFramed.SLABS_INNER_STAIR);
HELPER.assignItemModel("steps_cross" , ReFramed.STEPS_CROSS);
HELPER.assignItemModel("half_stairs_cube_stair" , ReFramed.HALF_STAIRS_CUBE_STAIR);
HELPER.assignItemModel("half_stairs_step_stair_1", ReFramed.HALF_STAIRS_STEP_STAIR);
}
private void privateInit() {

View File

@ -22,6 +22,8 @@ public class GBlockstate extends FabricModelProvider {
providers.put(ReFramedHalfStairBlock.class, new HalfStair());
providers.put(ReFramedHalfStairsSlabBlock.class, new HalfStairsSlab());
providers.put(ReFramedHalfStairsStairBlock.class, new HalfStairsStair());
providers.put(ReFramedHalfStairsCubeStairBlock.class, new HalfStairsCubeStair());
providers.put(ReFramedHalfStairsStepStairBlock.class, new HalfStairsStepStair());
providers.put(ReFramedLayerBlock.class, new Layer());
providers.put(ReFramedPillarBlock.class, new Pillar());
providers.put(ReFramedSlabBlock.class, new Slab());

View File

@ -24,6 +24,8 @@ public class GRecipe extends FabricRecipeProvider {
providers.put(ReFramedHalfStairBlock.class, new HalfStair());
providers.put(ReFramedHalfStairsSlabBlock.class, new HalfStairsSlab());
providers.put(ReFramedHalfStairsStairBlock.class, new HalfStairsStair());
providers.put(ReFramedHalfStairsCubeStairBlock.class, new HalfStairsCubeStair());
providers.put(ReFramedHalfStairsStepStairBlock.class, new HalfStairsStepStair());
providers.put(ReFramedLayerBlock.class, new Layer());
providers.put(ReFramedPillarBlock.class, new Pillar());
providers.put(ReFramedSlabBlock.class, new Slab());

View File

@ -0,0 +1,33 @@
package fr.adrien1106.reframed.generator.block;
import fr.adrien1106.reframed.ReFramed;
import fr.adrien1106.reframed.generator.BlockStateProvider;
import fr.adrien1106.reframed.generator.RecipeSetter;
import net.fabricmc.fabric.api.datagen.v1.provider.FabricRecipeProvider;
import net.minecraft.block.Block;
import net.minecraft.data.client.MultipartBlockStateSupplier;
import net.minecraft.data.server.recipe.RecipeExporter;
import net.minecraft.data.server.recipe.RecipeProvider;
import net.minecraft.data.server.recipe.ShapelessRecipeJsonBuilder;
import net.minecraft.item.ItemConvertible;
import net.minecraft.recipe.book.RecipeCategory;
public class HalfStairsCubeStair implements RecipeSetter, BlockStateProvider {
@Override
public void setRecipe(RecipeExporter exporter, ItemConvertible convertible) {
RecipeProvider.offerStonecuttingRecipe(exporter, RecipeCategory.BUILDING_BLOCKS, convertible, ReFramed.CUBE);
ShapelessRecipeJsonBuilder
.create(RecipeCategory.BUILDING_BLOCKS, convertible)
.input(ReFramed.SMALL_CUBE)
.input(ReFramed.HALF_STAIR)
.criterion(FabricRecipeProvider.hasItem(ReFramed.CUBE), FabricRecipeProvider.conditionsFromItem(ReFramed.CUBE))
.criterion(FabricRecipeProvider.hasItem(convertible), FabricRecipeProvider.conditionsFromItem(convertible))
.offerTo(exporter);
}
@Override
public MultipartBlockStateSupplier getMultipart(Block block) {
return CornerDouble.getMultipart(block, "half_stairs_cube_stair");
}
}

View File

@ -0,0 +1,159 @@
package fr.adrien1106.reframed.generator.block;
import fr.adrien1106.reframed.ReFramed;
import fr.adrien1106.reframed.generator.BlockStateProvider;
import fr.adrien1106.reframed.generator.GBlockstate;
import fr.adrien1106.reframed.generator.RecipeSetter;
import fr.adrien1106.reframed.util.blocks.Corner;
import net.fabricmc.fabric.api.datagen.v1.provider.FabricRecipeProvider;
import net.minecraft.block.Block;
import net.minecraft.data.client.MultipartBlockStateSupplier;
import net.minecraft.data.server.recipe.RecipeExporter;
import net.minecraft.data.server.recipe.RecipeProvider;
import net.minecraft.data.server.recipe.ShapelessRecipeJsonBuilder;
import net.minecraft.item.ItemConvertible;
import net.minecraft.recipe.book.RecipeCategory;
import net.minecraft.util.Identifier;
import static fr.adrien1106.reframed.util.blocks.BlockProperties.*;
import static net.minecraft.data.client.VariantSettings.Rotation.*;
import static net.minecraft.data.client.VariantSettings.Rotation.R270;
public class HalfStairsStepStair implements RecipeSetter, BlockStateProvider {
@Override
public void setRecipe(RecipeExporter exporter, ItemConvertible convertible) {
RecipeProvider.offerStonecuttingRecipe(exporter, RecipeCategory.BUILDING_BLOCKS, convertible, ReFramed.CUBE);
ShapelessRecipeJsonBuilder
.create(RecipeCategory.BUILDING_BLOCKS, convertible)
.input(ReFramed.SMALL_CUBE)
.input(ReFramed.HALF_STAIR)
.criterion(FabricRecipeProvider.hasItem(ReFramed.CUBE), FabricRecipeProvider.conditionsFromItem(ReFramed.CUBE))
.criterion(FabricRecipeProvider.hasItem(convertible), FabricRecipeProvider.conditionsFromItem(convertible))
.offerTo(exporter);
}
@Override
public MultipartBlockStateSupplier getMultipart(Block block) {
Identifier model_1_id = ReFramed.id("half_stairs_step_stair_1_special");
Identifier side_1_id = ReFramed.id("half_stairs_step_stair_side_1_special");
Identifier model_2_id = ReFramed.id("half_stairs_step_stair_2_special");
Identifier side_2_id = ReFramed.id("half_stairs_step_stair_side_2_special");
return MultipartBlockStateSupplier.create(block)
// BOTTOM
// --- 1 ---
.with(GBlockstate.when(CORNER, Corner.EAST_SOUTH_DOWN, CORNER_FACE, 2, CORNER_FEATURE, 0),
GBlockstate.variant(model_1_id, true, R0, R0))
.with(GBlockstate.when(CORNER, Corner.SOUTH_WEST_DOWN, CORNER_FACE, 2, CORNER_FEATURE, 0),
GBlockstate.variant(model_1_id, true, R0, R90))
.with(GBlockstate.when(CORNER, Corner.WEST_NORTH_DOWN, CORNER_FACE, 2, CORNER_FEATURE, 0),
GBlockstate.variant(model_1_id, true, R0, R180))
.with(GBlockstate.when(CORNER, Corner.NORTH_EAST_DOWN, CORNER_FACE, 2, CORNER_FEATURE, 0),
GBlockstate.variant(model_1_id, true, R0, R270))
// --- 2 ---
.with(GBlockstate.when(CORNER, Corner.EAST_SOUTH_DOWN, CORNER_FACE, 2, CORNER_FEATURE, 1),
GBlockstate.variant(model_2_id, true, R0, R0))
.with(GBlockstate.when(CORNER, Corner.SOUTH_WEST_DOWN, CORNER_FACE, 2, CORNER_FEATURE, 1),
GBlockstate.variant(model_2_id, true, R0, R90))
.with(GBlockstate.when(CORNER, Corner.WEST_NORTH_DOWN, CORNER_FACE, 2, CORNER_FEATURE, 1),
GBlockstate.variant(model_2_id, true, R0, R180))
.with(GBlockstate.when(CORNER, Corner.NORTH_EAST_DOWN, CORNER_FACE, 2, CORNER_FEATURE, 1),
GBlockstate.variant(model_2_id, true, R0, R270))
// TOP
// --- 1 ---
.with(GBlockstate.when(CORNER, Corner.NORTH_EAST_UP, CORNER_FACE, 2, CORNER_FEATURE, 1),
GBlockstate.variant(model_1_id, true, R180, R0))
.with(GBlockstate.when(CORNER, Corner.EAST_SOUTH_UP, CORNER_FACE, 2, CORNER_FEATURE, 1),
GBlockstate.variant(model_1_id, true, R180, R90))
.with(GBlockstate.when(CORNER, Corner.SOUTH_WEST_UP, CORNER_FACE, 2, CORNER_FEATURE, 1),
GBlockstate.variant(model_1_id, true, R180, R180))
.with(GBlockstate.when(CORNER, Corner.WEST_NORTH_UP, CORNER_FACE, 2, CORNER_FEATURE, 1),
GBlockstate.variant(model_1_id, true, R180, R270))
// --- 2 ---
.with(GBlockstate.when(CORNER, Corner.NORTH_EAST_UP, CORNER_FACE, 2, CORNER_FEATURE, 0),
GBlockstate.variant(model_2_id, true, R180, R0))
.with(GBlockstate.when(CORNER, Corner.EAST_SOUTH_UP, CORNER_FACE, 2, CORNER_FEATURE, 0),
GBlockstate.variant(model_2_id, true, R180, R90))
.with(GBlockstate.when(CORNER, Corner.SOUTH_WEST_UP, CORNER_FACE, 2, CORNER_FEATURE, 0),
GBlockstate.variant(model_2_id, true, R180, R180))
.with(GBlockstate.when(CORNER, Corner.WEST_NORTH_UP, CORNER_FACE, 2, CORNER_FEATURE, 0),
GBlockstate.variant(model_2_id, true, R180, R270))
// EAST
// --- 1 ---
.with(GBlockstate.when(CORNER, Corner.EAST_SOUTH_DOWN, CORNER_FACE, 0, CORNER_FEATURE, 0),
GBlockstate.variant(side_1_id, true, R0, R0))
.with(GBlockstate.when(CORNER, Corner.EAST_SOUTH_UP, CORNER_FACE, 0, CORNER_FEATURE, 1),
GBlockstate.variant(side_1_id, true, R90, R0))
.with(GBlockstate.when(CORNER, Corner.NORTH_EAST_UP, CORNER_FACE, 1, CORNER_FEATURE, 0),
GBlockstate.variant(side_1_id, true, R180, R0))
.with(GBlockstate.when(CORNER, Corner.NORTH_EAST_DOWN, CORNER_FACE, 1, CORNER_FEATURE, 1),
GBlockstate.variant(side_1_id, true, R270, R0))
// --- 2 ---
.with(GBlockstate.when(CORNER, Corner.EAST_SOUTH_DOWN, CORNER_FACE, 0, CORNER_FEATURE, 1),
GBlockstate.variant(side_2_id, true, R0, R0))
.with(GBlockstate.when(CORNER, Corner.EAST_SOUTH_UP, CORNER_FACE, 0, CORNER_FEATURE, 0),
GBlockstate.variant(side_2_id, true, R90, R0))
.with(GBlockstate.when(CORNER, Corner.NORTH_EAST_UP, CORNER_FACE, 1, CORNER_FEATURE, 1),
GBlockstate.variant(side_2_id, true, R180, R0))
.with(GBlockstate.when(CORNER, Corner.NORTH_EAST_DOWN, CORNER_FACE, 1, CORNER_FEATURE, 0),
GBlockstate.variant(side_2_id, true, R270, R0))
// SOUTH
// --- 1 ---
.with(GBlockstate.when(CORNER, Corner.SOUTH_WEST_DOWN, CORNER_FACE, 0, CORNER_FEATURE, 0),
GBlockstate.variant(side_1_id, true, R0, R90))
.with(GBlockstate.when(CORNER, Corner.SOUTH_WEST_UP, CORNER_FACE, 0, CORNER_FEATURE, 1),
GBlockstate.variant(side_1_id, true, R90, R90))
.with(GBlockstate.when(CORNER, Corner.EAST_SOUTH_UP, CORNER_FACE, 1, CORNER_FEATURE, 0),
GBlockstate.variant(side_1_id, true, R180, R90))
.with(GBlockstate.when(CORNER, Corner.EAST_SOUTH_DOWN, CORNER_FACE, 1, CORNER_FEATURE, 1),
GBlockstate.variant(side_1_id, true, R270, R90))
// --- 2 ---
.with(GBlockstate.when(CORNER, Corner.SOUTH_WEST_DOWN, CORNER_FACE, 0, CORNER_FEATURE, 1),
GBlockstate.variant(side_2_id, true, R0, R90))
.with(GBlockstate.when(CORNER, Corner.SOUTH_WEST_UP, CORNER_FACE, 0, CORNER_FEATURE, 0),
GBlockstate.variant(side_2_id, true, R90, R90))
.with(GBlockstate.when(CORNER, Corner.EAST_SOUTH_UP, CORNER_FACE, 1, CORNER_FEATURE, 1),
GBlockstate.variant(side_2_id, true, R180, R90))
.with(GBlockstate.when(CORNER, Corner.EAST_SOUTH_DOWN, CORNER_FACE, 1, CORNER_FEATURE, 0),
GBlockstate.variant(side_2_id, true, R270, R90))
// WEST
// --- 1 ---
.with(GBlockstate.when(CORNER, Corner.WEST_NORTH_DOWN, CORNER_FACE, 0, CORNER_FEATURE, 0),
GBlockstate.variant(side_1_id, true, R0, R180))
.with(GBlockstate.when(CORNER, Corner.WEST_NORTH_UP, CORNER_FACE, 0, CORNER_FEATURE, 1),
GBlockstate.variant(side_1_id, true, R90, R180))
.with(GBlockstate.when(CORNER, Corner.SOUTH_WEST_UP, CORNER_FACE, 1, CORNER_FEATURE, 0),
GBlockstate.variant(side_1_id, true, R180, R180))
.with(GBlockstate.when(CORNER, Corner.SOUTH_WEST_DOWN, CORNER_FACE, 1, CORNER_FEATURE, 1),
GBlockstate.variant(side_1_id, true, R270, R180))
// --- 2 ---
.with(GBlockstate.when(CORNER, Corner.WEST_NORTH_DOWN, CORNER_FACE, 0, CORNER_FEATURE, 1),
GBlockstate.variant(side_2_id, true, R0, R180))
.with(GBlockstate.when(CORNER, Corner.WEST_NORTH_UP, CORNER_FACE, 0, CORNER_FEATURE, 0),
GBlockstate.variant(side_2_id, true, R90, R180))
.with(GBlockstate.when(CORNER, Corner.SOUTH_WEST_UP, CORNER_FACE, 1, CORNER_FEATURE, 1),
GBlockstate.variant(side_2_id, true, R180, R180))
.with(GBlockstate.when(CORNER, Corner.SOUTH_WEST_DOWN, CORNER_FACE, 1, CORNER_FEATURE, 0),
GBlockstate.variant(side_2_id, true, R270, R180))
// NORTH
// --- 1 ---
.with(GBlockstate.when(CORNER, Corner.NORTH_EAST_DOWN, CORNER_FACE, 0, CORNER_FEATURE, 0),
GBlockstate.variant(side_1_id, true, R0, R270))
.with(GBlockstate.when(CORNER, Corner.NORTH_EAST_UP, CORNER_FACE, 0, CORNER_FEATURE, 1),
GBlockstate.variant(side_1_id, true, R90, R270))
.with(GBlockstate.when(CORNER, Corner.WEST_NORTH_UP, CORNER_FACE, 1, CORNER_FEATURE, 0),
GBlockstate.variant(side_1_id, true, R180, R270))
.with(GBlockstate.when(CORNER, Corner.WEST_NORTH_DOWN, CORNER_FACE, 1, CORNER_FEATURE, 1),
GBlockstate.variant(side_1_id, true, R270, R270))
// --- 2 ---
.with(GBlockstate.when(CORNER, Corner.NORTH_EAST_DOWN, CORNER_FACE, 0, CORNER_FEATURE, 1),
GBlockstate.variant(side_2_id, true, R0, R270))
.with(GBlockstate.when(CORNER, Corner.NORTH_EAST_UP, CORNER_FACE, 0, CORNER_FEATURE, 0),
GBlockstate.variant(side_2_id, true, R90, R270))
.with(GBlockstate.when(CORNER, Corner.WEST_NORTH_UP, CORNER_FACE, 1, CORNER_FEATURE, 1),
GBlockstate.variant(side_2_id, true, R180, R270))
.with(GBlockstate.when(CORNER, Corner.WEST_NORTH_DOWN, CORNER_FACE, 1, CORNER_FEATURE, 0),
GBlockstate.variant(side_2_id, true, R270, R270))
;
}
}

View File

@ -10,5 +10,6 @@ public class BlockProperties {
public static final IntProperty EDGE_FACE = IntProperty.of("face", 0, 1);
public static final EnumProperty<Corner> CORNER = EnumProperty.of("corner", Corner.class);
public static final IntProperty CORNER_FACE = IntProperty.of("face", 0, 2);
public static final IntProperty CORNER_FEATURE = IntProperty.of("corner_feature", 0, 1);
public static final EnumProperty<StairShape> STAIR_SHAPE = EnumProperty.of("shape", StairShape.class);
}

View File

@ -0,0 +1,56 @@
{
"credit": "Made with Blockbench",
"parent": "block/block",
"textures": {
"particle": "#side"
},
"elements": [
{
"from": [8, 0, 8],
"to": [16, 8, 16],
"faces": {
"east": {"uv": [0, 8, 8, 16], "texture": "#side", "cullface": "east"},
"south": {"uv": [8, 8, 16, 16], "texture": "#side", "cullface": "south"},
"up": {"uv": [8, 8, 16, 16], "texture": "#top"},
"down": {"uv": [8, 0, 16, 8], "texture": "#bottom", "cullface": "down"}
}
},
{
"from": [8, 0, 0],
"to": [16, 8, 8],
"faces": {
"north": {"uv": [0, 8, 8, 16], "texture": "#side", "cullface": "north"},
"east": {"uv": [8, 8, 16, 16], "texture": "#side", "cullface": "east"},
"west": {"uv": [0, 8, 8, 16], "texture": "#side"},
"up": {"uv": [8, 0, 16, 8], "texture": "#top"},
"down": {"uv": [8, 8, 16, 16], "texture": "#bottom", "cullface": "down"}
}
},
{
"from": [0, 0, 8],
"to": [8, 8, 16],
"rotation": {"angle": 0, "axis": "y", "origin": [0, 0, 8]},
"faces": {
"north": {"uv": [8, 8, 16, 16], "texture": "#side"},
"south": {"uv": [0, 8, 8, 16], "texture": "#side", "cullface": "south"},
"west": {"uv": [0, 8, 8, 16], "texture": "#side", "cullface": "west"},
"up": {"uv": [0, 8, 8, 16], "texture": "#top"},
"down": {"uv": [0, 0, 8, 8], "texture": "#bottom", "cullface": "down"}
}
}
],
"display": {
"thirdperson_lefthand": {
"rotation": [75, -135, 0],
"translation": [0, 2.5, 0],
"scale": [0.375, 0.375, 0.375]
},
"gui": {
"rotation": [30, 135, 0],
"scale": [0.625, 0.625, 0.625]
},
"head": {
"rotation": [0, -90, 0]
}
}
}

View File

@ -0,0 +1,58 @@
{
"credit": "Made with Blockbench",
"parent": "block/block",
"textures": {
"particle": "#side"
},
"elements": [
{
"from": [8, 8, 8],
"to": [16, 16, 16],
"rotation": {"angle": 0, "axis": "y", "origin": [0, 8, 0]},
"faces": {
"north": {"uv": [0, 0, 8, 8], "texture": "#side"},
"east": {"uv": [0, 0, 8, 8], "texture": "#side", "cullface": "east"},
"south": {"uv": [8, 0, 16, 8], "texture": "#side", "cullface": "south"},
"west": {"uv": [8, 0, 16, 8], "texture": "#side"},
"up": {"uv": [8, 8, 16, 16], "texture": "#top", "cullface": "up"}
}
},
{
"from": [8, 0, 0],
"to": [16, 8, 8],
"rotation": {"angle": 0, "axis": "y", "origin": [8, 0, 0]},
"faces": {
"north": {"uv": [0, 8, 8, 16], "texture": "#side", "cullface": "north"},
"east": {"uv": [8, 8, 16, 16], "texture": "#side", "cullface": "east"},
"west": {"uv": [0, 8, 8, 16], "texture": "#side"},
"up": {"uv": [8, 0, 16, 8], "texture": "#top"},
"down": {"uv": [8, 8, 16, 16], "texture": "#bottom", "cullface": "down"}
}
},
{
"from": [8, 0, 8],
"to": [16, 8, 16],
"rotation": {"angle": 0, "axis": "y", "origin": [8, 0, 8]},
"faces": {
"east": {"uv": [0, 8, 8, 16], "texture": "#side", "cullface": "east"},
"south": {"uv": [8, 8, 16, 16], "texture": "#side", "cullface": "south"},
"west": {"uv": [8, 8, 16, 16], "texture": "#side", "cullface": "down"},
"down": {"uv": [8, 0, 16, 8], "texture": "#bottom", "cullface": "down"}
}
}
],
"display": {
"thirdperson_lefthand": {
"rotation": [75, -135, 0],
"translation": [0, 2.5, 0],
"scale": [0.375, 0.375, 0.375]
},
"gui": {
"rotation": [30, 135, 0],
"scale": [0.625, 0.625, 0.625]
},
"head": {
"rotation": [0, -90, 0]
}
}
}

View File

@ -0,0 +1,36 @@
{
"credit": "Made with Blockbench",
"parent": "block/block",
"textures": {
"particle": "#side"
},
"elements": [
{
"from": [8, 8, 8],
"to": [16, 16, 16],
"rotation": {"angle": 0, "axis": "y", "origin": [0, 8, 0]},
"faces": {
"north": {"uv": [0, 0, 8, 8], "texture": "#side"},
"east": {"uv": [0, 0, 8, 8], "texture": "#side", "cullface": "east"},
"south": {"uv": [8, 0, 16, 8], "texture": "#side", "cullface": "south"},
"west": {"uv": [8, 0, 16, 8], "texture": "#side"},
"up": {"uv": [8, 8, 16, 16], "texture": "#top", "cullface": "up"},
"down": {"uv": [8, 0, 16, 8], "texture": "#bottom"}
}
}
],
"display": {
"thirdperson_lefthand": {
"rotation": [75, -135, 0],
"translation": [0, 2.5, 0],
"scale": [0.375, 0.375, 0.375]
},
"gui": {
"rotation": [30, 135, 0],
"scale": [0.625, 0.625, 0.625]
},
"head": {
"rotation": [0, -90, 0]
}
}
}

View File

@ -0,0 +1,35 @@
{
"credit": "Made with Blockbench",
"parent": "block/block",
"textures": {
"particle": "#side"
},
"elements": [
{
"from": [0, 0, 8],
"to": [8, 8, 16],
"faces": {
"north": {"uv": [8, 8, 16, 16], "texture": "#side"},
"east": {"uv": [0, 8, 8, 16], "texture": "#side"},
"south": {"uv": [0, 8, 8, 16], "texture": "#side", "cullface": "south"},
"west": {"uv": [8, 8, 16, 16], "texture": "#side", "cullface": "west"},
"up": {"uv": [0, 8, 8, 16], "texture": "#top"},
"down": {"uv": [0, 0, 8, 8], "texture": "#bottom", "cullface": "down"}
}
}
],
"display": {
"thirdperson_lefthand": {
"rotation": [75, -135, 0],
"translation": [0, 2.5, 0],
"scale": [0.375, 0.375, 0.375]
},
"gui": {
"rotation": [30, 135, 0],
"scale": [0.625, 0.625, 0.625]
},
"head": {
"rotation": [0, -90, 0]
}
}
}

View File

@ -0,0 +1,47 @@
{
"credit": "Made with Blockbench",
"parent": "block/block",
"textures": {
"particle": "#side"
},
"elements": [
{
"from": [8, 8, 8],
"to": [16, 16, 16],
"rotation": {"angle": 0, "axis": "y", "origin": [0, 8, 0]},
"faces": {
"east": {"uv": [0, 0, 8, 8], "texture": "#side", "cullface": "east"},
"south": {"uv": [8, 0, 16, 8], "texture": "#side", "cullface": "south"},
"west": {"uv": [8, 0, 16, 8], "texture": "#side"},
"up": {"uv": [8, 8, 16, 16], "texture": "#top", "cullface": "up"},
"down": {"uv": [8, 0, 16, 8], "texture": "#bottom"}
}
},
{
"from": [8, 8, 0],
"to": [16, 16, 8],
"rotation": {"angle": 0, "axis": "y", "origin": [8, 8, 0]},
"faces": {
"north": {"uv": [0, 0, 8, 8], "texture": "#side", "cullface": "north"},
"east": {"uv": [8, 0, 16, 8], "texture": "#side", "cullface": "east"},
"west": {"uv": [0, 0, 8, 8], "texture": "#side"},
"up": {"uv": [8, 0, 16, 8], "texture": "#top", "cullface": "up"},
"down": {"uv": [8, 8, 16, 16], "texture": "#bottom"}
}
}
],
"display": {
"thirdperson_lefthand": {
"rotation": [75, -135, 0],
"translation": [0, 2.5, 0],
"scale": [0.375, 0.375, 0.375]
},
"gui": {
"rotation": [30, 135, 0],
"scale": [0.625, 0.625, 0.625]
},
"head": {
"rotation": [0, -90, 0]
}
}
}

View File

@ -0,0 +1,47 @@
{
"credit": "Made with Blockbench",
"parent": "block/block",
"textures": {
"particle": "#side"
},
"elements": [
{
"from": [8, 8, 8],
"to": [16, 16, 16],
"rotation": {"angle": 0, "axis": "y", "origin": [0, 8, 0]},
"faces": {
"north": {"uv": [0, 0, 8, 8], "texture": "#side"},
"east": {"uv": [0, 0, 8, 8], "texture": "#side", "cullface": "east"},
"south": {"uv": [8, 0, 16, 8], "texture": "#side", "cullface": "south"},
"up": {"uv": [8, 8, 16, 16], "texture": "#top", "cullface": "up"},
"down": {"uv": [8, 0, 16, 8], "texture": "#bottom"}
}
},
{
"from": [0, 8, 8],
"to": [8, 16, 16],
"rotation": {"angle": 0, "axis": "y", "origin": [0, 8, 8]},
"faces": {
"north": {"uv": [8, 0, 16, 8], "texture": "#side"},
"south": {"uv": [0, 0, 8, 8], "texture": "#side", "cullface": "south"},
"west": {"uv": [8, 0, 16, 8], "texture": "#side", "cullface": "west"},
"up": {"uv": [0, 8, 8, 16], "texture": "#top", "cullface": "up"},
"down": {"uv": [0, 0, 8, 8], "texture": "#bottom"}
}
}
],
"display": {
"thirdperson_lefthand": {
"rotation": [75, -135, 0],
"translation": [0, 2.5, 0],
"scale": [0.375, 0.375, 0.375]
},
"gui": {
"rotation": [30, 135, 0],
"scale": [0.625, 0.625, 0.625]
},
"head": {
"rotation": [0, -90, 0]
}
}
}

View File

@ -0,0 +1,47 @@
{
"credit": "Made with Blockbench",
"parent": "block/block",
"textures": {
"particle": "#side"
},
"elements": [
{
"from": [0, 0, 8],
"to": [8, 8, 16],
"rotation": {"angle": 0, "axis": "y", "origin": [-8, 0, 0]},
"faces": {
"north": {"uv": [8, 8, 16, 16], "texture": "#side"},
"east": {"uv": [0, 8, 8, 16], "texture": "#side"},
"south": {"uv": [0, 8, 8, 16], "texture": "#side", "cullface": "south"},
"west": {"uv": [8, 8, 16, 16], "texture": "#side", "cullface": "west"},
"down": {"uv": [0, 0, 8, 8], "texture": "#bottom", "cullface": "down"}
}
},
{
"from": [0, 8, 8],
"to": [8, 16, 16],
"rotation": {"angle": 0, "axis": "y", "origin": [0, 8, 8]},
"faces": {
"north": {"uv": [8, 0, 16, 8], "texture": "#side"},
"east": {"uv": [0, 0, 8, 8], "texture": "#side"},
"south": {"uv": [0, 0, 8, 8], "texture": "#side", "cullface": "south"},
"west": {"uv": [8, 0, 16, 8], "texture": "#side", "cullface": "west"},
"up": {"uv": [0, 8, 8, 16], "texture": "#top", "cullface": "up"}
}
}
],
"display": {
"thirdperson_lefthand": {
"rotation": [75, -135, 0],
"translation": [0, 2.5, 0],
"scale": [0.375, 0.375, 0.375]
},
"gui": {
"rotation": [30, 135, 0],
"scale": [0.625, 0.625, 0.625]
},
"head": {
"rotation": [0, -90, 0]
}
}
}

View File

@ -0,0 +1,46 @@
{
"credit": "Made with Blockbench",
"parent": "block/block",
"textures": {
"particle": "#side"
},
"elements": [
{
"from": [0, 0, 8],
"to": [8, 8, 16],
"rotation": {"angle": 0, "axis": "y", "origin": [-8, 0, 0]},
"faces": {
"east": {"uv": [0, 8, 8, 16], "texture": "#side"},
"south": {"uv": [0, 8, 8, 16], "texture": "#side", "cullface": "south"},
"west": {"uv": [8, 8, 16, 16], "texture": "#side", "cullface": "west"},
"up": {"uv": [0, 8, 8, 16], "texture": "#top"},
"down": {"uv": [0, 0, 8, 8], "texture": "#bottom", "cullface": "down"}
}
},
{
"from": [0, 0, 0],
"to": [8, 8, 8],
"faces": {
"north": {"uv": [8, 0, 16, 8], "texture": "#side", "cullface": "north"},
"east": {"uv": [8, 8, 16, 16], "texture": "#side"},
"west": {"uv": [0, 8, 8, 16], "texture": "#side", "cullface": "west"},
"up": {"uv": [0, 0, 8, 8], "texture": "#top"},
"down": {"uv": [0, 8, 8, 16], "texture": "#bottom", "cullface": "down"}
}
}
],
"display": {
"thirdperson_lefthand": {
"rotation": [75, -135, 0],
"translation": [0, 2.5, 0],
"scale": [0.375, 0.375, 0.375]
},
"gui": {
"rotation": [30, 135, 0],
"scale": [0.625, 0.625, 0.625]
},
"head": {
"rotation": [0, -90, 0]
}
}
}