From b5d3d75680a9dcbdc15d60878a11fdbeef8c2655 Mon Sep 17 00:00:00 2001 From: trafficlunar Date: Wed, 22 Jan 2025 21:27:50 +0000 Subject: [PATCH] fix: add block entities to .schem files --- src/components/dialogs/SaveLitematic.tsx | 4 +-- src/components/dialogs/SaveSchem.tsx | 43 ++++++++++++++++++++++-- 2 files changed, 42 insertions(+), 5 deletions(-) diff --git a/src/components/dialogs/SaveLitematic.tsx b/src/components/dialogs/SaveLitematic.tsx index 8ce9204..bc013be 100644 --- a/src/components/dialogs/SaveLitematic.tsx +++ b/src/components/dialogs/SaveLitematic.tsx @@ -29,8 +29,8 @@ function SaveLitematic({ close }: DialogProps) { // Fill in empty blocks with "air" const filledBlocks: Block[] = []; - for (let x = canvasSize.minX; x <= canvasSize.maxX - 1; x++) { - for (let y = canvasSize.minY; y <= canvasSize.maxY - 1; y++) { + for (let x = canvasSize.minX; x < canvasSize.maxX; x++) { + for (let y = canvasSize.minY; y < canvasSize.maxY; y++) { const existingBlock = blocks.find((block) => block.x === x && block.y === y); if (existingBlock) { filledBlocks.push(existingBlock); diff --git a/src/components/dialogs/SaveSchem.tsx b/src/components/dialogs/SaveSchem.tsx index 5683af6..922f775 100644 --- a/src/components/dialogs/SaveSchem.tsx +++ b/src/components/dialogs/SaveSchem.tsx @@ -11,6 +11,33 @@ import { Input } from "@/components/ui/input"; import _blockData from "@/data/blocks/data.json"; const blockData: BlockData = _blockData; +interface BlockEntity { + Id: string; + Pos: Int32Array; +} + +const blockEntitiesWhitelist = [ + "barrel", + "beacon", + "bee", + "chiseled_bookshelf", + "command_block", + "crafter", + "creaking_heart", + "dispenser", + "dropper", + "furnace", + "jigsaw", + "spawner", + "piston", + "sculk", + "smoker", + "shulker", + "structure", + "suspicious", + "vault", +]; + function SaveLitematic({ close }: DialogProps) { const { canvasSize, blocks } = useContext(CanvasContext); const { setLoading } = useContext(LoadingContext); @@ -26,11 +53,13 @@ function SaveLitematic({ close }: DialogProps) { const width = canvasSize.maxX - canvasSize.minX; const height = canvasSize.maxY - canvasSize.minY; + const blockEntities: BlockEntity[] = []; + // Fill in empty blocks with "air" const filledBlocks: Block[] = []; - for (let x = canvasSize.minX; x <= canvasSize.maxX - 1; x++) { - for (let y = canvasSize.minY; y <= canvasSize.maxY - 1; y++) { + for (let x = canvasSize.minX; x < canvasSize.maxX; x++) { + for (let y = canvasSize.minY; y < canvasSize.maxY; y++) { const existingBlock = blocks.find((block) => block.x === x && block.y === y); if (existingBlock) { filledBlocks.push(existingBlock); @@ -58,6 +87,13 @@ function SaveLitematic({ close }: DialogProps) { .map(([key, value]) => `${key}=${value}`) .join(",")}]` : ""; + + if (blockEntitiesWhitelist.some((i) => blockInfo.id.includes(i))) { + blockEntities.push({ + Id: `minecraft:${blockInfo.id}`, + Pos: new Int32Array([block.x, block.y, 0]), + }); + } return `minecraft:${blockInfo.id}${properties}`; }) ) @@ -92,9 +128,10 @@ function SaveLitematic({ close }: DialogProps) { Height: new nbt.Int16(height), Length: new nbt.Int16(1), Metadata: { - Date: new Date().getTime(), + Date: BigInt(new Date().getTime()), }, Blocks: { + BlockEntities: blockEntities, Data: blockPlaceData, Palette: blockPalette, },