Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Acceleration ring 加速环 #1526

Merged
merged 6 commits into from
Jan 24, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions src/generated/resources/assets/anvilcraft/lang/en_ud.json
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
"advancements.anvilcraft.crab_claw.title": "ǝɔɐɹ uoıʇɔǝɹɹnsǝɹ ǝɥʇ ɟo ɟןɐɥ uıM",
"advancements.anvilcraft.root.description": "ɔıbɐɯ puɐ ʎboןouɥɔǝʇ ɟo pןɹoʍ ǝɥʇ ɹǝʇuǝ puɐ 'ɐןןıuɐʌ ǝɥʇ ɯoɹɟ ʇɹɐʇs 'ןıʌuɐ ǝɥʇ dn ʞɔıԀ",
"advancements.anvilcraft.root.title": "ʇɟɐɹƆןıʌuⱯ oʇ ǝɯoɔןǝM",
"block.anvilcraft.acceleration_ring": "buıᴚ uoıʇɐɹǝןǝɔɔⱯ",
"block.anvilcraft.active_silencer": "ɹǝɔuǝןıS ǝʌıʇɔⱯ",
"block.anvilcraft.amber_block": "ʞɔoןᗺ ɹǝqɯⱯ",
"block.anvilcraft.arrow": "ʍoɹɹⱯ",
Expand Down
1 change: 1 addition & 0 deletions src/generated/resources/assets/anvilcraft/lang/en_us.json
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
"advancements.anvilcraft.crab_claw.title": "Win half of the resurrection race",
"advancements.anvilcraft.root.description": "Pick up the anvil, start from the vanilla, and enter the world of technology and magic",
"advancements.anvilcraft.root.title": "Welcome to AnvilCraft",
"block.anvilcraft.acceleration_ring": "Acceleration Ring",
"block.anvilcraft.active_silencer": "Active Silencer",
"block.anvilcraft.amber_block": "Amber Block",
"block.anvilcraft.arrow": "Arrow",
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
{
"parent": "anvilcraft:block/acceleration_ring"
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
{
"parent": "minecraft:recipes/root",
"criteria": {
"has_the_recipe": {
"conditions": {
"recipe": "anvilcraft:multiblock/acceleration_ring"
},
"trigger": "minecraft:recipe_unlocked"
}
},
"requirements": [
[
"has_the_recipe"
]
],
"rewards": {
"recipes": [
"anvilcraft:multiblock/acceleration_ring"
]
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
{
"type": "minecraft:block",
"pools": [
{
"bonus_rolls": 0.0,
"conditions": [
{
"condition": "minecraft:survives_explosion"
}
],
"entries": [
{
"type": "minecraft:item",
"conditions": [
{
"block": "anvilcraft:acceleration_ring",
"condition": "minecraft:block_state_property",
"properties": {
"half": "mid_center"
}
}
],
"name": "anvilcraft:acceleration_ring"
}
],
"rolls": 1.0
}
],
"random_sequence": "anvilcraft:blocks/acceleration_ring"
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
{
"type": "anvilcraft:multiblock",
"pattern": {
"layers": [
[
"ABA",
"B B",
"ABA"
],
[
"CDC",
"D D",
"CDC"
],
[
"ABA",
"B B",
"ABA"
]
],
"symbols": {
"A": {
"block": "minecraft:copper_block"
},
"B": {
"block": "anvilcraft:heavy_iron_block"
},
"C": {
"block": "anvilcraft:magnetoelectric_core"
},
"D": {
"block": "anvilcraft:tungsten_block"
}
}
},
"result": {
"count": 1,
"id": "anvilcraft:acceleration_ring"
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,7 @@
"anvilcraft:simple_chute",
"anvilcraft:sliding_rail",
"anvilcraft:sliding_rail_stop",
"anvilcraft:acceleration_ring",
"anvilcraft:magnetoelectric_core",
"anvilcraft:royal_steel_block",
"anvilcraft:smooth_royal_steel_block",
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,206 @@
package dev.dubhe.anvilcraft.block;

import dev.dubhe.anvilcraft.block.state.IStateAddableMultiplePartBlockState;
import dev.dubhe.anvilcraft.util.Util;
import net.minecraft.core.BlockPos;
import net.minecraft.core.Direction;
import net.minecraft.core.Vec3i;
import net.minecraft.data.loot.BlockLootSubProvider;
import net.minecraft.world.InteractionHand;
import net.minecraft.world.InteractionResult;
import net.minecraft.world.ItemInteractionResult;
import net.minecraft.world.entity.LivingEntity;
import net.minecraft.world.entity.player.Player;
import net.minecraft.world.item.ItemStack;
import net.minecraft.world.item.context.BlockPlaceContext;
import net.minecraft.world.level.Level;
import net.minecraft.world.level.LevelAccessor;
import net.minecraft.world.level.LevelReader;
import net.minecraft.world.level.block.Block;
import net.minecraft.world.level.block.Blocks;
import net.minecraft.world.level.block.state.BlockState;
import net.minecraft.world.level.block.state.StateDefinition;
import net.minecraft.world.level.block.state.properties.Property;
import net.minecraft.world.phys.BlockHitResult;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;

import java.util.Arrays;

public abstract class AbstractStateAddableMultiplePartBlock<P extends Enum<P> & IStateAddableMultiplePartBlockState<P, E>, T extends Property<E>, E extends Comparable<E>> extends Block {
final P mainPart;

public AbstractStateAddableMultiplePartBlock(Properties properties) {
super(properties);
this.mainPart = Arrays.stream(getParts()).filter(IStateAddableMultiplePartBlockState::isMain).findFirst().orElse(null);
}

public abstract Property<P> getPart();

public abstract P[] getParts();

public abstract T getAdditionalProperty();

public <J extends Property<H>, H extends Comparable<H>> void updateState(Level level, BlockPos pos, J property, H value, int flag) {
BlockState state = level.getBlockState(pos);
E additionalPropertyValue = state.getValue(getAdditionalProperty());
Vec3i origin = pos.subtract(state.getValue(getPart()).getOffset(additionalPropertyValue));
for (P part : getParts()) {
Vec3i offset = origin.offset(part.getOffset(additionalPropertyValue));
level.setBlock(new BlockPos(offset), state.setValue(getPart(), part).setValue(property, value), flag);
}
}

@Override
protected void createBlockStateDefinition(StateDefinition.Builder<Block, BlockState> builder) {
builder.add(getPart(), getAdditionalProperty());
}

@Override
public void setPlacedBy(
@NotNull Level level,
@NotNull BlockPos pos,
BlockState state,
@Nullable LivingEntity placer,
@NotNull ItemStack stack
) {
if (!state.hasProperty(this.getPart())) return;
for (P part : this.getParts()) {
BlockPos blockPos = pos.offset(part.getOffset(state.getValue(getAdditionalProperty())));
BlockState newState = placedState(part, state);
level.setBlockAndUpdate(blockPos, newState);
}
}

protected BlockState placedState(P part, BlockState state) {
return state.setValue(this.getPart(), part);
}

@Override
public @NotNull BlockState updateShape(
BlockState state,
@NotNull Direction direction,
@NotNull BlockState neighborState,
@NotNull LevelAccessor level,
@NotNull BlockPos pos,
@NotNull BlockPos neighborPos) {
if (!state.hasProperty(this.getPart())) {
return super.updateShape(state, direction, neighborState, level, pos, neighborPos);
}
IStateAddableMultiplePartBlockState<P, E> state1 = state.getValue(this.getPart());
for (P part : getParts()) {
Vec3i offset = neighborPos.subtract(pos).offset(state1.getOffset(state.getValue(getAdditionalProperty()))); // 更新来源偏移值
if (offset.distSqr(part.getOffset(state.getValue(getAdditionalProperty()))) != 0) continue;
if (!neighborState.is(this)
|| !neighborState.hasProperty(this.getPart())
|| neighborState.getValue(this.getPart()) != part) {
return Blocks.AIR.defaultBlockState();
}
}
return super.updateShape(state, direction, neighborState, level, pos, neighborPos);
}

@Override
public @NotNull BlockState playerWillDestroy(
Level level,
@NotNull BlockPos pos,
@NotNull BlockState state,
@NotNull Player player
) {
if (!level.isClientSide && player.isCreative()) {
this.preventCreativeDropFromMainPart(level, pos, state, player);
}
return super.playerWillDestroy(level, pos, state, player);
}

private void preventCreativeDropFromMainPart(
Level level,
BlockPos pos,
BlockState state,
Player player
) {
if (!state.is(this)) return;
if (!state.hasProperty(this.getPart())) return;
P value = state.getValue(this.getPart());
if (value.isMain()) return;
BlockPos mainPartPos = pos.subtract(value.getOffset(state.getValue(getAdditionalProperty()))).offset(mainPart.getOffset(state.getValue(getAdditionalProperty())));
BlockState mainPartState = level.getBlockState(mainPartPos);
if (!mainPartState.is(this)) return;
if (!mainPartState.hasProperty(this.getPart())) return;
BlockState blockState2 = mainPartState.getFluidState().createLegacyBlock();
level.setBlock(mainPartPos, blockState2, 35);
level.levelEvent(player, 2001, mainPartPos, Block.getId(mainPartState));
}

/**
* 获取多方块战利品表
*
* @param provider 提供器
* @param block 方块
*/
public static <P extends Enum<P> & IStateAddableMultiplePartBlockState<P, E>, T extends Property<E>, E extends Comparable<E>> void loot(
BlockLootSubProvider provider, AbstractStateAddableMultiplePartBlock<P, T, E> block
) {
for (P part : block.getParts()) {
if (part.isMain()) {
provider.add(block, provider.createSinglePropConditionTable(block, block.getPart(), part));
break;
}
}
}

@Nullable
public BlockState getPlacementState(BlockPlaceContext context) {
return super.getStateForPlacement(context);
}

/**
* 是否有足够的空间放下方块
*/
public boolean hasEnoughSpace(BlockState originState, BlockPos pos, LevelReader level) {
for (P part : getParts()) {
BlockPos pos1 = pos.offset(part.getOffset(originState.getValue(getAdditionalProperty())));
if (level.isOutsideBuildHeight(pos1)) return false;
BlockState state = level.getBlockState(pos1);
if (!state.isAir() && !state.canBeReplaced()) {
return false;
}
}
return true;
}

@Override
protected @NotNull ItemInteractionResult useItemOn(
@NotNull ItemStack pStack,
@NotNull BlockState pState,
@NotNull Level pLevel,
@NotNull BlockPos pPos,
@NotNull Player pPlayer,
@NotNull InteractionHand pHand,
@NotNull BlockHitResult pHitResult) {
return Util.interactionResultConverter().apply(this.use(pState, pLevel, pPos, pPlayer, pHand, pHitResult));
}

@Override
protected @NotNull InteractionResult useWithoutItem(
@NotNull BlockState pState,
@NotNull Level pLevel,
@NotNull BlockPos pPos,
@NotNull Player pPlayer,
@NotNull BlockHitResult pHitResult
) {
return this.use(pState, pLevel, pPos, pPlayer, InteractionHand.MAIN_HAND, pHitResult);
}

@SuppressWarnings("unused")
public InteractionResult use(
BlockState state,
Level level,
BlockPos pos,
Player player,
InteractionHand hand,
BlockHitResult hit
) {
return InteractionResult.PASS;
}
}
Loading
Loading