Search in sources :

Example 1 with ChunkPipeline

use of org.spongepowered.common.event.tracking.context.transaction.pipeline.ChunkPipeline in project SpongeCommon by SpongePowered.

the class LevelChunkMixin_Tracker method bridge$createChunkPipeline.

/**
 * Technically a full overwrite for {@link LevelChunk#setBlockState(BlockPos, BlockState, boolean)}
 * and due to Sponge's hijacking of {@link ServerLevel#setBlock(BlockPos, BlockState, int)},
 * it needs to be able to record transactions when necessary. This implementation allows for us to
 * further specify the types of transactions and what proxies are needing to set up where.
 *
 * @param pos The position changing
 * @param newState The new state
 * @param currentState The current state - passed in from either chunk or world
 * @param flag The sponge change flag, converted from an int to a proper struct
 * @return The changed block state if not null
 * @author gabizou - January 13th, 2020 - Minecraft 1.14.3
 */
@Override
@NonNull
public ChunkPipeline bridge$createChunkPipeline(final BlockPos pos, final BlockState newState, final BlockState currentState, final SpongeBlockChangeFlag flag, final int limit) {
    final boolean isFake = ((LevelBridge) this.level).bridge$isFake();
    if (isFake) {
        throw new IllegalStateException("Cannot call ChunkBridge.bridge$buildChunkPipeline in non-Server managed worlds");
    }
    // int i = pos.getX() & 15;
    final int xPos = pos.getX() & 15;
    // int j = pos.getY();
    final int yPos = pos.getY();
    // int k = pos.getZ() & 15;
    final int zPos = pos.getZ() & 15;
    // Sponge - get the moving flag from our flag construct
    LevelChunkSection chunksection = this.sections[yPos >> 4];
    if (chunksection == LevelChunkMixin_Tracker.EMPTY_SECTION) {
        if (newState.isAir()) {
            return ChunkPipeline.nullReturn((LevelChunk) (Object) this, (ServerLevel) this.level);
        }
        chunksection = new LevelChunkSection(yPos >> 4 << 4);
        this.sections[yPos >> 4] = chunksection;
    }
    // Sponge Start - Build out the BlockTransaction
    final PhaseContext<@NonNull ?> context = PhaseTracker.getInstance().getPhaseContext();
    @Nullable final BlockEntity existing = this.shadow$getBlockEntity(pos, LevelChunk.EntityCreationType.CHECK);
    // Build a transaction maybe?
    final WeakReference<ServerLevel> ref = new WeakReference<>((ServerLevel) this.level);
    final SpongeBlockSnapshot snapshot = TrackingUtil.createPooledSnapshot(currentState, pos, flag, limit, existing, () -> Objects.requireNonNull(ref.get(), "ServerWorld dereferenced"), Optional::empty, Optional::empty);
    // Pulled up from below
    final ChangeBlock transaction = context.createTransaction(snapshot, newState, flag);
    snapshot.blockChange = context.associateBlockChangeWithSnapshot(newState, currentState);
    if (((BlockStateBridge) snapshot.state()).bridge$hasTileEntity() && (snapshot.blockChange == BlockChange.BREAK || snapshot.blockChange == BlockChange.MODIFY)) {
        transaction.queuedRemoval = existing;
    }
    final ChunkPipeline.Builder builder = ChunkPipeline.builder().kickOff(transaction).chunk((LevelChunk) (Object) this).chunkSection(chunksection).world((ServerLevel) this.level);
    // Populate the effects
    transaction.populateChunkEffects(builder);
    return builder.build();
}
Also used : ServerLevel(net.minecraft.server.level.ServerLevel) Optional(java.util.Optional) ChangeBlock(org.spongepowered.common.event.tracking.context.transaction.block.ChangeBlock) SpongeBlockSnapshot(org.spongepowered.common.block.SpongeBlockSnapshot) LevelBridge(org.spongepowered.common.bridge.world.level.LevelBridge) LevelChunkSection(net.minecraft.world.level.chunk.LevelChunkSection) WeakReference(java.lang.ref.WeakReference) Nullable(org.checkerframework.checker.nullness.qual.Nullable) ChunkPipeline(org.spongepowered.common.event.tracking.context.transaction.pipeline.ChunkPipeline) BlockEntity(net.minecraft.world.level.block.entity.BlockEntity) MonotonicNonNull(org.checkerframework.checker.nullness.qual.MonotonicNonNull) NonNull(org.checkerframework.checker.nullness.qual.NonNull)

Example 2 with ChunkPipeline

use of org.spongepowered.common.event.tracking.context.transaction.pipeline.ChunkPipeline in project SpongeCommon by SpongePowered.

the class ServerLevelMixin_Tracker method bridge$makePipeline.

private WorldPipeline.Builder bridge$makePipeline(final BlockPos pos, final BlockState currentState, final BlockState newState, final LevelChunk chunk, final SpongeBlockChangeFlag spongeFlag, final int limit) {
    final TrackedLevelChunkBridge mixinChunk = (TrackedLevelChunkBridge) chunk;
    // Then build and use the BlockPipeline
    final ChunkPipeline chunkPipeline = mixinChunk.bridge$createChunkPipeline(pos, newState, currentState, spongeFlag, limit);
    final WorldPipeline.Builder worldPipelineBuilder = WorldPipeline.builder(chunkPipeline);
    worldPipelineBuilder.addEffect((pipeline, oldState, newState1, flag1, cursorLimit) -> {
        if (oldState == null) {
            return EffectResult.NULL_RETURN;
        }
        return EffectResult.NULL_PASS;
    }).addEffect(UpdateLightSideEffect.getInstance()).addEffect(CheckBlockPostPlacementIsSameEffect.getInstance()).addEffect(UpdateWorldRendererEffect.getInstance()).addEffect(NotifyClientEffect.getInstance()).addEffect(NotifyNeighborSideEffect.getInstance()).addEffect(UpdateConnectingBlocksEffect.getInstance());
    return worldPipelineBuilder;
}
Also used : TrackedLevelChunkBridge(org.spongepowered.common.bridge.world.level.chunk.TrackedLevelChunkBridge) WorldPipeline(org.spongepowered.common.event.tracking.context.transaction.pipeline.WorldPipeline) ChunkPipeline(org.spongepowered.common.event.tracking.context.transaction.pipeline.ChunkPipeline)

Aggregations

ChunkPipeline (org.spongepowered.common.event.tracking.context.transaction.pipeline.ChunkPipeline)2 WeakReference (java.lang.ref.WeakReference)1 Optional (java.util.Optional)1 ServerLevel (net.minecraft.server.level.ServerLevel)1 BlockEntity (net.minecraft.world.level.block.entity.BlockEntity)1 LevelChunkSection (net.minecraft.world.level.chunk.LevelChunkSection)1 MonotonicNonNull (org.checkerframework.checker.nullness.qual.MonotonicNonNull)1 NonNull (org.checkerframework.checker.nullness.qual.NonNull)1 Nullable (org.checkerframework.checker.nullness.qual.Nullable)1 SpongeBlockSnapshot (org.spongepowered.common.block.SpongeBlockSnapshot)1 LevelBridge (org.spongepowered.common.bridge.world.level.LevelBridge)1 TrackedLevelChunkBridge (org.spongepowered.common.bridge.world.level.chunk.TrackedLevelChunkBridge)1 ChangeBlock (org.spongepowered.common.event.tracking.context.transaction.block.ChangeBlock)1 WorldPipeline (org.spongepowered.common.event.tracking.context.transaction.pipeline.WorldPipeline)1