Skip to content
8 changes: 0 additions & 8 deletions src/main/java/twilightforest/item/CustomDamageSwordItem.java
Original file line number Diff line number Diff line change
Expand Up @@ -5,24 +5,16 @@
import net.minecraft.world.damagesource.DamageType;
import net.minecraft.world.entity.LivingEntity;
import net.minecraft.world.item.Item;
import net.minecraft.world.item.Tier;
import net.minecraft.world.item.component.Tool;

//TODO data component-itize this
public class CustomDamageSwordItem extends Item implements CustomDamageProvider {

private final ResourceKey<DamageType> damageType;

public CustomDamageSwordItem(ResourceKey<DamageType> damageType, Properties properties) {
super(properties);
this.damageType = damageType;
}

public CustomDamageSwordItem(ResourceKey<DamageType> damageType, Tier tier, Properties properties, Tool toolComponentData) {
super(tier, properties, toolComponentData);
this.damageType = damageType;
}

@Override
public DamageSource getDamageSource(LivingEntity attacker) {
return attacker.damageSources().source(this.damageType, attacker);
Expand Down
2 changes: 1 addition & 1 deletion src/main/java/twilightforest/item/EmptyMazeMapItem.java
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ public InteractionResult use(Level level, Player player, InteractionHand hand) {
itemStack.consume(1, player);
player.awardStat(Stats.ITEM_USED.get(this));
serverLevel.playSound(null, player, SoundEvents.UI_CARTOGRAPHY_TABLE_TAKE_RESULT, player.getSoundSource(), 1.0F, 1.0F);
ItemStack map = MazeMapItem.setupNewMap(level, Mth.floor(player.getX()), Mth.floor(player.getZ()), (byte) 0, true, false, Mth.floor(player.getY()), this.mapOres);
ItemStack map = MazeMapItem.setupNewMap(serverLevel, Mth.floor(player.getX()), Mth.floor(player.getZ()), (byte) 0, true, false, Mth.floor(player.getY()), this.mapOres);
if (itemStack.isEmpty()) {
return InteractionResult.SUCCESS.heldItemTransformedTo(map);
} else {
Expand Down
5 changes: 2 additions & 3 deletions src/main/java/twilightforest/item/MagicMapItem.java
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,6 @@

// [VanillaCopy] super everything, but with appropriate redirections to our own datastructures. finer details noted
public class MagicMapItem extends MapItem {

public static final String STR_ID = "magicmap";

public MagicMapItem(Properties properties) {
Expand All @@ -53,7 +52,7 @@ public static ItemStack setupNewMap(ServerLevel level, int worldX, int worldZ, b
@Nullable
public static TFMagicMapData getData(ItemStack stack, Level level) {
MapId mapid = stack.get(DataComponents.MAP_ID);
return mapid == null ? null : TFMagicMapData.getMagicMapData(level, getMapName(mapid.id()));
return mapid == null ? null : TFMagicMapData.getMagicMapData(level, mapid);
}

@Nullable
Expand Down Expand Up @@ -89,7 +88,7 @@ private static TFMagicMapData createMapData(ItemStack stack, ServerLevel level,
ColumnPos pos = getMagicMapCenter(x, z);

TFMagicMapData mapdata = new TFMagicMapData(pos.x(), pos.z(), (byte) scale, trackingPosition, unlimitedTracking, false, dimension);
TFMagicMapData.registerMagicMapData(level, mapdata, getMapName(freeMapId.id())); // call our own register method
TFMagicMapData.registerMagicMapData(level, mapdata, new MapId(freeMapId.id())); // call our own register method
stack.set(DataComponents.MAP_ID, freeMapId);
return mapdata;
}
Expand Down
4 changes: 2 additions & 2 deletions src/main/java/twilightforest/item/MazeMapItem.java
Original file line number Diff line number Diff line change
Expand Up @@ -54,7 +54,7 @@ public static ItemStack setupNewMap(ServerLevel level, int worldX, int worldZ, b
@Nullable
public static TFMazeMapData getData(ItemStack stack, Level level) {
MapId id = stack.get(DataComponents.MAP_ID);
return id == null ? null : TFMazeMapData.getMazeMapData(level, getMapName(id.id()));
return id == null ? null : TFMazeMapData.getMazeMapData(level, id);
}

@Nullable
Expand All @@ -81,7 +81,7 @@ private static TFMazeMapData createMapData(ItemStack stack, ServerLevel level, i
TFMazeMapData mapdata = new TFMazeMapData(scaledX, scaledZ, (byte) scale, trackingPosition, unlimitedTracking, false, dimension);
mapdata.calculateMapCenter(level, x, y, z); // call our own map center calculation
mapdata.ore = ore;
TFMazeMapData.registerMazeMapData(level, mapdata, getMapName(i.id())); // call our own register method
TFMazeMapData.registerMazeMapData(level, mapdata, i); // call our own register method
stack.set(DataComponents.MAP_ID, i);
return mapdata;
}
Expand Down
16 changes: 9 additions & 7 deletions src/main/java/twilightforest/item/MoonDialItem.java
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
package twilightforest.item;

import net.minecraft.ChatFormatting;
import net.minecraft.client.Minecraft;
import net.minecraft.core.BlockPos;
import net.minecraft.network.chat.Component;
import net.minecraft.network.chat.MutableComponent;
import net.minecraft.world.attribute.EnvironmentAttributes;
Expand All @@ -9,11 +11,10 @@
import net.minecraft.world.item.TooltipFlag;
import net.minecraft.world.item.component.TooltipDisplay;
import net.minecraft.world.level.Level;
import net.minecraft.world.level.MoonPhase;
import org.jspecify.annotations.Nullable;

import java.time.LocalDate;
import java.util.function.Consumer;
import org.jetbrains.annotations.Nullable;
Comment thread
albazavr-alba marked this conversation as resolved.
Outdated
import twilightforest.util.MoonPhaseConverter;

public class MoonDialItem extends Item {
public MoonDialItem(Properties properties) {
Expand All @@ -22,18 +23,19 @@ public MoonDialItem(Properties properties) {

@Override
public void appendHoverText(ItemStack stack, TooltipContext context, TooltipDisplay display, Consumer<Component> builder, TooltipFlag flag) {
builder.accept(getMoonPhase(context.level()).withStyle(ChatFormatting.GRAY));
BlockPos pos = Minecraft.getInstance().player != null ? Minecraft.getInstance().player.blockPosition() : BlockPos.ZERO;
builder.accept(getMoonPhase(context.level(), pos).withStyle(ChatFormatting.GRAY));
}

public static MutableComponent getMoonPhase(@Nullable Level level) {
public static MutableComponent getMoonPhase(@Nullable Level level, BlockPos pos) {
String phaseType;
if (level != null && !level.dimensionType().hasFixedTime()) {
MoonPhase phase = level.environmentAttributes().getDimensionValue(EnvironmentAttributes.MOON_PHASE);
var phase = level.environmentAttributes().getValue(EnvironmentAttributes.MOON_PHASE, pos);
Comment thread
albazavr-alba marked this conversation as resolved.
Outdated
Comment thread
albazavr-alba marked this conversation as resolved.
Outdated
phaseType = phase.getSerializedName();
} else {
boolean aprilFools = LocalDate.of(LocalDate.now().getYear(), 4, 1).equals(LocalDate.now());
phaseType = aprilFools ? "unknown_fools" : "unknown";
}
return Component.translatable("item.twilightforest.moon_dial.phase_" + phaseType);
return Component.translatable("item.twilightforest.moon_dial.phase_" + MoonPhaseConverter.convertPhaseToIndex(phaseType));
Comment thread
albazavr-alba marked this conversation as resolved.
Outdated
}
}
1 change: 0 additions & 1 deletion src/main/java/twilightforest/item/food/TFFoods.java
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@
import net.minecraft.world.food.Foods;

public class TFFoods extends Foods {

public static final FoodProperties TORCHBERRIES = new FoodProperties.Builder().alwaysEdible().build();
public static final FoodProperties RAW_VENISON = new FoodProperties.Builder().nutrition(3).saturationModifier(0.3F).build();
public static final FoodProperties VENISON_STEAK = new FoodProperties.Builder().nutrition(8).saturationModifier(0.8F).build();
Expand Down
153 changes: 68 additions & 85 deletions src/main/java/twilightforest/item/mapdata/TFMagicMapData.java
Original file line number Diff line number Diff line change
Expand Up @@ -3,126 +3,109 @@
import com.mojang.serialization.Codec;
import com.mojang.serialization.codecs.RecordCodecBuilder;
import net.minecraft.core.Holder;
import net.minecraft.core.HolderLookup;
import net.minecraft.nbt.*;
import net.minecraft.core.registries.Registries;
import net.minecraft.network.protocol.Packet;
import net.minecraft.network.protocol.game.ClientboundMapItemDataPacket;
import net.minecraft.resources.ResourceKey;
import net.minecraft.server.level.ServerLevel;
import net.minecraft.util.datafix.DataFixTypes;
import net.minecraft.world.entity.player.Player;
import net.minecraft.world.level.Level;
import net.minecraft.world.level.LevelAccessor;
import net.minecraft.world.level.saveddata.SavedData;
import net.minecraft.world.level.saveddata.maps.MapDecoration;
import net.minecraft.world.level.saveddata.maps.MapDecorationType;
import net.minecraft.world.level.saveddata.maps.MapId;
import net.minecraft.world.level.saveddata.maps.MapItemSavedData;
import org.jetbrains.annotations.Nullable;
import twilightforest.TwilightForestMod;
import twilightforest.item.MagicMapItem;
import twilightforest.network.MagicMapPacket;
import twilightforest.util.Codecs;

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

public class TFMagicMapData extends MapItemSavedData {
private static final Map<String, TFMagicMapData> CLIENT_DATA = new HashMap<>();
public final List<String> conqueredStructures = new ArrayList<>();

public TFMagicMapData(int x, int z, byte scale, boolean trackpos, boolean unlimited, boolean locked, ResourceKey<Level> dim) {
super(x, z, scale, trackpos, unlimited, locked, dim);
}

public static TFMagicMapData load(CompoundTag nbt, HolderLookup.Provider provider) {
MapItemSavedData data = MapItemSavedData.load(nbt, provider);
final boolean trackingPosition = !nbt.contains("trackingPosition", 1) || nbt.getBoolean("trackingPosition");
final boolean unlimitedTracking = nbt.getBoolean("unlimitedTracking");
final boolean locked = nbt.getBoolean("locked");
TFMagicMapData tfdata = new TFMagicMapData(data.centerX, data.centerZ, data.scale, trackingPosition, unlimitedTracking, locked, data.dimension);

tfdata.colors = data.colors;
tfdata.bannerMarkers.putAll(data.bannerMarkers);
tfdata.frameMarkers.putAll(data.frameMarkers);

for (DecorationHolder decoration : DecorationHolder.CODEC.listOf()
.parse(provider.createSerializationContext(NbtOps.INSTANCE), nbt.get("decorations"))
.resultOrPartial(error -> TwilightForestMod.LOGGER.warn("Failed to parse map decoration: '{}'", error))
.orElse(List.of())) {
MapDecoration mapdecoration1 = decoration.decoration();
MapDecoration mapdecoration = tfdata.decorations.put(decoration.id(), mapdecoration1);
if (!mapdecoration1.equals(mapdecoration)) {
if (mapdecoration != null && mapdecoration.type().value().trackCount()) {
tfdata.trackedDecorationCount--;
}
private static final Codec<byte[]> COLORS_CODEC = Codec.BYTE.listOf()
.xmap(list -> {
byte[] arr = new byte[list.size()];
for (int i = 0; i < list.size(); i++) arr[i] = list.get(i);
return arr;
}, array -> {
List<Byte> list = new ArrayList<>(array.length);
for (byte b : array) list.add(b);
return list;
});

if (decoration.decoration().type().value().trackCount()) {
tfdata.trackedDecorationCount++;
public static final Codec<TFMagicMapData> CODEC = RecordCodecBuilder.create(instance ->
instance.group(
Codec.INT.fieldOf("xCenter").forGetter(data -> data.centerX),
Codec.INT.fieldOf("zCenter").forGetter(data -> data.centerZ),
Codec.BYTE.fieldOf("scale").forGetter(data -> data.scale),
Codec.BOOL.optionalFieldOf("trackingPosition", true).forGetter(data -> data.trackingPosition),
Codec.BOOL.optionalFieldOf("unlimitedTracking", false).forGetter(data -> data.unlimitedTracking),
Codec.BOOL.optionalFieldOf("locked", false).forGetter(data -> data.locked),
ResourceKey.codec(Registries.DIMENSION).fieldOf("dimension").forGetter(data -> data.dimension),
COLORS_CODEC.fieldOf("colors").forGetter(data -> data.colors),
DecorationHolder.CODEC.listOf().optionalFieldOf("decorations", List.of()).forGetter(data -> {
List<DecorationHolder> holders = new ArrayList<>();
data.decorations.forEach((s, decoration) -> {
if (decoration.type().value().showOnItemFrame()) {
holders.add(new DecorationHolder(s, decoration));
}
});
return holders;
}),
Codec.STRING.listOf().optionalFieldOf("conquered_structures", List.of()).forGetter(data -> data.conqueredStructures)
).apply(instance, (centerX, centerZ, scale, trackingPosition, unlimitedTracking, locked, dimension, colorsArray, decorationsList, conqueredList) -> {
TFMagicMapData tfdata = new TFMagicMapData(centerX, centerZ, scale, trackingPosition, unlimitedTracking, locked, dimension);
if (colorsArray.length == tfdata.colors.length) {
System.arraycopy(colorsArray, 0, tfdata.colors, 0, colorsArray.length);
}
for (DecorationHolder decoration : decorationsList) {
MapDecoration mapdecoration1 = decoration.decoration();
MapDecoration mapdecoration = tfdata.decorations.put(decoration.id(), mapdecoration1);
if (!mapdecoration1.equals(mapdecoration)) {
if (mapdecoration != null && mapdecoration.type().value().trackCount()) {
tfdata.trackedDecorationCount--;
}
if (decoration.decoration().type().value().trackCount()) {
tfdata.trackedDecorationCount++;
}
tfdata.setDecorationsDirty();
}
tfdata.setDecorationsDirty();
}
}

if (nbt.contains("conquered_structures", Tag.TAG_LIST)) {
tfdata.conqueredStructures.clear();
ListTag tag = nbt.getList("conquered_structures", Tag.TAG_STRING);
tag.forEach(tag1 -> tfdata.conqueredStructures.add(tag1.getAsString()));
}

return tfdata;
}
tfdata.conqueredStructures.addAll(conqueredList);
return tfdata;
})
);

@Override
public CompoundTag save(CompoundTag tag, HolderLookup.Provider provider) {
tag = super.save(tag, provider);

List<DecorationHolder> holders = new ArrayList<>();
this.decorations.forEach((s, decoration) -> {
if (decoration.type().value().showOnItemFrame()) {
holders.add(new DecorationHolder(s, decoration));
}
});
tag.put("decorations", DecorationHolder.CODEC.listOf().encodeStart(NbtOps.INSTANCE, holders).getOrThrow());

if (!this.conqueredStructures.isEmpty()) {
ListTag conqueredTag = new ListTag();
for (String structure : this.conqueredStructures) {
conqueredTag.add(StringTag.valueOf(structure));
}
tag.put("conquered_structures", conqueredTag);
}
private static final Map<MapId, TFMagicMapData> CLIENT_DATA = new HashMap<>();
public final List<String> conqueredStructures = new ArrayList<>();

return tag;
public TFMagicMapData(int x, int z, byte scale, boolean trackpos, boolean unlimited, boolean locked, ResourceKey<Level> dim) {
super(x, z, scale, trackpos, unlimited, locked, dim);
}

// [VanillaCopy] Adapted from World.getMapData
@Nullable
public static TFMagicMapData getMagicMapData(Level level, String name) {
if (level instanceof ServerLevel serverLevel) return (TFMagicMapData) serverLevel.getServer().overworld().getDataStorage().get(TFMagicMapData.factory(), name);
else return CLIENT_DATA.get(name);
public static TFMagicMapData getMagicMapData(Level level, MapId mapId) {
if (level instanceof ServerLevel serverLevel) {
MapItemSavedData baseData = serverLevel.getServer().overworld().getMapData(mapId);
if (baseData instanceof TFMagicMapData tfData) {
return tfData;
}
return null;
} else {
return CLIENT_DATA.get(mapId);
}
}

// Like the method above, but if we know we're on client
@Nullable
public static TFMagicMapData getClientMagicMapData(String name) {
return CLIENT_DATA.get(name);
}

// [VanillaCopy] Adapted from World.registerMapData
public static void registerMagicMapData(Level level, TFMagicMapData data, String id) {
if (level instanceof ServerLevel serverLevel) serverLevel.getServer().overworld().getDataStorage().set(id, data);
public static void registerMagicMapData(Level level, TFMagicMapData data, MapId id) {
if (level instanceof ServerLevel serverLevel) serverLevel.getServer().overworld().getDataStorage().set(type(id), data);
Comment thread
albazavr-alba marked this conversation as resolved.
Outdated
else CLIENT_DATA.put(id, data);
}

public static Factory<MapItemSavedData> factory() {
return new SavedData.Factory<>(() -> {
throw new IllegalStateException("Should never create an empty map saved data");
}, TFMagicMapData::load, DataFixTypes.SAVED_DATA_MAP_DATA);
}

@Nullable
@Override
public Packet<?> getUpdatePacket(MapId mapId, Player player) {
Expand Down
Loading
Loading