diff --git a/src/main/java/org/spongepowered/common/effect/particle/NumericalParticleType.java b/src/main/java/org/spongepowered/common/effect/particle/NumericalParticleType.java deleted file mode 100644 index 1e96ec973f2..00000000000 --- a/src/main/java/org/spongepowered/common/effect/particle/NumericalParticleType.java +++ /dev/null @@ -1,80 +0,0 @@ -/* - * This file is part of Sponge, licensed under the MIT License (MIT). - * - * Copyright (c) SpongePowered - * Copyright (c) contributors - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - */ -package org.spongepowered.common.effect.particle; - -import com.google.common.collect.ImmutableMap; -import org.checkerframework.checker.nullness.qual.Nullable; -import org.spongepowered.api.effect.particle.ParticleEffect; -import org.spongepowered.api.effect.particle.ParticleOption; -import org.spongepowered.api.effect.particle.ParticleType; - -import java.util.Map; -import java.util.Optional; - -public final class NumericalParticleType implements ParticleType { - - private final int id; - private final Map, Object> defaultOptions; - private final @Nullable DataCalculator dataCalculator; - - public NumericalParticleType(final int id, final Map, Object> defaultOptions, final @Nullable DataCalculator dataCalculator) { - this.id = id; - this.defaultOptions = ImmutableMap.copyOf(defaultOptions); - this.dataCalculator = dataCalculator; - } - - public NumericalParticleType(final int id) { - this.id = id; - this.defaultOptions = ImmutableMap.of(); - this.dataCalculator = null; - } - - public int getId() { - return this.id; - } - - @SuppressWarnings("unchecked") - @Override - public Optional defaultOption(final ParticleOption option) { - return Optional.ofNullable((V) this.defaultOptions.get(option)); - } - - @Override - public Map, Object> defaultOptions() { - return this.defaultOptions; - } - - public int getData(ParticleEffect effect) { - if (this.dataCalculator == null) { - return 0; - } else { - return this.dataCalculator.getData(effect); - } - } - - public interface DataCalculator { - int getData(ParticleEffect effect); - } -} diff --git a/src/main/java/org/spongepowered/common/effect/particle/SpongeParticleHelper.java b/src/main/java/org/spongepowered/common/effect/particle/SpongeParticleHelper.java index fed65103d3d..03d1637cd4e 100644 --- a/src/main/java/org/spongepowered/common/effect/particle/SpongeParticleHelper.java +++ b/src/main/java/org/spongepowered/common/effect/particle/SpongeParticleHelper.java @@ -26,16 +26,20 @@ import net.minecraft.core.BlockPos; import net.minecraft.core.particles.BlockParticleOption; +import net.minecraft.core.particles.DustColorTransitionOptions; import net.minecraft.core.particles.DustParticleOptions; import net.minecraft.core.particles.ItemParticleOption; +import net.minecraft.core.particles.SculkChargeParticleOptions; +import net.minecraft.core.particles.ShriekParticleOption; import net.minecraft.core.particles.SimpleParticleType; +import net.minecraft.core.particles.VibrationParticleOption; import net.minecraft.network.protocol.Packet; -import net.minecraft.network.protocol.game.ClientboundLevelEventPacket; import net.minecraft.network.protocol.game.ClientboundLevelParticlesPacket; import net.minecraft.resources.ResourceKey; import net.minecraft.server.players.PlayerList; import net.minecraft.world.level.Level; import net.minecraft.world.level.block.Block; +import net.minecraft.world.level.gameevent.BlockPositionSource; import org.spongepowered.api.block.BlockState; import org.spongepowered.api.block.BlockType; import org.spongepowered.api.effect.particle.ParticleEffect; @@ -44,6 +48,7 @@ import org.spongepowered.api.item.inventory.ItemStackSnapshot; import org.spongepowered.api.util.Color; import org.spongepowered.api.util.Direction; +import org.spongepowered.api.util.Ticks; import org.spongepowered.math.vector.Vector3d; import org.spongepowered.math.vector.Vector3f; @@ -83,22 +88,9 @@ public static List> toPackets(final ParticleEffect effect, final Vecto return packets; } - public static CachedParticlePacket getCachedPacket(final SpongeParticleEffect effect) { + private static CachedParticlePacket getCachedPacket(final SpongeParticleEffect effect) { final ParticleType type = effect.type(); - - if (type instanceof NumericalParticleType) { - // Special cased particle types with numerical IDs. - return SpongeParticleHelper.getNumericalPacket(effect, (NumericalParticleType) type); - } else { - // Normal named particle type. - return SpongeParticleHelper.getNamedPacket(effect, (net.minecraft.core.particles.ParticleType) type); - } - } - - private static CachedParticlePacket getNumericalPacket(final ParticleEffect effect, final NumericalParticleType type) { - int effectId = type.getId(); - - return new NumericalCachedPacket(effectId, type.getData(effect), false); + return SpongeParticleHelper.getNamedPacket(effect, (net.minecraft.core.particles.ParticleType) type); } @SuppressWarnings({"unchecked", "ConstantConditions"}) @@ -123,6 +115,33 @@ private static CachedParticlePacket getNamedPacket(final ParticleEffect effect, (net.minecraft.core.particles.ParticleType) internalType, (net.minecraft.world.level.block.state.BlockState) state); return new NamedCachedPacket(particleData, offset, quantity, velocity); + } else if (internalType.getDeserializer() == DustColorTransitionOptions.DESERIALIZER) { + final Color color = effect.optionOrDefault(ParticleOptions.COLOR).get(); + final Color toColor = effect.optionOrDefault(ParticleOptions.TO_COLOR).get(); + final double scale = effect.optionOrDefault(ParticleOptions.SCALE).get(); + final DustColorTransitionOptions particleData = new DustColorTransitionOptions( + new org.joml.Vector3f( + (float) color.red() / 255, + (float) color.green() / 255, + (float) color.blue() / 255 + ), + new org.joml.Vector3f( + (float) toColor.red() / 255, + (float) toColor.green() / 255, + (float) toColor.blue() / 255 + ), + (float) scale); + return new NamedCachedPacket(particleData, offset, quantity, velocity); + } else if (internalType.getDeserializer() == DustParticleOptions.DESERIALIZER) { + // This particle type supports a color option. + final Color color = effect.optionOrDefault(ParticleOptions.COLOR).get(); + final double scale = effect.optionOrDefault(ParticleOptions.SCALE).get(); + final DustParticleOptions particleData = new DustParticleOptions(new org.joml.Vector3f( + (float) color.red() / 255, + (float) color.green() / 255, + (float) color.blue() / 255), + (float) scale); + return new NamedCachedPacket(particleData, offset, quantity, velocity); } else if (internalType.getDeserializer() == ItemParticleOption.DESERIALIZER) { // This particle type supports an item option. final ItemStackSnapshot snapshot = effect.optionOrDefault(ParticleOptions.ITEM_STACK_SNAPSHOT).get(); @@ -130,15 +149,18 @@ private static CachedParticlePacket getNamedPacket(final ParticleEffect effect, (net.minecraft.core.particles.ParticleType) internalType, (net.minecraft.world.item.ItemStack) (Object) snapshot.createStack()); return new NamedCachedPacket(particleData, offset, quantity, velocity); - } else if (internalType.getDeserializer() == DustParticleOptions.DESERIALIZER) { - // This particle type supports a color option. - final Color color = effect.optionOrDefault(ParticleOptions.COLOR).get(); - final double scale = effect.optionOrDefault(ParticleOptions.SCALE).get(); - final DustParticleOptions particleData = new DustParticleOptions(new org.joml.Vector3f( - (float) color.red() / 255, - (float) color.green() / 255, - (float) color.blue() / 255), - (float) scale); + } else if (internalType.getDeserializer() == SculkChargeParticleOptions.DESERIALIZER) { + final double roll = effect.optionOrDefault(ParticleOptions.ROLL).get(); + final SculkChargeParticleOptions particleData = new SculkChargeParticleOptions((float) roll); + return new NamedCachedPacket(particleData, offset, quantity, velocity); + } else if (internalType.getDeserializer() == ShriekParticleOption.DESERIALIZER) { + final int delay = effect.optionOrDefault(ParticleOptions.DELAY).get(); + final ShriekParticleOption particleData = new ShriekParticleOption(delay); + return new NamedCachedPacket(particleData, offset, quantity, velocity); + } else if (internalType.getDeserializer() == VibrationParticleOption.DESERIALIZER) { + final Ticks delay = effect.optionOrDefault(ParticleOptions.TRAVEL_TIME).get(); + // TODO add position source + final VibrationParticleOption particleData = new VibrationParticleOption(new BlockPositionSource(BlockPos.ZERO), (int) delay.ticks()); return new NamedCachedPacket(particleData, offset, quantity, velocity); } @@ -259,24 +281,4 @@ public void process(final Vector3d position, final List> output) { } } } - - private static final class NumericalCachedPacket implements CachedParticlePacket { - - private final int type; - private final int data; - private final boolean broadcast; - - public NumericalCachedPacket(final int type, final int data, final boolean broadcast) { - this.type = type; - this.data = data; - this.broadcast = broadcast; - } - - @Override - public void process(final Vector3d position, final List> output) { - final BlockPos blockPos = new BlockPos(position.floorX(), position.floorY(), position.floorZ()); - final ClientboundLevelEventPacket packet = new ClientboundLevelEventPacket(this.type, blockPos, this.data, this.broadcast); - output.add(packet); - } - } } diff --git a/src/main/java/org/spongepowered/common/registry/loader/SpongeRegistryLoader.java b/src/main/java/org/spongepowered/common/registry/loader/SpongeRegistryLoader.java index 405b7a2d826..e024890bf00 100644 --- a/src/main/java/org/spongepowered/common/registry/loader/SpongeRegistryLoader.java +++ b/src/main/java/org/spongepowered/common/registry/loader/SpongeRegistryLoader.java @@ -102,6 +102,7 @@ import org.spongepowered.api.service.economy.transaction.TransactionTypes; import org.spongepowered.api.util.Color; import org.spongepowered.api.util.Direction; +import org.spongepowered.api.util.Ticks; import org.spongepowered.api.util.orientation.Orientation; import org.spongepowered.api.util.orientation.Orientations; import org.spongepowered.api.world.ChunkRegenerateFlag; @@ -424,12 +425,16 @@ public static RegistryLoader> particleOption() { return RegistryLoader.of(l -> { l.add(ParticleOptions.BLOCK_STATE, k -> new SpongeParticleOption<>(BlockState.class)); l.add(ParticleOptions.COLOR, k -> new SpongeParticleOption<>(Color.class)); + l.add(ParticleOptions.DELAY, k -> new SpongeParticleOption<>(Double.class)); l.add(ParticleOptions.DIRECTION, k -> new SpongeParticleOption<>(Direction.class)); l.add(ParticleOptions.ITEM_STACK_SNAPSHOT, k -> new SpongeParticleOption<>(ItemStackSnapshot.class)); l.add(ParticleOptions.OFFSET, k -> new SpongeParticleOption<>(Vector3d.class)); l.add(ParticleOptions.POTION_EFFECT_TYPE, k -> new SpongeParticleOption<>(PotionEffectType.class)); l.add(ParticleOptions.QUANTITY, k -> new SpongeParticleOption<>(Integer.class, v -> v < 1 ? new IllegalArgumentException("Quantity must be at least one") : null)); + l.add(ParticleOptions.ROLL, k -> new SpongeParticleOption<>(Double.class)); l.add(ParticleOptions.SCALE, k -> new SpongeParticleOption<>(Double.class, v -> v < 0 ? new IllegalArgumentException("Scale must not be negative") : null)); + l.add(ParticleOptions.TO_COLOR, k -> new SpongeParticleOption<>(Color.class)); + l.add(ParticleOptions.TRAVEL_TIME, k -> new SpongeParticleOption<>(Ticks.class)); l.add(ParticleOptions.VELOCITY, k -> new SpongeParticleOption<>(Vector3d.class)); }); }