From 4d37483057133c843557d634dbd9b248295a9873 Mon Sep 17 00:00:00 2001 From: mewhenthe Date: Sun, 3 May 2026 17:21:24 +0200 Subject: [PATCH] render a singular server --- .../client/NeoComputersFabricClient.java | 12 ++- .../org/neoflock/neocomputers/block/Blocks.kt | 1 + .../neoflock/neocomputers/block/RackBlock.kt | 49 ++++++++++++ .../neoflock/neocomputers/block/RobotBlock.kt | 1 - .../neocomputers/entity/BlockEntities.kt | 6 ++ .../neocomputers/entity/RackEntity.kt | 8 ++ .../entity/render/RackEntityRenderer.kt | 31 ++++++++ .../neoflock/neocomputers/item/RackItem.kt | 56 ++++++++++++++ .../assets/neocomputers/blockstates/rack.json | 5 ++ .../neocomputers/models/block/rack.json | 70 ++++++++++++++++++ .../textures/block/generic_top.png | Bin 0 -> 328 bytes .../textures/block/rack_server.png | Bin 0 -> 514 bytes .../neocomputers/textures/block/rack_side.png | Bin 0 -> 491 bytes .../textures/block/rack_terminal_server.png | Bin 0 -> 531 bytes 14 files changed, 231 insertions(+), 8 deletions(-) create mode 100644 src/main/kotlin/org/neoflock/neocomputers/block/RackBlock.kt create mode 100644 src/main/kotlin/org/neoflock/neocomputers/entity/RackEntity.kt create mode 100644 src/main/kotlin/org/neoflock/neocomputers/entity/render/RackEntityRenderer.kt create mode 100644 src/main/kotlin/org/neoflock/neocomputers/item/RackItem.kt create mode 100644 src/main/resources/assets/neocomputers/blockstates/rack.json create mode 100644 src/main/resources/assets/neocomputers/models/block/rack.json create mode 100644 src/main/resources/assets/neocomputers/textures/block/generic_top.png create mode 100644 src/main/resources/assets/neocomputers/textures/block/rack_server.png create mode 100644 src/main/resources/assets/neocomputers/textures/block/rack_side.png create mode 100644 src/main/resources/assets/neocomputers/textures/block/rack_terminal_server.png diff --git a/src/main/java/org/neoflock/neocomputers/platforms/fabric/client/NeoComputersFabricClient.java b/src/main/java/org/neoflock/neocomputers/platforms/fabric/client/NeoComputersFabricClient.java index 4c50720..c81dbb3 100644 --- a/src/main/java/org/neoflock/neocomputers/platforms/fabric/client/NeoComputersFabricClient.java +++ b/src/main/java/org/neoflock/neocomputers/platforms/fabric/client/NeoComputersFabricClient.java @@ -13,10 +13,7 @@ import org.neoflock.neocomputers.NeoComputers; import org.neoflock.neocomputers.block.Blocks; import org.neoflock.neocomputers.block.CableBlock; import org.neoflock.neocomputers.entity.BlockEntities; -import org.neoflock.neocomputers.entity.render.CaseEntityRenderer; -import org.neoflock.neocomputers.entity.render.RelayEntityRenderer; -import org.neoflock.neocomputers.entity.render.RobotEntityRenderer; -import org.neoflock.neocomputers.entity.render.ScreenEntityRenderer; +import org.neoflock.neocomputers.entity.render.*; import org.neoflock.neocomputers.item.Items; import org.neoflock.neocomputers.platforms.fabric.client.model.ModelLoader; @@ -24,10 +21,11 @@ public class NeoComputersFabricClient implements ClientModInitializer { @Override public void onInitializeClient() { ModelLoadingPlugin.register(new ModelLoader()); - BlockEntityRenderers.register(BlockEntities.INSTANCE.getSCREEN_ENTITY().get(), ScreenEntityRenderer::new); - BlockEntityRenderers.register(BlockEntities.INSTANCE.getCASE_ENTITY().get(), CaseEntityRenderer::new); - BlockEntityRenderers.register(BlockEntities.INSTANCE.getRELAY_ENTITY().get(), RelayEntityRenderer::new); + BlockEntityRenderers.register(BlockEntities.INSTANCE.getSCREEN_ENTITY().get(), ScreenEntityRenderer::new); // TODO: put this in common +// BlockEntityRenderers.register(BlockEntities.INSTANCE.getCASE_ENTITY().get(), CaseEntityRenderer::new); +// BlockEntityRenderers.register(BlockEntities.INSTANCE.getRELAY_ENTITY().get(), RelayEntityRenderer::new); BlockEntityRenderers.register(BlockEntities.INSTANCE.getROBOT_ENTITY().get(), RobotEntityRenderer::new); + BlockEntityRenderers.register(BlockEntities.INSTANCE.getRACK_ENTITY().get(), RackEntityRenderer::new); ColorProviderRegistry.BLOCK.register((state, world, pos, index) -> { if (index == 0) { diff --git a/src/main/kotlin/org/neoflock/neocomputers/block/Blocks.kt b/src/main/kotlin/org/neoflock/neocomputers/block/Blocks.kt index 2c8ccf0..1338371 100644 --- a/src/main/kotlin/org/neoflock/neocomputers/block/Blocks.kt +++ b/src/main/kotlin/org/neoflock/neocomputers/block/Blocks.kt @@ -36,6 +36,7 @@ object Blocks { val CABLE_BLOCK: RegistrySupplier = BaseBlock.register("cable") { CableBlock() } val RELAY_BLOCK: RegistrySupplier = BaseBlock.register("relay") { RelayBlock() } val ROBOT_BLOCK: RegistrySupplier = BaseBlock.register("robot") { RobotBlock() } + val RACK_BLOCK: RegistrySupplier = BaseBlock.register("rack") { RackBlock() } fun registerBlockItems() { BLOCKS.forEach(Consumer { sup: RegistrySupplier -> diff --git a/src/main/kotlin/org/neoflock/neocomputers/block/RackBlock.kt b/src/main/kotlin/org/neoflock/neocomputers/block/RackBlock.kt new file mode 100644 index 0000000..acc9569 --- /dev/null +++ b/src/main/kotlin/org/neoflock/neocomputers/block/RackBlock.kt @@ -0,0 +1,49 @@ +package org.neoflock.neocomputers.block + +import net.minecraft.core.BlockPos +import net.minecraft.world.InteractionResult +import net.minecraft.world.entity.player.Player +import net.minecraft.world.level.BlockGetter +import net.minecraft.world.level.Level +import net.minecraft.world.level.block.EntityBlock +import net.minecraft.world.level.block.RenderShape +import net.minecraft.world.level.block.entity.BlockEntity +import net.minecraft.world.level.block.state.BlockState +import net.minecraft.world.phys.BlockHitResult +import net.minecraft.world.phys.shapes.CollisionContext +import net.minecraft.world.phys.shapes.Shapes +import net.minecraft.world.phys.shapes.VoxelShape +import org.neoflock.neocomputers.entity.BlockEntities +import org.neoflock.neocomputers.entity.RackEntity + +class RackBlock : BaseBlock(Properties.of().noOcclusion()), EntityBlock { + override fun newBlockEntity( + pos: BlockPos, + state: BlockState + ): BlockEntity? { + return RackEntity(pos, state) + } + +// override fun getShape( +// state: BlockState, +// level: BlockGetter, +// pos: BlockPos, +// context: CollisionContext +// ): VoxelShape? { +// return Shapes.box(0.0,0.0,0.0,0.01,0.01,0.01) +// } + +// override fun getRenderShape(state: BlockState): RenderShape? { +// return RenderShape +// } + + +// override fun useWithoutItem( +// state: BlockState, +// level: Levesl, +// pos: BlockPos, +// player: Player, +// hitResult: BlockHitResult +// ): InteractionResult? { +// return super.useWithoutItem(state, level, pos, player, hitResult) +} \ No newline at end of file diff --git a/src/main/kotlin/org/neoflock/neocomputers/block/RobotBlock.kt b/src/main/kotlin/org/neoflock/neocomputers/block/RobotBlock.kt index dd3faea..37122b8 100644 --- a/src/main/kotlin/org/neoflock/neocomputers/block/RobotBlock.kt +++ b/src/main/kotlin/org/neoflock/neocomputers/block/RobotBlock.kt @@ -17,7 +17,6 @@ import org.neoflock.neocomputers.entity.RobotEntity class RobotBlock : BaseBlock(Properties.of().noOcclusion()), EntityBlock { // todo: node stuff override fun newBlockEntity(pos: BlockPos, state: BlockState): BlockEntity { NeoComputers.LOGGER.info("block entity created..") - Blocks.CHEST return RobotEntity(pos, state) } diff --git a/src/main/kotlin/org/neoflock/neocomputers/entity/BlockEntities.kt b/src/main/kotlin/org/neoflock/neocomputers/entity/BlockEntities.kt index 72ecd71..27b4737 100644 --- a/src/main/kotlin/org/neoflock/neocomputers/entity/BlockEntities.kt +++ b/src/main/kotlin/org/neoflock/neocomputers/entity/BlockEntities.kt @@ -100,6 +100,12 @@ object BlockEntities { ) } + val RACK_ENTITY: RegistrySupplier> = BLOCKENTITIES.register("rack") { + BlockEntityType( + ::RackEntity, setOf(Blocks.RACK_BLOCK.get()), BullshitFix() + ) + } + fun registerPowerBlocks() { PowerManager.registerPowerDevice(CAPACITOR_ENTITY.get()) PowerManager.registerPowerDevice(CAPACITOR2_ENTITY.get()) diff --git a/src/main/kotlin/org/neoflock/neocomputers/entity/RackEntity.kt b/src/main/kotlin/org/neoflock/neocomputers/entity/RackEntity.kt new file mode 100644 index 0000000..9283ee7 --- /dev/null +++ b/src/main/kotlin/org/neoflock/neocomputers/entity/RackEntity.kt @@ -0,0 +1,8 @@ +package org.neoflock.neocomputers.entity + +import net.minecraft.core.BlockPos +import net.minecraft.world.level.block.entity.BlockEntity +import net.minecraft.world.level.block.state.BlockState + +class RackEntity(pos: BlockPos, state: BlockState) : BlockEntity(BlockEntities.RACK_ENTITY.get(), pos, state) { +} \ No newline at end of file diff --git a/src/main/kotlin/org/neoflock/neocomputers/entity/render/RackEntityRenderer.kt b/src/main/kotlin/org/neoflock/neocomputers/entity/render/RackEntityRenderer.kt new file mode 100644 index 0000000..8cbe101 --- /dev/null +++ b/src/main/kotlin/org/neoflock/neocomputers/entity/render/RackEntityRenderer.kt @@ -0,0 +1,31 @@ +package org.neoflock.neocomputers.entity.render + +import com.mojang.authlib.minecraft.client.MinecraftClient +import com.mojang.blaze3d.vertex.PoseStack +import net.minecraft.client.Minecraft +import net.minecraft.client.renderer.LevelRenderer +import net.minecraft.client.renderer.LightTexture +import net.minecraft.client.renderer.MultiBufferSource +import net.minecraft.client.renderer.block.ModelBlockRenderer +import net.minecraft.client.renderer.blockentity.BlockEntityRenderer +import net.minecraft.client.renderer.blockentity.BlockEntityRendererProvider +import net.minecraft.world.level.LightLayer +import net.minecraft.world.level.dimension.DimensionType +import net.minecraft.world.level.lighting.BlockLightEngine +import org.neoflock.neocomputers.NeoComputers +import org.neoflock.neocomputers.entity.RackEntity +import org.neoflock.neocomputers.item.RackItem + +class RackEntityRenderer(val context: BlockEntityRendererProvider.Context) : BlockEntityRenderer { + + override fun render(ent: RackEntity, partialTick: Float, poseStack: PoseStack, source: MultiBufferSource, packedLight: Int, packedOverlay: Int) { + poseStack.pushPose() + poseStack.translate(1/16f, 11/16f, 1/16f) + + val render_slot = 2 // this is purely temporary type shit like true alpha shit, anyway it go to 0-3, change and test it if you want + poseStack.translate(0f, (render_slot)*-3/16f, 0f) + val server = object : RackItem {} + server.render(source, poseStack, packedLight) // who knows atp + poseStack.popPose() + } +} \ No newline at end of file diff --git a/src/main/kotlin/org/neoflock/neocomputers/item/RackItem.kt b/src/main/kotlin/org/neoflock/neocomputers/item/RackItem.kt new file mode 100644 index 0000000..d0a89b8 --- /dev/null +++ b/src/main/kotlin/org/neoflock/neocomputers/item/RackItem.kt @@ -0,0 +1,56 @@ +package org.neoflock.neocomputers.item + +import com.mojang.blaze3d.shaders.Shader +import com.mojang.blaze3d.vertex.DefaultVertexFormat +import com.mojang.blaze3d.vertex.PoseStack +import com.mojang.blaze3d.vertex.VertexConsumer +import com.mojang.blaze3d.vertex.VertexFormat +import net.minecraft.client.renderer.MultiBufferSource +import net.minecraft.client.renderer.RenderStateShard +import net.minecraft.client.renderer.RenderType +import net.minecraft.client.renderer.texture.OverlayTexture +import net.minecraft.resources.ResourceLocation +import org.neoflock.neocomputers.NeoComputers + +interface RackItem { +// companion object { +// val RENDER_TYPE = {l: ResourceLocation -> +// RenderType.create("nc_server", DefaultVertexFormat.POSITION_COLOR_TEX_LIGHTMAP, VertexFormat.Mode.QUADS, RenderType.SMALL_BUFFER_SIZE, RenderType.CompositeState.builder() +// .setShaderState(RenderStateShard.ShaderStateShard.POSITION_COLOR_TEX_LIGHTMAP_SHADER) +// .setLightmapState(RenderStateShard.LIGHTMAP) +// .setTextureState(RenderStateShard.TextureStateShard(l, false, false)) +// .createCompositeState(false)) +// } +// } + val TOP_TEX: ResourceLocation + get() = ResourceLocation.fromNamespaceAndPath(NeoComputers.MODID, "textures/block/generic_top.png") + + val FRONT_TEX: ResourceLocation + get() = ResourceLocation.fromNamespaceAndPath(NeoComputers.MODID, "textures/block/rack_server.png") + + fun render(source: MultiBufferSource, stack: PoseStack, light: Int, v_offset: Float = 2f) { + val pose = stack.last() + + +// var buffer = source.getBuffer(RenderType.gui()) // TODO: correct rendertype + var buffer = source.getBuffer(RenderType.entitySolid(TOP_TEX)) +// val u1 = 1/16f + buffer.addVertex(pose, 0f, 0f, 0f).setUv(1/16f, 15/16f).setColor(1f, 1f, 1f, 1f).setLight(light).setNormal(pose, 0f, -1f, 0f).setOverlay(OverlayTexture.NO_OVERLAY) + buffer.addVertex(pose, 14/16f, 0f, 0f).setUv(1/16f, 1/16f).setColor(1f, 1f, 1f, 1f).setLight(light).setNormal(pose, 0f, -1f, 0f).setOverlay(OverlayTexture.NO_OVERLAY) + buffer.addVertex(pose, 14/16f, 0f, 14/16f).setUv(15/16f, 1/16f).setColor(1f, 1f, 1f, 1f).setLight(light).setNormal(pose, 0f, -1f, 0f).setOverlay(OverlayTexture.NO_OVERLAY) + buffer.addVertex(pose, 0f, 0f, 14/16f).setUv(15/16f, 1/16f).setColor(1f, 1f, 1f, 1f).setLight(light).setNormal(pose, 0f, -1f, 0f).setOverlay(OverlayTexture.NO_OVERLAY) + + buffer.addVertex(pose, 0f, 3/16f, 14/16f).setUv(15/16f, 1/16f).setColor(1f, 1f, 1f, 1f).setLight(light).setNormal(pose, 0f, 1f, 0f).setOverlay(OverlayTexture.NO_OVERLAY) + buffer.addVertex(pose, 14/16f, 3/16f, 14/16f).setUv(15/16f, 15/16f).setColor(1f, 1f, 1f, 1f).setLight(light).setNormal(pose, 0f, 1f, 0f).setOverlay(OverlayTexture.NO_OVERLAY) + buffer.addVertex(pose, 14/16f, 3/16f, 0f).setUv(1/16f, 15/16f).setColor(1f, 1f, 1f, 1f).setLight(light).setNormal(pose, 0f, 1f, 0f).setOverlay(OverlayTexture.NO_OVERLAY) + buffer.addVertex(pose, 0f, 3/16f, 0f).setUv(1/16f, 1/16f).setColor(1f, 1f, 1f, 1f).setLight(light).setNormal(pose, 0f, 1f, 0f).setOverlay(OverlayTexture.NO_OVERLAY) + + buffer = source.getBuffer(RenderType.entitySolid(FRONT_TEX)) + buffer.addVertex(pose, 14/16f, 3/16f, 14/16f).setUv(1/16f, v_offset/16f).setColor(1f, 1f, 1f, 1f).setLight(light).setNormal(pose, 1f, 0f, 0f).setOverlay(OverlayTexture.NO_OVERLAY) + buffer.addVertex(pose, 14/16f, 0f, 14/16f).setUv(1/16f, (v_offset+3)/16f).setColor(1f, 1f, 1f, 1f).setLight(light).setNormal(pose, 1f, 0f, 0f).setOverlay(OverlayTexture.NO_OVERLAY) + buffer.addVertex(pose, 14/16f, 0/16f, 0/16f).setUv(15/16f, (v_offset+3)/16f).setColor(1f, 1f, 1f, 1f).setLight(light).setNormal(pose, 1f, 0f, 0f).setOverlay(OverlayTexture.NO_OVERLAY) + buffer.addVertex(pose, 14/16f, 3/16f, 0/16f).setUv(15/16f, v_offset/16f).setColor(1f, 1f, 1f, 1f).setLight(light).setNormal(pose, 1f, 0f, 0f).setOverlay(OverlayTexture.NO_OVERLAY) + + } + +} \ No newline at end of file diff --git a/src/main/resources/assets/neocomputers/blockstates/rack.json b/src/main/resources/assets/neocomputers/blockstates/rack.json new file mode 100644 index 0000000..18bb909 --- /dev/null +++ b/src/main/resources/assets/neocomputers/blockstates/rack.json @@ -0,0 +1,5 @@ +{ + "variants": { + "": { "model": "neocomputers:block/rack"} + } +} \ No newline at end of file diff --git a/src/main/resources/assets/neocomputers/models/block/rack.json b/src/main/resources/assets/neocomputers/models/block/rack.json new file mode 100644 index 0000000..f396222 --- /dev/null +++ b/src/main/resources/assets/neocomputers/models/block/rack.json @@ -0,0 +1,70 @@ +{ + "parent": "minecraft:block/block", + "render_type": "minecraft:solid", + "textures": { + "side": "neocomputers:block/rack_side", + "top": "neocomputers:block/generic_top" + }, + "elements": [ + { + "from": [0, 0, 0], + "to": [1, 16, 16], + "faces": { + "west": { "uv": [0, 0, 16, 16], "texture": "side", "tint_index": 0 }, + "east": { "uv": [0, 0, 16, 16], "texture": "side", "tint_index": 0 }, + "north": { "uv": [0, 0, 16, 1], "texture": "side", "tint_index": 0 }, + "south": { "uv": [0, 0, 16, 1], "texture": "side", "tint_index": 0 }, + "up": { "uv": [0, 0, 16, 1], "texture": "side", "tint_index": 0 }, + "down": { "uv": [0, 0, 16, 1], "texture": "side", "tint_index": 0 } + } + }, + { + "from": [1, 0, 0], + "to": [16, 16, 1], + "faces": { + "north": { "uv": [0, 0, 15, 16], "texture": "side", "tint_index": 0 }, + "south": { "uv": [1, 0, 16, 16], "texture": "side", "tint_index": 0 }, + "west": { "uv": [0, 0, 1, 16], "texture": "side", "tint_index": 0 }, + "east": { "uv": [0, 0, 1, 16], "texture": "side", "tint_index": 0 }, + "up": { "uv": [0, 0, 16, 1], "texture": "side", "tint_index": 0 }, + "down": { "uv": [0, 0, 16, 1], "texture": "side", "tint_index": 0 } + } + }, + { + "from": [1, 0, 15], + "to": [16, 16, 16], + "faces": { + "north": { "uv": [0, 0, 15, 16], "texture": "side", "tint_index": 0 }, + "south": { "uv": [1, 0, 16, 16], "texture": "side", "tint_index": 0 }, + "west": { "uv": [0, 0, 1, 16], "texture": "side", "tint_index": 0 }, + "east": { "uv": [0, 0, 1, 16], "texture": "side", "tint_index": 0 }, + "up": { "uv": [0, 0, 16, 1], "texture": "side", "tint_index": 0 }, + "down": { "uv": [0, 0, 16, 1], "texture": "side", "tint_index": 0 } + } + }, + { + "from": [1, 0, 1], + "to": [16, 2, 15], + "faces": { + "north": { "uv": [0, 0, 1, 16], "texture": "top", "tint_index": 0 }, + "south": { "uv": [0, 0, 1, 16], "texture": "top", "tint_index": 0 }, + "west": { "uv": [0, 0, 1, 16], "texture": "top", "tint_index": 0 }, + "east": { "uv": [0, 0, 1, 16], "texture": "top", "tint_index": 0 }, + "up": { "uv": [2, 1, 16, 15], "texture": "top", "tint_index": 0 }, + "down": { "uv": [0, 0, 1, 1], "texture": "top", "tint_index": 0 } + } + }, + { + "from": [1, 14, 1], + "to": [16, 16, 15], + "faces": { + "north": { "uv": [0, 0, 1, 16], "texture": "top", "tint_index": 0 }, + "south": { "uv": [0, 0, 1, 16], "texture": "top", "tint_index": 0 }, + "west": { "uv": [0, 0, 1, 16], "texture": "top", "tint_index": 0 }, + "east": { "uv": [1, 0, 15, 2], "texture": "top", "tint_index": 0 }, + "up": { "uv": [1, 1, 16, 15], "texture": "top", "tint_index": 0 }, + "down": { "uv": [0, 0, 1, 1], "texture": "top", "tint_index": 0 } + } + } + ] +} \ No newline at end of file diff --git a/src/main/resources/assets/neocomputers/textures/block/generic_top.png b/src/main/resources/assets/neocomputers/textures/block/generic_top.png new file mode 100644 index 0000000000000000000000000000000000000000..a7934abd06e56f0819f2530449f8d82924072ab3 GIT binary patch literal 328 zcmeAS@N?(olHy`uVBq!ia0vp^0wB!63?wyl`GbL!WQl7;NpOBzNqJ&XDuZK6ep0G} zXKrG8YEWuoN@d~6R2!fon*g5>*Px)Fz`#HW2?_V;NXyu5PyIF(9lqE zaq+OQu<-D3UteD-DJd~Av51HWA0HoSX=!h7@07XC-avB}dAc};RNNAo(4FV3$m5** zsqJ=Y_W%F!=>kHWH;xNNl;7O8w3a{ONW;`-jyX{``Z6yufBCaC(Q>cSPxeQwr~6*I0^oPU^Euy6W7zQk@`mG!PgZj0OZXwG7O<)?M} zwGornuHZwDe;l+jon+U=dT6>y%9Q7oEZx@A0HngA|f3f9W*pFEiEl2B_&QyPBAetFfcGuQc^4| zEHW}OE-o%MNH$efRWCj+R8&+yQ$9F2I7C@OHa0dOARsF%D>5@OH%T@)Nj54fDmzU& zGcq$hP&-jkQ5+l`Ls&sAEiN@hG(J*2JUl!xK`=2uFi%fUMqEWxQ&T=ZJ~}!&KT|y^ zDJeBIH90vsGBPtWLorrXRz*ccE-fuxgD9N<007cSL_t(|+7wU)j>A9@^J12=$u`uK z+iQ=R8UFvNo3%#v$kHHK1`05WEI`xD`-|oCyl`>4Cj?3W)YEp~Y5g_TH3b>&{B#xE?VEGIAvmCjA;cJ5bdh97JyIHm zG#-s<_`4oc0hGtHgAg|}v3n7vpgk%fDp8dL;%rEztdhh^omj=es)zf9G2aVryy1p{ zan3=Rx#Wg}(;ltXb=&Ih?4#4QrdtXcoj(BZ%>M!m0Kae!(n6&aVgLXD07*qoM6N<$ Ef}2mSdjJ3c literal 0 HcmV?d00001 diff --git a/src/main/resources/assets/neocomputers/textures/block/rack_side.png b/src/main/resources/assets/neocomputers/textures/block/rack_side.png new file mode 100644 index 0000000000000000000000000000000000000000..ae94723aff99875f7b2ae65d7507831806d67eb1 GIT binary patch literal 491 zcmeAS@N?(olHy`uVBq!ia0vp^0wB!63?wyl`GbL!WQl7;NpOBzNqJ&XDuZK6ep0G} zXKrG8YEWuoN@d~6R2!h8?EyX^t{}ydk`fXUTwGk@;^KmWg3{8`oSdBU^72wrQnIqL zLPA2u#>RerehLZ-92^|n+}u7sK0!f2a&mI~{QQQ7hHPwXCMG5_GBP|oJRu<=PEJnl z?(WLU%BH5K>gwvDp`iu_27G*cN=izqs;a`m!ok78Ha0c_0s`LN-inHfmX?-|j*j;B z_Lf#w+}vDZVq#p}Tmb$rfwOsL%ow%Qh>k8!(L5-$35tgde#szGr5;o;7 zbhs?l%ux8C&`k8Qr>^sy-#cf?9!cKx?})|U2=PUF2gyDFMCby>|^Wdo@?LcI@s0uhuvfH eFNG=&1BOfQc{WZj3b_OH6@#a%pUXO@geCw3vYfU6 literal 0 HcmV?d00001 diff --git a/src/main/resources/assets/neocomputers/textures/block/rack_terminal_server.png b/src/main/resources/assets/neocomputers/textures/block/rack_terminal_server.png new file mode 100644 index 0000000000000000000000000000000000000000..757e92480fdc9c0747738fe40393e50697adcd9b GIT binary patch literal 531 zcmV+u0_^>XP)IwOGcz+J zBqSOd8XFrM9v&VyH#amiG#?)yA|fIuCnp^p9ZpV8EiEl0BO@^}F(oA>Qc_YfGBPeM zE-Wl8Pft%UFfdhBRYyoiI5;>|R8%%LHXtA%IyyQ&K0Yu!KrT5xFFHR(MMY6jQ8q(J zKu}gYN>Cge9632TR#sL=M@Kz9JvvBDEiEoGGcr6&Q8q+LE-fuGGBYbHD?B_rJv=-? zQdmV+TsA{VK21|FJwZP|KPf3GH9|)7UvunZJn6gdHPJ?r)tf3vQxyVC`k zZoXbR=azHlP97Y<`0vy6p{UiAPl?pRV~qTRZxE;e;3w_XDCONmdI~bs(Z%bv+N87B zoGG9PO%p<+f(n#YbVo|Vkox;R4Y!wlDuD9l;N{bvmyfG0`)+BD%G%0SC4n>>T!<(* zsSrO=Xs~MgZD-f4jW>?Sz_ivd+L&W)G&If8O6l8Hj^AIS^pgHk(9?MXfX@0azyKeH V5CLyZC8GcU002ovPDHLkV1jgnwvGS* literal 0 HcmV?d00001