use of org.spongepowered.common.world.server.SpongeLocatableBlockBuilder in project SpongeCommon by SpongePowered.
the class TrackingUtil method randomTickBlock.
@SuppressWarnings("rawtypes")
public static void randomTickBlock(final TrackedWorldBridge mixinWorld, final net.minecraft.world.level.block.state.BlockState state, final BlockPos pos, final Random random) {
final ServerLevel world = (ServerLevel) mixinWorld;
final org.spongepowered.api.world.server.ServerWorld apiWorld = (org.spongepowered.api.world.server.ServerWorld) world;
if (ShouldFire.TICK_BLOCK_EVENT) {
final BlockSnapshot currentTickBlock = mixinWorld.bridge$createSnapshot(state, pos, BlockChangeFlags.NONE);
final TickBlockEvent event = SpongeEventFactory.createTickBlockEventRandom(PhaseTracker.getCauseStackManager().currentCause(), currentTickBlock);
SpongeCommon.post(event);
if (event.isCancelled()) {
return;
}
}
final LocatableBlock locatable = new SpongeLocatableBlockBuilder().world(apiWorld).position(pos.getX(), pos.getY(), pos.getZ()).state((BlockState) state).build();
final BlockTickContext phaseContext = TickPhase.Tick.RANDOM_BLOCK.createPhaseContext(PhaseTracker.SERVER).source(locatable);
// We have to associate any notifiers in case of scheduled block updates from other sources
final PhaseContext<@NonNull ?> currentContext = PhaseTracker.getInstance().getPhaseContext();
currentContext.appendNotifierPreBlockTick(world, pos, phaseContext);
// Now actually switch to the new phase
try (final PhaseContext<@NonNull ?> context = phaseContext) {
context.buildAndSwitch();
PhaseTracker.LOGGER.trace(TrackingUtil.BLOCK_TICK, "Wrapping Random Block Tick: {}", state);
state.randomTick(world, pos, random);
} catch (final Exception | NoClassDefFoundError e) {
PhasePrinter.printExceptionFromPhase(PhaseTracker.getInstance().stack, e, phaseContext);
}
}
use of org.spongepowered.common.world.server.SpongeLocatableBlockBuilder in project SpongeCommon by SpongePowered.
the class TrackingUtil method updateTickBlock.
@SuppressWarnings("rawtypes")
public static void updateTickBlock(final TrackedWorldBridge mixinWorld, final net.minecraft.world.level.block.state.BlockState block, final BlockPos pos, final Random random) {
final ServerLevel world = (ServerLevel) mixinWorld;
final org.spongepowered.api.world.server.ServerWorld apiWorld = (org.spongepowered.api.world.server.ServerWorld) world;
if (ShouldFire.TICK_BLOCK_EVENT) {
final BlockSnapshot snapshot = mixinWorld.bridge$createSnapshot(block, pos, BlockChangeFlags.NONE);
final TickBlockEvent event = SpongeEventFactory.createTickBlockEventScheduled(PhaseTracker.getCauseStackManager().currentCause(), snapshot);
SpongeCommon.post(event);
if (event.isCancelled()) {
return;
}
}
final LocatableBlock locatable = new SpongeLocatableBlockBuilder().world(apiWorld).position(pos.getX(), pos.getY(), pos.getZ()).state((BlockState) block).build();
final BlockTickContext phaseContext = TickPhase.Tick.BLOCK.createPhaseContext(PhaseTracker.SERVER).source(locatable);
// We have to associate any notifiers in case of scheduled block updates from other sources
final PhaseContext<@NonNull ?> currentContext = PhaseTracker.getInstance().getPhaseContext();
currentContext.appendNotifierPreBlockTick(world, pos, phaseContext);
try (final PhaseContext<@NonNull ?> context = phaseContext;
final Timing timing = ((TimingBridge) block.getBlock()).bridge$timings()) {
timing.startTiming();
context.buildAndSwitch();
PhaseTracker.LOGGER.trace(TrackingUtil.BLOCK_TICK, () -> "Wrapping Block Tick: " + block.toString());
block.tick(world, pos, random);
} catch (final Exception | NoClassDefFoundError e) {
PhasePrinter.printExceptionFromPhase(PhaseTracker.getInstance().stack, e, phaseContext);
}
}
use of org.spongepowered.common.world.server.SpongeLocatableBlockBuilder in project SpongeCommon by SpongePowered.
the class BlockEntityMixin_API method locatableBlock.
@Override
public LocatableBlock locatableBlock() {
if (this.api$LocatableBlock == null) {
final BlockState blockState = this.block();
this.api$LocatableBlock = new SpongeLocatableBlockBuilder().world((ServerWorld) this.level).position(this.shadow$getBlockPos().getX(), this.shadow$getBlockPos().getY(), this.shadow$getBlockPos().getZ()).state(blockState).build();
}
return this.api$LocatableBlock;
}
use of org.spongepowered.common.world.server.SpongeLocatableBlockBuilder in project SpongeCommon by SpongePowered.
the class LeavesBlockMixin_Tracker method randomTick.
/**
* @author gabizou - February 6th, 2020 - Minecraft 1.14.3
* @reason Rewrite to handle both drops and the change state for leaves
* that are considered to be decaying, so the drops do not leak into
* whatever previous phase is being handled in. Since the issue is that
* the block change takes place in a different phase (more than likely),
* the drops are either "lost" or not considered for drops because the
* blocks didn't change according to whatever previous phase.
*
* @param worldIn The world in
* @param pos The position
*/
@Overwrite
public void randomTick(final net.minecraft.world.level.block.state.BlockState state, final net.minecraft.server.level.ServerLevel worldIn, final BlockPos pos, final Random random) {
if (!state.getValue(LeavesBlockMixin_Tracker.PERSISTENT) && state.getValue(LeavesBlockMixin_Tracker.DISTANCE) == 7) {
// Sponge Start - PhaseTracker checks and phase entry
if (!((LevelBridge) worldIn).bridge$isFake()) {
try (final PhaseContext<@NonNull ?> context = BlockPhase.State.BLOCK_DECAY.createPhaseContext(PhaseTracker.SERVER).source(new SpongeLocatableBlockBuilder().world((ServerWorld) worldIn).position(pos.getX(), pos.getY(), pos.getZ()).state((BlockState) state).build())) {
context.buildAndSwitch();
Block.dropResources(state, worldIn, pos);
worldIn.removeBlock(pos, false);
}
return;
}
// Sponge End
Block.dropResources(state, worldIn, pos);
worldIn.removeBlock(pos, false);
}
}
use of org.spongepowered.common.world.server.SpongeLocatableBlockBuilder in project SpongeCommon by SpongePowered.
the class SpongeCommonEventFactory method handlePistonEvent.
/**
* This simulates the blocks a piston moves and calls the event for saner
* debugging.
*
* @return if the event was cancelled
*/
public static boolean handlePistonEvent(final TrackedWorldBridge world, final BlockPos pos, final net.minecraft.world.level.block.state.BlockState blockstate, final int eventId) {
final boolean extending = (eventId == 0);
final net.minecraft.core.Direction direction = blockstate.getValue(DirectionalBlock.FACING);
final LocatableBlock locatable = new SpongeLocatableBlockBuilder().world((ServerWorld) world).state((BlockState) blockstate).position(pos.getX(), pos.getY(), pos.getZ()).build();
// Sets toss out duplicate values (even though there shouldn't be any)
final HashSet<ServerLocation> locations = new HashSet<>();
locations.add(ServerLocation.of((ServerWorld) world, pos.getX(), pos.getY(), pos.getZ()));
final PistonStructureResolver movedBlocks = new PistonStructureResolver((ServerLevel) world, pos, direction, extending);
// calculates blocks to be moved
movedBlocks.resolve();
Stream.concat(movedBlocks.getToPush().stream(), movedBlocks.getToDestroy().stream()).map(block -> ServerLocation.of((ServerWorld) world, block.getX(), block.getY(), block.getZ())).collect(// SUPER
Collectors.toCollection(() -> locations));
// If the piston is extending and there are no blocks to destroy, add the offset location for protection purposes
if (extending && movedBlocks.getToDestroy().isEmpty()) {
final List<BlockPos> movedPositions = movedBlocks.getToPush();
final BlockPos offsetPos;
// If there are no blocks to move, add the offset of piston
if (movedPositions.isEmpty()) {
offsetPos = pos.relative(direction);
} else {
// Add the offset of last block set to move
offsetPos = movedPositions.get(movedPositions.size() - 1).relative(direction);
}
locations.add(ServerLocation.of((ServerWorld) world, offsetPos.getX(), offsetPos.getY(), offsetPos.getZ()));
}
try (final CauseStackManager.StackFrame frame = PhaseTracker.getInstance().pushCauseFrame()) {
if (extending) {
frame.addContext(EventContextKeys.PISTON_EXTEND, (ServerWorld) world);
} else {
frame.addContext(EventContextKeys.PISTON_RETRACT, (ServerWorld) world);
}
return SpongeCommonEventFactory.callChangeBlockEventPre((ServerLevelBridge) world, ImmutableList.copyOf(locations), locatable).isCancelled();
}
}
Aggregations