XFE Git
XFE Studio Git
Git 首页 全局搜索
XFE 主站 文档 NuGet

MyDimension

【Java】我的维度模组

公开
关注 0 Fork 0 Star 0
返回提交历史

XFEstudio/MyDimension

完善传送门框架

a9140f1
XFE工作室室长 <mail@xfegzs.com>
提交于

代码差异

24 个文件 +1126 -1
Added .vs/ProjectSettings.json +3 -0
@@ -0,0 +1,3 @@
1 {
2 "CurrentProjectSetting": null
3 }
Added .vs/slnx.sqlite +0 -0
二进制文件已变更,无法进行逐行预览。
Modified src/main/java/com/xfestudio/mydimension/MyDimension.java +4 -0
@@ -3,6 +3,8 @@ package com.xfestudio.mydimension;
3 3 import com.mojang.logging.LogUtils;
4 4 import com.xfestudio.mydimension.network.ModNetwork;
5 5 import com.xfestudio.mydimension.registry.ModChunkGenerators;
6 import com.xfestudio.mydimension.registry.ModBlockEntities;
7 import com.xfestudio.mydimension.registry.ModBlocks;
6 8 import com.xfestudio.mydimension.registry.ModEntities;
7 9 import com.xfestudio.mydimension.registry.ModItems;
8 10 import net.minecraftforge.common.MinecraftForge;
@@ -20,6 +22,8 @@ public class MyDimension {
20 22 public MyDimension() {
21 23 IEventBus modEventBus = FMLJavaModLoadingContext.get().getModEventBus();
22 24
25 ModBlocks.register(modEventBus);
26 ModBlockEntities.register(modEventBus);
23 27 ModEntities.register(modEventBus);
24 28 ModItems.register(modEventBus);
25 29 ModChunkGenerators.CHUNK_GENERATORS.register(modEventBus);
Added src/main/java/com/xfestudio/mydimension/client/MindPortalRenderer.java +106 -0
@@ -0,0 +1,106 @@
1 package com.xfestudio.mydimension.client;
2
3 import com.mojang.blaze3d.vertex.PoseStack;
4 import com.mojang.blaze3d.vertex.VertexConsumer;
5 import com.xfestudio.mydimension.world.block.MindPortalBlock;
6 import com.xfestudio.mydimension.world.block.entity.MindPortalBlockEntity;
7 import net.minecraft.client.Minecraft;
8 import net.minecraft.client.renderer.LightTexture;
9 import net.minecraft.client.renderer.MultiBufferSource;
10 import net.minecraft.client.renderer.RenderType;
11 import net.minecraft.client.renderer.blockentity.BlockEntityRenderer;
12 import net.minecraft.client.renderer.blockentity.BlockEntityRendererProvider;
13 import net.minecraft.client.renderer.texture.OverlayTexture;
14 import net.minecraft.client.renderer.texture.TextureAtlas;
15 import net.minecraft.client.renderer.texture.TextureAtlasSprite;
16 import net.minecraft.core.Direction;
17 import net.minecraft.resources.ResourceLocation;
18 import org.joml.Matrix3f;
19 import org.joml.Matrix4f;
20
21 public class MindPortalRenderer implements BlockEntityRenderer<MindPortalBlockEntity> {
22 private static final ResourceLocation PORTAL_SPRITE = new ResourceLocation("minecraft", "block/nether_portal");
23
24 public MindPortalRenderer(BlockEntityRendererProvider.Context context) {
25 }
26
27 @Override
28 public void render(MindPortalBlockEntity blockEntity, float partialTick, PoseStack poseStack,
29 MultiBufferSource buffer, int packedLight, int packedOverlay) {
30 if (blockEntity.linkId() == null || !blockEntity.getBlockState().getValue(MindPortalBlock.CORE)) {
31 return;
32 }
33
34 TextureAtlasSprite sprite = Minecraft.getInstance()
35 .getTextureAtlas(TextureAtlas.LOCATION_BLOCKS)
36 .apply(PORTAL_SPRITE);
37 VertexConsumer consumer = buffer.getBuffer(RenderType.entityTranslucent(TextureAtlas.LOCATION_BLOCKS));
38 long gameTime = blockEntity.getLevel() == null ? 0L : blockEntity.getLevel().getGameTime();
39 float pulse = (float) Math.sin((gameTime + partialTick) * 0.055D);
40 Direction.Axis axis = blockEntity.getBlockState().getValue(MindPortalBlock.AXIS);
41
42 poseStack.pushPose();
43 renderLayer(poseStack, consumer, sprite, axis, 0.486F + pulse * 0.012F,
44 82, 214, 255, 205, false);
45 renderLayer(poseStack, consumer, sprite, axis, 0.514F - pulse * 0.009F,
46 160, 92, 255, 135, true);
47 poseStack.popPose();
48 }
49
50 @Override
51 public boolean shouldRenderOffScreen(MindPortalBlockEntity blockEntity) {
52 return true;
53 }
54
55 @Override
56 public int getViewDistance() {
57 return 128;
58 }
59
60 private static void renderLayer(PoseStack poseStack, VertexConsumer consumer, TextureAtlasSprite sprite,
61 Direction.Axis axis, float depth, int red, int green, int blue, int alpha,
62 boolean flipUv) {
63 PoseStack.Pose pose = poseStack.last();
64 Matrix4f matrix = pose.pose();
65 Matrix3f normal = pose.normal();
66 float u0 = flipUv ? sprite.getU1() : sprite.getU0();
67 float u1 = flipUv ? sprite.getU0() : sprite.getU1();
68 float v0 = sprite.getV0();
69 float v1 = sprite.getV1();
70
71 if (axis == Direction.Axis.X) {
72 vertex(consumer, matrix, normal, 0.0F, 0.0F, depth, u0, v1, red, green, blue, alpha, 0.0F, 0.0F, 1.0F);
73 vertex(consumer, matrix, normal, 3.0F, 0.0F, depth, u1, v1, red, green, blue, alpha, 0.0F, 0.0F, 1.0F);
74 vertex(consumer, matrix, normal, 3.0F, 4.0F, depth, u1, v0, red, green, blue, alpha, 0.0F, 0.0F, 1.0F);
75 vertex(consumer, matrix, normal, 0.0F, 4.0F, depth, u0, v0, red, green, blue, alpha, 0.0F, 0.0F, 1.0F);
76
77 vertex(consumer, matrix, normal, 0.0F, 4.0F, depth, u0, v0, red, green, blue, alpha, 0.0F, 0.0F, -1.0F);
78 vertex(consumer, matrix, normal, 3.0F, 4.0F, depth, u1, v0, red, green, blue, alpha, 0.0F, 0.0F, -1.0F);
79 vertex(consumer, matrix, normal, 3.0F, 0.0F, depth, u1, v1, red, green, blue, alpha, 0.0F, 0.0F, -1.0F);
80 vertex(consumer, matrix, normal, 0.0F, 0.0F, depth, u0, v1, red, green, blue, alpha, 0.0F, 0.0F, -1.0F);
81 } else {
82 vertex(consumer, matrix, normal, depth, 0.0F, 0.0F, u0, v1, red, green, blue, alpha, 1.0F, 0.0F, 0.0F);
83 vertex(consumer, matrix, normal, depth, 4.0F, 0.0F, u0, v0, red, green, blue, alpha, 1.0F, 0.0F, 0.0F);
84 vertex(consumer, matrix, normal, depth, 4.0F, 3.0F, u1, v0, red, green, blue, alpha, 1.0F, 0.0F, 0.0F);
85 vertex(consumer, matrix, normal, depth, 0.0F, 3.0F, u1, v1, red, green, blue, alpha, 1.0F, 0.0F, 0.0F);
86
87 vertex(consumer, matrix, normal, depth, 0.0F, 3.0F, u1, v1, red, green, blue, alpha, -1.0F, 0.0F, 0.0F);
88 vertex(consumer, matrix, normal, depth, 4.0F, 3.0F, u1, v0, red, green, blue, alpha, -1.0F, 0.0F, 0.0F);
89 vertex(consumer, matrix, normal, depth, 4.0F, 0.0F, u0, v0, red, green, blue, alpha, -1.0F, 0.0F, 0.0F);
90 vertex(consumer, matrix, normal, depth, 0.0F, 0.0F, u0, v1, red, green, blue, alpha, -1.0F, 0.0F, 0.0F);
91 }
92 }
93
94 private static void vertex(VertexConsumer consumer, Matrix4f matrix, Matrix3f normal,
95 float x, float y, float z, float u, float v,
96 int red, int green, int blue, int alpha,
97 float normalX, float normalY, float normalZ) {
98 consumer.vertex(matrix, x, y, z)
99 .color(red, green, blue, alpha)
100 .uv(u, v)
101 .overlayCoords(OverlayTexture.NO_OVERLAY)
102 .uv2(LightTexture.FULL_BRIGHT)
103 .normal(normal, normalX, normalY, normalZ)
104 .endVertex();
105 }
106 }
Modified src/main/java/com/xfestudio/mydimension/client/ModClientEvents.java +2 -0
@@ -2,6 +2,7 @@ package com.xfestudio.mydimension.client;
2 2
3 3 import com.xfestudio.mydimension.MyDimension;
4 4 import com.xfestudio.mydimension.registry.ModEntities;
5 import com.xfestudio.mydimension.registry.ModBlockEntities;
5 6 import net.minecraftforge.api.distmarker.Dist;
6 7 import net.minecraftforge.client.event.EntityRenderersEvent;
7 8 import net.minecraftforge.eventbus.api.SubscribeEvent;
@@ -12,5 +13,6 @@ public class ModClientEvents {
12 13 @SubscribeEvent
13 14 public static void registerRenderers(EntityRenderersEvent.RegisterRenderers event) {
14 15 event.registerEntityRenderer(ModEntities.RIFT_ANCHOR.get(), RiftAnchorRenderer::new);
16 event.registerBlockEntityRenderer(ModBlockEntities.MIND_PORTAL.get(), MindPortalRenderer::new);
15 17 }
16 18 }
Modified src/main/java/com/xfestudio/mydimension/item/RiftItem.java +67 -0
@@ -3,8 +3,10 @@ package com.xfestudio.mydimension.item;
3 3 import com.xfestudio.mydimension.client.RiftClient;
4 4 import com.xfestudio.mydimension.world.MindInstances;
5 5 import com.xfestudio.mydimension.world.MindTeamAccess;
6 import com.xfestudio.mydimension.world.MindType;
6 7 import com.xfestudio.mydimension.world.ModDimensions;
7 8 import com.xfestudio.mydimension.world.PrivateMindFeature;
9 import com.xfestudio.mydimension.world.portal.MindPortalManager;
8 10 import com.xfestudio.mydimension.world.SoaringMindChunkGenerator;
9 11 import net.minecraft.core.BlockPos;
10 12 import net.minecraft.core.registries.Registries;
@@ -25,8 +27,10 @@ import net.minecraft.world.entity.player.Player;
25 27 import net.minecraft.world.entity.projectile.ProjectileUtil;
26 28 import net.minecraft.world.item.Item;
27 29 import net.minecraft.world.item.ItemStack;
30 import net.minecraft.world.item.context.UseOnContext;
28 31 import net.minecraft.world.level.Level;
29 32 import net.minecraft.world.level.block.entity.BlockEntity;
33 import net.minecraft.world.level.block.state.BlockState;
30 34 import net.minecraft.world.level.levelgen.Heightmap;
31 35 import net.minecraft.world.level.portal.PortalInfo;
32 36 import net.minecraft.world.phys.AABB;
@@ -122,6 +126,19 @@ public class RiftItem extends Item {
122 126 }
123 127 }
124 128
129 @Override
130 public InteractionResult useOn(UseOnContext context) {
131 BlockState state = context.getLevel().getBlockState(context.getClickedPos());
132 if (state.is(com.xfestudio.mydimension.registry.ModBlocks.MIND_PORTAL_FRAME.get())
133 || state.is(com.xfestudio.mydimension.registry.ModBlocks.MIND_PORTAL.get())) {
134 if (context.getLevel().isClientSide()) {
135 return InteractionResult.SUCCESS;
136 }
137 return MindPortalManager.useRiftOnPortal(context);
138 }
139 return super.useOn(context);
140 }
141
125 142 public static void setTeamMindTarget(ItemStack stack, UUID owner, ResourceKey<Level> baseDimension) {
126 143 CompoundTag tag = stack.getOrCreateTag();
127 144 tag.putString(SELECTED_ACTION_TAG, RiftAction.VISIT_TEAM_MIND.id());
@@ -129,6 +146,52 @@ public class RiftItem extends Item {
129 146 tag.putString(TEAM_DIMENSION_TAG, baseDimension.location().toString());
130 147 }
131 148
149 public static PortalTarget resolvePortalTarget(ServerPlayer player, ItemStack stack) {
150 RiftAction action = getSelectedAction(stack);
151 ResourceKey<Level> baseDimension;
152 ResourceKey<Level> actualDimension;
153 UUID targetOwner = null;
154 Component displayName;
155
156 if (action == RiftAction.VISIT_TEAM_MIND) {
157 TeamMindTarget teamTarget = readTeamMindTarget(stack);
158 if (teamTarget == null || !MindTeamAccess.hasAccess(player.getServer(), teamTarget.owner(), player.getUUID())) {
159 player.displayClientMessage(Component.translatable("message.mydimension.team.not_allowed"), true);
160 return null;
161 }
162 baseDimension = teamTarget.baseDimension();
163 actualDimension = MindInstances.dimensionForOwner(player.getServer(), teamTarget.owner(), baseDimension);
164 targetOwner = teamTarget.owner();
165 String ownerName = MindTeamAccess.entrancesFor(player).stream()
166 .filter(entry -> entry.id().equals(teamTarget.owner()))
167 .map(MindTeamAccess.PlayerEntry::name)
168 .findFirst()
169 .orElse("?");
170 MindType type = MindType.fromBaseDimension(baseDimension);
171 displayName = Component.translatable("message.mydimension.portal.team_target", ownerName,
172 type == null ? Component.literal(baseDimension.location().toString()) : type.displayName());
173 } else if (action.teleportsPlayer()) {
174 baseDimension = action.targetDimension();
175 if (action.usesSharedDimension()) {
176 actualDimension = baseDimension;
177 } else {
178 targetOwner = player.getUUID();
179 actualDimension = MindInstances.dimensionForOwner(player.getServer(), player.getUUID(), baseDimension);
180 }
181 MindType type = MindType.fromBaseDimension(baseDimension);
182 displayName = type == null ? Component.literal(baseDimension.location().toString()) : type.displayName();
183 } else {
184 player.displayClientMessage(Component.translatable("message.mydimension.portal.invalid_target"), true);
185 return null;
186 }
187
188 if (actualDimension == null) {
189 player.displayClientMessage(Component.translatable("message.mydimension.team.no_slot"), true);
190 return null;
191 }
192 return new PortalTarget(baseDimension, actualDimension, targetOwner, displayName);
193 }
194
132 195 public static RiftAction getSelectedAction(ItemStack stack) {
133 196 CompoundTag tag = stack.getTag();
134 197 if (tag == null || !tag.contains(SELECTED_ACTION_TAG)) {
@@ -608,6 +671,10 @@ public class RiftItem extends Item {
608 671 public record AnchorPoint(ResourceKey<Level> dimension, double x, double y, double z) {
609 672 }
610 673
674 public record PortalTarget(ResourceKey<Level> baseDimension, ResourceKey<Level> dimension,
675 UUID owner, Component displayName) {
676 }
677
611 678 private static class EtherealMindTeleporter implements ITeleporter {
612 679 private final double x;
613 680 private final double y;
Added src/main/java/com/xfestudio/mydimension/registry/ModBlockEntities.java +26 -0
@@ -0,0 +1,26 @@
1 package com.xfestudio.mydimension.registry;
2
3 import com.xfestudio.mydimension.MyDimension;
4 import com.xfestudio.mydimension.world.block.entity.MindPortalBlockEntity;
5 import net.minecraft.world.level.block.entity.BlockEntityType;
6 import net.minecraftforge.eventbus.api.IEventBus;
7 import net.minecraftforge.registries.DeferredRegister;
8 import net.minecraftforge.registries.ForgeRegistries;
9 import net.minecraftforge.registries.RegistryObject;
10
11 public final class ModBlockEntities {
12 public static final DeferredRegister<BlockEntityType<?>> BLOCK_ENTITIES =
13 DeferredRegister.create(ForgeRegistries.BLOCK_ENTITY_TYPES, MyDimension.MOD_ID);
14
15 public static final RegistryObject<BlockEntityType<MindPortalBlockEntity>> MIND_PORTAL = BLOCK_ENTITIES.register(
16 "mind_portal",
17 () -> BlockEntityType.Builder.of(MindPortalBlockEntity::new, ModBlocks.MIND_PORTAL.get()).build(null)
18 );
19
20 private ModBlockEntities() {
21 }
22
23 public static void register(IEventBus eventBus) {
24 BLOCK_ENTITIES.register(eventBus);
25 }
26 }
Added src/main/java/com/xfestudio/mydimension/registry/ModBlocks.java +37 -0
@@ -0,0 +1,37 @@
1 package com.xfestudio.mydimension.registry;
2
3 import com.xfestudio.mydimension.MyDimension;
4 import com.xfestudio.mydimension.world.block.MindPortalBlock;
5 import com.xfestudio.mydimension.world.block.MindPortalFrameBlock;
6 import net.minecraft.world.level.block.Block;
7 import net.minecraft.world.level.block.Blocks;
8 import net.minecraft.world.level.block.SoundType;
9 import net.minecraft.world.level.block.state.BlockBehaviour;
10 import net.minecraftforge.eventbus.api.IEventBus;
11 import net.minecraftforge.registries.DeferredRegister;
12 import net.minecraftforge.registries.ForgeRegistries;
13 import net.minecraftforge.registries.RegistryObject;
14
15 public final class ModBlocks {
16 public static final DeferredRegister<Block> BLOCKS = DeferredRegister.create(ForgeRegistries.BLOCKS, MyDimension.MOD_ID);
17
18 public static final RegistryObject<Block> MIND_PORTAL_FRAME = BLOCKS.register("mind_portal_frame",
19 () -> new MindPortalFrameBlock(BlockBehaviour.Properties.copy(Blocks.CRYING_OBSIDIAN)
20 .strength(25.0F, 1200.0F)
21 .lightLevel(state -> 7)));
22
23 public static final RegistryObject<Block> MIND_PORTAL = BLOCKS.register("mind_portal",
24 () -> new MindPortalBlock(BlockBehaviour.Properties.of()
25 .noCollission()
26 .noOcclusion()
27 .strength(-1.0F, 3600000.0F)
28 .lightLevel(state -> 12)
29 .sound(SoundType.GLASS)));
30
31 private ModBlocks() {
32 }
33
34 public static void register(IEventBus eventBus) {
35 BLOCKS.register(eventBus);
36 }
37 }
Modified src/main/java/com/xfestudio/mydimension/registry/ModItems.java +6 -0
@@ -4,6 +4,7 @@ import com.xfestudio.mydimension.MyDimension;
4 4 import com.xfestudio.mydimension.item.RiftItem;
5 5 import net.minecraft.world.item.CreativeModeTabs;
6 6 import net.minecraft.world.item.Item;
7 import net.minecraft.world.item.BlockItem;
7 8 import net.minecraftforge.event.BuildCreativeModeTabContentsEvent;
8 9 import net.minecraftforge.eventbus.api.IEventBus;
9 10 import net.minecraftforge.registries.DeferredRegister;
@@ -14,6 +15,8 @@ public class ModItems {
14 15 public static final DeferredRegister<Item> ITEMS = DeferredRegister.create(ForgeRegistries.ITEMS, MyDimension.MOD_ID);
15 16
16 17 public static final RegistryObject<Item> RIFT = ITEMS.register("rift", () -> new RiftItem(new Item.Properties().stacksTo(1)));
18 public static final RegistryObject<Item> MIND_PORTAL_FRAME = ITEMS.register("mind_portal_frame",
19 () -> new BlockItem(ModBlocks.MIND_PORTAL_FRAME.get(), new Item.Properties()));
17 20
18 21 public static void register(IEventBus eventBus) {
19 22 ITEMS.register(eventBus);
@@ -23,5 +26,8 @@ public class ModItems {
23 26 if (event.getTabKey() == CreativeModeTabs.TOOLS_AND_UTILITIES) {
24 27 event.accept(RIFT);
25 28 }
29 if (event.getTabKey() == CreativeModeTabs.BUILDING_BLOCKS) {
30 event.accept(MIND_PORTAL_FRAME);
31 }
26 32 }
27 33 }
Modified src/main/java/com/xfestudio/mydimension/world/MindType.java +9 -0
@@ -26,4 +26,13 @@ public enum MindType {
26 26 public Component displayName() {
27 27 return Component.translatable(translationKey);
28 28 }
29
30 public static MindType fromBaseDimension(ResourceKey<Level> dimension) {
31 for (MindType type : values()) {
32 if (type.baseDimension.equals(dimension)) {
33 return type;
34 }
35 }
36 return null;
37 }
29 38 }
Added src/main/java/com/xfestudio/mydimension/world/block/MindPortalBlock.java +85 -0
@@ -0,0 +1,85 @@
1 package com.xfestudio.mydimension.world.block;
2
3 import com.xfestudio.mydimension.world.block.entity.MindPortalBlockEntity;
4 import com.xfestudio.mydimension.world.portal.MindPortalManager;
5 import net.minecraft.core.BlockPos;
6 import net.minecraft.core.Direction;
7 import net.minecraft.core.particles.ParticleTypes;
8 import net.minecraft.server.level.ServerPlayer;
9 import net.minecraft.sounds.SoundEvents;
10 import net.minecraft.sounds.SoundSource;
11 import net.minecraft.util.RandomSource;
12 import net.minecraft.world.entity.Entity;
13 import net.minecraft.world.level.BlockGetter;
14 import net.minecraft.world.level.Level;
15 import net.minecraft.world.level.block.BaseEntityBlock;
16 import net.minecraft.world.level.block.RenderShape;
17 import net.minecraft.world.level.block.entity.BlockEntity;
18 import net.minecraft.world.level.block.state.BlockState;
19 import net.minecraft.world.level.block.state.StateDefinition;
20 import net.minecraft.world.level.block.state.properties.BlockStateProperties;
21 import net.minecraft.world.level.block.state.properties.BooleanProperty;
22 import net.minecraft.world.level.block.state.properties.EnumProperty;
23 import net.minecraft.world.phys.shapes.CollisionContext;
24 import net.minecraft.world.phys.shapes.Shapes;
25 import net.minecraft.world.phys.shapes.VoxelShape;
26 import org.jetbrains.annotations.Nullable;
27
28 public class MindPortalBlock extends BaseEntityBlock {
29 public static final EnumProperty<Direction.Axis> AXIS = BlockStateProperties.HORIZONTAL_AXIS;
30 public static final BooleanProperty CORE = BooleanProperty.create("core");
31
32 public MindPortalBlock(Properties properties) {
33 super(properties);
34 registerDefaultState(stateDefinition.any().setValue(AXIS, Direction.Axis.X).setValue(CORE, false));
35 }
36
37 @Override
38 protected void createBlockStateDefinition(StateDefinition.Builder<net.minecraft.world.level.block.Block, BlockState> builder) {
39 builder.add(AXIS, CORE);
40 }
41
42 @Override
43 public RenderShape getRenderShape(BlockState state) {
44 return RenderShape.INVISIBLE;
45 }
46
47 @Override
48 public VoxelShape getShape(BlockState state, BlockGetter level, BlockPos pos, CollisionContext context) {
49 return Shapes.empty();
50 }
51
52 @Override
53 public void entityInside(BlockState state, Level level, BlockPos pos, Entity entity) {
54 if (!level.isClientSide() && entity instanceof ServerPlayer player) {
55 MindPortalManager.touchPortal(player, pos, state.getValue(AXIS));
56 }
57 }
58
59 @Override
60 public void animateTick(BlockState state, Level level, BlockPos pos, RandomSource random) {
61 if (random.nextInt(36) == 0) {
62 level.playLocalSound(pos.getX() + 0.5D, pos.getY() + 0.5D, pos.getZ() + 0.5D,
63 SoundEvents.PORTAL_AMBIENT, SoundSource.BLOCKS, 0.35F, 0.8F + random.nextFloat() * 0.4F, false);
64 }
65
66 for (int i = 0; i < 2; i++) {
67 double x = pos.getX() + random.nextDouble();
68 double y = pos.getY() + random.nextDouble();
69 double z = pos.getZ() + random.nextDouble();
70 double normalSpeed = (random.nextDouble() - 0.5D) * 0.12D;
71 double verticalSpeed = (random.nextDouble() - 0.5D) * 0.04D;
72 if (state.getValue(AXIS) == Direction.Axis.X) {
73 level.addParticle(ParticleTypes.REVERSE_PORTAL, x, y, z, 0.0D, verticalSpeed, normalSpeed);
74 } else {
75 level.addParticle(ParticleTypes.REVERSE_PORTAL, x, y, z, normalSpeed, verticalSpeed, 0.0D);
76 }
77 }
78 }
79
80 @Nullable
81 @Override
82 public BlockEntity newBlockEntity(BlockPos pos, BlockState state) {
83 return new MindPortalBlockEntity(pos, state);
84 }
85 }
Added src/main/java/com/xfestudio/mydimension/world/block/MindPortalFrameBlock.java +22 -0
@@ -0,0 +1,22 @@
1 package com.xfestudio.mydimension.world.block;
2
3 import com.xfestudio.mydimension.world.portal.MindPortalManager;
4 import net.minecraft.core.BlockPos;
5 import net.minecraft.world.entity.player.Player;
6 import net.minecraft.world.level.Level;
7 import net.minecraft.world.level.block.Block;
8 import net.minecraft.world.level.block.state.BlockState;
9
10 public class MindPortalFrameBlock extends Block {
11 public MindPortalFrameBlock(Properties properties) {
12 super(properties);
13 }
14
15 @Override
16 public void playerWillDestroy(Level level, BlockPos pos, BlockState state, Player player) {
17 if (!level.isClientSide()) {
18 MindPortalManager.frameBroken(level, pos);
19 }
20 super.playerWillDestroy(level, pos, state, player);
21 }
22 }
Added src/main/java/com/xfestudio/mydimension/world/block/entity/MindPortalBlockEntity.java +65 -0
@@ -0,0 +1,65 @@
1 package com.xfestudio.mydimension.world.block.entity;
2
3 import com.xfestudio.mydimension.registry.ModBlockEntities;
4 import net.minecraft.core.BlockPos;
5 import net.minecraft.nbt.CompoundTag;
6 import net.minecraft.network.protocol.game.ClientboundBlockEntityDataPacket;
7 import net.minecraft.world.level.block.entity.BlockEntity;
8 import net.minecraft.world.level.block.state.BlockState;
9
10 import java.util.UUID;
11
12 public class MindPortalBlockEntity extends BlockEntity {
13 private static final String LINK_ID_TAG = "LinkId";
14 private static final String SOURCE_SIDE_TAG = "SourceSide";
15
16 private UUID linkId;
17 private boolean sourceSide;
18
19 public MindPortalBlockEntity(BlockPos pos, BlockState state) {
20 super(ModBlockEntities.MIND_PORTAL.get(), pos, state);
21 }
22
23 public void configure(UUID linkId, boolean sourceSide) {
24 this.linkId = linkId;
25 this.sourceSide = sourceSide;
26 setChanged();
27 if (level != null) {
28 level.sendBlockUpdated(worldPosition, getBlockState(), getBlockState(), 3);
29 }
30 }
31
32 public UUID linkId() {
33 return linkId;
34 }
35
36 public boolean sourceSide() {
37 return sourceSide;
38 }
39
40 @Override
41 protected void saveAdditional(CompoundTag tag) {
42 super.saveAdditional(tag);
43 if (linkId != null) {
44 tag.putUUID(LINK_ID_TAG, linkId);
45 }
46 tag.putBoolean(SOURCE_SIDE_TAG, sourceSide);
47 }
48
49 @Override
50 public void load(CompoundTag tag) {
51 super.load(tag);
52 linkId = tag.hasUUID(LINK_ID_TAG) ? tag.getUUID(LINK_ID_TAG) : null;
53 sourceSide = tag.getBoolean(SOURCE_SIDE_TAG);
54 }
55
56 @Override
57 public CompoundTag getUpdateTag() {
58 return saveWithoutMetadata();
59 }
60
61 @Override
62 public ClientboundBlockEntityDataPacket getUpdatePacket() {
63 return ClientboundBlockEntityDataPacket.create(this);
64 }
65 }
Added src/main/resources/assets/mydimension/blockstates/mind_portal.json +8 -0
Added src/main/resources/assets/mydimension/blockstates/mind_portal_frame.json +7 -0
Modified src/main/resources/assets/mydimension/lang/en_us.json +12 -1
Modified src/main/resources/assets/mydimension/lang/zh_cn.json +11 -0
Added src/main/resources/assets/mydimension/models/block/mind_portal.json +7 -0
Added src/main/resources/assets/mydimension/models/block/mind_portal_frame.json +63 -0
Added src/main/resources/assets/mydimension/models/item/mind_portal_frame.json +3 -0
Added src/main/resources/data/mydimension/advancements/recipes/building_blocks/mind_portal_frame.json +38 -0
Added src/main/resources/data/mydimension/loot_tables/blocks/mind_portal_frame.json +19 -0
Added src/main/resources/data/mydimension/recipes/mind_portal_frame.json +25 -0