Skip to content

Commit

Permalink
chore: merge upstream changes
Browse files Browse the repository at this point in the history
Signed-off-by: Gabriel Harris-Rouquette <[email protected]>
  • Loading branch information
gabizou committed Sep 28, 2024
2 parents 668afe2 + 02f45e8 commit 3b268bc
Show file tree
Hide file tree
Showing 10 changed files with 109 additions and 120 deletions.
2 changes: 1 addition & 1 deletion SpongeAPI
Original file line number Diff line number Diff line change
Expand Up @@ -24,8 +24,14 @@
*/
package org.spongepowered.forge.hook;

import net.minecraft.world.item.ItemStack;
import net.minecraft.world.item.enchantment.Enchantment;
import org.spongepowered.common.hooks.ItemHooks;

public class ForgeItemHooks implements ItemHooks {

@Override
public boolean canEnchantmentBeAppliedToItem(Enchantment enchantment, ItemStack stack) {
return stack.canApplyAtEnchantingTable(enchantment);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,6 @@
package org.spongepowered.common.accessor.world.level.chunk;

import net.minecraft.world.level.block.entity.BlockEntity;
import net.minecraft.world.level.block.entity.BlockEntityTicker;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.gen.Accessor;

Expand All @@ -34,5 +33,4 @@ public interface LevelChunk$BoundTickingBlockEntityAccessor {

@Accessor("blockEntity") BlockEntity accessor$blockEntity();

@Accessor("ticker") BlockEntityTicker accessor$ticker();
}
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,6 @@
import net.minecraft.core.component.DataComponents;
import net.minecraft.core.registries.Registries;
import net.minecraft.world.item.ItemStack;
import net.minecraft.world.item.Items;
import net.minecraft.world.item.enchantment.ItemEnchantments;
import org.spongepowered.api.data.Keys;
import org.spongepowered.api.item.enchantment.Enchantment;
Expand Down Expand Up @@ -58,8 +57,7 @@ public static void register(final DataProviderRegistrator registrator) {
.create(Keys.STORED_ENCHANTMENTS)
.get(h -> BookPagesItemStackData.get(h, DataComponents.STORED_ENCHANTMENTS))
.set((h, v) -> BookPagesItemStackData.set(h, v, Collection::stream, DataComponents.STORED_ENCHANTMENTS))
.delete(h -> BookPagesItemStackData.delete(h, DataComponents.STORED_ENCHANTMENTS))
.supports(h -> h.getItem() == Items.ENCHANTED_BOOK);
.delete(h -> BookPagesItemStackData.delete(h, DataComponents.STORED_ENCHANTMENTS));
}
// @formatter:on

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -25,8 +25,6 @@
package org.spongepowered.common.event.tracking.context.transaction.block;

import com.google.common.collect.ImmutableList;
import com.google.common.collect.LinkedListMultimap;
import com.google.common.collect.ListMultimap;
import net.minecraft.core.BlockPos;
import net.minecraft.world.level.block.state.BlockState;
import org.checkerframework.checker.nullness.qual.NonNull;
Expand All @@ -49,8 +47,8 @@
import org.spongepowered.common.event.tracking.context.transaction.world.WorldBasedTransaction;
import org.spongepowered.math.vector.Vector3i;

import java.util.ArrayList;
import java.util.List;
import java.util.HashMap;
import java.util.Map;
import java.util.Optional;

abstract class BlockEventBasedTransaction extends WorldBasedTransaction<ChangeBlockEvent.All> {
Expand All @@ -75,57 +73,41 @@ public final Optional<ChangeBlockEvent.All> generateEvent(
if (!o.isPresent()) {
return Optional.empty();
}
final ListMultimap<BlockPos, SpongeBlockSnapshot> positions = LinkedListMultimap.create();

final Map<BlockPos, BlockTransaction> eventTransactions = new HashMap<>();
for (final GameTransaction<@NonNull ?> transaction : transactions) {
final BlockEventBasedTransaction blockTransaction = (BlockEventBasedTransaction) transaction;
if (!positions.containsKey(blockTransaction.affectedPosition)) {
positions.put(
blockTransaction.affectedPosition,
blockTransaction.getOriginalSnapshot()
);
}
if (blockTransaction.getResultingSnapshot() != null) {
positions.put(
blockTransaction.affectedPosition,
blockTransaction.getResultingSnapshot()
);
if (!blockTransaction.actualBlockTransaction()) {
continue;
}
final SpongeBlockSnapshot original = blockTransaction.getOriginalSnapshot();
final SpongeBlockSnapshot result = blockTransaction.getResultingSnapshot();
final Operation operation = context.getBlockOperation(original, result);
final BlockTransaction eventTransaction = new BlockTransaction(original, result, operation);
eventTransactions.merge(blockTransaction.affectedPosition, eventTransaction, (oldValue, newValue) -> {
final ImmutableList.Builder<BlockSnapshot> intermediary = ImmutableList.builderWithExpectedSize(oldValue.intermediary().size() + 1);
intermediary.addAll(oldValue.intermediary());
intermediary.add(oldValue.finalReplacement());
final Operation mergedOperation = context.getBlockOperation((SpongeBlockSnapshot) oldValue.original(), (SpongeBlockSnapshot) newValue.finalReplacement());
return new BlockTransaction(oldValue.original(), newValue.finalReplacement(), intermediary.build(), mergedOperation);
});
}

final ImmutableList<BlockTransaction> eventTransactions = positions.asMap().values()
.stream()
.map(spongeBlockSnapshots -> {
final List<SpongeBlockSnapshot> snapshots = new ArrayList<>(spongeBlockSnapshots);
if (snapshots.isEmpty() || snapshots.size() < 2) {
// Error case
return Optional.<BlockTransaction>empty();
}
final SpongeBlockSnapshot original = snapshots.get(0);
final SpongeBlockSnapshot result = snapshots.get(snapshots.size() - 1);
final ImmutableList<BlockSnapshot> intermediary;
if (snapshots.size() > 2) {
intermediary = ImmutableList.copyOf(snapshots.subList(1, snapshots.size() - 2));
} else {
intermediary = ImmutableList.of();
}
final Operation operation = context.getBlockOperation(original, result);
final BlockTransaction eventTransaction = new BlockTransaction(original, result, intermediary, operation);
return Optional.of(eventTransaction);
})
.filter(Optional::isPresent)
.map(Optional::get)
.collect(ImmutableList.toImmutableList());

if (eventTransactions.isEmpty()) {
return Optional.empty();
}

return Optional.of(SpongeEventFactory.createChangeBlockEventAll(
currentCause,
eventTransactions,
ImmutableList.copyOf(eventTransactions.values()),
o.get()
));
}

protected boolean actualBlockTransaction() {
return true;
}

protected abstract SpongeBlockSnapshot getResultingSnapshot();

protected abstract SpongeBlockSnapshot getOriginalSnapshot();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -52,9 +52,14 @@ public PrepareBlockDropsTransaction(
this.originalState = original;
}

@Override
protected boolean actualBlockTransaction() {
return false;
}

@Override
protected SpongeBlockSnapshot getResultingSnapshot() {
return null;
throw new UnsupportedOperationException();
}

@Override
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,11 +24,8 @@
*/
package org.spongepowered.common.event.tracking.context.transaction.type;

import com.google.common.collect.ImmutableList;
import com.google.common.collect.LinkedListMultimap;
import com.google.common.collect.ListMultimap;
import com.google.common.collect.Multimap;
import net.minecraft.core.BlockPos;
import org.checkerframework.checker.nullness.qual.NonNull;
import org.spongepowered.api.ResourceKey;
import org.spongepowered.api.block.transaction.BlockTransaction;
Expand All @@ -46,7 +43,7 @@

import java.util.ArrayList;
import java.util.Collection;
import java.util.List;
import java.util.Collections;
import java.util.Optional;

public final class BlockTransactionType extends TransactionType<ChangeBlockEvent.All> {
Expand All @@ -69,49 +66,36 @@ protected void consumeEventsAndMarker(
if (!serverWorld.isPresent()) {
return;
}
final ListMultimap<BlockPos, SpongeBlockSnapshot> positions = LinkedListMultimap.create();

// Gather transactions that were valid
events.stream()
.filter(event -> !event.isCancelled())
.flatMap(event -> event.transactions().stream())
.filter(BlockTransaction::isValid)
.forEach(transactions -> {
// Then "put" the most recent transactions such that we have a complete rebuild of
// each position according to what originally existed and then
// the ultimate final block on that position
final SpongeBlockSnapshot original = (SpongeBlockSnapshot) transactions.original();
positions.put(original.getBlockPos(), original);
positions.put(original.getBlockPos(), (SpongeBlockSnapshot) transactions.finalReplacement());
});
final ArrayList<BlockTransactionReceipt> transactions = new ArrayList<>();
for (final ChangeBlockEvent.All event : events) {
if (event.isCancelled()) {
continue;
}

// Do not bother turning the positions into receipts if it's empty
// just return.
if (positions.isEmpty()) {
return;
}
final ImmutableList<BlockTransactionReceipt> transactions = positions.asMap()
.values()
.stream()
.map(spongeBlockSnapshots -> {
final List<SpongeBlockSnapshot> snapshots = new ArrayList<>(spongeBlockSnapshots);
if (snapshots.isEmpty() || snapshots.size() < 2) {
// Error case
return Optional.<BlockTransactionReceipt>empty();
transactions.ensureCapacity(event.transactions().size());
for (final BlockTransaction transaction : event.transactions()) {
if (!transaction.isValid()) {
continue;
}
final SpongeBlockSnapshot original = snapshots.get(0);
final SpongeBlockSnapshot result = snapshots.get(snapshots.size() - 1);

final SpongeBlockSnapshot original = (SpongeBlockSnapshot) transaction.original();
final SpongeBlockSnapshot result = (SpongeBlockSnapshot) transaction.finalReplacement();
final Operation operation = context.getBlockOperation(original, result);
final BlockTransactionReceipt eventTransaction = new BlockTransactionReceipt(original, result, operation);
transactions.add(eventTransaction);
context.postBlockTransactionApplication(original.blockChange, eventTransaction);
return Optional.of(eventTransaction);
})
.filter(Optional::isPresent)
.map(Optional::get)
.collect(ImmutableList.toImmutableList());
}
}

if (transactions.isEmpty()) {
return;
}

final Cause cause = PhaseTracker.getInstance().currentCause();

SpongeCommon.post(SpongeEventFactory.createChangeBlockEventPost(cause, transactions, serverWorld.get()));
SpongeCommon.post(SpongeEventFactory.createChangeBlockEventPost(cause, Collections.unmodifiableList(transactions), serverWorld.get()));
});
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -206,17 +206,7 @@ public Stream<VolumeElement<V, T>> toStream() {

@Override
public <W extends MutableVolume> void apply(final VolumeCollector<W, T, ?> collector) {
final PhaseTracker instance = PhaseTracker.getInstance();
try (final @Nullable PhaseContext<@NonNull ?> context = instance.getPhaseContext().isApplyingStreams()
? null
: PluginPhase.State.VOLUME_STREAM_APPLICATION
.createPhaseContext(instance)
.setVolumeStream(this)
.spawnType(() -> PhaseTracker.getCauseStackManager().context(EventContextKeys.SPAWN_TYPE).orElse(null))
) {
if (context != null) {
context.buildAndSwitch();
}
this.startPhase(() -> {
this.stream.forEach(element -> {
final W targetVolume = collector.target().get();
final VolumeElement<W, T> transformed = collector.positionTransform().apply(VolumeElement.of(
Expand All @@ -227,40 +217,60 @@ public <W extends MutableVolume> void apply(final VolumeCollector<W, T, ?> colle
collector.applicator()
.apply(targetVolume, transformed);
});
}
});
}

@Override
public <W extends MutableVolume, R> void applyUntil(final VolumeCollector<W, T, R> collector, final Predicate<R> predicate) {
boolean doWork = true;
for (final Iterator<VolumeElement<V, T>> iterator = this.stream.iterator(); doWork && iterator.hasNext(); ) {
final W targetVolume = collector.target().get();
final VolumeElement<V, T> element = iterator.next();
final VolumeElement<W, T> transformed = collector.positionTransform().apply(VolumeElement.of(
collector.target(),
element::type,
element.position()
));
final R apply = collector.applicator()
.apply(targetVolume, transformed);
doWork = predicate.test(apply);
}
this.startPhase(() -> {
boolean doWork = true;
for (final Iterator<VolumeElement<V, T>> iterator = this.stream.iterator(); doWork && iterator.hasNext(); ) {
final W targetVolume = collector.target().get();
final VolumeElement<V, T> element = iterator.next();
final VolumeElement<W, T> transformed = collector.positionTransform().apply(VolumeElement.of(
collector.target(),
element::type,
element.position()
));
final R apply = collector.applicator()
.apply(targetVolume, transformed);
doWork = predicate.test(apply);
}
});
}

@Override
public void forEach(final VolumeConsumer<V, T> visitor) {
this.stream.forEach(element -> visitor.consume(
element.volume(),
element.type(),
element.position().x(),
element.position().y(),
element.position().z()
));
this.startPhase(() -> {
this.stream.forEach(element -> visitor.consume(
element.volume(),
element.type(),
element.position().x(),
element.position().y(),
element.position().z()
));
});
}

@Override
public void forEach(final Consumer<VolumeElement<V, T>> consumer) {
this.stream.forEach(consumer);
}

private void startPhase(final Runnable runnable) {
final PhaseTracker instance = PhaseTracker.getInstance();
try (final @Nullable PhaseContext<@NonNull ?> context = instance.getPhaseContext().isApplyingStreams()
? null
: PluginPhase.State.VOLUME_STREAM_APPLICATION
.createPhaseContext(instance)
.setVolumeStream(this)
.spawnType(() -> PhaseTracker.getCauseStackManager().context(EventContextKeys.SPAWN_TYPE).orElse(null))
) {
if (context != null) {
context.buildAndSwitch();
}

runnable.run();
}
}
}
Loading

0 comments on commit 3b268bc

Please sign in to comment.