mirror of
https://github.com/GeyserMC/Geyser.git
synced 2025-12-19 14:59:27 +00:00
Add loading of new util.json mappings (#5823)
* Add loading of new util.json mappings * Remove now unused set * Switch to loading util mappings through registries * Add Javadocs for UtilMappings * Target mappings with util.json
This commit is contained in:
@@ -29,6 +29,7 @@ import it.unimi.dsi.fastutil.ints.Int2ObjectOpenHashMap;
|
||||
import it.unimi.dsi.fastutil.objects.Object2IntMap;
|
||||
import it.unimi.dsi.fastutil.objects.Object2ObjectMap;
|
||||
import it.unimi.dsi.fastutil.objects.Object2ObjectOpenHashMap;
|
||||
import net.kyori.adventure.key.Key;
|
||||
import org.cloudburstmc.nbt.NbtMap;
|
||||
import org.cloudburstmc.nbt.NbtMapBuilder;
|
||||
import org.cloudburstmc.protocol.bedrock.data.biome.BiomeDefinitions;
|
||||
@@ -56,6 +57,7 @@ import org.geysermc.geyser.registry.provider.ProviderSupplier;
|
||||
import org.geysermc.geyser.registry.type.ItemMappings;
|
||||
import org.geysermc.geyser.registry.type.ParticleMapping;
|
||||
import org.geysermc.geyser.registry.type.SoundMapping;
|
||||
import org.geysermc.geyser.registry.type.UtilMappings;
|
||||
import org.geysermc.geyser.translator.level.block.entity.BlockEntityTranslator;
|
||||
import org.geysermc.geyser.translator.level.event.LevelEventTranslator;
|
||||
import org.geysermc.geyser.translator.sound.SoundInteractionTranslator;
|
||||
@@ -197,6 +199,21 @@ public final class Registries {
|
||||
*/
|
||||
public static final SimpleMappedDeferredRegistry<SoundTranslator, SoundInteractionTranslator<?>> SOUND_TRANSLATORS = SimpleMappedDeferredRegistry.create("org.geysermc.geyser.translator.sound.SoundTranslator", SoundTranslatorRegistryLoader::new);
|
||||
|
||||
/**
|
||||
* A registry containing all of Java's "game master blocks" - blocks that can't be broken without operator permission level 2 or higher.
|
||||
*/
|
||||
public static final ListDeferredRegistry<Key> GAME_MASTER_BLOCKS = ListDeferredRegistry.create(UtilMappings::gameMasterBlocks, RegistryLoaders.UTIL_MAPPINGS_KEYS);
|
||||
|
||||
/**
|
||||
* A registry containing all block entities Java considers "dangerous" - these have a red warning in the item tooltip on Java.
|
||||
*/
|
||||
public static final ListDeferredRegistry<Key> DANGEROUS_BLOCK_ENTITIES = ListDeferredRegistry.create(UtilMappings::dangerousBlockEntities, RegistryLoaders.UTIL_MAPPINGS_KEYS);
|
||||
|
||||
/**
|
||||
* A registry containing all entities Java considers "dangerous" - spawn eggs of these entities have a red warning in the item tooltip on Java.
|
||||
*/
|
||||
public static final ListDeferredRegistry<Key> DANGEROUS_ENTITIES = ListDeferredRegistry.create(UtilMappings::dangerousEntities, RegistryLoaders.UTIL_MAPPINGS_KEYS);
|
||||
|
||||
public static void load() {
|
||||
if (loaded) return;
|
||||
loaded = true;
|
||||
@@ -216,6 +233,10 @@ public final class Registries {
|
||||
SOUNDS.load();
|
||||
SOUND_LEVEL_EVENTS.load();
|
||||
SOUND_TRANSLATORS.load();
|
||||
|
||||
GAME_MASTER_BLOCKS.load();
|
||||
DANGEROUS_BLOCK_ENTITIES.load();
|
||||
DANGEROUS_ENTITIES.load();
|
||||
}
|
||||
|
||||
public static void populate() {
|
||||
|
||||
@@ -25,8 +25,11 @@
|
||||
|
||||
package org.geysermc.geyser.registry.loader;
|
||||
|
||||
import net.kyori.adventure.key.Key;
|
||||
import org.checkerframework.checker.nullness.qual.NonNull;
|
||||
import org.geysermc.geyser.registry.type.UtilMappings;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.function.Supplier;
|
||||
|
||||
/**
|
||||
@@ -48,6 +51,8 @@ public final class RegistryLoaders {
|
||||
*/
|
||||
public static final ResourcePackLoader RESOURCE_PACKS = new ResourcePackLoader();
|
||||
|
||||
public static final UtilMappings.Loader<List<Key>> UTIL_MAPPINGS_KEYS = new UtilMappings.Loader<>();
|
||||
|
||||
/**
|
||||
* Wraps the surrounding {@link Supplier} in a {@link RegistryLoader} which does
|
||||
* not take in any input value.
|
||||
|
||||
@@ -0,0 +1,90 @@
|
||||
/*
|
||||
* Copyright (c) 2025 GeyserMC. http://geysermc.org
|
||||
*
|
||||
* 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.
|
||||
*
|
||||
* @author GeyserMC
|
||||
* @link https://github.com/GeyserMC/Geyser
|
||||
*/
|
||||
|
||||
package org.geysermc.geyser.registry.type;
|
||||
|
||||
import com.google.gson.JsonObject;
|
||||
import com.google.gson.JsonParser;
|
||||
import net.kyori.adventure.key.Key;
|
||||
import org.geysermc.geyser.GeyserImpl;
|
||||
import org.geysermc.geyser.registry.loader.RegistryLoader;
|
||||
import org.geysermc.geyser.util.MinecraftKey;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.io.InputStreamReader;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.function.Function;
|
||||
|
||||
/**
|
||||
* Used to load and store the {@code mappings/util.json} file. When adding new fields to util mappings, be sure to create a proper registry for them
|
||||
* in {@link org.geysermc.geyser.registry.Registries}. Use {@link org.geysermc.geyser.registry.loader.RegistryLoaders#UTIL_MAPPINGS_KEYS} (or create a new loader if loading something
|
||||
* other than keys).
|
||||
*/
|
||||
public record UtilMappings(List<Key> gameMasterBlocks, List<Key> dangerousBlockEntities, List<Key> dangerousEntities) {
|
||||
private static final String INPUT = "mappings/util.json";
|
||||
private static UtilMappings loaded = null;
|
||||
|
||||
/**
|
||||
* Gets the loaded util mappings, or loads them if they weren't yet.
|
||||
*/
|
||||
private static UtilMappings get() {
|
||||
if (loaded == null) {
|
||||
try (InputStream utilInput = GeyserImpl.getInstance().getBootstrap().getResourceOrThrow(INPUT)) {
|
||||
JsonObject utilJson = JsonParser.parseReader(new InputStreamReader(utilInput)).getAsJsonObject();
|
||||
|
||||
List<Key> gameMasterBlocks = new ArrayList<>();
|
||||
List<Key> dangerousBlockEntities = new ArrayList<>();
|
||||
List<Key> dangerousEntities = new ArrayList<>();
|
||||
|
||||
utilJson.get("game_master_blocks").getAsJsonArray()
|
||||
.forEach(element -> gameMasterBlocks.add(MinecraftKey.key(element.getAsString())));
|
||||
utilJson.get("dangerous_block_entities").getAsJsonArray()
|
||||
.forEach(element -> dangerousBlockEntities.add(MinecraftKey.key(element.getAsString())));
|
||||
utilJson.get("dangerous_entities").getAsJsonArray()
|
||||
.forEach(element -> dangerousEntities.add(MinecraftKey.key(element.getAsString())));
|
||||
|
||||
loaded = new UtilMappings(List.copyOf(gameMasterBlocks), List.copyOf(dangerousBlockEntities), List.copyOf(dangerousEntities));
|
||||
} catch (IOException e) {
|
||||
throw new AssertionError("Failed to load " + INPUT);
|
||||
}
|
||||
}
|
||||
return loaded;
|
||||
}
|
||||
|
||||
/**
|
||||
* Simply gets a field of the loaded {@link UtilMappings} object. Instead of re-opening the util mappings file every time a field is loaded,
|
||||
* the mappings are parsed once by {@link UtilMappings#get()} and kept in a static variable.
|
||||
* Loader input is a function that extracts the field to get from the {@link UtilMappings} object.
|
||||
*/
|
||||
public static class Loader<T> implements RegistryLoader<Function<UtilMappings, T>, T> {
|
||||
|
||||
@Override
|
||||
public T load(Function<UtilMappings, T> input) {
|
||||
return input.apply(UtilMappings.get());
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -50,6 +50,7 @@ import org.geysermc.geyser.level.block.type.Block;
|
||||
import org.geysermc.geyser.level.block.type.BlockState;
|
||||
import org.geysermc.geyser.level.physics.Direction;
|
||||
import org.geysermc.geyser.registry.BlockRegistries;
|
||||
import org.geysermc.geyser.registry.Registries;
|
||||
import org.geysermc.geyser.registry.type.ItemMapping;
|
||||
import org.geysermc.geyser.session.GeyserSession;
|
||||
import org.geysermc.geyser.translator.item.CustomItemTranslator;
|
||||
@@ -76,16 +77,6 @@ import java.util.concurrent.TimeUnit;
|
||||
*/
|
||||
public class BlockBreakHandler {
|
||||
|
||||
private final static Set<Block> GAME_MASTER_BLOCKS = Set.of(
|
||||
Blocks.COMMAND_BLOCK,
|
||||
Blocks.CHAIN_COMMAND_BLOCK,
|
||||
Blocks.REPEATING_COMMAND_BLOCK,
|
||||
Blocks.JIGSAW,
|
||||
Blocks.STRUCTURE_BLOCK,
|
||||
Blocks.TEST_BLOCK,
|
||||
Blocks.TEST_INSTANCE_BLOCK
|
||||
);
|
||||
|
||||
protected final GeyserSession session;
|
||||
|
||||
/**
|
||||
@@ -457,7 +448,7 @@ public class BlockBreakHandler {
|
||||
}
|
||||
}
|
||||
|
||||
if (GAME_MASTER_BLOCKS.contains(state.block())) {
|
||||
if (Registries.GAME_MASTER_BLOCKS.get().contains(state.block().javaIdentifier())) {
|
||||
if (!instabuild || session.getOpPermissionLevel() < 2) {
|
||||
return false;
|
||||
}
|
||||
|
||||
Submodule core/src/main/resources/mappings updated: 8002ed6ed8...01a320f40a
Reference in New Issue
Block a user