[Change] WorldPresets are configured through BiomeSources
This commit is contained in:
parent
2a03b46a98
commit
877691011f
39 changed files with 1092 additions and 723 deletions
|
@ -0,0 +1,10 @@
|
|||
package org.betterx.worlds.together.biomesource;
|
||||
|
||||
import org.betterx.worlds.together.biomesource.config.BiomeSourceConfig;
|
||||
|
||||
import net.minecraft.world.level.biome.BiomeSource;
|
||||
|
||||
public interface BiomeSourceWithConfig<B extends BiomeSource, C extends BiomeSourceConfig<B>> {
|
||||
C getTogetherConfig();
|
||||
void setTogetherConfig(C newConfig);
|
||||
}
|
|
@ -0,0 +1,17 @@
|
|||
package org.betterx.worlds.together.biomesource;
|
||||
|
||||
import net.minecraft.world.level.biome.BiomeSource;
|
||||
|
||||
public interface MergeableBiomeSource<B extends BiomeSource> {
|
||||
|
||||
/**
|
||||
* Returns a BiomeSource that merges the settings of this one with the Biomes (and possibly settings) from the
|
||||
* {@code inputBiomeSource}.
|
||||
*
|
||||
* @param inputBiomeSource The {@link BiomeSource} you want to copy
|
||||
* @return The merged or new BiomeSource
|
||||
*/
|
||||
B mergeWithBiomeSource(BiomeSource inputBiomeSource);
|
||||
|
||||
|
||||
}
|
|
@ -0,0 +1,7 @@
|
|||
package org.betterx.worlds.together.biomesource;
|
||||
|
||||
import org.jetbrains.annotations.ApiStatus;
|
||||
|
||||
@ApiStatus.Internal
|
||||
public interface MultiNoiseBiomeSourceAccessor {
|
||||
}
|
|
@ -0,0 +1,8 @@
|
|||
package org.betterx.worlds.together.biomesource.config;
|
||||
|
||||
import net.minecraft.world.level.biome.BiomeSource;
|
||||
|
||||
public interface BiomeSourceConfig<B extends BiomeSource> {
|
||||
boolean couldSetWithoutRepair(BiomeSourceConfig<?> input);
|
||||
boolean sameConfig(BiomeSourceConfig<?> input);
|
||||
}
|
|
@ -0,0 +1,20 @@
|
|||
package org.betterx.worlds.together.chunkgenerator;
|
||||
|
||||
import net.minecraft.resources.ResourceKey;
|
||||
import net.minecraft.world.level.dimension.LevelStem;
|
||||
import net.minecraft.world.level.levelgen.WorldGenSettings;
|
||||
|
||||
public class ChunkGeneratorUtils {
|
||||
public static void restoreOriginalBiomeSourceInAllDimension(WorldGenSettings settings) {
|
||||
for (var entry : settings.dimensions().entrySet()) {
|
||||
ResourceKey<LevelStem> key = entry.getKey();
|
||||
LevelStem stem = entry.getValue();
|
||||
|
||||
if (stem.generator() instanceof RestorableBiomeSource<?> generator) {
|
||||
generator.restoreInitialBiomeSource(key);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
}
|
|
@ -0,0 +1,35 @@
|
|||
package org.betterx.worlds.together.chunkgenerator;
|
||||
|
||||
import org.betterx.worlds.together.biomesource.BiomeSourceWithConfig;
|
||||
|
||||
import net.minecraft.core.RegistryAccess;
|
||||
import net.minecraft.resources.ResourceKey;
|
||||
import net.minecraft.world.level.biome.BiomeSource;
|
||||
import net.minecraft.world.level.chunk.ChunkGenerator;
|
||||
import net.minecraft.world.level.dimension.DimensionType;
|
||||
import net.minecraft.world.level.dimension.LevelStem;
|
||||
import net.minecraft.world.level.levelgen.WorldGenSettings;
|
||||
|
||||
public interface EnforceableChunkGenerator<G extends ChunkGenerator> {
|
||||
WorldGenSettings enforceGeneratorInWorldGenSettings(
|
||||
RegistryAccess access,
|
||||
ResourceKey<LevelStem> dimensionKey,
|
||||
ResourceKey<DimensionType> dimensionTypeKey,
|
||||
ChunkGenerator loadedChunkGenerator,
|
||||
WorldGenSettings settings
|
||||
);
|
||||
|
||||
default boolean needsChunkGeneratorRepair(ChunkGenerator chunkGenerator) {
|
||||
ChunkGenerator self = (ChunkGenerator) this;
|
||||
if (this == chunkGenerator || chunkGenerator == null) return false;
|
||||
|
||||
BiomeSource one = self.getBiomeSource();
|
||||
BiomeSource two = chunkGenerator.getBiomeSource();
|
||||
if (one == two) return false;
|
||||
|
||||
if (one instanceof BiomeSourceWithConfig<?, ?> ba && two instanceof BiomeSourceWithConfig<?, ?> bb) {
|
||||
return !ba.getTogetherConfig().couldSetWithoutRepair(bb.getTogetherConfig());
|
||||
}
|
||||
return !one.getClass().isAssignableFrom(two.getClass()) && !two.getClass().isAssignableFrom(one.getClass());
|
||||
}
|
||||
}
|
|
@ -0,0 +1,21 @@
|
|||
package org.betterx.worlds.together.chunkgenerator;
|
||||
|
||||
import org.betterx.worlds.together.surfaceRules.SurfaceRuleUtil;
|
||||
|
||||
import net.minecraft.resources.ResourceKey;
|
||||
import net.minecraft.world.level.chunk.ChunkGenerator;
|
||||
import net.minecraft.world.level.dimension.LevelStem;
|
||||
import net.minecraft.world.level.levelgen.NoiseBasedChunkGenerator;
|
||||
|
||||
public interface InjectableSurfaceRules<G extends ChunkGenerator> {
|
||||
/**
|
||||
* Called when the Surface Rules for this BiomeSource need to be
|
||||
*
|
||||
* @param dimensionKey The Dimension for which this injection is performed
|
||||
*/
|
||||
default void injectSurfaceRules(ResourceKey<LevelStem> dimensionKey) {
|
||||
if (this instanceof NoiseBasedChunkGenerator nbc) {
|
||||
SurfaceRuleUtil.injectSurfaceRules(nbc.generatorSettings().value(), nbc.getBiomeSource());
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,9 @@
|
|||
package org.betterx.worlds.together.chunkgenerator;
|
||||
|
||||
import net.minecraft.resources.ResourceKey;
|
||||
import net.minecraft.world.level.chunk.ChunkGenerator;
|
||||
import net.minecraft.world.level.dimension.LevelStem;
|
||||
|
||||
public interface RestorableBiomeSource<G extends ChunkGenerator> {
|
||||
void restoreInitialBiomeSource(ResourceKey<LevelStem> dimensionKey);
|
||||
}
|
|
@ -1,6 +1,11 @@
|
|||
package org.betterx.worlds.together.world;
|
||||
package org.betterx.worlds.together.levelgen;
|
||||
|
||||
import org.betterx.worlds.together.WorldsTogether;
|
||||
import org.betterx.worlds.together.biomesource.BiomeSourceWithConfig;
|
||||
import org.betterx.worlds.together.chunkgenerator.EnforceableChunkGenerator;
|
||||
import org.betterx.worlds.together.world.BiomeSourceWithSeed;
|
||||
import org.betterx.worlds.together.world.WorldConfig;
|
||||
import org.betterx.worlds.together.worldPreset.TogetherWorldPreset;
|
||||
import org.betterx.worlds.together.worldPreset.WorldPresets;
|
||||
import org.betterx.worlds.together.worldPreset.settings.WorldPresetSettings;
|
||||
|
||||
|
@ -17,6 +22,7 @@ import net.minecraft.resources.RegistryOps;
|
|||
import net.minecraft.resources.ResourceKey;
|
||||
import net.minecraft.util.RandomSource;
|
||||
import net.minecraft.world.level.biome.Biome;
|
||||
import net.minecraft.world.level.chunk.ChunkGenerator;
|
||||
import net.minecraft.world.level.dimension.DimensionType;
|
||||
import net.minecraft.world.level.dimension.LevelStem;
|
||||
import net.minecraft.world.level.levelgen.NoiseGeneratorSettings;
|
||||
|
@ -85,7 +91,6 @@ public class WorldGenUtil {
|
|||
}
|
||||
|
||||
public static WorldPresetSettings getWorldSettings() {
|
||||
if (BuiltinRegistries.ACCESS == null) return null;
|
||||
final RegistryAccess registryAccess = BuiltinRegistries.ACCESS;
|
||||
final RegistryOps<Tag> registryOps = RegistryOps.create(NbtOps.INSTANCE, registryAccess);
|
||||
|
||||
|
@ -128,4 +133,39 @@ public class WorldGenUtil {
|
|||
this.generatorSettings = generatorSettings;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
public static WorldGenSettings repairBiomeSourceInAllDimensions(
|
||||
RegistryAccess registryAccess,
|
||||
WorldGenSettings settings
|
||||
) {
|
||||
var dimensions = TogetherWorldPreset.getWorldDimensions();
|
||||
for (var entry : settings.dimensions().entrySet()) {
|
||||
ResourceKey<LevelStem> key = entry.getKey();
|
||||
LevelStem loadedStem = entry.getValue();
|
||||
|
||||
ChunkGenerator referenceGenerator = dimensions.get(key);
|
||||
if (referenceGenerator instanceof EnforceableChunkGenerator enforcer) {
|
||||
final ChunkGenerator loadedChunkGenerator = loadedStem.generator();
|
||||
|
||||
if (enforcer.needsChunkGeneratorRepair(loadedChunkGenerator)) {
|
||||
settings = enforcer.enforceGeneratorInWorldGenSettings(
|
||||
registryAccess,
|
||||
key,
|
||||
loadedStem.typeHolder().unwrapKey().orElseThrow(),
|
||||
loadedChunkGenerator,
|
||||
settings
|
||||
);
|
||||
} else if (loadedChunkGenerator.getBiomeSource() instanceof BiomeSourceWithConfig bs) {
|
||||
if (referenceGenerator.getBiomeSource() instanceof BiomeSourceWithConfig refbs) {
|
||||
if (!refbs.getTogetherConfig().sameConfig(bs.getTogetherConfig())) {
|
||||
bs.setTogetherConfig(refbs.getTogetherConfig());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return settings;
|
||||
}
|
||||
}
|
|
@ -1,6 +1,6 @@
|
|||
package org.betterx.worlds.together.mixin.client;
|
||||
|
||||
import org.betterx.worlds.together.world.WorldGenUtil;
|
||||
import org.betterx.worlds.together.levelgen.WorldGenUtil;
|
||||
import org.betterx.worlds.together.world.event.WorldBootstrap;
|
||||
import org.betterx.worlds.together.worldPreset.WorldPresets;
|
||||
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
package org.betterx.worlds.together.mixin.common;
|
||||
|
||||
import org.betterx.worlds.together.world.WorldGenUtil;
|
||||
import org.betterx.worlds.together.surfaceRules.SurfaceRuleUtil;
|
||||
|
||||
import net.minecraft.core.RegistryAccess;
|
||||
import net.minecraft.server.MinecraftServer;
|
||||
|
@ -29,6 +29,6 @@ public class MinecraftServerMixin {
|
|||
|
||||
@Inject(method = "createLevels", at = @At(value = "HEAD"))
|
||||
private void together_addSurfaceRules(ChunkProgressListener worldGenerationProgressListener, CallbackInfo ci) {
|
||||
WorldGenUtil.getWorldSettings().injectSurfaceRules(registryHolder, this.worldData.worldGenSettings());
|
||||
SurfaceRuleUtil.injectSurfaceRulesToAllDimensions(this.worldData.worldGenSettings());
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,36 @@
|
|||
package org.betterx.worlds.together.mixin.common;
|
||||
|
||||
import org.betterx.worlds.together.chunkgenerator.ChunkGeneratorUtils;
|
||||
|
||||
import com.mojang.datafixers.DataFixer;
|
||||
import net.minecraft.server.MinecraftServer;
|
||||
import net.minecraft.server.Services;
|
||||
import net.minecraft.server.WorldStem;
|
||||
import net.minecraft.server.level.progress.ChunkProgressListenerFactory;
|
||||
import net.minecraft.server.packs.repository.PackRepository;
|
||||
import net.minecraft.world.level.storage.LevelStorageSource;
|
||||
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.injection.At;
|
||||
import org.spongepowered.asm.mixin.injection.Inject;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||
|
||||
import java.net.Proxy;
|
||||
|
||||
@Mixin(value = MinecraftServer.class, priority = 2000)
|
||||
public class MinecraftServerMixinLate {
|
||||
@Inject(at = @At("RETURN"), method = "<init>")
|
||||
private void bcl_restoreBiomeSource(
|
||||
Thread thread,
|
||||
LevelStorageSource.LevelStorageAccess levelStorageAccess,
|
||||
PackRepository packRepository,
|
||||
WorldStem worldStem,
|
||||
Proxy proxy,
|
||||
DataFixer dataFixer,
|
||||
Services services,
|
||||
ChunkProgressListenerFactory chunkProgressListenerFactory,
|
||||
CallbackInfo ci
|
||||
) {
|
||||
ChunkGeneratorUtils.restoreOriginalBiomeSourceInAllDimension(worldStem.worldData().worldGenSettings());
|
||||
}
|
||||
}
|
|
@ -0,0 +1,11 @@
|
|||
package org.betterx.worlds.together.mixin.common;
|
||||
|
||||
import org.betterx.worlds.together.chunkgenerator.InjectableSurfaceRules;
|
||||
|
||||
import net.minecraft.world.level.levelgen.NoiseBasedChunkGenerator;
|
||||
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
|
||||
@Mixin(NoiseBasedChunkGenerator.class)
|
||||
public class NoiseBasedChunkGeneratorMixin implements InjectableSurfaceRules {
|
||||
}
|
|
@ -1,22 +1,16 @@
|
|||
package org.betterx.worlds.together.mixin.common;
|
||||
|
||||
import org.betterx.bclib.api.v2.levelgen.surface.SurfaceRuleUtil;
|
||||
import org.betterx.worlds.together.WorldsTogether;
|
||||
import org.betterx.worlds.together.surfaceRules.SurfaceRuleProvider;
|
||||
|
||||
import net.minecraft.world.level.biome.BiomeSource;
|
||||
import net.minecraft.world.level.levelgen.NoiseGeneratorSettings;
|
||||
import net.minecraft.world.level.levelgen.SurfaceRules;
|
||||
import net.minecraft.world.level.levelgen.SurfaceRules.RuleSource;
|
||||
|
||||
import org.spongepowered.asm.mixin.Final;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Mutable;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
|
||||
import java.util.HashSet;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
|
||||
@Mixin(NoiseGeneratorSettings.class)
|
||||
public class NoiseGeneratorSettingsMixin implements SurfaceRuleProvider {
|
||||
@Mutable
|
||||
|
@ -24,80 +18,15 @@ public class NoiseGeneratorSettingsMixin implements SurfaceRuleProvider {
|
|||
@Shadow
|
||||
private SurfaceRules.RuleSource surfaceRule;
|
||||
|
||||
private SurfaceRules.RuleSource bclib_originalSurfaceRule;
|
||||
private final Set<BiomeSource> bclib_biomeSources = new HashSet<>();
|
||||
|
||||
private void bclib_updateCustomRules() {
|
||||
bclib_setCustomRules(SurfaceRuleUtil.getRuleSources(bclib_biomeSources));
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bclib_addBiomeSource(BiomeSource source) {
|
||||
// bclib_biomeSources.add(source);
|
||||
// bclib_updateCustomRules();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void bclib_clearBiomeSources() {
|
||||
// bclib_biomeSources.clear();
|
||||
// bclib_clearCustomRules();
|
||||
}
|
||||
|
||||
private void bclib_clearCustomRules() {
|
||||
// if (bclib_originalSurfaceRule != null) {
|
||||
// this.surfaceRule = bclib_originalSurfaceRule;
|
||||
// bclib_originalSurfaceRule = null;
|
||||
// }
|
||||
}
|
||||
|
||||
private void bclib_setCustomRules(List<RuleSource> rules) {
|
||||
// if (rules.size() == 0) {
|
||||
// bclib_clearCustomRules();
|
||||
// return;
|
||||
// }
|
||||
//
|
||||
// RuleSource org = bclib_getOriginalSurfaceRule();
|
||||
// if (org instanceof SurfaceRules.SequenceRuleSource sequenceRule) {
|
||||
// List<RuleSource> currentSequence = sequenceRule.sequence();
|
||||
// rules = rules.stream().filter(r -> currentSequence.indexOf(r) < 0).collect(Collectors.toList());
|
||||
// rules.addAll(sequenceRule.sequence());
|
||||
// } else {
|
||||
// rules.add(org);
|
||||
// }
|
||||
//
|
||||
// bclib_setSurfaceRule(SurfaceRules.sequence(rules.toArray(new RuleSource[rules.size()])));
|
||||
}
|
||||
|
||||
public void bclib_overwrite(SurfaceRules.RuleSource surfaceRule) {
|
||||
if (surfaceRule == this.surfaceRule) return;
|
||||
if (this.bcl_containsOverride) {
|
||||
System.out.println("Adding another override");
|
||||
WorldsTogether.LOGGER.warning("Overwriting an overwritten set of Surface Rules.");
|
||||
}
|
||||
this.bcl_containsOverride = true;
|
||||
this.surfaceRule = surfaceRule;
|
||||
}
|
||||
|
||||
void bclib_setSurfaceRule(SurfaceRules.RuleSource surfaceRule) {
|
||||
if (bclib_originalSurfaceRule == null) {
|
||||
bclib_originalSurfaceRule = this.surfaceRule;
|
||||
}
|
||||
this.surfaceRule = surfaceRule;
|
||||
}
|
||||
|
||||
private boolean bcl_containsOverride = false;
|
||||
|
||||
RuleSource bclib_getOriginalSurfaceRule() {
|
||||
if (bclib_originalSurfaceRule == null) {
|
||||
return surfaceRule;
|
||||
}
|
||||
|
||||
return bclib_originalSurfaceRule;
|
||||
}
|
||||
|
||||
// @Inject(method = "surfaceRule", at = @At("HEAD"), cancellable = true)
|
||||
// private void bclib_surfaceRule(CallbackInfoReturnable<SurfaceRules.RuleSource> info) {
|
||||
// if (bclib_surfaceRule != null) {
|
||||
// info.setReturnValue(bclib_surfaceRule);
|
||||
// }
|
||||
// }
|
||||
}
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
package org.betterx.worlds.together.mixin.common;
|
||||
|
||||
import org.betterx.worlds.together.world.WorldGenUtil;
|
||||
import org.betterx.worlds.together.levelgen.WorldGenUtil;
|
||||
import org.betterx.worlds.together.worldPreset.WorldPresets;
|
||||
import org.betterx.worlds.together.worldPreset.settings.WorldPresetSettings;
|
||||
|
||||
|
|
|
@ -1,10 +1,7 @@
|
|||
package org.betterx.worlds.together.surfaceRules;
|
||||
|
||||
import net.minecraft.world.level.biome.BiomeSource;
|
||||
import net.minecraft.world.level.levelgen.SurfaceRules;
|
||||
|
||||
public interface SurfaceRuleProvider {
|
||||
void bclib_addBiomeSource(BiomeSource source);
|
||||
void bclib_clearBiomeSources();
|
||||
void bclib_overwrite(SurfaceRules.RuleSource surfaceRule);
|
||||
}
|
||||
|
|
|
@ -1,29 +1,24 @@
|
|||
package org.betterx.worlds.together.surfaceRules;
|
||||
|
||||
import org.betterx.bclib.api.v2.levelgen.biomes.InternalBiomeAPI;
|
||||
import org.betterx.worlds.together.WorldsTogether;
|
||||
import org.betterx.worlds.together.chunkgenerator.InjectableSurfaceRules;
|
||||
import org.betterx.worlds.together.world.event.WorldBootstrap;
|
||||
|
||||
import net.minecraft.core.Holder;
|
||||
import net.minecraft.core.Registry;
|
||||
import net.minecraft.resources.ResourceKey;
|
||||
import net.minecraft.resources.ResourceLocation;
|
||||
import net.minecraft.world.level.biome.Biome;
|
||||
import net.minecraft.world.level.biome.BiomeSource;
|
||||
import net.minecraft.world.level.chunk.ChunkGenerator;
|
||||
import net.minecraft.world.level.dimension.LevelStem;
|
||||
import net.minecraft.world.level.levelgen.NoiseBasedChunkGenerator;
|
||||
import net.minecraft.world.level.levelgen.NoiseGeneratorSettings;
|
||||
import net.minecraft.world.level.levelgen.SurfaceRules;
|
||||
import net.minecraft.world.level.levelgen.WorldGenSettings;
|
||||
|
||||
import java.util.LinkedList;
|
||||
import java.util.List;
|
||||
import java.util.Optional;
|
||||
import java.util.function.Predicate;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
public class SurfaceRuleUtil {
|
||||
public static List<SurfaceRules.RuleSource> getRulesForBiome(ResourceLocation biomeID) {
|
||||
private static List<SurfaceRules.RuleSource> getRulesForBiome(ResourceLocation biomeID) {
|
||||
Registry<AssignedSurfaceRule> registry = SurfaceRuleRegistry.BUILTIN_SURFACE_RULES;
|
||||
if (WorldBootstrap.getLastRegistryAccess() != null)
|
||||
registry = WorldBootstrap.getLastRegistryAccess()
|
||||
|
@ -36,31 +31,30 @@ public class SurfaceRuleUtil {
|
|||
|
||||
}
|
||||
|
||||
public static List<SurfaceRules.RuleSource> getRulesForBiomes(List<Biome> biomes) {
|
||||
private static List<SurfaceRules.RuleSource> getRulesForBiomes(List<Biome> biomes) {
|
||||
Registry<Biome> biomeRegistry = WorldBootstrap.getLastRegistryAccess().registryOrThrow(Registry.BIOME_REGISTRY);
|
||||
List<ResourceLocation> biomeIDs = biomes.stream()
|
||||
.map(b -> biomeRegistry.getKey(b))
|
||||
.filter(id -> id != null)
|
||||
.toList();
|
||||
|
||||
return biomeIDs.stream().map(biomeID -> getRulesForBiome(biomeID)).flatMap(List::stream).toList();
|
||||
return biomeIDs.stream()
|
||||
.map(biomeID -> getRulesForBiome(biomeID))
|
||||
.flatMap(List::stream)
|
||||
.collect(Collectors.toCollection(LinkedList::new));
|
||||
}
|
||||
|
||||
public static SurfaceRules.RuleSource mergeSurfaceRulesFromBiomes(
|
||||
private static SurfaceRules.RuleSource mergeSurfaceRulesFromBiomes(
|
||||
SurfaceRules.RuleSource org,
|
||||
BiomeSource source
|
||||
) {
|
||||
return mergeSurfaceRules(org, getRulesForBiomes(source.possibleBiomes().stream().map(h -> h.value()).toList()));
|
||||
return mergeSurfaceRules(
|
||||
org,
|
||||
getRulesForBiomes(source.possibleBiomes().stream().map(h -> h.value()).toList())
|
||||
);
|
||||
}
|
||||
|
||||
public static SurfaceRules.RuleSource mergeSurfaceRulesFromBiomes(
|
||||
SurfaceRules.RuleSource org,
|
||||
List<Biome> biomes
|
||||
) {
|
||||
return mergeSurfaceRules(org, getRulesForBiomes(biomes));
|
||||
}
|
||||
|
||||
public static SurfaceRules.RuleSource mergeSurfaceRules(
|
||||
private static SurfaceRules.RuleSource mergeSurfaceRules(
|
||||
SurfaceRules.RuleSource org,
|
||||
List<SurfaceRules.RuleSource> additionalRules
|
||||
) {
|
||||
|
@ -82,20 +76,6 @@ public class SurfaceRuleUtil {
|
|||
return new SurfaceRules.SequenceRuleSource(additionalRules);
|
||||
}
|
||||
|
||||
public static void injectSurfaceRules(
|
||||
ResourceKey<LevelStem> dimensionKey,
|
||||
ChunkGenerator loadedChunkGenerator
|
||||
) {
|
||||
WorldsTogether.LOGGER.debug("Checking Surface Rules for " + dimensionKey.location().toString());
|
||||
|
||||
final BiomeSource loadedBiomeSource = loadedChunkGenerator.getBiomeSource();
|
||||
InternalBiomeAPI.applyModifications(loadedBiomeSource, dimensionKey);
|
||||
|
||||
if (loadedChunkGenerator instanceof NoiseBasedChunkGenerator nbc) {
|
||||
injectSurfaceRules(nbc.generatorSettings().value(), loadedBiomeSource);
|
||||
}
|
||||
}
|
||||
|
||||
public static void injectSurfaceRules(NoiseGeneratorSettings noiseSettings, BiomeSource loadedBiomeSource) {
|
||||
if (((Object) noiseSettings) instanceof SurfaceRuleProvider srp) {
|
||||
SurfaceRules.RuleSource originalRules = noiseSettings.surfaceRule();
|
||||
|
@ -103,19 +83,13 @@ public class SurfaceRuleUtil {
|
|||
}
|
||||
}
|
||||
|
||||
public static void injectSurfaceRules(WorldGenSettings settings, Predicate<ResourceKey<LevelStem>> filter) {
|
||||
List<ResourceKey<LevelStem>> otherDimensions = settings
|
||||
.dimensions()
|
||||
.entrySet()
|
||||
.stream()
|
||||
.map(e -> e.getKey())
|
||||
.filter(filter)
|
||||
.toList();
|
||||
public static void injectSurfaceRulesToAllDimensions(WorldGenSettings settings) {
|
||||
for (var entry : settings.dimensions().entrySet()) {
|
||||
ResourceKey<LevelStem> key = entry.getKey();
|
||||
LevelStem stem = entry.getValue();
|
||||
|
||||
for (ResourceKey<LevelStem> key : otherDimensions) {
|
||||
Optional<Holder<LevelStem>> stem = settings.dimensions().getHolder(key);
|
||||
if (stem.isPresent()) {
|
||||
injectSurfaceRules(key, stem.get().value().generator());
|
||||
if (stem.generator() instanceof InjectableSurfaceRules<?> generator) {
|
||||
generator.injectSurfaceRules(key);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -2,9 +2,10 @@ package org.betterx.worlds.together.world.event;
|
|||
|
||||
import org.betterx.bclib.BCLib;
|
||||
import org.betterx.worlds.together.WorldsTogether;
|
||||
import org.betterx.worlds.together.levelgen.WorldGenUtil;
|
||||
import org.betterx.worlds.together.mixin.common.RegistryOpsAccessor;
|
||||
import org.betterx.worlds.together.mixin.common.WorldPresetAccessor;
|
||||
import org.betterx.worlds.together.world.WorldConfig;
|
||||
import org.betterx.worlds.together.world.WorldGenUtil;
|
||||
import org.betterx.worlds.together.worldPreset.TogetherWorldPreset;
|
||||
import org.betterx.worlds.together.worldPreset.WorldGenSettingsComponentAccessor;
|
||||
import org.betterx.worlds.together.worldPreset.WorldPresets;
|
||||
|
@ -36,15 +37,15 @@ public class WorldBootstrap {
|
|||
}
|
||||
|
||||
public static class Helpers {
|
||||
private static void initializeWorldDataAPI(
|
||||
private static void initializeWorldConfig(
|
||||
LevelStorageSource.LevelStorageAccess levelStorageAccess,
|
||||
boolean newWorld
|
||||
) {
|
||||
File levelPath = levelStorageAccess.getLevelPath(LevelResource.ROOT).toFile();
|
||||
initializeWorldDataAPI(levelPath, newWorld);
|
||||
initializeWorldConfig(levelPath, newWorld);
|
||||
}
|
||||
|
||||
private static void initializeWorldDataAPI(File levelBaseDir, boolean newWorld) {
|
||||
private static void initializeWorldConfig(File levelBaseDir, boolean newWorld) {
|
||||
WorldConfig.load(new File(levelBaseDir, "data"));
|
||||
|
||||
if (newWorld) {
|
||||
|
@ -105,12 +106,12 @@ public class WorldBootstrap {
|
|||
BCLib.LOGGER.info("Creating a new World, no fixes needed");
|
||||
final WorldPresetSettings settings = Helpers.defaultServerSettings();
|
||||
|
||||
Helpers.initializeWorldDataAPI(levelStorageAccess, true);
|
||||
Helpers.initializeWorldConfig(levelStorageAccess, true);
|
||||
WorldEventsImpl.BEFORE_SERVER_WORLD_LOAD.emit(e -> e.prepareWorld(
|
||||
levelStorageAccess, settings, true
|
||||
));
|
||||
} else {
|
||||
Helpers.initializeWorldDataAPI(levelStorageAccess, false);
|
||||
Helpers.initializeWorldConfig(levelStorageAccess, false);
|
||||
WorldEventsImpl.BEFORE_SERVER_WORLD_LOAD.emit(e -> e.prepareWorld(
|
||||
levelStorageAccess,
|
||||
WorldGenUtil.getWorldSettings(),
|
||||
|
@ -130,6 +131,12 @@ public class WorldBootstrap {
|
|||
settings = t.settings;
|
||||
}
|
||||
TogetherWorldPreset.writeWorldPresetSettings(settings);
|
||||
if (currentPreset.map(h -> h.value()).orElse(null) instanceof WorldPresetAccessor acc) {
|
||||
TogetherWorldPreset.writeWorldPresetSettings(acc.bcl_getDimensions());
|
||||
} else {
|
||||
WorldsTogether.LOGGER.error("Failed writing together File");
|
||||
//TogetherWorldPreset.writeWorldPresetSettings(worldGenSettings);
|
||||
}
|
||||
WorldEventsImpl.ON_WORLD_LOAD.emit(OnWorldLoad::onLoad);
|
||||
}
|
||||
}
|
||||
|
@ -173,9 +180,9 @@ public class WorldBootstrap {
|
|||
static Optional<Holder<WorldPreset>> setupNewWorldCommon(
|
||||
LevelStorageSource.LevelStorageAccess levelStorageAccess,
|
||||
Optional<Holder<WorldPreset>> currentPreset,
|
||||
WorldGenSettings worldgenSettings
|
||||
WorldGenSettings worldGenSettings
|
||||
) {
|
||||
Helpers.initializeWorldDataAPI(levelStorageAccess, true);
|
||||
Helpers.initializeWorldConfig(levelStorageAccess, true);
|
||||
|
||||
|
||||
final WorldPresetSettings settings;
|
||||
|
@ -193,9 +200,15 @@ public class WorldBootstrap {
|
|||
true
|
||||
));
|
||||
|
||||
currentPreset = WorldEventsImpl.ADAPT_WORLD_PRESET.emit(currentPreset, worldgenSettings);
|
||||
currentPreset = WorldEventsImpl.ADAPT_WORLD_PRESET.emit(currentPreset, worldGenSettings);
|
||||
|
||||
TogetherWorldPreset.writeWorldPresetSettings(currentPreset);
|
||||
if (currentPreset.map(h -> h.value()).orElse(null) instanceof WorldPresetAccessor acc) {
|
||||
TogetherWorldPreset.writeWorldPresetSettings(acc.bcl_getDimensions());
|
||||
} else {
|
||||
WorldsTogether.LOGGER.error("Failed writing together File");
|
||||
//TogetherWorldPreset.writeWorldPresetSettings(worldGenSettings);
|
||||
}
|
||||
|
||||
//LifeCycleAPI._runBeforeLevelLoad();
|
||||
WorldEventsImpl.ON_WORLD_LOAD.emit(OnWorldLoad::onLoad);
|
||||
|
@ -212,7 +225,7 @@ public class WorldBootstrap {
|
|||
) {
|
||||
try {
|
||||
var levelStorageAccess = levelSource.createAccess(levelID);
|
||||
Helpers.initializeWorldDataAPI(levelStorageAccess, false);
|
||||
Helpers.initializeWorldConfig(levelStorageAccess, false);
|
||||
|
||||
//Helpers.setupWorld();
|
||||
WorldEventsImpl.BEFORE_WORLD_LOAD.emit(e -> e.prepareWorld(
|
||||
|
@ -270,10 +283,7 @@ public class WorldBootstrap {
|
|||
}
|
||||
|
||||
public static WorldGenSettings enforceInNewWorld(WorldGenSettings worldGenSettings) {
|
||||
worldGenSettings = WorldGenUtil
|
||||
.getWorldSettings()
|
||||
.repairSettingsOnLoad(LAST_REGISTRY_ACCESS, worldGenSettings);
|
||||
return worldGenSettings;
|
||||
return WorldGenUtil.repairBiomeSourceInAllDimensions(LAST_REGISTRY_ACCESS, worldGenSettings);
|
||||
}
|
||||
|
||||
public static WorldGenSettings enforceInLoadedWorld(
|
||||
|
@ -281,9 +291,7 @@ public class WorldBootstrap {
|
|||
WorldGenSettings worldGenSettings
|
||||
) {
|
||||
if (registryOps.orElse(null) instanceof RegistryOpsAccessor acc) {
|
||||
return WorldGenUtil
|
||||
.getWorldSettings()
|
||||
.repairSettingsOnLoad(acc.bcl_getRegistryAccess(), worldGenSettings);
|
||||
return WorldGenUtil.repairBiomeSourceInAllDimensions(acc.bcl_getRegistryAccess(), worldGenSettings);
|
||||
//.repairSettingsOnLoad(LAST_REGISTRY_ACCESS, worldGenSettings);
|
||||
} else {
|
||||
BCLib.LOGGER.error("Unable to obtain registryAccess when enforcing generators.");
|
||||
|
|
|
@ -1,24 +1,32 @@
|
|||
package org.betterx.worlds.together.worldPreset;
|
||||
|
||||
import org.betterx.worlds.together.WorldsTogether;
|
||||
import org.betterx.worlds.together.levelgen.WorldGenUtil;
|
||||
import org.betterx.worlds.together.mixin.common.WorldPresetAccessor;
|
||||
import org.betterx.worlds.together.world.WorldConfig;
|
||||
import org.betterx.worlds.together.world.WorldGenUtil;
|
||||
import org.betterx.worlds.together.world.event.WorldBootstrap;
|
||||
import org.betterx.worlds.together.worldPreset.settings.VanillaWorldPresetSettings;
|
||||
import org.betterx.worlds.together.worldPreset.settings.WorldPresetSettings;
|
||||
|
||||
import net.minecraft.core.Holder;
|
||||
import com.mojang.serialization.Codec;
|
||||
import com.mojang.serialization.Dynamic;
|
||||
import com.mojang.serialization.codecs.RecordCodecBuilder;
|
||||
import net.minecraft.core.Registry;
|
||||
import net.minecraft.core.RegistryAccess;
|
||||
import net.minecraft.data.BuiltinRegistries;
|
||||
import net.minecraft.nbt.CompoundTag;
|
||||
import net.minecraft.nbt.NbtOps;
|
||||
import net.minecraft.nbt.Tag;
|
||||
import net.minecraft.resources.RegistryOps;
|
||||
import net.minecraft.resources.ResourceKey;
|
||||
import net.minecraft.world.level.chunk.ChunkGenerator;
|
||||
import net.minecraft.world.level.dimension.LevelStem;
|
||||
import net.minecraft.world.level.levelgen.presets.WorldPreset;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.Optional;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
public class TogetherWorldPreset extends WorldPreset {
|
||||
public final WorldPresetSettings settings;
|
||||
|
@ -54,20 +62,17 @@ public class TogetherWorldPreset extends WorldPreset {
|
|||
return ((WorldPresetAccessor) this).bcl_getDimensions();
|
||||
}
|
||||
|
||||
public static WorldPresetSettings writeWorldPresetSettings(Optional<Holder<WorldPreset>> worldPreset) {
|
||||
if (worldPreset.isPresent() && worldPreset.get().value() instanceof TogetherWorldPreset wp) {
|
||||
writeWorldPresetSettings(wp.settings);
|
||||
return wp.settings;
|
||||
} else {
|
||||
writeWorldPresetSettings(VanillaWorldPresetSettings.DEFAULT);
|
||||
return VanillaWorldPresetSettings.DEFAULT;
|
||||
}
|
||||
public LevelStem getDimension(ResourceKey<LevelStem> key) {
|
||||
return getDimensions().get(key);
|
||||
}
|
||||
|
||||
public static void writeWorldPresetSettings(WorldPresetSettings presetSettings) {
|
||||
final RegistryOps<Tag> registryOps = RegistryOps.create(NbtOps.INSTANCE, BuiltinRegistries.ACCESS);
|
||||
final var codec = WorldPresetSettings.CODEC.orElse(presetSettings);
|
||||
final var encodeResult = codec.encodeStart(registryOps, presetSettings);
|
||||
public static void writeWorldPresetSettings(Map<ResourceKey<LevelStem>, LevelStem> settings) {
|
||||
final RegistryOps<Tag> registryOps = RegistryOps.create(
|
||||
NbtOps.INSTANCE,
|
||||
WorldBootstrap.getLastRegistryAccess()
|
||||
);
|
||||
DimensionsWrapper wrapper = new DimensionsWrapper(DimensionsWrapper.build(settings));
|
||||
final var encodeResult = wrapper.CODEC.encodeStart(registryOps, wrapper);
|
||||
|
||||
if (encodeResult.result().isPresent()) {
|
||||
final CompoundTag settingsNbt = WorldConfig.getRootTag(WorldsTogether.MOD_ID);
|
||||
|
@ -78,4 +83,75 @@ public class TogetherWorldPreset extends WorldPreset {
|
|||
|
||||
WorldConfig.saveFile(WorldsTogether.MOD_ID);
|
||||
}
|
||||
|
||||
private static DimensionsWrapper DEFAULT_DIMENSIONS_WRAPPER = null;
|
||||
|
||||
public static @NotNull Map<ResourceKey<LevelStem>, ChunkGenerator> getWorldDimensions() {
|
||||
if (BuiltinRegistries.ACCESS == null) return null;
|
||||
final RegistryAccess registryAccess;
|
||||
if (WorldBootstrap.getLastRegistryAccess() != null) {
|
||||
registryAccess = WorldBootstrap.getLastRegistryAccess();
|
||||
} else {
|
||||
registryAccess = BuiltinRegistries.ACCESS;
|
||||
}
|
||||
final RegistryOps<Tag> registryOps = RegistryOps.create(NbtOps.INSTANCE, registryAccess);
|
||||
|
||||
Optional<DimensionsWrapper> oLevelStem = DimensionsWrapper.CODEC
|
||||
.parse(new Dynamic<>(registryOps, WorldGenUtil.getSettingsNbt()))
|
||||
.resultOrPartial(WorldsTogether.LOGGER::error);
|
||||
|
||||
if (DEFAULT_DIMENSIONS_WRAPPER == null) {
|
||||
DEFAULT_DIMENSIONS_WRAPPER = new DimensionsWrapper(WorldPresets
|
||||
.get(
|
||||
registryAccess,
|
||||
WorldPresets.DEFAULT.orElseThrow()
|
||||
)
|
||||
.value()
|
||||
.createWorldGenSettings(0, true, true)
|
||||
.dimensions());
|
||||
}
|
||||
|
||||
return oLevelStem.orElse(DEFAULT_DIMENSIONS_WRAPPER).dimensions;
|
||||
}
|
||||
|
||||
private static class DimensionsWrapper {
|
||||
public static final Codec<DimensionsWrapper> CODEC = RecordCodecBuilder.create(instance -> instance
|
||||
.group(Codec.unboundedMap(
|
||||
ResourceKey.codec(Registry.LEVEL_STEM_REGISTRY),
|
||||
ChunkGenerator.CODEC
|
||||
)
|
||||
.fieldOf("dimensions")
|
||||
.orElse(new HashMap<>())
|
||||
.forGetter(o -> o.dimensions))
|
||||
.apply(instance, DimensionsWrapper::new));
|
||||
final Map<ResourceKey<LevelStem>, ChunkGenerator> dimensions;
|
||||
|
||||
static Map<ResourceKey<LevelStem>, ChunkGenerator> build(Registry<LevelStem> dimensions) {
|
||||
Map<ResourceKey<LevelStem>, ChunkGenerator> map = new HashMap<>();
|
||||
for (var entry : dimensions.entrySet()) {
|
||||
ResourceKey<LevelStem> key = entry.getKey();
|
||||
LevelStem stem = entry.getValue();
|
||||
map.put(key, stem.generator());
|
||||
}
|
||||
return map;
|
||||
}
|
||||
|
||||
static Map<ResourceKey<LevelStem>, ChunkGenerator> build(Map<ResourceKey<LevelStem>, LevelStem> input) {
|
||||
Map<ResourceKey<LevelStem>, ChunkGenerator> map = new HashMap<>();
|
||||
for (var entry : input.entrySet()) {
|
||||
ResourceKey<LevelStem> key = entry.getKey();
|
||||
LevelStem stem = entry.getValue();
|
||||
map.put(key, stem.generator());
|
||||
}
|
||||
return map;
|
||||
}
|
||||
|
||||
DimensionsWrapper(Registry<LevelStem> dimensions) {
|
||||
this(build(dimensions));
|
||||
}
|
||||
|
||||
private DimensionsWrapper(Map<ResourceKey<LevelStem>, ChunkGenerator> dimensions) {
|
||||
this.dimensions = dimensions;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -4,7 +4,7 @@ import org.betterx.bclib.registry.PresetsRegistry;
|
|||
import org.betterx.worlds.together.WorldsTogether;
|
||||
import org.betterx.worlds.together.tag.v3.TagManager;
|
||||
import org.betterx.worlds.together.tag.v3.TagRegistry;
|
||||
import org.betterx.worlds.together.world.WorldGenUtil;
|
||||
import org.betterx.worlds.together.levelgen.WorldGenUtil;
|
||||
import org.betterx.worlds.together.worldPreset.client.WorldPresetsClient;
|
||||
import org.betterx.worlds.together.worldPreset.settings.VanillaWorldPresetSettings;
|
||||
import org.betterx.worlds.together.worldPreset.settings.WorldPresetSettings;
|
||||
|
|
|
@ -1,8 +1,5 @@
|
|||
package org.betterx.worlds.together.worldPreset.settings;
|
||||
|
||||
import org.betterx.worlds.together.surfaceRules.SurfaceRuleRegistry;
|
||||
import org.betterx.worlds.together.surfaceRules.SurfaceRuleUtil;
|
||||
|
||||
import com.mojang.serialization.Codec;
|
||||
import net.minecraft.core.Holder;
|
||||
import net.minecraft.core.RegistryAccess;
|
||||
|
@ -30,9 +27,4 @@ public class VanillaWorldPresetSettings extends WorldPresetSettings {
|
|||
public BiomeSource addDatapackBiomes(BiomeSource biomeSource, Set<Holder<Biome>> datapackBiomes) {
|
||||
return biomeSource;
|
||||
}
|
||||
|
||||
|
||||
public void injectSurfaceRules(RegistryAccess registryAccess, WorldGenSettings settings) {
|
||||
SurfaceRuleUtil.injectSurfaceRules(settings, SurfaceRuleRegistry.ALL_DIMENSIONS);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -52,5 +52,5 @@ public abstract class WorldPresetSettings {
|
|||
public abstract Codec<? extends WorldPresetSettings> codec();
|
||||
public abstract WorldGenSettings repairSettingsOnLoad(RegistryAccess registryAccess, WorldGenSettings settings);
|
||||
public abstract BiomeSource addDatapackBiomes(BiomeSource biomeSource, Set<Holder<Biome>> datapackBiomes);
|
||||
public abstract void injectSurfaceRules(RegistryAccess registryAccess, WorldGenSettings settings);
|
||||
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue