forked from FabricMC/fabric
Add checkstyle, format existing code accordingly.
This commit is contained in:
parent
d1753d4af9
commit
dfdb52d6e5
301 changed files with 3209 additions and 2520 deletions
1
.gitignore
vendored
1
.gitignore
vendored
|
@ -2,6 +2,7 @@
|
|||
.gradle
|
||||
|
||||
# Eclipse
|
||||
.checkstyle
|
||||
.classpath
|
||||
.metadata
|
||||
.settings
|
||||
|
|
12
build.gradle
12
build.gradle
|
@ -43,6 +43,7 @@ def getBranch(){
|
|||
}
|
||||
|
||||
allprojects {
|
||||
apply plugin: 'checkstyle'
|
||||
apply plugin: 'maven-publish'
|
||||
apply plugin: 'fabric-loom'
|
||||
apply plugin: 'net.minecrell.licenser'
|
||||
|
@ -52,8 +53,6 @@ allprojects {
|
|||
|
||||
group = "net.fabricmc.fabric-api"
|
||||
|
||||
|
||||
|
||||
dependencies {
|
||||
minecraft "com.mojang:minecraft:$Globals.mcVersion"
|
||||
mappings "net.fabricmc:yarn:${Globals.mcVersion}${Globals.yarnVersion}"
|
||||
|
@ -105,9 +104,14 @@ allprojects {
|
|||
classifier = 'sources'
|
||||
from sourceSets.main.allSource
|
||||
}
|
||||
|
||||
|
||||
checkstyle {
|
||||
configFile = rootProject.file("checkstyle.xml")
|
||||
toolVersion = '8.25'
|
||||
}
|
||||
}
|
||||
javadoc{
|
||||
|
||||
javadoc {
|
||||
options.memberLevel = "PACKAGE"
|
||||
allprojects.each{
|
||||
source( it.sourceSets.main.allJava.srcDirs)
|
||||
|
|
162
checkstyle.xml
Normal file
162
checkstyle.xml
Normal file
|
@ -0,0 +1,162 @@
|
|||
<?xml version="1.0"?>
|
||||
<!DOCTYPE module PUBLIC "-//Puppy Crawl//DTD Check Configuration 1.2//EN" "http://www.puppycrawl.com/dtds/configuration_1_2.dtd">
|
||||
<module name="Checker">
|
||||
<property name="charset" value="UTF-8"/>
|
||||
<property name="fileExtensions" value="java"/>
|
||||
|
||||
<module name="NewlineAtEndOfFile"/>
|
||||
|
||||
<!-- disallow trailing whitespace -->
|
||||
<module name="RegexpSingleline">
|
||||
<property name="format" value="\s+$"/>
|
||||
<property name="message" value="trailing whitespace"/>
|
||||
</module>
|
||||
|
||||
<!-- note: RegexpMultiline shows nicer messages than Regexp, but has to be outside TreeWalker -->
|
||||
<!-- disallow multiple consecutive blank lines -->
|
||||
<module name="RegexpMultiline">
|
||||
<property name="format" value="\n[\r\t ]*\n[\r\t ]*\n"/>
|
||||
<property name="message" value="adjacent blank lines"/>
|
||||
</module>
|
||||
|
||||
<!-- disallow blank after { -->
|
||||
<module name="RegexpMultiline">
|
||||
<property name="format" value="\{[\r\t ]*\n[\r\t ]*\n"/>
|
||||
<property name="message" value="blank line after '{'"/>
|
||||
</module>
|
||||
|
||||
<!-- disallow blank before } -->
|
||||
<module name="RegexpMultiline">
|
||||
<property name="format" value="\n[\r\t ]*\n[\r\t ]*\}"/>
|
||||
<property name="message" value="blank line before '}'"/>
|
||||
</module>
|
||||
|
||||
<!-- require blank before { in the same indentation level -->
|
||||
<module name="RegexpMultiline">
|
||||
<!-- the regex works as follows:
|
||||
It matches (=fails) for \n<indentation><something>\n<same indentation><control statement>[...]{\n
|
||||
while <something> is a single line comment, it'll look for a blank line one line earlier
|
||||
if <something> is a space, indicating a formatting error or ' */', it'll ignore the instance
|
||||
if <something> is a tab, indicating a continued line, it'll ignore the instance
|
||||
<control statement> is 'if', 'do', 'while', 'for', 'try' or nothing (instance initializer block)
|
||||
|
||||
- first \n: with positive lookbehind (?<=\n) to move the error marker to a more reasonable place
|
||||
- capture tabs for <indentation>, later referenced via \1
|
||||
- remaining preceding line as a non-comment (doesn't start with '/', '//', ' ' or '\t') or multiple lines where all but the first are a single line comment with the same indentation
|
||||
- new line
|
||||
- <indentation> as captured earlier
|
||||
- <control statement> as specified above
|
||||
- { before the next new line -->
|
||||
<property name="format" value="(?<=\n)([\t]+)(?:[^/\n \t][^\n]*|/[^/\n][^\n]*|[^/\n][^\n]*(\n\1//[^\n]*)+)\n\1(|(if|do|while|for|try)[^\n]+)\{[\r\t ]*\n"/>
|
||||
<property name="message" value="missing blank line before block at same indentation level"/>
|
||||
</module>
|
||||
|
||||
<!-- require blank after } in the same indentation level -->
|
||||
<module name="RegexpMultiline">
|
||||
<!-- \n<indentation>}\n<same indentation><whatever unless newline, '}' or starting with cas(e) or def(ault)> -->
|
||||
<property name="format" value="(?<=\n)([\t]+)\}\n\1(?:[^\r\n\}cd]|c[^\r\na]|ca[^\r\ns]|d[^\r\ne]|de[^\r\nf])"/>
|
||||
<property name="message" value="missing blank line after block at same indentation level"/>
|
||||
</module>
|
||||
|
||||
<module name="TreeWalker">
|
||||
<!-- Ensure all imports are ship shape -->
|
||||
<module name="AvoidStarImport"/>
|
||||
<module name="IllegalImport"/>
|
||||
<module name="RedundantImport"/>
|
||||
<module name="UnusedImports"/>
|
||||
|
||||
<module name="ImportOrder">
|
||||
<property name="groups" value="java,javax,*,net.minecraft,net.fabricmc"/>
|
||||
<property name="ordered" value="false"/><!-- the plugin orders alphabetically without considering separators.. -->
|
||||
<property name="separated" value="true"/>
|
||||
<property name="option" value="top"/>
|
||||
<property name="sortStaticImportsAlphabetically" value="true"/>
|
||||
</module>
|
||||
|
||||
<!-- Ensures braces are at the end of a line -->
|
||||
<module name="LeftCurly"/>
|
||||
<module name="RightCurly"/>
|
||||
|
||||
<!-- single line statements on one line, -->
|
||||
<module name="NeedBraces">
|
||||
<property name="tokens" value="LITERAL_IF,LITERAL_FOR,LITERAL_WHILE"/>
|
||||
<property name="allowSingleLineStatement" value="true"/>
|
||||
</module>
|
||||
<module name="NeedBraces">
|
||||
<property name="tokens" value="LITERAL_ELSE,LITERAL_DO"/>
|
||||
<property name="allowSingleLineStatement" value="false"/>
|
||||
</module>
|
||||
|
||||
<module name="EmptyLineSeparator">
|
||||
<property name="allowNoEmptyLineBetweenFields" value="true"/>
|
||||
<property name="allowMultipleEmptyLines" value="false"/>
|
||||
<!-- exclude METHOD_DEF and VARIABLE_DEF -->
|
||||
<property name="tokens" value="PACKAGE_DEF,IMPORT,STATIC_IMPORT,CLASS_DEF,INTERFACE_DEF,ENUM_DEF,STATIC_INIT,INSTANCE_INIT,CTOR_DEF"/>
|
||||
</module>
|
||||
|
||||
<module name="OperatorWrap"/>
|
||||
<module name="SeparatorWrap">
|
||||
<property name="tokens" value="DOT,ELLIPSIS,AT"/>
|
||||
<property name="option" value="nl"/>
|
||||
</module>
|
||||
<module name="SeparatorWrap">
|
||||
<property name="tokens" value="COMMA,SEMI"/>
|
||||
<property name="option" value="eol"/>
|
||||
</module>
|
||||
|
||||
<module name="Indentation">
|
||||
<property name="basicOffset" value="8"/>
|
||||
<property name="caseIndent" value="0"/>
|
||||
<property name="throwsIndent" value="8"/>
|
||||
<property name="arrayInitIndent" value="8"/>
|
||||
<property name="lineWrappingIndentation" value="16"/>
|
||||
</module>
|
||||
|
||||
<module name="ParenPad"/>
|
||||
<module name="NoWhitespaceBefore"/>
|
||||
<module name="NoWhitespaceAfter">
|
||||
<!-- allow ARRAY_INIT -->
|
||||
<property name="tokens" value="AT,INC,DEC,UNARY_MINUS,UNARY_PLUS,BNOT,LNOT,DOT,ARRAY_DECLARATOR,INDEX_OP"/>
|
||||
</module>
|
||||
<module name="WhitespaceAfter"/>
|
||||
<module name="WhitespaceAround">
|
||||
<!-- Allow PLUS, MINUS, MUL, DIV as they may be more readable without spaces in some cases -->
|
||||
<property name="tokens" value="ASSIGN,BAND,BAND_ASSIGN,BOR,BOR_ASSIGN,BSR,BSR_ASSIGN,BXOR,BXOR_ASSIGN,COLON,DIV_ASSIGN,DO_WHILE,EQUAL,GE,GT,LAMBDA,LAND,LCURLY,LE,LITERAL_CATCH,LITERAL_DO,LITERAL_ELSE,LITERAL_FINALLY,LITERAL_FOR,LITERAL_IF,LITERAL_RETURN,LITERAL_SWITCH,LITERAL_SYNCHRONIZED,LITERAL_TRY,LITERAL_WHILE,LOR,LT,MINUS_ASSIGN,MOD,MOD_ASSIGN,NOT_EQUAL,PLUS_ASSIGN,QUESTION,RCURLY,SL,SLIST,SL_ASSIGN,SR,SR_ASSIGN,STAR,STAR_ASSIGN,LITERAL_ASSERT,TYPE_EXTENSION_AND"/>
|
||||
</module>
|
||||
<module name="SingleSpaceSeparator"/>
|
||||
<module name="GenericWhitespace"/>
|
||||
<module name="CommentsIndentation"/>
|
||||
|
||||
<module name="ArrayTypeStyle"/>
|
||||
<module name="DefaultComesLast">
|
||||
<property name="skipIfLastAndSharedWithCase" value="true"/>
|
||||
</module>
|
||||
<module name="SimplifyBooleanExpression"/>
|
||||
<module name="SimplifyBooleanReturn"/>
|
||||
<module name="StringLiteralEquality"/>
|
||||
|
||||
<module name="ModifierOrder"/>
|
||||
<module name="RedundantModifier"/>
|
||||
|
||||
<module name="AnnotationLocation"/>
|
||||
<module name="MissingOverride"/>
|
||||
|
||||
<!-- By default this allows catch blocks with only comments -->
|
||||
<module name="EmptyCatchBlock"/>
|
||||
|
||||
<!-- Enforce tabs -->
|
||||
<module name="RegexpSinglelineJava">
|
||||
<property name="format" value="^\t* ([^*]|\*[^ /])"/>
|
||||
<property name="message" value="non-tab indentation"/>
|
||||
</module>
|
||||
|
||||
<module name="OuterTypeFilename"/>
|
||||
|
||||
<!--<module name="InvalidJavadocPosition"/>-->
|
||||
<module name="JavadocParagraph"/>
|
||||
<module name="JavadocStyle"/>
|
||||
<module name="AtclauseOrder">
|
||||
<property name="tagOrder" value="@param,@return,@throws,@deprecated"/>
|
||||
</module>
|
||||
</module>
|
||||
</module>
|
|
@ -32,8 +32,8 @@ public abstract class Event<T> {
|
|||
|
||||
/**
|
||||
* Returns the invoker instance.
|
||||
* <p>
|
||||
* An "invoker" is an object which hides multiple registered
|
||||
*
|
||||
* <p>An "invoker" is an object which hides multiple registered
|
||||
* listeners of type T under one instance of type T, executing
|
||||
* them and leaving early as necessary.
|
||||
*
|
||||
|
|
|
@ -16,19 +16,17 @@
|
|||
|
||||
package net.fabricmc.fabric.api.event;
|
||||
|
||||
import net.fabricmc.fabric.impl.event.EventFactoryImpl;
|
||||
|
||||
import java.util.function.Function;
|
||||
|
||||
import net.fabricmc.fabric.impl.event.EventFactoryImpl;
|
||||
|
||||
/**
|
||||
* Helper for creating {@link Event} classes.
|
||||
*/
|
||||
public final class EventFactory {
|
||||
private static boolean profilingEnabled = true;
|
||||
|
||||
private EventFactory() {
|
||||
|
||||
}
|
||||
private EventFactory() { }
|
||||
|
||||
/**
|
||||
* @return True if events are supposed to be profiled.
|
||||
|
@ -61,8 +59,8 @@ public final class EventFactory {
|
|||
|
||||
/**
|
||||
* Create an "array-backed" Event instance with a custom empty invoker.
|
||||
* <p>
|
||||
* Having a custom empty invoker (of type (...) -> {}) increases performance
|
||||
*
|
||||
* <p>Having a custom empty invoker (of type (...) -> {}) increases performance
|
||||
* relative to iterating over an empty array; however, it only really matters
|
||||
* if the event is executed thousands of times a second.
|
||||
*
|
||||
|
|
|
@ -22,10 +22,10 @@ import net.minecraft.nbt.Tag;
|
|||
/**
|
||||
* NBT type ID constants. Useful for filtering by value type in a few cases.
|
||||
*
|
||||
* <p>For the current list of types, check with {@link Tag#TYPES}.
|
||||
*
|
||||
* @see CompoundTag#containsKey(String, int)
|
||||
* @see Tag#idToString(int)
|
||||
* <p>
|
||||
* For the current list of types, check with {@link Tag#TYPES}.
|
||||
*/
|
||||
public final class NbtType {
|
||||
public static final int END = 0;
|
||||
|
@ -49,7 +49,5 @@ public final class NbtType {
|
|||
*/
|
||||
public static final int NUMBER = 99;
|
||||
|
||||
private NbtType() {
|
||||
|
||||
}
|
||||
private NbtType() { }
|
||||
}
|
||||
|
|
|
@ -16,12 +16,12 @@
|
|||
|
||||
package net.fabricmc.fabric.impl.event;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
|
||||
import java.lang.reflect.Array;
|
||||
import java.util.Arrays;
|
||||
import java.util.function.Function;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
|
||||
class ArrayBackedEvent<T> extends Event<T> {
|
||||
private final Class<? super T> type;
|
||||
private final Function<T[], T> invokerFactory;
|
||||
|
|
|
@ -16,8 +16,6 @@
|
|||
|
||||
package net.fabricmc.fabric.impl.event;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
|
||||
import java.lang.invoke.MethodHandle;
|
||||
import java.lang.invoke.MethodHandles;
|
||||
import java.lang.invoke.MethodType;
|
||||
|
@ -29,12 +27,12 @@ import java.util.ArrayList;
|
|||
import java.util.List;
|
||||
import java.util.function.Function;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
|
||||
public final class EventFactoryImpl {
|
||||
private static final List<ArrayBackedEvent<?>> ARRAY_BACKED_EVENTS = new ArrayList<>();
|
||||
|
||||
private EventFactoryImpl() {
|
||||
|
||||
}
|
||||
private EventFactoryImpl() { }
|
||||
|
||||
public static void invalidate() {
|
||||
ARRAY_BACKED_EVENTS.forEach(ArrayBackedEvent::update);
|
||||
|
|
|
@ -16,24 +16,22 @@
|
|||
|
||||
package net.fabricmc.fabric.api.biomes.v1;
|
||||
|
||||
import net.fabricmc.fabric.impl.biomes.InternalBiomeData;
|
||||
import net.minecraft.world.biome.Biome;
|
||||
|
||||
import net.fabricmc.fabric.impl.biomes.InternalBiomeData;
|
||||
|
||||
/**
|
||||
* General API that applies to all biome sources
|
||||
* General API that applies to all biome sources.
|
||||
*/
|
||||
public final class FabricBiomes {
|
||||
|
||||
private FabricBiomes() {
|
||||
}
|
||||
private FabricBiomes() { }
|
||||
|
||||
/**
|
||||
* Allows players to naturally spawn in this biome
|
||||
* Allows players to naturally spawn in this biome.
|
||||
*
|
||||
* @param biome a biome the player should be able to spawn in
|
||||
*/
|
||||
public static void addSpawnBiome(Biome biome) {
|
||||
InternalBiomeData.addSpawnBiome(biome);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -16,16 +16,15 @@
|
|||
|
||||
package net.fabricmc.fabric.api.biomes.v1;
|
||||
|
||||
import net.fabricmc.fabric.impl.biomes.InternalBiomeData;
|
||||
import net.minecraft.world.biome.Biome;
|
||||
|
||||
import net.fabricmc.fabric.impl.biomes.InternalBiomeData;
|
||||
|
||||
/**
|
||||
* API that exposes some internals of the minecraft default biome source for the overworld
|
||||
* API that exposes some internals of the minecraft default biome source for the overworld.
|
||||
*/
|
||||
public final class OverworldBiomes {
|
||||
|
||||
private OverworldBiomes() {
|
||||
}
|
||||
private OverworldBiomes() { }
|
||||
|
||||
/**
|
||||
* Adds the biome to the specified climate group, with the specified weight. This is only for the biomes that make up the initial continents in generation.
|
||||
|
@ -41,7 +40,7 @@ public final class OverworldBiomes {
|
|||
}
|
||||
|
||||
/**
|
||||
* Adds the biome as a hills variant of the parent biome, with the specified weight
|
||||
* Adds the biome as a hills variant of the parent biome, with the specified weight.
|
||||
*
|
||||
* @param parent the biome to where the hills variant is added
|
||||
* @param hills the biome to be set as a hills variant
|
||||
|
@ -54,7 +53,7 @@ public final class OverworldBiomes {
|
|||
}
|
||||
|
||||
/**
|
||||
* Adds the biome as a shore/beach biome for the parent biome, with the specified weight
|
||||
* Adds the biome as a shore/beach biome for the parent biome, with the specified weight.
|
||||
*
|
||||
* @param parent the base biome to where the shore biome is added
|
||||
* @param shore the biome to be added as a shore biome
|
||||
|
@ -67,7 +66,7 @@ public final class OverworldBiomes {
|
|||
}
|
||||
|
||||
/**
|
||||
* Adds the biome as an an edge biome (excluding as a beach) of the parent biome, with the specified weight
|
||||
* Adds the biome as an an edge biome (excluding as a beach) of the parent biome, with the specified weight.
|
||||
*
|
||||
* @param parent the base biome to where the edge biome is added
|
||||
* @param edge the biome to be added as an edge biome
|
||||
|
@ -81,7 +80,8 @@ public final class OverworldBiomes {
|
|||
|
||||
/**
|
||||
* Adds a 'variant' biome which replaces another biome on occasion.
|
||||
* For example, addBiomeVariant(Biomes.JUNGLE, Biomes.DESERT, 0.2) will replace 20% of jungles with deserts.
|
||||
*
|
||||
* <p>For example, addBiomeVariant(Biomes.JUNGLE, Biomes.DESERT, 0.2) will replace 20% of jungles with deserts.
|
||||
* This method is rather useful for replacing biomes not generated through standard methods, such as oceans,
|
||||
* deep oceans, jungles, mushroom islands, etc. When replacing ocean and deep ocean biomes, one must specify
|
||||
* the biome without temperature (Biomes.OCEAN / Biomes.DEEP_OCEAN) only, as ocean temperatures have not been
|
||||
|
@ -107,5 +107,4 @@ public final class OverworldBiomes {
|
|||
public static void setRiverBiome(Biome parent, Biome river) {
|
||||
InternalBiomeData.setOverworldRiverBiome(parent, river);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -17,27 +17,26 @@
|
|||
package net.fabricmc.fabric.api.biomes.v1;
|
||||
|
||||
/**
|
||||
* Represents the climates of biomes on the overworld continents
|
||||
* Represents the climates of biomes on the overworld continents.
|
||||
*/
|
||||
public enum OverworldClimate {
|
||||
|
||||
/**
|
||||
* Includes Snowy Tundra (with a weight of 3) and Snowy Taiga (with a weight of 1)
|
||||
* Includes Snowy Tundra (with a weight of 3) and Snowy Taiga (with a weight of 1).
|
||||
*/
|
||||
SNOWY,
|
||||
|
||||
/**
|
||||
* Includes Forest, Taiga, Mountains, and Plains (all with weights of 1)
|
||||
* Includes Forest, Taiga, Mountains, and Plains (all with weights of 1).
|
||||
*/
|
||||
COOL,
|
||||
|
||||
/**
|
||||
* Includes Forest, Dark Forest, Mountains, Plains, Birch Forest, and Swamp (all with weights of 1)
|
||||
* Includes Forest, Dark Forest, Mountains, Plains, Birch Forest, and Swamp (all with weights of 1).
|
||||
*/
|
||||
TEMPERATE,
|
||||
|
||||
/**
|
||||
* Includes Desert (with a weight of 3), Savanna (with a weight of 2), and Plains (with a weight of 1)
|
||||
* Includes Desert (with a weight of 3), Savanna (with a weight of 2), and Plains (with a weight of 1).
|
||||
*/
|
||||
DRY
|
||||
}
|
||||
|
|
|
@ -19,10 +19,9 @@ package net.fabricmc.fabric.impl.biomes;
|
|||
import net.minecraft.world.biome.Biome;
|
||||
|
||||
/**
|
||||
* Represents a biome variant and its corresponding chance
|
||||
* Represents a biome variant and its corresponding chance.
|
||||
*/
|
||||
final class BiomeVariant {
|
||||
|
||||
private final Biome variant;
|
||||
private final double chance;
|
||||
|
||||
|
@ -48,5 +47,4 @@ final class BiomeVariant {
|
|||
double getChance() {
|
||||
return chance;
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -19,7 +19,7 @@ package net.fabricmc.fabric.impl.biomes;
|
|||
import net.minecraft.world.biome.Biome;
|
||||
|
||||
/**
|
||||
* Represents a biome and its corresponding weight
|
||||
* Represents a biome and its corresponding weight.
|
||||
*/
|
||||
final class ContinentalBiomeEntry {
|
||||
private final Biome biome;
|
||||
|
|
|
@ -16,26 +16,30 @@
|
|||
|
||||
package net.fabricmc.fabric.impl.biomes;
|
||||
|
||||
import java.lang.reflect.InvocationTargetException;
|
||||
import java.lang.reflect.Method;
|
||||
import java.util.EnumMap;
|
||||
import java.util.HashMap;
|
||||
import java.util.HashSet;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
|
||||
import com.google.common.base.Preconditions;
|
||||
import com.google.common.collect.ImmutableMap;
|
||||
import net.fabricmc.fabric.api.biomes.v1.OverworldClimate;
|
||||
|
||||
import net.minecraft.util.registry.Registry;
|
||||
import net.minecraft.world.biome.Biome;
|
||||
import net.minecraft.world.biome.Biomes;
|
||||
import net.minecraft.world.biome.layer.BiomeLayers;
|
||||
import net.minecraft.world.biome.source.VanillaLayeredBiomeSource;
|
||||
|
||||
import java.lang.reflect.InvocationTargetException;
|
||||
import java.lang.reflect.Method;
|
||||
import java.util.*;
|
||||
import net.fabricmc.fabric.api.biomes.v1.OverworldClimate;
|
||||
|
||||
/**
|
||||
* Lists and maps for internal use only! Stores data that is used by the various mixins into the world generation
|
||||
*/
|
||||
public final class InternalBiomeData {
|
||||
|
||||
private InternalBiomeData() {
|
||||
}
|
||||
private InternalBiomeData() { }
|
||||
|
||||
private static final EnumMap<OverworldClimate, WeightedBiomePicker> OVERWORLD_MODDED_CONTINENTAL_BIOME_PICKERS = new EnumMap<>(OverworldClimate.class);
|
||||
private static final Map<Biome, WeightedBiomePicker> OVERWORLD_HILLS_MAP = new HashMap<>();
|
||||
|
@ -95,6 +99,7 @@ public final class InternalBiomeData {
|
|||
public static void setOverworldRiverBiome(Biome primary, Biome river) {
|
||||
Preconditions.checkArgument(primary != null, "Primary biome is null");
|
||||
OVERWORLD_RIVER_MAP.put(primary, river);
|
||||
|
||||
if (river != null) {
|
||||
injectOverworldBiome(river);
|
||||
}
|
||||
|
@ -113,7 +118,7 @@ public final class InternalBiomeData {
|
|||
}
|
||||
|
||||
injectBiomeMethod.invoke(null, biome);
|
||||
} catch (NoSuchMethodException | SecurityException | IllegalAccessException | InvocationTargetException e){
|
||||
} catch (NoSuchMethodException | SecurityException | IllegalAccessException | InvocationTargetException e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -16,23 +16,22 @@
|
|||
|
||||
package net.fabricmc.fabric.impl.biomes;
|
||||
|
||||
import net.fabricmc.fabric.api.biomes.v1.OverworldClimate;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.function.IntConsumer;
|
||||
|
||||
import net.minecraft.util.Identifier;
|
||||
import net.minecraft.util.registry.Registry;
|
||||
import net.minecraft.world.biome.Biome;
|
||||
import net.minecraft.world.biome.layer.LayerRandomnessSource;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.function.IntConsumer;
|
||||
import net.fabricmc.fabric.api.biomes.v1.OverworldClimate;
|
||||
|
||||
/**
|
||||
* Internal utilities used for biome sampling
|
||||
* Internal utilities used for biome sampling.
|
||||
*/
|
||||
public final class InternalBiomeUtils {
|
||||
|
||||
private InternalBiomeUtils() {
|
||||
}
|
||||
private InternalBiomeUtils() { }
|
||||
|
||||
/**
|
||||
* @param north raw id of the biome to the north
|
||||
|
@ -85,14 +84,17 @@ public final class InternalBiomeUtils {
|
|||
reqWeightSum -= vanillaArrayWeight;
|
||||
int low = 0;
|
||||
int high = moddedBiomes.size() - 1;
|
||||
|
||||
while (low < high) {
|
||||
int mid = (high + low) >>> 1;
|
||||
|
||||
if (reqWeightSum < moddedBiomes.get(mid).getUpperWeightBound()) {
|
||||
high = mid;
|
||||
} else {
|
||||
low = mid + 1;
|
||||
}
|
||||
}
|
||||
|
||||
return low;
|
||||
}
|
||||
|
||||
|
@ -127,7 +129,7 @@ public final class InternalBiomeUtils {
|
|||
}
|
||||
|
||||
int vanillaArrayWeight = vanillaArray.length;
|
||||
double reqWeightSum = (double) random.nextInt(Integer.MAX_VALUE) * (vanillaArray.length + picker.getCurrentWeightTotal()) / Integer.MAX_VALUE;
|
||||
double reqWeightSum = random.nextInt(Integer.MAX_VALUE) * (vanillaArray.length + picker.getCurrentWeightTotal()) / Integer.MAX_VALUE;
|
||||
|
||||
if (reqWeightSum < vanillaArray.length) {
|
||||
// Vanilla biome; look it up from the vanilla array and transform accordingly.
|
||||
|
|
|
@ -16,17 +16,18 @@
|
|||
|
||||
package net.fabricmc.fabric.impl.biomes;
|
||||
|
||||
import net.fabricmc.fabric.api.biomes.v1.OverworldClimate;
|
||||
import net.minecraft.world.biome.Biome;
|
||||
import net.minecraft.world.biome.layer.LayerRandomnessSource;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
import net.minecraft.world.biome.Biome;
|
||||
import net.minecraft.world.biome.layer.LayerRandomnessSource;
|
||||
|
||||
import net.fabricmc.fabric.api.biomes.v1.OverworldClimate;
|
||||
|
||||
/**
|
||||
* Deals with picking variants for you
|
||||
* Deals with picking variants for you.
|
||||
*/
|
||||
final class VariantTransformer {
|
||||
private final SubTransformer defaultTransformer = new SubTransformer();
|
||||
|
@ -49,7 +50,7 @@ final class VariantTransformer {
|
|||
}
|
||||
|
||||
/**
|
||||
* Transforms a biome into a variant randomly depending on its chance
|
||||
* Transforms a biome into a variant randomly depending on its chance.
|
||||
*
|
||||
* @param replaced biome to transform
|
||||
* @param random the {@link LayerRandomnessSource} from the layer
|
||||
|
@ -81,7 +82,7 @@ final class VariantTransformer {
|
|||
}
|
||||
|
||||
/**
|
||||
* Transforms a biome into a variant randomly depending on its chance
|
||||
* Transforms a biome into a variant randomly depending on its chance.
|
||||
*
|
||||
* @param replaced biome to transform
|
||||
* @param random the {@link LayerRandomnessSource} from the layer
|
||||
|
@ -93,6 +94,7 @@ final class VariantTransformer {
|
|||
return variant.getVariant();
|
||||
}
|
||||
}
|
||||
|
||||
return replaced;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -16,13 +16,14 @@
|
|||
|
||||
package net.fabricmc.fabric.impl.biomes;
|
||||
|
||||
import com.google.common.base.Preconditions;
|
||||
import net.minecraft.world.biome.Biome;
|
||||
import net.minecraft.world.biome.layer.LayerRandomnessSource;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import com.google.common.base.Preconditions;
|
||||
|
||||
import net.minecraft.world.biome.Biome;
|
||||
import net.minecraft.world.biome.layer.LayerRandomnessSource;
|
||||
|
||||
/**
|
||||
* Picks biomes with arbitrary double weights using a binary search.
|
||||
*/
|
||||
|
@ -46,13 +47,13 @@ public final class WeightedBiomePicker {
|
|||
}
|
||||
|
||||
public Biome pickRandom(LayerRandomnessSource random) {
|
||||
double target = (double) random.nextInt(Integer.MAX_VALUE) * getCurrentWeightTotal() / Integer.MAX_VALUE;
|
||||
double target = random.nextInt(Integer.MAX_VALUE) * getCurrentWeightTotal() / Integer.MAX_VALUE;
|
||||
|
||||
return search(target).getBiome();
|
||||
}
|
||||
|
||||
/**
|
||||
* Searches with the specified target value
|
||||
* Searches with the specified target value.
|
||||
*
|
||||
* @param target The target value, must satisfy the constraint 0 <= target <= currentTotal
|
||||
* @return The result of the search
|
||||
|
@ -67,6 +68,7 @@ public final class WeightedBiomePicker {
|
|||
|
||||
while (low < high) {
|
||||
int mid = (high + low) >>> 1;
|
||||
|
||||
if (target < entries.get(mid).getUpperWeightBound()) {
|
||||
high = mid;
|
||||
} else {
|
||||
|
|
|
@ -16,32 +16,33 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.biomes;
|
||||
|
||||
import net.fabricmc.fabric.api.biomes.v1.OverworldBiomes;
|
||||
import net.fabricmc.fabric.impl.biomes.InternalBiomeData;
|
||||
import net.fabricmc.fabric.impl.biomes.InternalBiomeUtils;
|
||||
import net.minecraft.util.registry.Registry;
|
||||
import net.minecraft.world.biome.Biome;
|
||||
import net.minecraft.world.biome.layer.AddEdgeBiomesLayer;
|
||||
import net.minecraft.world.biome.layer.LayerRandomnessSource;
|
||||
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.CallbackInfoReturnable;
|
||||
|
||||
import net.minecraft.util.registry.Registry;
|
||||
import net.minecraft.world.biome.Biome;
|
||||
import net.minecraft.world.biome.layer.AddEdgeBiomesLayer;
|
||||
import net.minecraft.world.biome.layer.LayerRandomnessSource;
|
||||
|
||||
import net.fabricmc.fabric.api.biomes.v1.OverworldBiomes;
|
||||
import net.fabricmc.fabric.impl.biomes.InternalBiomeData;
|
||||
import net.fabricmc.fabric.impl.biomes.InternalBiomeUtils;
|
||||
|
||||
/**
|
||||
* Adds edges and shores specified in {@link OverworldBiomes#addEdgeBiome(Biome, Biome, double)} and {@link OverworldBiomes#addShoreBiome(Biome, Biome, double)} to the edges layer
|
||||
* Adds edges and shores specified in {@link OverworldBiomes#addEdgeBiome(Biome, Biome, double)} and {@link OverworldBiomes#addShoreBiome(Biome, Biome, double)} to the edges layer.
|
||||
*/
|
||||
@Mixin(AddEdgeBiomesLayer.class)
|
||||
public class MixinAddEdgeBiomesLayer {
|
||||
|
||||
@Inject(at = @At("HEAD"), method = "sample", cancellable = true)
|
||||
private void sample(LayerRandomnessSource rand, int north, int east, int south, int west, int center, CallbackInfoReturnable<Integer> info) {
|
||||
Biome centerBiome = Registry.BIOME.get(center);
|
||||
|
||||
if (InternalBiomeData.getOverworldShores().containsKey(centerBiome) && InternalBiomeUtils.neighborsOcean(north, east, south, west)) {
|
||||
info.setReturnValue(Registry.BIOME.getRawId(InternalBiomeData.getOverworldShores().get(centerBiome).pickRandom(rand)));
|
||||
} else if (InternalBiomeData.getOverworldEdges().containsKey(centerBiome) && InternalBiomeUtils.isEdge(north, east, south, west, center)) {
|
||||
info.setReturnValue(Registry.BIOME.getRawId(InternalBiomeData.getOverworldEdges().get(centerBiome).pickRandom(rand)));
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -16,26 +16,27 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.biomes;
|
||||
|
||||
import net.fabricmc.fabric.api.biomes.v1.OverworldBiomes;
|
||||
import net.fabricmc.fabric.impl.biomes.InternalBiomeData;
|
||||
import net.fabricmc.fabric.impl.biomes.WeightedBiomePicker;
|
||||
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.CallbackInfoReturnable;
|
||||
|
||||
import net.minecraft.util.registry.Registry;
|
||||
import net.minecraft.world.biome.Biome;
|
||||
import net.minecraft.world.biome.layer.AddHillsLayer;
|
||||
import net.minecraft.world.biome.layer.BiomeLayers;
|
||||
import net.minecraft.world.biome.layer.LayerRandomnessSource;
|
||||
import net.minecraft.world.biome.layer.LayerSampler;
|
||||
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.CallbackInfoReturnable;
|
||||
|
||||
import net.fabricmc.fabric.api.biomes.v1.OverworldBiomes;
|
||||
import net.fabricmc.fabric.impl.biomes.InternalBiomeData;
|
||||
import net.fabricmc.fabric.impl.biomes.WeightedBiomePicker;
|
||||
|
||||
/**
|
||||
* Injects hills biomes specified from {@link OverworldBiomes#addHillsBiome(Biome, Biome, double)}into the default hills layer
|
||||
* Injects hills biomes specified from {@link OverworldBiomes#addHillsBiome(Biome, Biome, double)}into the default hills layer.
|
||||
*/
|
||||
@Mixin(AddHillsLayer.class)
|
||||
public class MixinAddHillsLayer {
|
||||
|
||||
@Inject(at = @At("HEAD"), method = "sample", cancellable = true)
|
||||
private void sample(LayerRandomnessSource rand, LayerSampler biomeSampler, LayerSampler noiseSampler, int chunkX, int chunkZ, CallbackInfoReturnable<Integer> info) {
|
||||
if (InternalBiomeData.getOverworldHills().isEmpty()) {
|
||||
|
@ -67,18 +68,23 @@ public class MixinAddHillsLayer {
|
|||
|
||||
if (biomeReturn != biomeId) {
|
||||
int similarity = 0;
|
||||
|
||||
if (BiomeLayers.areSimilar(biomeSampler.sample(chunkX, chunkZ - 1), biomeId)) {
|
||||
++similarity;
|
||||
}
|
||||
|
||||
if (BiomeLayers.areSimilar(biomeSampler.sample(chunkX + 1, chunkZ), biomeId)) {
|
||||
++similarity;
|
||||
}
|
||||
|
||||
if (BiomeLayers.areSimilar(biomeSampler.sample(chunkX - 1, chunkZ), biomeId)) {
|
||||
++similarity;
|
||||
}
|
||||
|
||||
if (BiomeLayers.areSimilar(biomeSampler.sample(chunkX, chunkZ + 1), biomeId)) {
|
||||
++similarity;
|
||||
}
|
||||
|
||||
if (similarity >= 3) {
|
||||
info.setReturnValue(biomeReturn);
|
||||
return;
|
||||
|
@ -89,5 +95,4 @@ public class MixinAddHillsLayer {
|
|||
// Cancel vanilla logic.
|
||||
info.setReturnValue(biomeId);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -16,13 +16,8 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.biomes;
|
||||
|
||||
import net.fabricmc.fabric.api.biomes.v1.OverworldBiomes;
|
||||
import net.fabricmc.fabric.impl.biomes.InternalBiomeData;
|
||||
import net.minecraft.util.registry.Registry;
|
||||
import net.minecraft.world.biome.Biome;
|
||||
import net.minecraft.world.biome.layer.AddRiversLayer;
|
||||
import net.minecraft.world.biome.layer.LayerRandomnessSource;
|
||||
import net.minecraft.world.biome.layer.LayerSampler;
|
||||
import java.util.Map;
|
||||
|
||||
import org.spongepowered.asm.mixin.Final;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
|
@ -30,14 +25,20 @@ import org.spongepowered.asm.mixin.injection.At;
|
|||
import org.spongepowered.asm.mixin.injection.Inject;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable;
|
||||
|
||||
import java.util.Map;
|
||||
import net.minecraft.util.registry.Registry;
|
||||
import net.minecraft.world.biome.Biome;
|
||||
import net.minecraft.world.biome.layer.AddRiversLayer;
|
||||
import net.minecraft.world.biome.layer.LayerRandomnessSource;
|
||||
import net.minecraft.world.biome.layer.LayerSampler;
|
||||
|
||||
import net.fabricmc.fabric.api.biomes.v1.OverworldBiomes;
|
||||
import net.fabricmc.fabric.impl.biomes.InternalBiomeData;
|
||||
|
||||
/**
|
||||
* Sets river biomes specified with {@link OverworldBiomes#setRiverBiome(Biome, Biome)}
|
||||
* Sets river biomes specified with {@link OverworldBiomes#setRiverBiome(Biome, Biome)}.
|
||||
*/
|
||||
@Mixin(AddRiversLayer.class)
|
||||
public class MixinAddRiversLayer {
|
||||
|
||||
@Shadow
|
||||
@Final
|
||||
private static int RIVER_ID;
|
||||
|
@ -49,10 +50,10 @@ public class MixinAddRiversLayer {
|
|||
|
||||
int riverBiomeId = riverSampler.sample(x, z);
|
||||
Map<Biome, Biome> overworldRivers = InternalBiomeData.getOverworldRivers();
|
||||
|
||||
if (overworldRivers.containsKey(landBiome) && riverBiomeId == RIVER_ID) {
|
||||
Biome riverBiome = overworldRivers.get(landBiome);
|
||||
info.setReturnValue(riverBiome == null ? landBiomeId : Registry.BIOME.getRawId(riverBiome));
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -16,9 +16,11 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.biomes;
|
||||
|
||||
import net.fabricmc.fabric.impl.biomes.InternalBiomeData;
|
||||
import net.minecraft.world.biome.Biome;
|
||||
import net.minecraft.world.biome.source.BiomeSource;
|
||||
import java.util.ArrayList;
|
||||
import java.util.LinkedHashSet;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
|
||||
import org.spongepowered.asm.mixin.Final;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
|
@ -26,17 +28,16 @@ import org.spongepowered.asm.mixin.injection.At;
|
|||
import org.spongepowered.asm.mixin.injection.Inject;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.LinkedHashSet;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
import net.minecraft.world.biome.Biome;
|
||||
import net.minecraft.world.biome.source.BiomeSource;
|
||||
|
||||
import net.fabricmc.fabric.impl.biomes.InternalBiomeData;
|
||||
|
||||
/**
|
||||
* Adds spawn biomes to the base {@link BiomeSource} class.
|
||||
*/
|
||||
@Mixin(BiomeSource.class)
|
||||
public class MixinBiomeSource {
|
||||
|
||||
@Shadow
|
||||
@Final
|
||||
private static List<Biome> SPAWN_BIOMES;
|
||||
|
@ -44,9 +45,9 @@ public class MixinBiomeSource {
|
|||
@Inject(at = @At("RETURN"), cancellable = true, method = "getSpawnBiomes")
|
||||
private void getSpawnBiomes(CallbackInfoReturnable<List<Biome>> info) {
|
||||
Set<Biome> biomes = new LinkedHashSet<>(info.getReturnValue());
|
||||
|
||||
if (biomes.addAll(InternalBiomeData.getSpawnBiomes())) {
|
||||
info.setReturnValue(new ArrayList<>(biomes));
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -16,12 +16,6 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.biomes;
|
||||
|
||||
import net.fabricmc.fabric.api.biomes.v1.OverworldClimate;
|
||||
import net.fabricmc.fabric.impl.biomes.InternalBiomeUtils;
|
||||
import net.minecraft.util.registry.Registry;
|
||||
import net.minecraft.world.biome.Biome;
|
||||
import net.minecraft.world.biome.layer.LayerRandomnessSource;
|
||||
import net.minecraft.world.biome.layer.SetBaseBiomesLayer;
|
||||
import org.spongepowered.asm.mixin.Final;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Mutable;
|
||||
|
@ -30,12 +24,19 @@ import org.spongepowered.asm.mixin.injection.At;
|
|||
import org.spongepowered.asm.mixin.injection.Inject;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable;
|
||||
|
||||
import net.minecraft.util.registry.Registry;
|
||||
import net.minecraft.world.biome.Biome;
|
||||
import net.minecraft.world.biome.layer.LayerRandomnessSource;
|
||||
import net.minecraft.world.biome.layer.SetBaseBiomesLayer;
|
||||
|
||||
import net.fabricmc.fabric.api.biomes.v1.OverworldClimate;
|
||||
import net.fabricmc.fabric.impl.biomes.InternalBiomeUtils;
|
||||
|
||||
/**
|
||||
* Injects biomes into the arrays of biomes in the {@link SetBaseBiomesLayer}
|
||||
* Injects biomes into the arrays of biomes in the {@link SetBaseBiomesLayer}.
|
||||
*/
|
||||
@Mixin(SetBaseBiomesLayer.class)
|
||||
public class MixinSetBaseBiomesLayer {
|
||||
|
||||
@Shadow
|
||||
@Final
|
||||
@Mutable
|
||||
|
@ -112,5 +113,4 @@ public class MixinSetBaseBiomesLayer {
|
|||
|
||||
info.setReturnValue(InternalBiomeUtils.transformBiome(random, biome, climate));
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -16,9 +16,9 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.biomes;
|
||||
|
||||
import net.minecraft.world.biome.Biome;
|
||||
import net.minecraft.world.biome.source.VanillaLayeredBiomeSource;
|
||||
import net.minecraft.world.gen.feature.StructureFeature;
|
||||
import java.util.HashSet;
|
||||
import java.util.Set;
|
||||
|
||||
import org.spongepowered.asm.mixin.Final;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Mutable;
|
||||
|
@ -27,8 +27,9 @@ import org.spongepowered.asm.mixin.injection.At;
|
|||
import org.spongepowered.asm.mixin.injection.Inject;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||
|
||||
import java.util.HashSet;
|
||||
import java.util.Set;
|
||||
import net.minecraft.world.biome.Biome;
|
||||
import net.minecraft.world.biome.source.VanillaLayeredBiomeSource;
|
||||
import net.minecraft.world.gen.feature.StructureFeature;
|
||||
|
||||
/**
|
||||
* Adds the biomes in world gen to the array for the vanilla layered biome source.
|
||||
|
@ -36,14 +37,13 @@ import java.util.Set;
|
|||
*/
|
||||
@Mixin(VanillaLayeredBiomeSource.class)
|
||||
public class MixinVanillaLayeredBiomeSource {
|
||||
|
||||
@Shadow
|
||||
@Final
|
||||
@Mutable
|
||||
private static Set<Biome> BIOMES;
|
||||
|
||||
@Inject(method = "<clinit>", at = @At("RETURN"))
|
||||
private static void cinit(CallbackInfo info){
|
||||
private static void cinit(CallbackInfo info) {
|
||||
BIOMES = new HashSet<>(BIOMES);
|
||||
}
|
||||
|
||||
|
@ -51,5 +51,4 @@ public class MixinVanillaLayeredBiomeSource {
|
|||
private static void fabric_injectBiome(Biome biome) {
|
||||
BIOMES.add(biome);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -16,31 +16,32 @@
|
|||
|
||||
package net.fabricmc.fabric.api.blockrenderlayer.v1;
|
||||
|
||||
import net.fabricmc.fabric.impl.blockrenderlayer.BlockRenderLayerMapImpl;
|
||||
import net.minecraft.block.Block;
|
||||
import net.minecraft.client.render.RenderLayer;
|
||||
import net.minecraft.fluid.Fluid;
|
||||
import net.minecraft.item.Item;
|
||||
|
||||
import net.fabricmc.fabric.impl.blockrenderlayer.BlockRenderLayerMapImpl;
|
||||
|
||||
/**
|
||||
* Use to associate blocks or fluids with block render layer other than default.
|
||||
* Replaces the {@code renderLayer} property previously on {@code Block}.<p>
|
||||
*
|
||||
* {@code BlockRenderLayer} controls how sprite pixels for fluids and blocks are blended
|
||||
* with the scene. Consult the vanilla {@code BlockRenderLayer} implementation for examples.<p>
|
||||
*
|
||||
* The Fabric Renderer API can be used to control this at a per-quad level at the code
|
||||
* via {@code BlendMode}.<p>
|
||||
*
|
||||
* Client-side only.
|
||||
* Use to associate blocks or fluids with block render layer other than default.
|
||||
* Replaces the {@code renderLayer} property previously on {@code Block}.
|
||||
*
|
||||
* <p>{@code BlockRenderLayer} controls how sprite pixels for fluids and blocks are blended
|
||||
* with the scene. Consult the vanilla {@code BlockRenderLayer} implementation for examples.
|
||||
*
|
||||
* <p>The Fabric Renderer API can be used to control this at a per-quad level at the code
|
||||
* via {@code BlendMode}.
|
||||
*
|
||||
* <p>Client-side only.
|
||||
*/
|
||||
public interface BlockRenderLayerMap {
|
||||
BlockRenderLayerMap INSTANCE = BlockRenderLayerMapImpl.INSTANCE;
|
||||
|
||||
|
||||
/**
|
||||
* Map (or re-map) a block state with a render layer. Re-mapping is not recommended but if done, last one in wins.
|
||||
* Must be called from client thread prior to world load/rendering. Best practice will be to call from mod's client initializer.
|
||||
*
|
||||
*
|
||||
* @param block Identifies block to be mapped.
|
||||
* @param renderLayer Render layer. Should be one of the layers used for terrain rendering.
|
||||
*/
|
||||
|
@ -58,7 +59,7 @@ public interface BlockRenderLayerMap {
|
|||
/**
|
||||
* Map (or re-map) a fluid state with a render layer. Re-mapping is not recommended but if done, last one in wins.
|
||||
* Must be called from client thread prior to world load/rendering. Best practice will be to call from mod's client initializer.
|
||||
*
|
||||
*
|
||||
* @param fluid Identifies fluid to be mapped.
|
||||
* @param renderLayer Render layer. Should be one of the layers used for terrain rendering.
|
||||
*/
|
||||
|
|
|
@ -20,16 +20,16 @@ import java.util.HashMap;
|
|||
import java.util.Map;
|
||||
import java.util.function.BiConsumer;
|
||||
|
||||
import net.minecraft.block.Block;
|
||||
import net.minecraft.client.render.RenderLayer;
|
||||
import net.minecraft.fluid.Fluid;
|
||||
import net.minecraft.item.Item;
|
||||
|
||||
import net.fabricmc.fabric.api.blockrenderlayer.v1.BlockRenderLayerMap;
|
||||
import net.minecraft.block.Block;
|
||||
import net.minecraft.fluid.Fluid;
|
||||
|
||||
public class BlockRenderLayerMapImpl implements BlockRenderLayerMap {
|
||||
private BlockRenderLayerMapImpl() {}
|
||||
|
||||
private BlockRenderLayerMapImpl() { }
|
||||
|
||||
@Override
|
||||
public void putBlock(Block block, RenderLayer renderLayer) {
|
||||
if (block == null) throw new IllegalArgumentException("Request to map null block to BlockRenderLayer");
|
||||
|
@ -53,7 +53,7 @@ public class BlockRenderLayerMapImpl implements BlockRenderLayerMap {
|
|||
|
||||
fluidHandler.accept(fluid, renderLayer);
|
||||
}
|
||||
|
||||
|
||||
public static final BlockRenderLayerMap INSTANCE = new BlockRenderLayerMapImpl();
|
||||
|
||||
private static Map<Block, RenderLayer> blockRenderLayerMap = new HashMap<>();
|
||||
|
|
|
@ -18,25 +18,26 @@ package net.fabricmc.fabric.mixin.blockrenderlayer;
|
|||
|
||||
import java.util.Map;
|
||||
|
||||
import net.minecraft.class_4696;
|
||||
import net.minecraft.client.render.RenderLayer;
|
||||
import net.minecraft.item.Item;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
import org.spongepowered.asm.mixin.injection.At;
|
||||
import org.spongepowered.asm.mixin.injection.Inject;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||
|
||||
import net.fabricmc.fabric.impl.blockrenderlayer.BlockRenderLayerMapImpl;
|
||||
import net.minecraft.class_4696;
|
||||
import net.minecraft.block.Block;
|
||||
import net.minecraft.client.render.RenderLayer;
|
||||
import net.minecraft.fluid.Fluid;
|
||||
import net.minecraft.item.Item;
|
||||
|
||||
import net.fabricmc.fabric.impl.blockrenderlayer.BlockRenderLayerMapImpl;
|
||||
|
||||
@Mixin(class_4696.class)
|
||||
public class MixinBlockRenderLayer {
|
||||
@Shadow private static Map<Block, RenderLayer> field_21469;
|
||||
@Shadow private static Map<Item, RenderLayer> field_21470;
|
||||
@Shadow private static Map<Fluid, RenderLayer> field_21471;
|
||||
|
||||
|
||||
@Inject(method = "<clinit>*", at = @At("RETURN"))
|
||||
private static void onInitialize(CallbackInfo info) {
|
||||
BlockRenderLayerMapImpl.initialize(field_21469::put, field_21470::put, field_21471::put);
|
||||
|
|
|
@ -16,11 +16,13 @@
|
|||
|
||||
package net.fabricmc.fabric.api.registry;
|
||||
|
||||
import java.util.function.Consumer;
|
||||
|
||||
import com.mojang.brigadier.CommandDispatcher;
|
||||
import net.fabricmc.fabric.impl.registry.CommandRegistryImpl;
|
||||
|
||||
import net.minecraft.server.command.ServerCommandSource;
|
||||
|
||||
import java.util.function.Consumer;
|
||||
import net.fabricmc.fabric.impl.registry.CommandRegistryImpl;
|
||||
|
||||
/**
|
||||
* Registry for server-side command providers.
|
||||
|
|
|
@ -16,14 +16,15 @@
|
|||
|
||||
package net.fabricmc.fabric.impl.registry;
|
||||
|
||||
import com.mojang.brigadier.CommandDispatcher;
|
||||
import net.minecraft.server.command.ServerCommandSource;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
import java.util.function.Consumer;
|
||||
|
||||
import com.mojang.brigadier.CommandDispatcher;
|
||||
|
||||
import net.minecraft.server.command.ServerCommandSource;
|
||||
|
||||
public class CommandRegistryImpl {
|
||||
public static final CommandRegistryImpl INSTANCE = new CommandRegistryImpl();
|
||||
|
||||
|
|
|
@ -17,15 +17,17 @@
|
|||
package net.fabricmc.fabric.mixin.registrycommands;
|
||||
|
||||
import com.mojang.brigadier.CommandDispatcher;
|
||||
import net.fabricmc.fabric.impl.registry.CommandRegistryImpl;
|
||||
import net.minecraft.server.command.CommandManager;
|
||||
import net.minecraft.server.command.ServerCommandSource;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
import org.spongepowered.asm.mixin.injection.At;
|
||||
import org.spongepowered.asm.mixin.injection.Inject;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||
|
||||
import net.minecraft.server.command.CommandManager;
|
||||
import net.minecraft.server.command.ServerCommandSource;
|
||||
|
||||
import net.fabricmc.fabric.impl.registry.CommandRegistryImpl;
|
||||
|
||||
@Mixin(CommandManager.class)
|
||||
public class MixinCommandManagerIntegrated {
|
||||
@Shadow
|
||||
|
|
|
@ -16,27 +16,28 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.registrycommands;
|
||||
|
||||
import java.io.File;
|
||||
import java.net.Proxy;
|
||||
|
||||
import com.mojang.authlib.GameProfileRepository;
|
||||
import com.mojang.authlib.minecraft.MinecraftSessionService;
|
||||
import com.mojang.authlib.yggdrasil.YggdrasilAuthenticationService;
|
||||
import com.mojang.datafixers.DataFixer;
|
||||
import net.fabricmc.fabric.impl.registry.CommandRegistryImpl;
|
||||
import net.minecraft.server.MinecraftServer;
|
||||
import net.minecraft.server.WorldGenerationProgressListenerFactory;
|
||||
import net.minecraft.server.command.CommandManager;
|
||||
import net.minecraft.server.dedicated.MinecraftDedicatedServer;
|
||||
import net.minecraft.util.UserCache;
|
||||
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.CallbackInfoReturnable;
|
||||
|
||||
import java.io.File;
|
||||
import java.net.Proxy;
|
||||
import net.minecraft.server.MinecraftServer;
|
||||
import net.minecraft.server.WorldGenerationProgressListenerFactory;
|
||||
import net.minecraft.server.command.CommandManager;
|
||||
import net.minecraft.server.dedicated.MinecraftDedicatedServer;
|
||||
import net.minecraft.util.UserCache;
|
||||
|
||||
import net.fabricmc.fabric.impl.registry.CommandRegistryImpl;
|
||||
|
||||
@Mixin(MinecraftDedicatedServer.class)
|
||||
public abstract class MixinMinecraftDedicatedServer extends MinecraftServer {
|
||||
|
||||
public MixinMinecraftDedicatedServer(File file_1, Proxy proxy_1, DataFixer dataFixer_1, CommandManager serverCommandManager_1, YggdrasilAuthenticationService yggdrasilAuthenticationService_1, MinecraftSessionService minecraftSessionService_1, GameProfileRepository gameProfileRepository_1, UserCache userCache_1, WorldGenerationProgressListenerFactory worldGenerationProgressListenerFactory_1, String string_1) {
|
||||
super(file_1, proxy_1, dataFixer_1, serverCommandManager_1, yggdrasilAuthenticationService_1, minecraftSessionService_1, gameProfileRepository_1, userCache_1, worldGenerationProgressListenerFactory_1, string_1);
|
||||
}
|
||||
|
|
|
@ -21,7 +21,5 @@ import net.minecraft.container.Container;
|
|||
|
||||
@FunctionalInterface
|
||||
public interface ContainerScreenFactory<C extends Container> {
|
||||
|
||||
AbstractContainerScreen create(C container);
|
||||
|
||||
}
|
||||
|
|
|
@ -16,15 +16,15 @@
|
|||
|
||||
package net.fabricmc.fabric.api.client.screen;
|
||||
|
||||
import net.fabricmc.fabric.api.container.ContainerFactory;
|
||||
import net.fabricmc.fabric.api.container.ContainerProviderRegistry;
|
||||
import net.fabricmc.fabric.impl.client.gui.ScreenProviderRegistryImpl;
|
||||
import net.minecraft.client.gui.screen.ingame.AbstractContainerScreen;
|
||||
import net.minecraft.container.Container;
|
||||
import net.minecraft.util.Identifier;
|
||||
|
||||
public interface ScreenProviderRegistry {
|
||||
import net.fabricmc.fabric.api.container.ContainerFactory;
|
||||
import net.fabricmc.fabric.api.container.ContainerProviderRegistry;
|
||||
import net.fabricmc.fabric.impl.client.gui.ScreenProviderRegistryImpl;
|
||||
|
||||
public interface ScreenProviderRegistry {
|
||||
ScreenProviderRegistry INSTANCE = ScreenProviderRegistryImpl.INSTANCE;
|
||||
|
||||
/**
|
||||
|
@ -43,5 +43,4 @@ public interface ScreenProviderRegistry {
|
|||
* @param factory the gui factory, this should return a new {@link AbstractContainerScreen}
|
||||
*/
|
||||
void registerFactory(Identifier identifier, ContainerFactory<AbstractContainerScreen> factory);
|
||||
|
||||
}
|
||||
|
|
|
@ -22,7 +22,6 @@ import net.minecraft.util.PacketByteBuf;
|
|||
|
||||
@FunctionalInterface
|
||||
public interface ContainerFactory<T> {
|
||||
|
||||
/**
|
||||
* Creates the new object.
|
||||
*
|
||||
|
@ -33,5 +32,4 @@ public interface ContainerFactory<T> {
|
|||
* @return the new gui or container
|
||||
*/
|
||||
T create(int syncId, Identifier identifier, PlayerEntity player, PacketByteBuf buf);
|
||||
|
||||
}
|
||||
|
|
|
@ -16,18 +16,18 @@
|
|||
|
||||
package net.fabricmc.fabric.api.container;
|
||||
|
||||
import net.fabricmc.fabric.api.client.screen.ScreenProviderRegistry;
|
||||
import net.fabricmc.fabric.impl.container.ContainerProviderImpl;
|
||||
import java.util.function.Consumer;
|
||||
|
||||
import net.minecraft.container.Container;
|
||||
import net.minecraft.entity.player.PlayerEntity;
|
||||
import net.minecraft.server.network.ServerPlayerEntity;
|
||||
import net.minecraft.util.Identifier;
|
||||
import net.minecraft.util.PacketByteBuf;
|
||||
|
||||
import java.util.function.Consumer;
|
||||
import net.fabricmc.fabric.api.client.screen.ScreenProviderRegistry;
|
||||
import net.fabricmc.fabric.impl.container.ContainerProviderImpl;
|
||||
|
||||
public interface ContainerProviderRegistry {
|
||||
|
||||
ContainerProviderRegistry INSTANCE = ContainerProviderImpl.INSTANCE;
|
||||
|
||||
/**
|
||||
|
|
|
@ -16,26 +16,27 @@
|
|||
|
||||
package net.fabricmc.fabric.impl.client.gui;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
import org.apache.logging.log4j.LogManager;
|
||||
import org.apache.logging.log4j.Logger;
|
||||
|
||||
import net.minecraft.client.MinecraftClient;
|
||||
import net.minecraft.client.gui.screen.ingame.AbstractContainerScreen;
|
||||
import net.minecraft.container.Container;
|
||||
import net.minecraft.util.Identifier;
|
||||
|
||||
import net.fabricmc.fabric.api.client.screen.ContainerScreenFactory;
|
||||
import net.fabricmc.fabric.api.client.screen.ScreenProviderRegistry;
|
||||
import net.fabricmc.fabric.api.container.ContainerFactory;
|
||||
import net.fabricmc.fabric.api.network.ClientSidePacketRegistry;
|
||||
import net.fabricmc.fabric.impl.container.ContainerProviderImpl;
|
||||
import net.fabricmc.fabric.impl.network.PacketTypes;
|
||||
import net.minecraft.client.MinecraftClient;
|
||||
import net.minecraft.client.gui.screen.ingame.AbstractContainerScreen;
|
||||
import net.minecraft.container.Container;
|
||||
import net.minecraft.util.Identifier;
|
||||
import org.apache.logging.log4j.LogManager;
|
||||
import org.apache.logging.log4j.Logger;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
public class ScreenProviderRegistryImpl implements ScreenProviderRegistry {
|
||||
|
||||
/**
|
||||
* Use the instance provided by ScreenProviderRegistry
|
||||
* Use the instance provided by ScreenProviderRegistry.
|
||||
*/
|
||||
public static final ScreenProviderRegistry INSTANCE = new ScreenProviderRegistryImpl();
|
||||
|
||||
|
@ -43,10 +44,12 @@ public class ScreenProviderRegistryImpl implements ScreenProviderRegistry {
|
|||
|
||||
private static final Map<Identifier, ContainerFactory<AbstractContainerScreen>> FACTORIES = new HashMap<>();
|
||||
|
||||
@Override
|
||||
public void registerFactory(Identifier identifier, ContainerFactory<AbstractContainerScreen> factory) {
|
||||
if (FACTORIES.containsKey(identifier)) {
|
||||
throw new RuntimeException("A factory has already been registered as " + identifier + "!");
|
||||
}
|
||||
|
||||
FACTORIES.put(identifier, factory);
|
||||
}
|
||||
|
||||
|
@ -54,10 +57,12 @@ public class ScreenProviderRegistryImpl implements ScreenProviderRegistry {
|
|||
public <C extends Container> void registerFactory(Identifier identifier, ContainerScreenFactory<C> containerScreenFactory) {
|
||||
registerFactory(identifier, (syncId, identifier1, player, buf) -> {
|
||||
C container = ContainerProviderImpl.INSTANCE.createContainer(syncId, identifier1, player, buf);
|
||||
|
||||
if (container == null) {
|
||||
LOGGER.error("Could not open container for {} - a null object was created!", identifier1.toString());
|
||||
return null;
|
||||
}
|
||||
|
||||
return containerScreenFactory.create(container);
|
||||
});
|
||||
}
|
||||
|
@ -71,10 +76,12 @@ public class ScreenProviderRegistryImpl implements ScreenProviderRegistry {
|
|||
MinecraftClient.getInstance().execute(() -> {
|
||||
try {
|
||||
ContainerFactory<AbstractContainerScreen> factory = FACTORIES.get(identifier);
|
||||
|
||||
if (factory == null) {
|
||||
LOGGER.error("No GUI factory found for {}!", identifier.toString());
|
||||
return;
|
||||
}
|
||||
|
||||
AbstractContainerScreen gui = factory.create(syncId, identifier, packetContext.getPlayer(), packetByteBuf);
|
||||
packetContext.getPlayer().container = gui.getContainer();
|
||||
MinecraftClient.getInstance().openScreen(gui);
|
||||
|
|
|
@ -16,28 +16,29 @@
|
|||
|
||||
package net.fabricmc.fabric.impl.container;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.function.Consumer;
|
||||
|
||||
import io.netty.buffer.Unpooled;
|
||||
import net.fabricmc.fabric.api.container.ContainerFactory;
|
||||
import net.fabricmc.fabric.api.container.ContainerProviderRegistry;
|
||||
import net.fabricmc.fabric.impl.network.PacketTypes;
|
||||
import net.fabricmc.fabric.mixin.container.ServerPlayerEntityAccessor;
|
||||
import org.apache.logging.log4j.LogManager;
|
||||
import org.apache.logging.log4j.Logger;
|
||||
|
||||
import net.minecraft.client.network.packet.CustomPayloadS2CPacket;
|
||||
import net.minecraft.container.Container;
|
||||
import net.minecraft.entity.player.PlayerEntity;
|
||||
import net.minecraft.server.network.ServerPlayerEntity;
|
||||
import net.minecraft.util.Identifier;
|
||||
import net.minecraft.util.PacketByteBuf;
|
||||
import org.apache.logging.log4j.LogManager;
|
||||
import org.apache.logging.log4j.Logger;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.function.Consumer;
|
||||
import net.fabricmc.fabric.api.container.ContainerFactory;
|
||||
import net.fabricmc.fabric.api.container.ContainerProviderRegistry;
|
||||
import net.fabricmc.fabric.impl.network.PacketTypes;
|
||||
import net.fabricmc.fabric.mixin.container.ServerPlayerEntityAccessor;
|
||||
|
||||
public class ContainerProviderImpl implements ContainerProviderRegistry {
|
||||
|
||||
/**
|
||||
* Use the instance provided by ContainerProviderRegistry
|
||||
* Use the instance provided by ContainerProviderRegistry.
|
||||
*/
|
||||
public static final ContainerProviderImpl INSTANCE = new ContainerProviderImpl();
|
||||
|
||||
|
@ -50,6 +51,7 @@ public class ContainerProviderImpl implements ContainerProviderRegistry {
|
|||
if (FACTORIES.containsKey(identifier)) {
|
||||
throw new RuntimeException("A factory has already been registered as " + identifier.toString());
|
||||
}
|
||||
|
||||
FACTORIES.put(identifier, factory);
|
||||
}
|
||||
|
||||
|
@ -96,19 +98,23 @@ public class ContainerProviderImpl implements ContainerProviderRegistry {
|
|||
clonedBuf.readUnsignedByte();
|
||||
|
||||
Container container = createContainer(syncId, identifier, player, clonedBuf);
|
||||
|
||||
if (container == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
player.container = container;
|
||||
player.container.addListener(player);
|
||||
}
|
||||
|
||||
public <C extends Container> C createContainer(int syncId, Identifier identifier, PlayerEntity player, PacketByteBuf buf) {
|
||||
ContainerFactory<Container> factory = FACTORIES.get(identifier);
|
||||
|
||||
if (factory == null) {
|
||||
LOGGER.error("No container factory found for {}!", identifier.toString());
|
||||
return null;
|
||||
}
|
||||
|
||||
//noinspection unchecked
|
||||
return (C) factory.create(syncId, identifier, player, buf);
|
||||
}
|
||||
|
|
|
@ -20,12 +20,10 @@ package net.fabricmc.fabric.impl.container;
|
|||
* This is a interface that is present on a ServerPlayerEntity, it allows access to the sync id.
|
||||
*/
|
||||
public interface ServerPlayerEntitySyncHook {
|
||||
|
||||
/**
|
||||
* gets and sets the new player sync id, and returns the new value
|
||||
* Gets and sets the new player sync id, and returns the new value.
|
||||
*
|
||||
* @return the new sync id of the player
|
||||
*/
|
||||
int fabric_incrementSyncId();
|
||||
|
||||
}
|
||||
|
|
|
@ -16,11 +16,13 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.container;
|
||||
|
||||
import net.fabricmc.fabric.impl.container.ServerPlayerEntitySyncHook;
|
||||
import net.minecraft.server.network.ServerPlayerEntity;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
|
||||
import net.minecraft.server.network.ServerPlayerEntity;
|
||||
|
||||
import net.fabricmc.fabric.impl.container.ServerPlayerEntitySyncHook;
|
||||
|
||||
@Mixin(ServerPlayerEntity.class)
|
||||
public abstract class MixinServerPlayerEntity implements ServerPlayerEntitySyncHook {
|
||||
@Shadow
|
||||
|
|
|
@ -16,10 +16,11 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.container;
|
||||
|
||||
import net.minecraft.server.network.ServerPlayerEntity;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.gen.Accessor;
|
||||
|
||||
import net.minecraft.server.network.ServerPlayerEntity;
|
||||
|
||||
@Mixin(ServerPlayerEntity.class)
|
||||
public interface ServerPlayerEntityAccessor {
|
||||
@Accessor
|
||||
|
|
|
@ -21,8 +21,8 @@ import net.fabricmc.fabric.impl.registry.CompostingChanceRegistryImpl;
|
|||
|
||||
/**
|
||||
* Registry of items to 0.0-1.0 values, defining the chance of a given item
|
||||
* increasing the Composter block's level
|
||||
* increasing the Composter block's level.
|
||||
*/
|
||||
public interface CompostingChanceRegistry extends Item2ObjectMap<Float> {
|
||||
final CompostingChanceRegistry INSTANCE = new CompostingChanceRegistryImpl();
|
||||
CompostingChanceRegistry INSTANCE = new CompostingChanceRegistryImpl();
|
||||
}
|
||||
|
|
|
@ -16,12 +16,13 @@
|
|||
|
||||
package net.fabricmc.fabric.api.registry;
|
||||
|
||||
import net.fabricmc.fabric.api.util.Block2ObjectMap;
|
||||
import net.fabricmc.fabric.impl.registry.FlammableBlockRegistryImpl;
|
||||
import net.minecraft.block.Block;
|
||||
import net.minecraft.block.Blocks;
|
||||
import net.minecraft.tag.Tag;
|
||||
|
||||
import net.fabricmc.fabric.api.util.Block2ObjectMap;
|
||||
import net.fabricmc.fabric.impl.registry.FlammableBlockRegistryImpl;
|
||||
|
||||
public interface FlammableBlockRegistry extends Block2ObjectMap<FlammableBlockRegistry.Entry> {
|
||||
static FlammableBlockRegistry getDefaultInstance() {
|
||||
return getInstance(Blocks.FIRE);
|
||||
|
@ -39,7 +40,7 @@ public interface FlammableBlockRegistry extends Block2ObjectMap<FlammableBlockRe
|
|||
this.add(tag, new Entry(burn, spread));
|
||||
}
|
||||
|
||||
public static final class Entry {
|
||||
final class Entry {
|
||||
private final int burn, spread;
|
||||
|
||||
public Entry(int burn, int spread) {
|
||||
|
|
|
@ -23,5 +23,5 @@ import net.fabricmc.fabric.impl.registry.FuelRegistryImpl;
|
|||
* Registry of items to 0-32767 fuel burn time values, in in-game ticks.
|
||||
*/
|
||||
public interface FuelRegistry extends Item2ObjectMap<Integer> {
|
||||
final FuelRegistry INSTANCE = FuelRegistryImpl.INSTANCE;
|
||||
FuelRegistry INSTANCE = FuelRegistryImpl.INSTANCE;
|
||||
}
|
||||
|
|
|
@ -16,16 +16,17 @@
|
|||
|
||||
package net.fabricmc.fabric.api.registry;
|
||||
|
||||
import net.minecraft.world.loot.entry.LootEntry;
|
||||
|
||||
import net.fabricmc.fabric.impl.registry.LootEntryTypeRegistryImpl;
|
||||
|
||||
import net.minecraft.world.loot.entry.LootEntry;
|
||||
/**
|
||||
* @deprecated Use {@link net.fabricmc.fabric.api.loot.v1.LootEntryTypeRegistry}
|
||||
*/
|
||||
@Deprecated
|
||||
public interface LootEntryTypeRegistry {
|
||||
@Deprecated
|
||||
final LootEntryTypeRegistry INSTANCE = LootEntryTypeRegistryImpl.INSTANCE;
|
||||
LootEntryTypeRegistry INSTANCE = LootEntryTypeRegistryImpl.INSTANCE;
|
||||
|
||||
@Deprecated
|
||||
void register(LootEntry.Serializer<?> serializer);
|
||||
|
|
|
@ -16,12 +16,13 @@
|
|||
|
||||
package net.fabricmc.fabric.impl.registry;
|
||||
|
||||
import net.fabricmc.fabric.api.registry.CompostingChanceRegistry;
|
||||
import net.minecraft.block.ComposterBlock;
|
||||
import net.minecraft.item.Item;
|
||||
import net.minecraft.item.ItemConvertible;
|
||||
import net.minecraft.tag.Tag;
|
||||
|
||||
import net.fabricmc.fabric.api.registry.CompostingChanceRegistry;
|
||||
|
||||
public class CompostingChanceRegistryImpl implements CompostingChanceRegistry {
|
||||
@Override
|
||||
public Float get(ItemConvertible item) {
|
||||
|
|
|
@ -16,9 +16,10 @@
|
|||
|
||||
package net.fabricmc.fabric.impl.registry;
|
||||
|
||||
import net.fabricmc.fabric.api.registry.FlammableBlockRegistry;
|
||||
import net.minecraft.block.BlockState;
|
||||
|
||||
import net.fabricmc.fabric.api.registry.FlammableBlockRegistry;
|
||||
|
||||
public interface FireBlockHooks {
|
||||
FlammableBlockRegistry.Entry fabric_getVanillaEntry(BlockState block);
|
||||
}
|
||||
|
|
|
@ -16,20 +16,21 @@
|
|||
|
||||
package net.fabricmc.fabric.impl.registry;
|
||||
|
||||
import net.fabricmc.fabric.api.registry.FlammableBlockRegistry;
|
||||
import net.fabricmc.fabric.api.resource.ResourceManagerHelper;
|
||||
import net.fabricmc.fabric.api.resource.ResourceReloadListenerKeys;
|
||||
import net.fabricmc.fabric.api.resource.SimpleSynchronousResourceReloadListener;
|
||||
import java.util.Collection;
|
||||
import java.util.Collections;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
import net.minecraft.block.Block;
|
||||
import net.minecraft.resource.ResourceManager;
|
||||
import net.minecraft.resource.ResourceType;
|
||||
import net.minecraft.tag.Tag;
|
||||
import net.minecraft.util.Identifier;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.Collections;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import net.fabricmc.fabric.api.registry.FlammableBlockRegistry;
|
||||
import net.fabricmc.fabric.api.resource.ResourceManagerHelper;
|
||||
import net.fabricmc.fabric.api.resource.ResourceReloadListenerKeys;
|
||||
import net.fabricmc.fabric.api.resource.SimpleSynchronousResourceReloadListener;
|
||||
|
||||
public class FlammableBlockRegistryImpl implements FlammableBlockRegistry, SimpleSynchronousResourceReloadListener {
|
||||
private static final FlammableBlockRegistry.Entry REMOVED = new FlammableBlockRegistry.Entry(0, 0);
|
||||
|
@ -59,13 +60,16 @@ public class FlammableBlockRegistryImpl implements FlammableBlockRegistry, Simpl
|
|||
|
||||
private void reload() {
|
||||
computedEntries.clear();
|
||||
|
||||
// tags take precedence before blocks
|
||||
for (Tag<Block> tag : registeredEntriesTag.keySet()) {
|
||||
FlammableBlockRegistry.Entry entry = registeredEntriesTag.get(tag);
|
||||
|
||||
for (Block block : tag.values()) {
|
||||
computedEntries.put(block, entry);
|
||||
}
|
||||
}
|
||||
|
||||
computedEntries.putAll(registeredEntriesBlock);
|
||||
|
||||
/* computedBurnChances.clear();
|
||||
|
@ -82,6 +86,7 @@ public class FlammableBlockRegistryImpl implements FlammableBlockRegistry, Simpl
|
|||
@Override
|
||||
public Entry get(Block block) {
|
||||
Entry entry = computedEntries.get(block);
|
||||
|
||||
if (entry != null) {
|
||||
return entry;
|
||||
} else {
|
||||
|
|
|
@ -16,17 +16,19 @@
|
|||
|
||||
package net.fabricmc.fabric.impl.registry;
|
||||
|
||||
import java.util.Map;
|
||||
|
||||
import it.unimi.dsi.fastutil.objects.Object2IntLinkedOpenHashMap;
|
||||
import it.unimi.dsi.fastutil.objects.Object2IntMap;
|
||||
import net.fabricmc.fabric.api.registry.FuelRegistry;
|
||||
import org.apache.logging.log4j.LogManager;
|
||||
import org.apache.logging.log4j.Logger;
|
||||
|
||||
import net.minecraft.block.entity.AbstractFurnaceBlockEntity;
|
||||
import net.minecraft.item.Item;
|
||||
import net.minecraft.item.ItemConvertible;
|
||||
import net.minecraft.tag.Tag;
|
||||
import org.apache.logging.log4j.LogManager;
|
||||
import org.apache.logging.log4j.Logger;
|
||||
|
||||
import java.util.Map;
|
||||
import net.fabricmc.fabric.api.registry.FuelRegistry;
|
||||
|
||||
// TODO: Clamp values to 32767 (+ add hook for mods which extend the limit to disable the check?)
|
||||
public class FuelRegistryImpl implements FuelRegistry {
|
||||
|
@ -35,9 +37,7 @@ public class FuelRegistryImpl implements FuelRegistry {
|
|||
private final Object2IntMap<ItemConvertible> itemCookTimes = new Object2IntLinkedOpenHashMap<>();
|
||||
private final Object2IntMap<Tag<Item>> tagCookTimes = new Object2IntLinkedOpenHashMap<>();
|
||||
|
||||
public FuelRegistryImpl() {
|
||||
|
||||
}
|
||||
public FuelRegistryImpl() { }
|
||||
|
||||
@Override
|
||||
public Integer get(ItemConvertible item) {
|
||||
|
@ -49,6 +49,7 @@ public class FuelRegistryImpl implements FuelRegistry {
|
|||
if (cookTime > 32767) {
|
||||
LOGGER.warn("Tried to register an overly high cookTime: " + cookTime + " > 32767! (" + item + ")");
|
||||
}
|
||||
|
||||
itemCookTimes.put(item, cookTime.intValue());
|
||||
}
|
||||
|
||||
|
@ -57,6 +58,7 @@ public class FuelRegistryImpl implements FuelRegistry {
|
|||
if (cookTime > 32767) {
|
||||
LOGGER.warn("Tried to register an overly high cookTime: " + cookTime + " > 32767! (" + tag.getId() + ")");
|
||||
}
|
||||
|
||||
tagCookTimes.put(tag, cookTime.intValue());
|
||||
}
|
||||
|
||||
|
@ -84,6 +86,7 @@ public class FuelRegistryImpl implements FuelRegistry {
|
|||
// tags take precedence before blocks
|
||||
for (Tag<Item> tag : tagCookTimes.keySet()) {
|
||||
int time = tagCookTimes.getInt(tag);
|
||||
|
||||
if (time <= 0) {
|
||||
for (Item i : tag.values()) {
|
||||
map.remove(i);
|
||||
|
@ -97,6 +100,7 @@ public class FuelRegistryImpl implements FuelRegistry {
|
|||
|
||||
for (ItemConvertible item : itemCookTimes.keySet()) {
|
||||
int time = itemCookTimes.getInt(item);
|
||||
|
||||
if (time <= 0) {
|
||||
map.remove(item.asItem());
|
||||
} else {
|
||||
|
|
|
@ -16,11 +16,12 @@
|
|||
|
||||
package net.fabricmc.fabric.impl.registry;
|
||||
|
||||
import net.fabricmc.fabric.api.registry.LootEntryTypeRegistry;
|
||||
import java.lang.reflect.Method;
|
||||
|
||||
import net.minecraft.world.loot.entry.LootEntries;
|
||||
import net.minecraft.world.loot.entry.LootEntry;
|
||||
|
||||
import java.lang.reflect.Method;
|
||||
import net.fabricmc.fabric.api.registry.LootEntryTypeRegistry;
|
||||
|
||||
@Deprecated
|
||||
public final class LootEntryTypeRegistryImpl implements LootEntryTypeRegistry {
|
||||
|
@ -29,6 +30,7 @@ public final class LootEntryTypeRegistryImpl implements LootEntryTypeRegistry {
|
|||
|
||||
static {
|
||||
Method target = null;
|
||||
|
||||
for (Method m : LootEntries.class.getDeclaredMethods()) {
|
||||
if (m.getParameterCount() == 1 && m.getParameterTypes()[0] == LootEntry.Serializer.class) {
|
||||
if (target != null) {
|
||||
|
@ -47,8 +49,7 @@ public final class LootEntryTypeRegistryImpl implements LootEntryTypeRegistry {
|
|||
}
|
||||
}
|
||||
|
||||
private LootEntryTypeRegistryImpl() {
|
||||
}
|
||||
private LootEntryTypeRegistryImpl() { }
|
||||
|
||||
@Override
|
||||
public void register(LootEntry.Serializer<?> serializer) {
|
||||
|
|
|
@ -16,15 +16,17 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.registryextras;
|
||||
|
||||
import net.fabricmc.fabric.impl.registry.FuelRegistryImpl;
|
||||
import net.minecraft.block.entity.AbstractFurnaceBlockEntity;
|
||||
import net.minecraft.item.Item;
|
||||
import java.util.Map;
|
||||
|
||||
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.CallbackInfoReturnable;
|
||||
|
||||
import java.util.Map;
|
||||
import net.minecraft.block.entity.AbstractFurnaceBlockEntity;
|
||||
import net.minecraft.item.Item;
|
||||
|
||||
import net.fabricmc.fabric.impl.registry.FuelRegistryImpl;
|
||||
|
||||
@Mixin(AbstractFurnaceBlockEntity.class)
|
||||
public class MixinAbstractFurnaceBlockEntity {
|
||||
|
@ -32,4 +34,4 @@ public class MixinAbstractFurnaceBlockEntity {
|
|||
private static void fuelTimeMapHook(CallbackInfoReturnable<Map<Item, Integer>> info) {
|
||||
FuelRegistryImpl.INSTANCE.apply(info.getReturnValue());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -16,13 +16,6 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.registryextras;
|
||||
|
||||
import net.fabricmc.fabric.api.registry.FlammableBlockRegistry;
|
||||
import net.fabricmc.fabric.impl.registry.FireBlockHooks;
|
||||
import net.fabricmc.fabric.impl.registry.FlammableBlockRegistryImpl;
|
||||
import net.minecraft.block.Block;
|
||||
import net.minecraft.block.BlockState;
|
||||
import net.minecraft.block.FireBlock;
|
||||
import net.minecraft.state.property.Properties;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
import org.spongepowered.asm.mixin.injection.At;
|
||||
|
@ -30,6 +23,15 @@ import org.spongepowered.asm.mixin.injection.Inject;
|
|||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable;
|
||||
|
||||
import net.minecraft.block.Block;
|
||||
import net.minecraft.block.BlockState;
|
||||
import net.minecraft.block.FireBlock;
|
||||
import net.minecraft.state.property.Properties;
|
||||
|
||||
import net.fabricmc.fabric.api.registry.FlammableBlockRegistry;
|
||||
import net.fabricmc.fabric.impl.registry.FireBlockHooks;
|
||||
import net.fabricmc.fabric.impl.registry.FlammableBlockRegistryImpl;
|
||||
|
||||
@Mixin(FireBlock.class)
|
||||
public class MixinFireBlock implements FireBlockHooks {
|
||||
private FlammableBlockRegistryImpl fabric_registry;
|
||||
|
@ -52,6 +54,7 @@ public class MixinFireBlock implements FireBlockHooks {
|
|||
@Inject(at = @At("HEAD"), method = "getBurnChance", cancellable = true)
|
||||
private void getFabricBurnChance(BlockState block, CallbackInfoReturnable info) {
|
||||
FlammableBlockRegistry.Entry entry = fabric_registry.getFabric(block.getBlock());
|
||||
|
||||
if (entry != null) {
|
||||
// TODO: use a (BlockState -> int) with this as the default impl
|
||||
if (block.contains(Properties.WATERLOGGED) && block.get(Properties.WATERLOGGED)) {
|
||||
|
@ -65,6 +68,7 @@ public class MixinFireBlock implements FireBlockHooks {
|
|||
@Inject(at = @At("HEAD"), method = "getSpreadChance", cancellable = true)
|
||||
private void getFabricSpreadChance(BlockState block, CallbackInfoReturnable info) {
|
||||
FlammableBlockRegistry.Entry entry = fabric_registry.getFabric(block.getBlock());
|
||||
|
||||
if (entry != null) {
|
||||
// TODO: use a (BlockState -> int) with this as the default impl
|
||||
if (block.contains(Properties.WATERLOGGED) && block.get(Properties.WATERLOGGED)) {
|
||||
|
|
|
@ -16,18 +16,20 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.crash;
|
||||
|
||||
import net.fabricmc.loader.api.FabricLoader;
|
||||
import net.fabricmc.loader.api.ModContainer;
|
||||
import net.minecraft.util.crash.CrashReport;
|
||||
import net.minecraft.util.crash.CrashReportSection;
|
||||
import java.util.Map;
|
||||
import java.util.TreeMap;
|
||||
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
import org.spongepowered.asm.mixin.injection.At;
|
||||
import org.spongepowered.asm.mixin.injection.Inject;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||
|
||||
import java.util.Map;
|
||||
import java.util.TreeMap;
|
||||
import net.minecraft.util.crash.CrashReport;
|
||||
import net.minecraft.util.crash.CrashReportSection;
|
||||
|
||||
import net.fabricmc.loader.api.FabricLoader;
|
||||
import net.fabricmc.loader.api.ModContainer;
|
||||
|
||||
@Mixin(CrashReport.class)
|
||||
public abstract class MixinCrashReport {
|
||||
|
@ -38,6 +40,7 @@ public abstract class MixinCrashReport {
|
|||
private void fillSystemDetails(CallbackInfo info) {
|
||||
getSystemDetailsSection().add("Fabric Mods", () -> {
|
||||
Map<String, String> mods = new TreeMap<>();
|
||||
|
||||
for (ModContainer container : FabricLoader.getInstance().getAllMods()) {
|
||||
mods.put(container.getMetadata().getId(), container.getMetadata().getName() + " " + container.getMetadata().getVersion().getFriendlyString());
|
||||
}
|
||||
|
|
|
@ -20,7 +20,6 @@ import net.minecraft.block.pattern.BlockPattern;
|
|||
import net.minecraft.entity.Entity;
|
||||
import net.minecraft.server.world.ServerWorld;
|
||||
import net.minecraft.util.math.Direction;
|
||||
import net.minecraft.world.dimension.DimensionType;
|
||||
|
||||
/**
|
||||
* Responsible for placing an Entity once they have entered a dimension.
|
||||
|
@ -35,7 +34,7 @@ public interface EntityPlacer {
|
|||
* Handles the placement of an entity going to a dimension.
|
||||
* Utilized by {@link FabricDimensions#teleport(Entity, DimensionType, EntityPlacer)} to specify placement logic when needed.
|
||||
*
|
||||
* <p> This method may have side effects such as the creation of a portal in the target dimension,
|
||||
* <p>This method may have side effects such as the creation of a portal in the target dimension,
|
||||
* or the creation of a chunk loading ticket.
|
||||
*
|
||||
* @param portalDir the direction the portal is facing, meaningless if no portal was used
|
||||
|
|
|
@ -16,6 +16,8 @@
|
|||
|
||||
package net.fabricmc.fabric.api.dimension.v1;
|
||||
|
||||
import java.util.function.BiFunction;
|
||||
|
||||
import com.google.common.base.Preconditions;
|
||||
|
||||
import net.minecraft.entity.Entity;
|
||||
|
@ -29,8 +31,6 @@ import net.minecraft.world.biome.VoronoiBiomeAccessType;
|
|||
import net.minecraft.world.dimension.Dimension;
|
||||
import net.minecraft.world.dimension.DimensionType;
|
||||
|
||||
import java.util.function.BiFunction;
|
||||
|
||||
/**
|
||||
* An extended version of {@link DimensionType} with automatic raw id management and default placement settings.
|
||||
* {@code FabricDimensionType} instances are constructed and registered through a {@link Builder}.
|
||||
|
@ -42,7 +42,7 @@ import java.util.function.BiFunction;
|
|||
public final class FabricDimensionType extends DimensionType {
|
||||
private final EntityPlacer defaultPlacement;
|
||||
private int desiredRawId;
|
||||
/** The fixed raw id for this dimension type, set through reflection */
|
||||
/** The fixed raw id for this dimension type, set through reflection. */
|
||||
private int fixedRawId;
|
||||
|
||||
/**
|
||||
|
@ -77,7 +77,7 @@ public final class FabricDimensionType extends DimensionType {
|
|||
/**
|
||||
* Return the current raw id for this dimension type.
|
||||
*
|
||||
* <p> The returned id is guaranteed to be unique and persistent in a save,
|
||||
* <p>The returned id is guaranteed to be unique and persistent in a save,
|
||||
* as well as synchronized between a server and its connected clients.
|
||||
* It may change when connecting to a different server or opening a new save.
|
||||
*
|
||||
|
@ -131,7 +131,7 @@ public final class FabricDimensionType extends DimensionType {
|
|||
* Set the default placer used when teleporting entities to dimensions of the built type.
|
||||
* The default placer must be set before building a dimension type.
|
||||
*
|
||||
* <p> A dimension type's default placer must never return {@code null} when its
|
||||
* <p>A dimension type's default placer must never return {@code null} when its
|
||||
* {@link EntityPlacer#placeEntity(Entity, ServerWorld, Direction, double, double) placeEntity} method
|
||||
* is called.
|
||||
*
|
||||
|
@ -194,7 +194,7 @@ public final class FabricDimensionType extends DimensionType {
|
|||
* If this method is not called, the value defaults to the raw registry id
|
||||
* of the dimension type.
|
||||
*
|
||||
* <p> A Fabric Dimension's desired raw id is used as its actual raw id
|
||||
* <p>A Fabric Dimension's desired raw id is used as its actual raw id
|
||||
* when it does not conflict with any existing id, and the world
|
||||
* save does not map the dimension to a different raw id.
|
||||
*
|
||||
|
@ -212,7 +212,7 @@ public final class FabricDimensionType extends DimensionType {
|
|||
/**
|
||||
* Build and register a {@code FabricDimensionType}.
|
||||
*
|
||||
* <p> The {@code dimensionId} is used as a registry ID, and as
|
||||
* <p>The {@code dimensionId} is used as a registry ID, and as
|
||||
* a unique name both for the dimension suffix and the save directory.
|
||||
*
|
||||
* @param dimensionId the id used to name and register the dimension
|
||||
|
@ -225,7 +225,7 @@ public final class FabricDimensionType extends DimensionType {
|
|||
Preconditions.checkArgument(Registry.DIMENSION.get(dimensionId) == null);
|
||||
Preconditions.checkState(this.defaultPlacer != null, "No defaultPlacer has been specified!");
|
||||
Preconditions.checkState(this.factory != null, "No dimension factory has been specified!");
|
||||
|
||||
|
||||
String suffix = dimensionId.getNamespace() + "_" + dimensionId.getPath();
|
||||
String saveDir = "DIM_" + dimensionId.getNamespace() + "_" + dimensionId.getPath();
|
||||
FabricDimensionType built = new FabricDimensionType(suffix, saveDir, this);
|
||||
|
|
|
@ -17,10 +17,12 @@
|
|||
package net.fabricmc.fabric.api.dimension.v1;
|
||||
|
||||
import com.google.common.base.Preconditions;
|
||||
import net.fabricmc.fabric.impl.dimension.FabricDimensionInternals;
|
||||
|
||||
import net.minecraft.entity.Entity;
|
||||
import net.minecraft.world.dimension.DimensionType;
|
||||
|
||||
import net.fabricmc.fabric.impl.dimension.FabricDimensionInternals;
|
||||
|
||||
/**
|
||||
* This class consists exclusively of static methods that operate on world dimensions.
|
||||
*/
|
||||
|
@ -32,10 +34,10 @@ public final class FabricDimensions {
|
|||
/**
|
||||
* Teleports an entity to a different dimension, using custom placement logic.
|
||||
*
|
||||
* <p> This method behaves as if:
|
||||
* <p>This method behaves as if:
|
||||
* <pre>{@code teleported.changeDimension(destination)}</pre>
|
||||
*
|
||||
* <p> If {@code destination} is a {@link FabricDimensionType}, the placement logic used
|
||||
* <p>If {@code destination} is a {@link FabricDimensionType}, the placement logic used
|
||||
* is {@link FabricDimensionType#getDefaultPlacement()}. If {@code destination} is
|
||||
* the nether or the overworld, the default logic is the vanilla path.
|
||||
* For any other dimension, the default placement behaviour is undefined.
|
||||
|
@ -43,7 +45,7 @@ public final class FabricDimensions {
|
|||
* {@code lastPortalDirectionVector}, and {@code lastPortalDirection} fields should be updated
|
||||
* before calling this method.
|
||||
*
|
||||
* <p> After calling this method, {@code teleported} may be invalidated. Callers should use
|
||||
* <p>After calling this method, {@code teleported} may be invalidated. Callers should use
|
||||
* the returned entity for any further manipulation.
|
||||
*
|
||||
* @param teleported the entity to teleport
|
||||
|
@ -58,12 +60,12 @@ public final class FabricDimensions {
|
|||
/**
|
||||
* Teleports an entity to a different dimension, using custom placement logic.
|
||||
*
|
||||
* <p> If {@code customPlacement} is {@code null}, this method behaves as if:
|
||||
* <p>If {@code customPlacement} is {@code null}, this method behaves as if:
|
||||
* <pre>{@code teleported.changeDimension(destination)}</pre>
|
||||
* The {@code customPlacement} may itself return {@code null}, in which case
|
||||
* the default placement logic for that dimension will be run.
|
||||
*
|
||||
* <p> If {@code destination} is a {@link FabricDimensionType}, the default placement logic
|
||||
* <p>If {@code destination} is a {@link FabricDimensionType}, the default placement logic
|
||||
* is {@link FabricDimensionType#getDefaultPlacement()}. If {@code destination} is the nether
|
||||
* or the overworld, the default logic is the vanilla path.
|
||||
* For any other dimension, the default placement behaviour is undefined.
|
||||
|
@ -71,7 +73,7 @@ public final class FabricDimensions {
|
|||
* {@code lastPortalDirectionVector}, and {@code lastPortalDirection} fields should be updated
|
||||
* before calling this method.
|
||||
*
|
||||
* <p> After calling this method, {@code teleported} may be invalidated. Callers should use
|
||||
* <p>After calling this method, {@code teleported} may be invalidated. Callers should use
|
||||
* the returned entity for any further manipulation.
|
||||
*
|
||||
* @param teleported the entity to teleport
|
||||
|
|
|
@ -16,12 +16,15 @@
|
|||
|
||||
package net.fabricmc.fabric.impl.dimension;
|
||||
|
||||
import java.lang.reflect.Field;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.Objects;
|
||||
|
||||
import io.netty.buffer.Unpooled;
|
||||
import it.unimi.dsi.fastutil.ints.Int2ObjectMap;
|
||||
import it.unimi.dsi.fastutil.ints.Int2ObjectOpenHashMap;
|
||||
import net.fabricmc.fabric.api.dimension.v1.FabricDimensionType;
|
||||
import net.fabricmc.fabric.api.network.ServerSidePacketRegistry;
|
||||
import net.fabricmc.fabric.impl.registry.RemapException;
|
||||
|
||||
import net.minecraft.nbt.CompoundTag;
|
||||
import net.minecraft.network.Packet;
|
||||
import net.minecraft.util.Identifier;
|
||||
|
@ -30,10 +33,9 @@ import net.minecraft.util.registry.Registry;
|
|||
import net.minecraft.world.dimension.DimensionType;
|
||||
import net.minecraft.world.level.LevelProperties;
|
||||
|
||||
import java.lang.reflect.Field;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.Objects;
|
||||
import net.fabricmc.fabric.api.dimension.v1.FabricDimensionType;
|
||||
import net.fabricmc.fabric.api.network.ServerSidePacketRegistry;
|
||||
import net.fabricmc.fabric.impl.registry.RemapException;
|
||||
|
||||
/**
|
||||
* Handles fixing raw dimension ids between saves and servers,
|
||||
|
@ -72,6 +74,7 @@ public class DimensionIdsFixer {
|
|||
setFixedRawId(fabricDimension, fabricDimension.getDesiredRawId());
|
||||
} else {
|
||||
Identifier existing = fixedIds.put(dimensionType.getRawId(), id);
|
||||
|
||||
if (existing != null) {
|
||||
throw new RemapException("Two non-fabric dimensions have the same raw dim id (" + dimensionType.getRawId() + ") : " + existing + " and " + id);
|
||||
}
|
||||
|
@ -89,6 +92,7 @@ public class DimensionIdsFixer {
|
|||
}
|
||||
|
||||
DimensionType dim = DimensionType.byId(dimId);
|
||||
|
||||
if (dim instanceof FabricDimensionType) {
|
||||
setFixedRawId((FabricDimensionType) dim, savedRawId);
|
||||
} else {
|
||||
|
@ -100,6 +104,7 @@ public class DimensionIdsFixer {
|
|||
|
||||
// step 3: de-duplicate raw ids for dimensions which ids are not fixed yet
|
||||
int nextFreeId = 0;
|
||||
|
||||
for (FabricDimensionType fabricDimension : fabricDimensions) {
|
||||
int rawDimId = fabricDimension.getRawId();
|
||||
Identifier dimId = Objects.requireNonNull(DimensionType.getId(fabricDimension));
|
||||
|
|
|
@ -19,7 +19,7 @@ package net.fabricmc.fabric.impl.dimension;
|
|||
import net.minecraft.nbt.CompoundTag;
|
||||
|
||||
/**
|
||||
* An object holding a raw id -> full id map for fabric dimensions
|
||||
* An object holding a raw id -> full id map for fabric dimensions.
|
||||
*/
|
||||
public interface DimensionIdsHolder {
|
||||
CompoundTag fabric_getDimensionIds();
|
||||
|
|
|
@ -16,18 +16,20 @@
|
|||
|
||||
package net.fabricmc.fabric.impl.dimension;
|
||||
|
||||
import net.fabricmc.fabric.api.network.ClientSidePacketRegistry;
|
||||
import net.fabricmc.fabric.api.network.PacketContext;
|
||||
import net.fabricmc.fabric.impl.registry.RemapException;
|
||||
import org.apache.logging.log4j.LogManager;
|
||||
import org.apache.logging.log4j.Logger;
|
||||
|
||||
import net.minecraft.client.MinecraftClient;
|
||||
import net.minecraft.client.network.ClientPlayerEntity;
|
||||
import net.minecraft.nbt.CompoundTag;
|
||||
import net.minecraft.text.LiteralText;
|
||||
import org.apache.logging.log4j.LogManager;
|
||||
import org.apache.logging.log4j.Logger;
|
||||
|
||||
import net.fabricmc.fabric.api.network.ClientSidePacketRegistry;
|
||||
import net.fabricmc.fabric.api.network.PacketContext;
|
||||
import net.fabricmc.fabric.impl.registry.RemapException;
|
||||
|
||||
/**
|
||||
* Client entry point for fabric-dimensions
|
||||
* Client entry point for fabric-dimensions.
|
||||
*/
|
||||
public final class FabricDimensionClientInit {
|
||||
private static final Logger LOGGER = LogManager.getLogger();
|
||||
|
@ -55,8 +57,7 @@ public final class FabricDimensionClientInit {
|
|||
LOGGER.error("Dimension id remapping failed!", e);
|
||||
|
||||
MinecraftClient.getInstance().execute(() -> ((ClientPlayerEntity) ctx.getPlayer()).networkHandler.getConnection().disconnect(
|
||||
new LiteralText("Dimension id remapping failed: " + e)
|
||||
new LiteralText("Dimension id remapping failed: " + e)
|
||||
));
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -17,17 +17,19 @@
|
|||
package net.fabricmc.fabric.impl.dimension;
|
||||
|
||||
import com.google.common.base.Preconditions;
|
||||
import net.fabricmc.fabric.api.dimension.v1.EntityPlacer;
|
||||
import net.fabricmc.fabric.api.dimension.v1.FabricDimensionType;
|
||||
import net.fabricmc.fabric.api.dimension.v1.FabricDimensions;
|
||||
import net.fabricmc.fabric.mixin.EntityHooks;
|
||||
import org.apache.logging.log4j.LogManager;
|
||||
import org.apache.logging.log4j.Logger;
|
||||
|
||||
import net.minecraft.block.pattern.BlockPattern;
|
||||
import net.minecraft.entity.Entity;
|
||||
import net.minecraft.server.world.ServerWorld;
|
||||
import net.minecraft.util.math.Direction;
|
||||
import net.minecraft.world.dimension.DimensionType;
|
||||
import org.apache.logging.log4j.LogManager;
|
||||
import org.apache.logging.log4j.Logger;
|
||||
|
||||
import net.fabricmc.fabric.api.dimension.v1.EntityPlacer;
|
||||
import net.fabricmc.fabric.api.dimension.v1.FabricDimensionType;
|
||||
import net.fabricmc.fabric.api.dimension.v1.FabricDimensions;
|
||||
import net.fabricmc.fabric.mixin.EntityHooks;
|
||||
|
||||
public final class FabricDimensionInternals {
|
||||
private FabricDimensionInternals() {
|
||||
|
@ -38,11 +40,11 @@ public final class FabricDimensionInternals {
|
|||
public static final Logger LOGGER = LogManager.getLogger();
|
||||
|
||||
/**
|
||||
* The entity currently being transported to another dimension
|
||||
* The entity currently being transported to another dimension.
|
||||
*/
|
||||
private static final ThreadLocal<Entity> PORTAL_ENTITY = new ThreadLocal<>();
|
||||
/**
|
||||
* The custom placement logic passed from {@link FabricDimensions#teleport(Entity, DimensionType, EntityPlacer)}
|
||||
* The custom placement logic passed from {@link FabricDimensions#teleport(Entity, DimensionType, EntityPlacer)}.
|
||||
*/
|
||||
private static EntityPlacer customPlacement;
|
||||
|
||||
|
@ -65,9 +67,11 @@ public final class FabricDimensionInternals {
|
|||
|
||||
// Set values used by `PortalForcer#changeDimension` to prevent a NPE crash.
|
||||
EntityHooks access = ((EntityHooks) entity);
|
||||
|
||||
if (entity.getLastPortalDirectionVector() == null) {
|
||||
access.setLastPortalDirectionVector(entity.getRotationVector());
|
||||
}
|
||||
|
||||
if (entity.getLastPortalDirection() == null) {
|
||||
access.setLastPortalDirection(entity.getHorizontalFacing());
|
||||
}
|
||||
|
@ -86,6 +90,7 @@ public final class FabricDimensionInternals {
|
|||
|
||||
// Custom placement logic, falls back to default dimension placement if no placement or target found
|
||||
EntityPlacer customPlacement = FabricDimensionInternals.customPlacement;
|
||||
|
||||
if (customPlacement != null) {
|
||||
BlockPattern.TeleportTarget customTarget = customPlacement.placeEntity(teleported, destination, portalDir, portalX, portalY);
|
||||
|
||||
|
@ -96,12 +101,14 @@ public final class FabricDimensionInternals {
|
|||
|
||||
// Default placement logic, falls back to vanilla if not a fabric dimension
|
||||
DimensionType dimType = destination.getDimension().getType();
|
||||
|
||||
if (dimType instanceof FabricDimensionType) {
|
||||
BlockPattern.TeleportTarget defaultTarget = ((FabricDimensionType) dimType).getDefaultPlacement().placeEntity(teleported, destination, portalDir, portalX, portalY);
|
||||
|
||||
if (defaultTarget == null) {
|
||||
throw new IllegalStateException("Mod dimension " + DimensionType.getId(dimType) + " returned an invalid teleport target");
|
||||
}
|
||||
|
||||
return defaultTarget;
|
||||
}
|
||||
|
||||
|
@ -121,5 +128,4 @@ public final class FabricDimensionInternals {
|
|||
customPlacement = null;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -16,11 +16,12 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin;
|
||||
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.gen.Accessor;
|
||||
|
||||
import net.minecraft.entity.Entity;
|
||||
import net.minecraft.util.math.Direction;
|
||||
import net.minecraft.util.math.Vec3d;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.gen.Accessor;
|
||||
|
||||
@Mixin(Entity.class)
|
||||
public interface EntityHooks {
|
||||
|
@ -29,5 +30,4 @@ public interface EntityHooks {
|
|||
|
||||
@Accessor
|
||||
void setLastPortalDirection(Direction dir);
|
||||
|
||||
}
|
||||
|
|
|
@ -16,17 +16,18 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin;
|
||||
|
||||
import net.fabricmc.fabric.impl.dimension.FabricDimensionInternals;
|
||||
import net.minecraft.entity.Entity;
|
||||
import net.minecraft.world.dimension.DimensionType;
|
||||
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.CallbackInfoReturnable;
|
||||
|
||||
import net.minecraft.entity.Entity;
|
||||
import net.minecraft.world.dimension.DimensionType;
|
||||
|
||||
import net.fabricmc.fabric.impl.dimension.FabricDimensionInternals;
|
||||
|
||||
@Mixin(Entity.class)
|
||||
public abstract class MixinEntity {
|
||||
|
||||
// Inject right before the direction vector is retrieved by the game
|
||||
@Inject(method = "changeDimension", at = @At(value = "INVOKE", target = "Lnet/minecraft/entity/Entity;getLastPortalDirectionVector()Lnet/minecraft/util/math/Vec3d;"))
|
||||
private void onGetPortal(DimensionType dimension, CallbackInfoReturnable<Entity> cir) {
|
||||
|
|
|
@ -16,7 +16,13 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin;
|
||||
|
||||
import net.fabricmc.fabric.impl.dimension.FabricDimensionInternals;
|
||||
import org.spongepowered.asm.mixin.Final;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
import org.spongepowered.asm.mixin.injection.At;
|
||||
import org.spongepowered.asm.mixin.injection.Inject;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable;
|
||||
|
||||
import net.minecraft.block.pattern.BlockPattern;
|
||||
import net.minecraft.entity.Entity;
|
||||
import net.minecraft.server.world.ServerWorld;
|
||||
|
@ -24,12 +30,8 @@ import net.minecraft.util.math.BlockPos;
|
|||
import net.minecraft.util.math.Direction;
|
||||
import net.minecraft.util.math.Vec3d;
|
||||
import net.minecraft.world.PortalForcer;
|
||||
import org.spongepowered.asm.mixin.Final;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
import org.spongepowered.asm.mixin.injection.At;
|
||||
import org.spongepowered.asm.mixin.injection.Inject;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable;
|
||||
|
||||
import net.fabricmc.fabric.impl.dimension.FabricDimensionInternals;
|
||||
|
||||
@Mixin(PortalForcer.class)
|
||||
public abstract class MixinPortalForcer {
|
||||
|
|
|
@ -16,13 +16,14 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.idremap;
|
||||
|
||||
import net.minecraft.util.registry.Registry;
|
||||
import net.minecraft.world.dimension.DimensionType;
|
||||
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.CallbackInfoReturnable;
|
||||
|
||||
import net.minecraft.util.registry.Registry;
|
||||
import net.minecraft.world.dimension.DimensionType;
|
||||
|
||||
// NOTE: This probably goes into dimension-fixes
|
||||
@Mixin(DimensionType.class)
|
||||
public abstract class MixinDimensionRawIndexFix {
|
||||
|
|
|
@ -17,18 +17,20 @@
|
|||
package net.fabricmc.fabric.mixin.idremap;
|
||||
|
||||
import com.mojang.datafixers.DataFixer;
|
||||
import net.fabricmc.fabric.impl.dimension.DimensionIdsFixer;
|
||||
import net.fabricmc.fabric.impl.dimension.DimensionIdsHolder;
|
||||
import net.fabricmc.fabric.impl.dimension.DimensionRemapException;
|
||||
import net.fabricmc.fabric.impl.registry.RemapException;
|
||||
import net.minecraft.nbt.CompoundTag;
|
||||
import net.minecraft.world.level.LevelProperties;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Unique;
|
||||
import org.spongepowered.asm.mixin.injection.At;
|
||||
import org.spongepowered.asm.mixin.injection.Inject;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||
|
||||
import net.minecraft.nbt.CompoundTag;
|
||||
import net.minecraft.world.level.LevelProperties;
|
||||
|
||||
import net.fabricmc.fabric.impl.dimension.DimensionIdsFixer;
|
||||
import net.fabricmc.fabric.impl.dimension.DimensionIdsHolder;
|
||||
import net.fabricmc.fabric.impl.dimension.DimensionRemapException;
|
||||
import net.fabricmc.fabric.impl.registry.RemapException;
|
||||
|
||||
@Mixin(LevelProperties.class)
|
||||
public abstract class MixinLevelProperties implements DimensionIdsHolder {
|
||||
@Unique
|
||||
|
@ -42,6 +44,7 @@ public abstract class MixinLevelProperties implements DimensionIdsHolder {
|
|||
@Inject(method = "<init>(Lnet/minecraft/nbt/CompoundTag;Lcom/mojang/datafixers/DataFixer;ILnet/minecraft/nbt/CompoundTag;)V", at = @At("RETURN"))
|
||||
private void readDimensionIds(CompoundTag data, DataFixer fixer, int version, CompoundTag player, CallbackInfo ci) {
|
||||
CompoundTag savedIds = data.getCompound("fabric_DimensionIds");
|
||||
|
||||
try {
|
||||
this.fabricDimensionIds = DimensionIdsFixer.apply(savedIds);
|
||||
} catch (RemapException e) {
|
||||
|
|
|
@ -16,12 +16,14 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.idremap;
|
||||
|
||||
import net.fabricmc.fabric.impl.dimension.DimensionRemapException;
|
||||
import net.minecraft.world.level.storage.LevelStorage;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.injection.At;
|
||||
import org.spongepowered.asm.mixin.injection.ModifyArg;
|
||||
|
||||
import net.minecraft.world.level.storage.LevelStorage;
|
||||
|
||||
import net.fabricmc.fabric.impl.dimension.DimensionRemapException;
|
||||
|
||||
@Mixin(LevelStorage.class)
|
||||
public abstract class MixinLevelStorage {
|
||||
@ModifyArg(method = "readLevelProperties", at = @At(value = "INVOKE", target = "Lorg/apache/logging/log4j/Logger;error(Ljava/lang/String;Ljava/lang/Object;Ljava/lang/Object;)V", remap = false), index = 2)
|
||||
|
|
|
@ -16,20 +16,22 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.idremap;
|
||||
|
||||
import net.fabricmc.fabric.impl.dimension.DimensionIdsFixer;
|
||||
import net.fabricmc.fabric.impl.dimension.FabricDimensionInternals;
|
||||
import net.minecraft.network.ClientConnection;
|
||||
import net.minecraft.server.PlayerManager;
|
||||
import net.minecraft.server.network.ServerPlayerEntity;
|
||||
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 net.minecraft.network.ClientConnection;
|
||||
import net.minecraft.server.PlayerManager;
|
||||
import net.minecraft.server.network.ServerPlayerEntity;
|
||||
|
||||
import net.fabricmc.fabric.impl.dimension.DimensionIdsFixer;
|
||||
import net.fabricmc.fabric.impl.dimension.FabricDimensionInternals;
|
||||
|
||||
@Mixin(PlayerManager.class)
|
||||
public abstract class MixinPlayerManager {
|
||||
/**
|
||||
* Synchronizes raw dimension ids to connecting players
|
||||
* Synchronizes raw dimension ids to connecting players.
|
||||
*/
|
||||
@Inject(method = "onPlayerConnect", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/network/packet/DifficultyS2CPacket;<init>(Lnet/minecraft/world/Difficulty;Z)V"))
|
||||
private void onPlayerConnect(ClientConnection conn, ServerPlayerEntity player, CallbackInfo info) {
|
||||
|
|
|
@ -16,14 +16,16 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.idremap;
|
||||
|
||||
import net.fabricmc.fabric.impl.dimension.DimensionIdsHolder;
|
||||
import net.minecraft.nbt.CompoundTag;
|
||||
import net.minecraft.world.level.LevelProperties;
|
||||
import net.minecraft.world.level.UnmodifiableLevelProperties;
|
||||
import org.spongepowered.asm.mixin.Final;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
|
||||
import net.minecraft.nbt.CompoundTag;
|
||||
import net.minecraft.world.level.LevelProperties;
|
||||
import net.minecraft.world.level.UnmodifiableLevelProperties;
|
||||
|
||||
import net.fabricmc.fabric.impl.dimension.DimensionIdsHolder;
|
||||
|
||||
@Mixin(UnmodifiableLevelProperties.class)
|
||||
public abstract class MixinUnmodifiableLevelProperties implements DimensionIdsHolder {
|
||||
@Shadow
|
||||
|
@ -31,7 +33,7 @@ public abstract class MixinUnmodifiableLevelProperties implements DimensionIdsHo
|
|||
private LevelProperties properties;
|
||||
|
||||
/**
|
||||
* Delegates to the main level properties
|
||||
* Delegates to the main level properties.
|
||||
*/
|
||||
@Override
|
||||
public CompoundTag fabric_getDimensionIds() {
|
||||
|
|
|
@ -16,31 +16,33 @@
|
|||
|
||||
package net.fabricmc.fabric.api.event.client.player;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
import net.minecraft.entity.player.PlayerEntity;
|
||||
import net.minecraft.item.ItemStack;
|
||||
import net.minecraft.util.hit.HitResult;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
|
||||
/**
|
||||
* This event is emitted during the block-picking process. It can be used to
|
||||
* modify the returned ItemStack, as well as nullify it - returning an empty
|
||||
* ItemStack will cause the event to leave, and no block to be picked.
|
||||
*/
|
||||
public interface ClientPickBlockApplyCallback {
|
||||
public static final Event<ClientPickBlockApplyCallback> EVENT = EventFactory.createArrayBacked(ClientPickBlockApplyCallback.class,
|
||||
(listeners) -> (player, result, _stack) -> {
|
||||
ItemStack stack = _stack;
|
||||
Event<ClientPickBlockApplyCallback> EVENT = EventFactory.createArrayBacked(ClientPickBlockApplyCallback.class,
|
||||
(listeners) -> (player, result, _stack) -> {
|
||||
ItemStack stack = _stack;
|
||||
|
||||
for (ClientPickBlockApplyCallback event : listeners) {
|
||||
stack = event.pick(player, result, stack);
|
||||
if (stack.isEmpty()) {
|
||||
return ItemStack.EMPTY;
|
||||
for (ClientPickBlockApplyCallback event : listeners) {
|
||||
stack = event.pick(player, result, stack);
|
||||
|
||||
if (stack.isEmpty()) {
|
||||
return ItemStack.EMPTY;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return stack;
|
||||
}
|
||||
return stack;
|
||||
}
|
||||
);
|
||||
|
||||
ItemStack pick(PlayerEntity player, HitResult result, ItemStack stack);
|
||||
|
|
|
@ -16,12 +16,13 @@
|
|||
|
||||
package net.fabricmc.fabric.api.event.client.player;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
import net.minecraft.entity.player.PlayerEntity;
|
||||
import net.minecraft.item.ItemStack;
|
||||
import net.minecraft.util.hit.HitResult;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
|
||||
/**
|
||||
* This event handler has been deprecated due to not hooking nicely
|
||||
* into the game. Please use the alternatives.
|
||||
|
@ -32,7 +33,7 @@ import net.minecraft.util.hit.HitResult;
|
|||
@Deprecated
|
||||
public interface ClientPickBlockCallback {
|
||||
@Deprecated
|
||||
public static final class Container {
|
||||
final class Container {
|
||||
private ItemStack stack;
|
||||
|
||||
public Container(ItemStack stack) {
|
||||
|
@ -48,8 +49,7 @@ public interface ClientPickBlockCallback {
|
|||
}
|
||||
}
|
||||
|
||||
@Deprecated
|
||||
public static final Event<ClientPickBlockCallback> EVENT = EventFactory.createArrayBacked(ClientPickBlockCallback.class,
|
||||
@Deprecated Event<ClientPickBlockCallback> EVENT = EventFactory.createArrayBacked(ClientPickBlockCallback.class,
|
||||
(listeners) -> (player, result, container) -> {
|
||||
for (ClientPickBlockCallback event : listeners) {
|
||||
if (!event.pick(player, result, container)) {
|
||||
|
|
|
@ -16,29 +16,31 @@
|
|||
|
||||
package net.fabricmc.fabric.api.event.client.player;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
import net.minecraft.entity.player.PlayerEntity;
|
||||
import net.minecraft.item.ItemStack;
|
||||
import net.minecraft.util.hit.HitResult;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
|
||||
/**
|
||||
* This event is emitted at the beginning of the block picking process in
|
||||
* order to find any applicable ItemStack. The first non-empty ItemStack
|
||||
* will be returned, overriding vanilla behaviour.
|
||||
*/
|
||||
public interface ClientPickBlockGatherCallback {
|
||||
public static final Event<ClientPickBlockGatherCallback> EVENT = EventFactory.createArrayBacked(ClientPickBlockGatherCallback.class,
|
||||
(listeners) -> (player, result) -> {
|
||||
for (ClientPickBlockGatherCallback event : listeners) {
|
||||
ItemStack stack = event.pick(player, result);
|
||||
if (stack != ItemStack.EMPTY && !stack.isEmpty()) {
|
||||
return stack;
|
||||
}
|
||||
}
|
||||
Event<ClientPickBlockGatherCallback> EVENT = EventFactory.createArrayBacked(ClientPickBlockGatherCallback.class,
|
||||
(listeners) -> (player, result) -> {
|
||||
for (ClientPickBlockGatherCallback event : listeners) {
|
||||
ItemStack stack = event.pick(player, result);
|
||||
|
||||
return ItemStack.EMPTY;
|
||||
}
|
||||
if (stack != ItemStack.EMPTY && !stack.isEmpty()) {
|
||||
return stack;
|
||||
}
|
||||
}
|
||||
|
||||
return ItemStack.EMPTY;
|
||||
}
|
||||
);
|
||||
|
||||
ItemStack pick(PlayerEntity player, HitResult result);
|
||||
|
|
|
@ -16,8 +16,6 @@
|
|||
|
||||
package net.fabricmc.fabric.api.event.player;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
import net.minecraft.entity.player.PlayerEntity;
|
||||
import net.minecraft.util.ActionResult;
|
||||
import net.minecraft.util.Hand;
|
||||
|
@ -25,29 +23,33 @@ import net.minecraft.util.math.BlockPos;
|
|||
import net.minecraft.util.math.Direction;
|
||||
import net.minecraft.world.World;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
|
||||
/**
|
||||
* Callback for left-clicking ("attacking") a block.
|
||||
* Is hooked in before the spectator check, so make sure to check for the player's game mode as well!
|
||||
* <p>
|
||||
* Upon return:
|
||||
* - SUCCESS cancels further processing and, on the client, sends a packet to the server.
|
||||
* - PASS falls back to further processing.
|
||||
* - FAIL cancels further processing and does not send a packet to the server.
|
||||
* <p>
|
||||
* ATTACK_BLOCK does not let you control the packet sending process yet.
|
||||
*
|
||||
* <p>Upon return:
|
||||
* <ul><li>SUCCESS cancels further processing and, on the client, sends a packet to the server.
|
||||
* <li>PASS falls back to further processing.
|
||||
* <li>FAIL cancels further processing and does not send a packet to the server.</ul>
|
||||
*
|
||||
* <p>ATTACK_BLOCK does not let you control the packet sending process yet.
|
||||
*/
|
||||
public interface AttackBlockCallback {
|
||||
public static final Event<AttackBlockCallback> EVENT = EventFactory.createArrayBacked(AttackBlockCallback.class,
|
||||
(listeners) -> (player, world, hand, pos, direction) -> {
|
||||
for (AttackBlockCallback event : listeners) {
|
||||
ActionResult result = event.interact(player, world, hand, pos, direction);
|
||||
if (result != ActionResult.PASS) {
|
||||
return result;
|
||||
}
|
||||
}
|
||||
Event<AttackBlockCallback> EVENT = EventFactory.createArrayBacked(AttackBlockCallback.class,
|
||||
(listeners) -> (player, world, hand, pos, direction) -> {
|
||||
for (AttackBlockCallback event : listeners) {
|
||||
ActionResult result = event.interact(player, world, hand, pos, direction);
|
||||
|
||||
return ActionResult.PASS;
|
||||
}
|
||||
if (result != ActionResult.PASS) {
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
return ActionResult.PASS;
|
||||
}
|
||||
);
|
||||
|
||||
ActionResult interact(PlayerEntity player, World world, Hand hand, BlockPos pos, Direction direction);
|
||||
|
|
|
@ -16,8 +16,6 @@
|
|||
|
||||
package net.fabricmc.fabric.api.event.player;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
import net.minecraft.entity.Entity;
|
||||
import net.minecraft.entity.player.PlayerEntity;
|
||||
import net.minecraft.util.ActionResult;
|
||||
|
@ -25,27 +23,31 @@ import net.minecraft.util.Hand;
|
|||
import net.minecraft.util.hit.EntityHitResult;
|
||||
import net.minecraft.world.World;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
|
||||
/**
|
||||
* Callback for left-clicking ("attacking") an entity.
|
||||
* Is hooked in before the spectator check, so make sure to check for the player's game mode as well!
|
||||
* <p>
|
||||
* Upon return:
|
||||
* - SUCCESS cancels further processing and, on the client, sends a packet to the server.
|
||||
* - PASS falls back to further processing.
|
||||
* - FAIL cancels further processing and does not send a packet to the server.
|
||||
*
|
||||
* <p>Upon return:
|
||||
* <ul><li>SUCCESS cancels further processing and, on the client, sends a packet to the server.
|
||||
* <li>PASS falls back to further processing.
|
||||
* <li>FAIL cancels further processing and does not send a packet to the server.</ul>
|
||||
*/
|
||||
public interface AttackEntityCallback {
|
||||
public static final Event<AttackEntityCallback> EVENT = EventFactory.createArrayBacked(AttackEntityCallback.class,
|
||||
(listeners) -> (player, world, hand, entity, hitResult) -> {
|
||||
for (AttackEntityCallback event : listeners) {
|
||||
ActionResult result = event.interact(player, world, hand, entity, hitResult);
|
||||
if (result != ActionResult.PASS) {
|
||||
return result;
|
||||
}
|
||||
}
|
||||
Event<AttackEntityCallback> EVENT = EventFactory.createArrayBacked(AttackEntityCallback.class,
|
||||
(listeners) -> (player, world, hand, entity, hitResult) -> {
|
||||
for (AttackEntityCallback event : listeners) {
|
||||
ActionResult result = event.interact(player, world, hand, entity, hitResult);
|
||||
|
||||
return ActionResult.PASS;
|
||||
}
|
||||
if (result != ActionResult.PASS) {
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
return ActionResult.PASS;
|
||||
}
|
||||
);
|
||||
|
||||
ActionResult interact(PlayerEntity player, World world, Hand hand, Entity entity, /* Nullable */ EntityHitResult hitResult);
|
||||
|
|
|
@ -16,35 +16,37 @@
|
|||
|
||||
package net.fabricmc.fabric.api.event.player;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
import net.minecraft.entity.player.PlayerEntity;
|
||||
import net.minecraft.util.ActionResult;
|
||||
import net.minecraft.util.Hand;
|
||||
import net.minecraft.util.hit.BlockHitResult;
|
||||
import net.minecraft.world.World;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
|
||||
/**
|
||||
* Callback for right-clicking ("using") a block.
|
||||
* Is hooked in before the spectator check, so make sure to check for the player's game mode as well!
|
||||
* <p>
|
||||
* Upon return:
|
||||
* - SUCCESS cancels further processing and, on the client, sends a packet to the server.
|
||||
* - PASS falls back to further processing.
|
||||
* - FAIL cancels further processing and does not send a packet to the server.
|
||||
*
|
||||
* <p>Upon return:
|
||||
* <ul><li>SUCCESS cancels further processing and, on the client, sends a packet to the server.
|
||||
* <li>PASS falls back to further processing.
|
||||
* <li>FAIL cancels further processing and does not send a packet to the server.</ul>
|
||||
*/
|
||||
public interface UseBlockCallback {
|
||||
public static final Event<UseBlockCallback> EVENT = EventFactory.createArrayBacked(UseBlockCallback.class,
|
||||
(listeners) -> (player, world, hand, hitResult) -> {
|
||||
for (UseBlockCallback event : listeners) {
|
||||
ActionResult result = event.interact(player, world, hand, hitResult);
|
||||
if (result != ActionResult.PASS) {
|
||||
return result;
|
||||
}
|
||||
}
|
||||
Event<UseBlockCallback> EVENT = EventFactory.createArrayBacked(UseBlockCallback.class,
|
||||
(listeners) -> (player, world, hand, hitResult) -> {
|
||||
for (UseBlockCallback event : listeners) {
|
||||
ActionResult result = event.interact(player, world, hand, hitResult);
|
||||
|
||||
return ActionResult.PASS;
|
||||
}
|
||||
if (result != ActionResult.PASS) {
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
return ActionResult.PASS;
|
||||
}
|
||||
);
|
||||
|
||||
ActionResult interact(PlayerEntity player, World world, Hand hand, BlockHitResult hitResult);
|
||||
|
|
|
@ -16,8 +16,6 @@
|
|||
|
||||
package net.fabricmc.fabric.api.event.player;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
import net.minecraft.entity.Entity;
|
||||
import net.minecraft.entity.player.PlayerEntity;
|
||||
import net.minecraft.util.ActionResult;
|
||||
|
@ -25,27 +23,31 @@ import net.minecraft.util.Hand;
|
|||
import net.minecraft.util.hit.EntityHitResult;
|
||||
import net.minecraft.world.World;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
|
||||
/**
|
||||
* Callback for right-clicking ("using") an entity.
|
||||
* Is hooked in before the spectator check, so make sure to check for the player's game mode as well!
|
||||
* <p>
|
||||
* Upon return:
|
||||
* - SUCCESS cancels further processing and, on the client, sends a packet to the server.
|
||||
* - PASS falls back to further processing.
|
||||
* - FAIL cancels further processing and does not send a packet to the server.
|
||||
*
|
||||
* <p>Upon return:
|
||||
* <ul><li>SUCCESS cancels further processing and, on the client, sends a packet to the server.
|
||||
* <li>PASS falls back to further processing.
|
||||
* <li>FAIL cancels further processing and does not send a packet to the server.</ul>
|
||||
*/
|
||||
public interface UseEntityCallback {
|
||||
public static final Event<UseEntityCallback> EVENT = EventFactory.createArrayBacked(UseEntityCallback.class,
|
||||
(listeners) -> (player, world, hand, entity, hitResult) -> {
|
||||
for (UseEntityCallback event : listeners) {
|
||||
ActionResult result = event.interact(player, world, hand, entity, hitResult);
|
||||
if (result != ActionResult.PASS) {
|
||||
return result;
|
||||
}
|
||||
}
|
||||
Event<UseEntityCallback> EVENT = EventFactory.createArrayBacked(UseEntityCallback.class,
|
||||
(listeners) -> (player, world, hand, entity, hitResult) -> {
|
||||
for (UseEntityCallback event : listeners) {
|
||||
ActionResult result = event.interact(player, world, hand, entity, hitResult);
|
||||
|
||||
return ActionResult.PASS;
|
||||
}
|
||||
if (result != ActionResult.PASS) {
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
return ActionResult.PASS;
|
||||
}
|
||||
);
|
||||
|
||||
ActionResult interact(PlayerEntity player, World world, Hand hand, Entity entity, /* Nullable */ EntityHitResult hitResult);
|
||||
|
|
|
@ -16,8 +16,6 @@
|
|||
|
||||
package net.fabricmc.fabric.api.event.player;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
import net.minecraft.entity.player.PlayerEntity;
|
||||
import net.minecraft.item.ItemStack;
|
||||
import net.minecraft.util.ActionResult;
|
||||
|
@ -25,27 +23,31 @@ import net.minecraft.util.Hand;
|
|||
import net.minecraft.util.TypedActionResult;
|
||||
import net.minecraft.world.World;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
|
||||
/**
|
||||
* Callback for right-clicking ("using") an item.
|
||||
* Is hooked in before the spectator check, so make sure to check for the player's game mode as well!
|
||||
* <p>
|
||||
* Upon return:
|
||||
* - SUCCESS cancels further processing and, on the client, sends a packet to the server.
|
||||
* - PASS falls back to further processing.
|
||||
* - FAIL cancels further processing and does not send a packet to the server.
|
||||
*
|
||||
* <p>Upon return:
|
||||
* <ul><li>SUCCESS cancels further processing and, on the client, sends a packet to the server.
|
||||
* <li>PASS falls back to further processing.
|
||||
* <li>FAIL cancels further processing and does not send a packet to the server.</ul>
|
||||
*/
|
||||
public interface UseItemCallback {
|
||||
public static final Event<UseItemCallback> EVENT = EventFactory.createArrayBacked(UseItemCallback.class,
|
||||
listeners -> (player, world, hand) -> {
|
||||
for (UseItemCallback event : listeners) {
|
||||
TypedActionResult<ItemStack> result = event.interact(player, world, hand);
|
||||
if (result.getResult() != ActionResult.PASS) {
|
||||
return result;
|
||||
}
|
||||
}
|
||||
Event<UseItemCallback> EVENT = EventFactory.createArrayBacked(UseItemCallback.class,
|
||||
listeners -> (player, world, hand) -> {
|
||||
for (UseItemCallback event : listeners) {
|
||||
TypedActionResult<ItemStack> result = event.interact(player, world, hand);
|
||||
|
||||
return TypedActionResult.pass(ItemStack.EMPTY);
|
||||
}
|
||||
if (result.getResult() != ActionResult.PASS) {
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
return TypedActionResult.pass(ItemStack.EMPTY);
|
||||
}
|
||||
);
|
||||
|
||||
TypedActionResult<ItemStack> interact(PlayerEntity player, World world, Hand hand);
|
||||
|
|
|
@ -16,17 +16,19 @@
|
|||
|
||||
package net.fabricmc.fabric.impl.event;
|
||||
|
||||
import net.minecraft.block.BlockState;
|
||||
import net.minecraft.util.ActionResult;
|
||||
|
||||
import net.fabricmc.api.ModInitializer;
|
||||
import net.fabricmc.fabric.api.block.BlockAttackInteractionAware;
|
||||
import net.fabricmc.fabric.api.event.player.AttackBlockCallback;
|
||||
import net.minecraft.block.BlockState;
|
||||
import net.minecraft.util.ActionResult;
|
||||
|
||||
public class InteractionEventsRouter implements ModInitializer {
|
||||
@Override
|
||||
public void onInitialize() {
|
||||
AttackBlockCallback.EVENT.register((player, world, hand, pos, direction) -> {
|
||||
BlockState state = world.getBlockState(pos);
|
||||
|
||||
if (state instanceof BlockAttackInteractionAware) {
|
||||
if (((BlockAttackInteractionAware) state).onAttackInteraction(state, world, pos, player, hand, direction)) {
|
||||
return ActionResult.FAIL;
|
||||
|
|
|
@ -16,10 +16,6 @@
|
|||
|
||||
package net.fabricmc.fabric.impl.event;
|
||||
|
||||
import net.fabricmc.api.ClientModInitializer;
|
||||
import net.fabricmc.fabric.api.block.BlockPickInteractionAware;
|
||||
import net.fabricmc.fabric.api.entity.EntityPickInteractionAware;
|
||||
import net.fabricmc.fabric.api.event.client.player.ClientPickBlockGatherCallback;
|
||||
import net.minecraft.block.BlockState;
|
||||
import net.minecraft.entity.Entity;
|
||||
import net.minecraft.item.ItemStack;
|
||||
|
@ -28,6 +24,11 @@ import net.minecraft.util.hit.EntityHitResult;
|
|||
import net.minecraft.util.math.BlockPos;
|
||||
import net.minecraft.world.BlockView;
|
||||
|
||||
import net.fabricmc.api.ClientModInitializer;
|
||||
import net.fabricmc.fabric.api.block.BlockPickInteractionAware;
|
||||
import net.fabricmc.fabric.api.entity.EntityPickInteractionAware;
|
||||
import net.fabricmc.fabric.api.event.client.player.ClientPickBlockGatherCallback;
|
||||
|
||||
public class InteractionEventsRouterClient implements ClientModInitializer {
|
||||
@Override
|
||||
public void onInitializeClient() {
|
||||
|
|
|
@ -16,7 +16,13 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.eventsinteraction;
|
||||
|
||||
import net.fabricmc.fabric.api.event.player.*;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
import org.spongepowered.asm.mixin.injection.At;
|
||||
import org.spongepowered.asm.mixin.injection.Inject;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable;
|
||||
|
||||
import net.minecraft.client.MinecraftClient;
|
||||
import net.minecraft.client.network.ClientPlayNetworkHandler;
|
||||
import net.minecraft.client.network.ClientPlayerEntity;
|
||||
|
@ -38,12 +44,12 @@ import net.minecraft.util.math.Direction;
|
|||
import net.minecraft.util.math.Vec3d;
|
||||
import net.minecraft.world.GameMode;
|
||||
import net.minecraft.world.World;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
import org.spongepowered.asm.mixin.injection.At;
|
||||
import org.spongepowered.asm.mixin.injection.Inject;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable;
|
||||
|
||||
import net.fabricmc.fabric.api.event.player.AttackBlockCallback;
|
||||
import net.fabricmc.fabric.api.event.player.AttackEntityCallback;
|
||||
import net.fabricmc.fabric.api.event.player.UseBlockCallback;
|
||||
import net.fabricmc.fabric.api.event.player.UseEntityCallback;
|
||||
import net.fabricmc.fabric.api.event.player.UseItemCallback;
|
||||
|
||||
@Mixin(ClientPlayerInteractionManager.class)
|
||||
public class MixinClientPlayerInteractionManager {
|
||||
|
@ -57,6 +63,7 @@ public class MixinClientPlayerInteractionManager {
|
|||
@Inject(at = @At(value = "INVOKE", target = "Lnet/minecraft/world/GameMode;isCreative()Z", ordinal = 0), method = "attackBlock", cancellable = true)
|
||||
public void attackBlock(BlockPos pos, Direction direction, CallbackInfoReturnable<Boolean> info) {
|
||||
ActionResult result = AttackBlockCallback.EVENT.invoker().interact(client.player, client.world, Hand.MAIN_HAND, pos, direction);
|
||||
|
||||
if (result != ActionResult.PASS) {
|
||||
info.setReturnValue(result == ActionResult.SUCCESS);
|
||||
info.cancel();
|
||||
|
@ -70,6 +77,7 @@ public class MixinClientPlayerInteractionManager {
|
|||
}
|
||||
|
||||
ActionResult result = AttackBlockCallback.EVENT.invoker().interact(client.player, client.world, Hand.MAIN_HAND, pos, direction);
|
||||
|
||||
if (result != ActionResult.PASS) {
|
||||
info.setReturnValue(result == ActionResult.SUCCESS);
|
||||
info.cancel();
|
||||
|
@ -79,10 +87,12 @@ public class MixinClientPlayerInteractionManager {
|
|||
@Inject(at = @At(value = "INVOKE", target = "Lnet/minecraft/client/network/ClientPlayerEntity;getStackInHand(Lnet/minecraft/util/Hand;)Lnet/minecraft/item/ItemStack;", ordinal = 0), method = "interactBlock", cancellable = true)
|
||||
public void interactBlock(ClientPlayerEntity player, ClientWorld world, Hand hand, BlockHitResult blockHitResult, CallbackInfoReturnable<ActionResult> info) {
|
||||
ActionResult result = UseBlockCallback.EVENT.invoker().interact(player, world, hand, blockHitResult);
|
||||
|
||||
if (result != ActionResult.PASS) {
|
||||
if (result == ActionResult.SUCCESS) {
|
||||
this.networkHandler.sendPacket(new PlayerInteractBlockC2SPacket(hand, blockHitResult));
|
||||
}
|
||||
|
||||
info.setReturnValue(result);
|
||||
info.cancel();
|
||||
}
|
||||
|
@ -91,10 +101,12 @@ public class MixinClientPlayerInteractionManager {
|
|||
@Inject(at = @At(value = "INVOKE", target = "Lnet/minecraft/client/network/ClientPlayNetworkHandler;sendPacket(Lnet/minecraft/network/Packet;)V", ordinal = 0), method = "interactItem", cancellable = true)
|
||||
public void interactItem(PlayerEntity player, World world, Hand hand, CallbackInfoReturnable<TypedActionResult<ItemStack>> info) {
|
||||
TypedActionResult<ItemStack> result = UseItemCallback.EVENT.invoker().interact(player, world, hand);
|
||||
|
||||
if (result.getResult() != ActionResult.PASS) {
|
||||
if (result.getResult() == ActionResult.SUCCESS) {
|
||||
this.networkHandler.sendPacket(new PlayerInteractItemC2SPacket(hand));
|
||||
}
|
||||
|
||||
info.setReturnValue(result);
|
||||
info.cancel();
|
||||
return;
|
||||
|
@ -104,10 +116,12 @@ public class MixinClientPlayerInteractionManager {
|
|||
@Inject(at = @At(value = "INVOKE", target = "Lnet/minecraft/client/network/ClientPlayNetworkHandler;sendPacket(Lnet/minecraft/network/Packet;)V", ordinal = 0), method = "attackEntity", cancellable = true)
|
||||
public void attackEntity(PlayerEntity player, Entity entity, CallbackInfo info) {
|
||||
ActionResult result = AttackEntityCallback.EVENT.invoker().interact(player, player.getEntityWorld(), Hand.MAIN_HAND /* TODO */, entity, null);
|
||||
|
||||
if (result != ActionResult.PASS) {
|
||||
if (result == ActionResult.SUCCESS) {
|
||||
this.networkHandler.sendPacket(new PlayerInteractEntityC2SPacket(entity));
|
||||
}
|
||||
|
||||
info.cancel();
|
||||
}
|
||||
}
|
||||
|
@ -115,11 +129,13 @@ public class MixinClientPlayerInteractionManager {
|
|||
@Inject(at = @At(value = "INVOKE", target = "Lnet/minecraft/client/network/ClientPlayNetworkHandler;sendPacket(Lnet/minecraft/network/Packet;)V", ordinal = 0), method = "interactEntityAtLocation", cancellable = true)
|
||||
public void interactEntityAtLocation(PlayerEntity player, Entity entity, EntityHitResult hitResult, Hand hand, CallbackInfoReturnable<ActionResult> info) {
|
||||
ActionResult result = UseEntityCallback.EVENT.invoker().interact(player, player.getEntityWorld(), hand, entity, hitResult);
|
||||
|
||||
if (result != ActionResult.PASS) {
|
||||
if (result == ActionResult.SUCCESS) {
|
||||
Vec3d hitVec = hitResult.getPos().subtract(entity.getX(), entity.getY(), entity.getZ());
|
||||
this.networkHandler.sendPacket(new PlayerInteractEntityC2SPacket(entity, hand, hitVec));
|
||||
}
|
||||
|
||||
info.setReturnValue(result);
|
||||
info.cancel();
|
||||
return;
|
||||
|
|
|
@ -16,9 +16,13 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.eventsinteraction;
|
||||
|
||||
import net.fabricmc.fabric.api.event.client.player.ClientPickBlockApplyCallback;
|
||||
import net.fabricmc.fabric.api.event.client.player.ClientPickBlockCallback;
|
||||
import net.fabricmc.fabric.api.event.client.player.ClientPickBlockGatherCallback;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
import org.spongepowered.asm.mixin.injection.At;
|
||||
import org.spongepowered.asm.mixin.injection.Inject;
|
||||
import org.spongepowered.asm.mixin.injection.ModifyVariable;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||
|
||||
import net.minecraft.block.entity.BlockEntity;
|
||||
import net.minecraft.client.MinecraftClient;
|
||||
import net.minecraft.client.gui.screen.Screen;
|
||||
|
@ -27,12 +31,10 @@ import net.minecraft.item.ItemStack;
|
|||
import net.minecraft.util.Hand;
|
||||
import net.minecraft.util.hit.BlockHitResult;
|
||||
import net.minecraft.util.hit.HitResult;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
import org.spongepowered.asm.mixin.injection.At;
|
||||
import org.spongepowered.asm.mixin.injection.Inject;
|
||||
import org.spongepowered.asm.mixin.injection.ModifyVariable;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||
|
||||
import net.fabricmc.fabric.api.event.client.player.ClientPickBlockApplyCallback;
|
||||
import net.fabricmc.fabric.api.event.client.player.ClientPickBlockCallback;
|
||||
import net.fabricmc.fabric.api.event.client.player.ClientPickBlockGatherCallback;
|
||||
|
||||
@Mixin(MinecraftClient.class)
|
||||
public abstract class MixinMinecraftClient {
|
||||
|
@ -52,6 +54,7 @@ public abstract class MixinMinecraftClient {
|
|||
|
||||
// Do a "best effort" emulation of the old events.
|
||||
ItemStack stack = ClientPickBlockGatherCallback.EVENT.invoker().pick(client.player, client.hitResult);
|
||||
|
||||
// TODO: Remove in 0.3.0
|
||||
if (stack.isEmpty()) {
|
||||
stack = fabric_emulateOldPick();
|
||||
|
@ -67,12 +70,14 @@ public abstract class MixinMinecraftClient {
|
|||
|
||||
if (client.player.abilities.creativeMode && Screen.hasControlDown() && client.hitResult.getType() == HitResult.Type.BLOCK) {
|
||||
BlockEntity be = client.world.getBlockEntity(((BlockHitResult) client.hitResult).getBlockPos());
|
||||
|
||||
if (be != null) {
|
||||
stack = addBlockEntityNbt(stack, be);
|
||||
}
|
||||
}
|
||||
|
||||
stack = ClientPickBlockApplyCallback.EVENT.invoker().pick(client.player, client.hitResult, stack);
|
||||
|
||||
if (stack.isEmpty()) {
|
||||
return;
|
||||
}
|
||||
|
@ -82,6 +87,7 @@ public abstract class MixinMinecraftClient {
|
|||
client.interactionManager.clickCreativeStack(client.player.getStackInHand(Hand.MAIN_HAND), 36 + playerInventory.selectedSlot);
|
||||
} else {
|
||||
int slot = playerInventory.getSlotWithStack(stack);
|
||||
|
||||
if (slot >= 0) {
|
||||
if (PlayerInventory.isValidHotbarIndex(slot)) {
|
||||
playerInventory.selectedSlot = slot;
|
||||
|
|
|
@ -16,7 +16,12 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.eventsinteraction;
|
||||
|
||||
import net.fabricmc.fabric.api.event.player.UseEntityCallback;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
import org.spongepowered.asm.mixin.injection.At;
|
||||
import org.spongepowered.asm.mixin.injection.Inject;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||
|
||||
import net.minecraft.entity.Entity;
|
||||
import net.minecraft.server.network.ServerPlayNetworkHandler;
|
||||
import net.minecraft.server.network.ServerPlayerEntity;
|
||||
|
@ -24,11 +29,8 @@ import net.minecraft.server.network.packet.PlayerInteractEntityC2SPacket;
|
|||
import net.minecraft.util.ActionResult;
|
||||
import net.minecraft.util.hit.EntityHitResult;
|
||||
import net.minecraft.world.World;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
import org.spongepowered.asm.mixin.injection.At;
|
||||
import org.spongepowered.asm.mixin.injection.Inject;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||
|
||||
import net.fabricmc.fabric.api.event.player.UseEntityCallback;
|
||||
|
||||
@Mixin(ServerPlayNetworkHandler.class)
|
||||
public class MixinServerPlayNetworkHandler {
|
||||
|
@ -39,10 +41,12 @@ public class MixinServerPlayNetworkHandler {
|
|||
public void onPlayerInteractEntity(PlayerInteractEntityC2SPacket packet, CallbackInfo info) {
|
||||
World world = player.getEntityWorld();
|
||||
Entity entity = packet.getEntity(world);
|
||||
|
||||
if (entity != null) {
|
||||
EntityHitResult hitResult = new EntityHitResult(entity, packet.getHitPosition().add(entity.getX(), entity.getY(), entity.getZ()));
|
||||
|
||||
ActionResult result = UseEntityCallback.EVENT.invoker().interact(player, world, packet.getHand(), entity, hitResult);
|
||||
|
||||
if (result != ActionResult.PASS) {
|
||||
info.cancel();
|
||||
}
|
||||
|
|
|
@ -16,22 +16,25 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.eventsinteraction;
|
||||
|
||||
import net.fabricmc.fabric.api.event.player.AttackEntityCallback;
|
||||
import net.minecraft.entity.Entity;
|
||||
import net.minecraft.server.network.ServerPlayerEntity;
|
||||
import net.minecraft.util.ActionResult;
|
||||
import net.minecraft.util.Hand;
|
||||
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 net.minecraft.entity.Entity;
|
||||
import net.minecraft.server.network.ServerPlayerEntity;
|
||||
import net.minecraft.util.ActionResult;
|
||||
import net.minecraft.util.Hand;
|
||||
|
||||
import net.fabricmc.fabric.api.event.player.AttackEntityCallback;
|
||||
|
||||
@Mixin(ServerPlayerEntity.class)
|
||||
public class MixinServerPlayerEntity {
|
||||
@Inject(method = "attack", at = @At("HEAD"), cancellable = true)
|
||||
public void onPlayerInteractEntity(Entity target, CallbackInfo info) {
|
||||
ServerPlayerEntity player = (ServerPlayerEntity) (Object) this;
|
||||
ActionResult result = AttackEntityCallback.EVENT.invoker().interact(player, player.getEntityWorld(), Hand.MAIN_HAND, target, null);
|
||||
|
||||
if (result != ActionResult.PASS) {
|
||||
info.cancel();
|
||||
}
|
||||
|
|
|
@ -16,9 +16,13 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.eventsinteraction;
|
||||
|
||||
import net.fabricmc.fabric.api.event.player.AttackBlockCallback;
|
||||
import net.fabricmc.fabric.api.event.player.UseBlockCallback;
|
||||
import net.fabricmc.fabric.api.event.player.UseItemCallback;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
import org.spongepowered.asm.mixin.injection.At;
|
||||
import org.spongepowered.asm.mixin.injection.Inject;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable;
|
||||
|
||||
import net.minecraft.client.network.packet.BlockUpdateS2CPacket;
|
||||
import net.minecraft.entity.player.PlayerEntity;
|
||||
import net.minecraft.item.ItemStack;
|
||||
|
@ -33,12 +37,10 @@ import net.minecraft.util.hit.BlockHitResult;
|
|||
import net.minecraft.util.math.BlockPos;
|
||||
import net.minecraft.util.math.Direction;
|
||||
import net.minecraft.world.World;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
import org.spongepowered.asm.mixin.injection.At;
|
||||
import org.spongepowered.asm.mixin.injection.Inject;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable;
|
||||
|
||||
import net.fabricmc.fabric.api.event.player.AttackBlockCallback;
|
||||
import net.fabricmc.fabric.api.event.player.UseBlockCallback;
|
||||
import net.fabricmc.fabric.api.event.player.UseItemCallback;
|
||||
|
||||
@Mixin(ServerPlayerInteractionManager.class)
|
||||
public class MixinServerPlayerInteractionManager {
|
||||
|
@ -50,6 +52,7 @@ public class MixinServerPlayerInteractionManager {
|
|||
@Inject(at = @At("HEAD"), method = "processBlockBreakingAction", cancellable = true)
|
||||
public void startBlockBreak(BlockPos pos, PlayerActionC2SPacket.Action playerAction, Direction direction, int i, CallbackInfo info) {
|
||||
ActionResult result = AttackBlockCallback.EVENT.invoker().interact(player, world, Hand.MAIN_HAND, pos, direction);
|
||||
|
||||
if (result != ActionResult.PASS) {
|
||||
// The client might have broken the block on its side, so make sure to let it know.
|
||||
this.player.networkHandler.sendPacket(new BlockUpdateS2CPacket(world, pos));
|
||||
|
@ -60,6 +63,7 @@ public class MixinServerPlayerInteractionManager {
|
|||
@Inject(at = @At("HEAD"), method = "interactBlock", cancellable = true)
|
||||
public void interactBlock(PlayerEntity player, World world, ItemStack stack, Hand hand, BlockHitResult blockHitResult, CallbackInfoReturnable<ActionResult> info) {
|
||||
ActionResult result = UseBlockCallback.EVENT.invoker().interact(player, world, hand, blockHitResult);
|
||||
|
||||
if (result != ActionResult.PASS) {
|
||||
info.setReturnValue(result);
|
||||
info.cancel();
|
||||
|
@ -70,6 +74,7 @@ public class MixinServerPlayerInteractionManager {
|
|||
@Inject(at = @At("HEAD"), method = "interactItem", cancellable = true)
|
||||
public void interactItem(PlayerEntity player, World world, ItemStack stack, Hand hand, CallbackInfoReturnable<ActionResult> info) {
|
||||
TypedActionResult<ItemStack> result = UseItemCallback.EVENT.invoker().interact(player, world, hand);
|
||||
|
||||
if (result.getResult() != ActionResult.PASS) {
|
||||
info.setReturnValue(result.getResult());
|
||||
info.cancel();
|
||||
|
|
|
@ -16,31 +16,34 @@
|
|||
|
||||
package net.fabricmc.fabric.api.event.client;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
import net.minecraft.client.MinecraftClient;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
|
||||
public interface ClientTickCallback {
|
||||
public static final Event<ClientTickCallback> EVENT = EventFactory.createArrayBacked(ClientTickCallback.class,
|
||||
(listeners) -> {
|
||||
if (EventFactory.isProfilingEnabled()) {
|
||||
return (client) -> {
|
||||
client.getProfiler().push("fabricClientTick");
|
||||
for (ClientTickCallback event : listeners) {
|
||||
client.getProfiler().push(EventFactory.getHandlerName(event));
|
||||
event.tick(client);
|
||||
Event<ClientTickCallback> EVENT = EventFactory.createArrayBacked(ClientTickCallback.class,
|
||||
(listeners) -> {
|
||||
if (EventFactory.isProfilingEnabled()) {
|
||||
return (client) -> {
|
||||
client.getProfiler().push("fabricClientTick");
|
||||
|
||||
for (ClientTickCallback event : listeners) {
|
||||
client.getProfiler().push(EventFactory.getHandlerName(event));
|
||||
event.tick(client);
|
||||
client.getProfiler().pop();
|
||||
}
|
||||
|
||||
client.getProfiler().pop();
|
||||
}
|
||||
client.getProfiler().pop();
|
||||
};
|
||||
} else {
|
||||
return (client) -> {
|
||||
for (ClientTickCallback event : listeners) {
|
||||
event.tick(client);
|
||||
}
|
||||
};
|
||||
};
|
||||
} else {
|
||||
return (client) -> {
|
||||
for (ClientTickCallback event : listeners) {
|
||||
event.tick(client);
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
}
|
||||
);
|
||||
|
||||
void tick(MinecraftClient client);
|
||||
|
|
|
@ -16,24 +16,23 @@
|
|||
|
||||
package net.fabricmc.fabric.api.event.client;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
import java.util.List;
|
||||
|
||||
import net.minecraft.client.item.TooltipContext;
|
||||
import net.minecraft.item.ItemStack;
|
||||
import net.minecraft.text.Text;
|
||||
|
||||
import java.util.List;
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
|
||||
public interface ItemTooltipCallback {
|
||||
|
||||
/** Fired after the game has appended all base tooltip lines to the list */
|
||||
/** Fired after the game has appended all base tooltip lines to the list. */
|
||||
Event<ItemTooltipCallback> EVENT = EventFactory.createArrayBacked(ItemTooltipCallback.class, (listeners) ->
|
||||
(stack, tooltipContext, lines) -> {
|
||||
for(ItemTooltipCallback callback : listeners){
|
||||
callback.getTooltip(stack, tooltipContext, lines);
|
||||
}
|
||||
(stack, tooltipContext, lines) -> {
|
||||
for (ItemTooltipCallback callback : listeners) {
|
||||
callback.getTooltip(stack, tooltipContext, lines);
|
||||
}
|
||||
);
|
||||
});
|
||||
|
||||
/**
|
||||
* Called when an item stack's tooltip is rendered. Text added to {@code lines} will be
|
||||
|
@ -41,5 +40,4 @@ public interface ItemTooltipCallback {
|
|||
* @param lines the list containing the lines of text displayed on the stack's tooltip
|
||||
*/
|
||||
void getTooltip(ItemStack stack, TooltipContext tooltipContext, List<Text> lines);
|
||||
|
||||
}
|
||||
|
|
|
@ -16,17 +16,18 @@
|
|||
|
||||
package net.fabricmc.fabric.api.event.server;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
import net.minecraft.server.MinecraftServer;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
|
||||
public interface ServerStartCallback {
|
||||
public static final Event<ServerStartCallback> EVENT = EventFactory.createArrayBacked(ServerStartCallback.class,
|
||||
(listeners) -> (server) -> {
|
||||
for (ServerStartCallback event : listeners) {
|
||||
event.onStartServer(server);
|
||||
Event<ServerStartCallback> EVENT = EventFactory.createArrayBacked(ServerStartCallback.class,
|
||||
(listeners) -> (server) -> {
|
||||
for (ServerStartCallback event : listeners) {
|
||||
event.onStartServer(server);
|
||||
}
|
||||
}
|
||||
}
|
||||
);
|
||||
|
||||
void onStartServer(MinecraftServer server);
|
||||
|
|
|
@ -16,17 +16,18 @@
|
|||
|
||||
package net.fabricmc.fabric.api.event.server;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
import net.minecraft.server.MinecraftServer;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
|
||||
public interface ServerStopCallback {
|
||||
public static final Event<ServerStopCallback> EVENT = EventFactory.createArrayBacked(ServerStopCallback.class,
|
||||
(listeners) -> (server) -> {
|
||||
for (ServerStopCallback event : listeners) {
|
||||
event.onStopServer(server);
|
||||
Event<ServerStopCallback> EVENT = EventFactory.createArrayBacked(ServerStopCallback.class,
|
||||
(listeners) -> (server) -> {
|
||||
for (ServerStopCallback event : listeners) {
|
||||
event.onStopServer(server);
|
||||
}
|
||||
}
|
||||
}
|
||||
);
|
||||
|
||||
void onStopServer(MinecraftServer server);
|
||||
|
|
|
@ -16,31 +16,34 @@
|
|||
|
||||
package net.fabricmc.fabric.api.event.server;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
import net.minecraft.server.MinecraftServer;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
|
||||
public interface ServerTickCallback {
|
||||
public static final Event<ServerTickCallback> EVENT = EventFactory.createArrayBacked(ServerTickCallback.class,
|
||||
(listeners) -> {
|
||||
if (EventFactory.isProfilingEnabled()) {
|
||||
return (server) -> {
|
||||
server.getProfiler().push("fabricServerTick");
|
||||
for (ServerTickCallback event : listeners) {
|
||||
server.getProfiler().push(EventFactory.getHandlerName(event));
|
||||
event.tick(server);
|
||||
Event<ServerTickCallback> EVENT = EventFactory.createArrayBacked(ServerTickCallback.class,
|
||||
(listeners) -> {
|
||||
if (EventFactory.isProfilingEnabled()) {
|
||||
return (server) -> {
|
||||
server.getProfiler().push("fabricServerTick");
|
||||
|
||||
for (ServerTickCallback event : listeners) {
|
||||
server.getProfiler().push(EventFactory.getHandlerName(event));
|
||||
event.tick(server);
|
||||
server.getProfiler().pop();
|
||||
}
|
||||
|
||||
server.getProfiler().pop();
|
||||
}
|
||||
server.getProfiler().pop();
|
||||
};
|
||||
} else {
|
||||
return (server) -> {
|
||||
for (ServerTickCallback event : listeners) {
|
||||
event.tick(server);
|
||||
}
|
||||
};
|
||||
};
|
||||
} else {
|
||||
return (server) -> {
|
||||
for (ServerTickCallback event : listeners) {
|
||||
event.tick(server);
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
}
|
||||
);
|
||||
|
||||
void tick(MinecraftServer server);
|
||||
|
|
|
@ -16,31 +16,34 @@
|
|||
|
||||
package net.fabricmc.fabric.api.event.world;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
import net.minecraft.world.World;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
|
||||
public interface WorldTickCallback {
|
||||
public static final Event<WorldTickCallback> EVENT = EventFactory.createArrayBacked(WorldTickCallback.class,
|
||||
(listeners) -> {
|
||||
if (EventFactory.isProfilingEnabled()) {
|
||||
return (world) -> {
|
||||
world.getProfiler().push("fabricWorldTick");
|
||||
for (WorldTickCallback event : listeners) {
|
||||
world.getProfiler().push(EventFactory.getHandlerName(event));
|
||||
event.tick(world);
|
||||
Event<WorldTickCallback> EVENT = EventFactory.createArrayBacked(WorldTickCallback.class,
|
||||
(listeners) -> {
|
||||
if (EventFactory.isProfilingEnabled()) {
|
||||
return (world) -> {
|
||||
world.getProfiler().push("fabricWorldTick");
|
||||
|
||||
for (WorldTickCallback event : listeners) {
|
||||
world.getProfiler().push(EventFactory.getHandlerName(event));
|
||||
event.tick(world);
|
||||
world.getProfiler().pop();
|
||||
}
|
||||
|
||||
world.getProfiler().pop();
|
||||
}
|
||||
world.getProfiler().pop();
|
||||
};
|
||||
} else {
|
||||
return (world) -> {
|
||||
for (WorldTickCallback event : listeners) {
|
||||
event.tick(world);
|
||||
}
|
||||
};
|
||||
};
|
||||
} else {
|
||||
return (world) -> {
|
||||
for (WorldTickCallback event : listeners) {
|
||||
event.tick(world);
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
}
|
||||
);
|
||||
|
||||
void tick(World world);
|
||||
|
|
|
@ -16,25 +16,24 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.eventslifecycle;
|
||||
|
||||
import net.fabricmc.fabric.api.event.client.ItemTooltipCallback;
|
||||
import net.minecraft.client.item.TooltipContext;
|
||||
import net.minecraft.entity.player.PlayerEntity;
|
||||
import net.minecraft.item.ItemStack;
|
||||
import net.minecraft.text.Text;
|
||||
import java.util.List;
|
||||
|
||||
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.CallbackInfoReturnable;
|
||||
import org.spongepowered.asm.mixin.injection.callback.LocalCapture;
|
||||
|
||||
import java.util.List;
|
||||
import net.minecraft.client.item.TooltipContext;
|
||||
import net.minecraft.entity.player.PlayerEntity;
|
||||
import net.minecraft.item.ItemStack;
|
||||
import net.minecraft.text.Text;
|
||||
|
||||
import net.fabricmc.fabric.api.event.client.ItemTooltipCallback;
|
||||
|
||||
@Mixin(ItemStack.class)
|
||||
public class MixinItemStack {
|
||||
|
||||
@Inject(method = "getTooltip", at = @At("RETURN"))
|
||||
private void getTooltip(PlayerEntity entity, TooltipContext tooltipContext, CallbackInfoReturnable<List<Text>> info){
|
||||
ItemTooltipCallback.EVENT.invoker().getTooltip((ItemStack) (Object)this, tooltipContext, info.getReturnValue());
|
||||
private void getTooltip(PlayerEntity entity, TooltipContext tooltipContext, CallbackInfoReturnable<List<Text>> info) {
|
||||
ItemTooltipCallback.EVENT.invoker().getTooltip((ItemStack) (Object) this, tooltipContext, info.getReturnValue());
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -16,13 +16,15 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.eventslifecycle;
|
||||
|
||||
import net.fabricmc.fabric.api.event.client.ClientTickCallback;
|
||||
import net.minecraft.client.MinecraftClient;
|
||||
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 net.minecraft.client.MinecraftClient;
|
||||
|
||||
import net.fabricmc.fabric.api.event.client.ClientTickCallback;
|
||||
|
||||
@Mixin(MinecraftClient.class)
|
||||
public class MixinMinecraftClient {
|
||||
@Inject(at = @At("RETURN"), method = "tick")
|
||||
|
|
|
@ -16,16 +16,18 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.eventslifecycle;
|
||||
|
||||
import net.fabricmc.fabric.api.event.server.ServerStartCallback;
|
||||
import net.fabricmc.fabric.api.event.server.ServerStopCallback;
|
||||
import net.fabricmc.fabric.api.event.server.ServerTickCallback;
|
||||
import net.minecraft.server.MinecraftServer;
|
||||
import java.util.function.BooleanSupplier;
|
||||
|
||||
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.util.function.BooleanSupplier;
|
||||
import net.minecraft.server.MinecraftServer;
|
||||
|
||||
import net.fabricmc.fabric.api.event.server.ServerStartCallback;
|
||||
import net.fabricmc.fabric.api.event.server.ServerStopCallback;
|
||||
import net.fabricmc.fabric.api.event.server.ServerTickCallback;
|
||||
|
||||
@Mixin(MinecraftServer.class)
|
||||
public class MixinMinecraftServer {
|
||||
|
|
|
@ -16,13 +16,15 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.eventslifecycle;
|
||||
|
||||
import net.fabricmc.fabric.api.event.world.WorldTickCallback;
|
||||
import net.minecraft.world.World;
|
||||
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 net.minecraft.world.World;
|
||||
|
||||
import net.fabricmc.fabric.api.event.world.WorldTickCallback;
|
||||
|
||||
@Mixin(World.class)
|
||||
public class MixinWorld {
|
||||
// TODO split into ClientWorld/ServerWorld ticks? mmm need more mappings
|
||||
|
|
|
@ -16,18 +16,18 @@
|
|||
|
||||
package net.fabricmc.fabric.api.client.itemgroup;
|
||||
|
||||
import net.fabricmc.fabric.impl.itemgroup.ItemGroupExtensions;
|
||||
import java.util.List;
|
||||
import java.util.function.Consumer;
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import net.minecraft.item.ItemGroup;
|
||||
import net.minecraft.item.ItemStack;
|
||||
import net.minecraft.util.DefaultedList;
|
||||
import net.minecraft.util.Identifier;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.function.Consumer;
|
||||
import java.util.function.Supplier;
|
||||
import net.fabricmc.fabric.impl.itemgroup.ItemGroupExtensions;
|
||||
|
||||
public final class FabricItemGroupBuilder {
|
||||
|
||||
private Identifier identifier;
|
||||
private Supplier<ItemStack> stackSupplier = () -> ItemStack.EMPTY;
|
||||
private Consumer<List<ItemStack>> stacksForDisplay;
|
||||
|
@ -37,7 +37,7 @@ public final class FabricItemGroupBuilder {
|
|||
}
|
||||
|
||||
/**
|
||||
* Create a new Item Group Builder
|
||||
* Create a new Item Group Builder.
|
||||
*
|
||||
* @param identifier the id will become the name of the ItemGroup and will be used for the translation key
|
||||
* @return a FabricItemGroupBuilder
|
||||
|
@ -47,7 +47,7 @@ public final class FabricItemGroupBuilder {
|
|||
}
|
||||
|
||||
/**
|
||||
* This is used to add an icon to to the item group
|
||||
* This is used to add an icon to to the item group.
|
||||
*
|
||||
* @param stackSupplier the supplier should return the item stack that you wish to show on the tab
|
||||
* @return a reference to the FabricItemGroupBuilder
|
||||
|
@ -58,7 +58,7 @@ public final class FabricItemGroupBuilder {
|
|||
}
|
||||
|
||||
/**
|
||||
* This allows for a custom list of items to be displayed in a tab, this enabled tabs to be created with a custom set of items
|
||||
* This allows for a custom list of items to be displayed in a tab, this enabled tabs to be created with a custom set of items.
|
||||
*
|
||||
* @param appender Add ItemStack's to this list to show in the ItemGroup
|
||||
* @return a reference to the FabricItemGroupBuilder
|
||||
|
@ -70,7 +70,7 @@ public final class FabricItemGroupBuilder {
|
|||
}
|
||||
|
||||
/**
|
||||
* This allows for a custom list of items to be displayed in a tab, this enabled tabs to be created with a custom set of items
|
||||
* This allows for a custom list of items to be displayed in a tab, this enabled tabs to be created with a custom set of items.
|
||||
*
|
||||
* @param stacksForDisplay Add ItemStack's to this list to show in the ItemGroup
|
||||
* @return a reference to the FabricItemGroupBuilder
|
||||
|
@ -81,7 +81,7 @@ public final class FabricItemGroupBuilder {
|
|||
}
|
||||
|
||||
/**
|
||||
* This is a single method that makes creating an ItemGroup with an icon one call
|
||||
* This is a single method that makes creating an ItemGroup with an icon one call.
|
||||
*
|
||||
* @param identifier the id will become the name of the ItemGroup and will be used for the translation key
|
||||
* @param stackSupplier the supplier should return the item stack that you wish to show on the tab
|
||||
|
@ -92,7 +92,7 @@ public final class FabricItemGroupBuilder {
|
|||
}
|
||||
|
||||
/**
|
||||
* Create an instance of the ItemGroup
|
||||
* Create an instance of the ItemGroup.
|
||||
*
|
||||
* @return An instance of the built ItemGroup
|
||||
*/
|
||||
|
@ -110,9 +110,9 @@ public final class FabricItemGroupBuilder {
|
|||
stacksForDisplay.accept(stacks);
|
||||
return;
|
||||
}
|
||||
|
||||
super.appendStacks(stacks);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -17,7 +17,6 @@
|
|||
package net.fabricmc.fabric.impl.itemgroup;
|
||||
|
||||
public interface CreativeGuiExtensions {
|
||||
|
||||
void fabric_nextPage();
|
||||
|
||||
void fabric_previousPage();
|
||||
|
|
|
@ -16,21 +16,20 @@
|
|||
|
||||
package net.fabricmc.fabric.impl.itemgroup;
|
||||
|
||||
import com.mojang.blaze3d.systems.RenderSystem;
|
||||
import net.minecraft.client.MinecraftClient;
|
||||
import java.util.HashSet;
|
||||
import java.util.Set;
|
||||
import java.util.function.Consumer;
|
||||
|
||||
import com.mojang.blaze3d.systems.RenderSystem;
|
||||
|
||||
import net.minecraft.client.MinecraftClient;
|
||||
import net.minecraft.client.gui.screen.ingame.CreativeInventoryScreen;
|
||||
import net.minecraft.client.gui.widget.ButtonWidget;
|
||||
import net.minecraft.client.resource.language.I18n;
|
||||
import net.minecraft.item.ItemGroup;
|
||||
import net.minecraft.util.Identifier;
|
||||
|
||||
import java.util.HashSet;
|
||||
import java.util.Set;
|
||||
import java.util.function.Consumer;
|
||||
|
||||
public class FabricCreativeGuiComponents {
|
||||
|
||||
private static final Identifier BUTTON_TEX = new Identifier("fabric", "textures/gui/creative_buttons.png");
|
||||
public static final Set<ItemGroup> COMMON_GROUPS = new HashSet<>();
|
||||
|
||||
|
@ -41,7 +40,6 @@ public class FabricCreativeGuiComponents {
|
|||
}
|
||||
|
||||
public static class ItemGroupButtonWidget extends ButtonWidget {
|
||||
|
||||
CreativeGuiExtensions extensions;
|
||||
CreativeInventoryScreen gui;
|
||||
Type type;
|
||||
|
@ -73,7 +71,6 @@ public class FabricCreativeGuiComponents {
|
|||
}
|
||||
|
||||
public enum Type {
|
||||
|
||||
NEXT(">", CreativeGuiExtensions::fabric_nextPage),
|
||||
PREVIOUS("<", CreativeGuiExtensions::fabric_previousPage);
|
||||
|
||||
|
@ -85,5 +82,4 @@ public class FabricCreativeGuiComponents {
|
|||
this.clickConsumer = clickConsumer;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -17,7 +17,5 @@
|
|||
package net.fabricmc.fabric.impl.itemgroup;
|
||||
|
||||
public interface ItemGroupExtensions {
|
||||
|
||||
void fabric_expandArray();
|
||||
|
||||
}
|
||||
|
|
|
@ -16,16 +16,17 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.itemgroup;
|
||||
|
||||
import net.fabricmc.fabric.impl.itemgroup.ItemGroupExtensions;
|
||||
import net.minecraft.item.ItemGroup;
|
||||
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 net.minecraft.item.ItemGroup;
|
||||
|
||||
import net.fabricmc.fabric.impl.itemgroup.ItemGroupExtensions;
|
||||
|
||||
@Mixin(ItemGroup.class)
|
||||
public abstract class MixinItemGroup implements ItemGroupExtensions {
|
||||
|
||||
@Shadow
|
||||
@Final
|
||||
@Mutable
|
||||
|
@ -35,9 +36,9 @@ public abstract class MixinItemGroup implements ItemGroupExtensions {
|
|||
public void fabric_expandArray() {
|
||||
ItemGroup[] tempGroups = GROUPS;
|
||||
GROUPS = new ItemGroup[GROUPS.length + 1];
|
||||
|
||||
for (int i = 0; i < tempGroups.length; i++) {
|
||||
GROUPS[i] = tempGroups[i];
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -16,14 +16,6 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.itemgroup.client;
|
||||
|
||||
import net.fabricmc.fabric.impl.itemgroup.CreativeGuiExtensions;
|
||||
import net.fabricmc.fabric.impl.itemgroup.FabricCreativeGuiComponents;
|
||||
import net.minecraft.client.gui.screen.ingame.AbstractInventoryScreen;
|
||||
import net.minecraft.client.gui.screen.ingame.CreativeInventoryScreen;
|
||||
import net.minecraft.container.Container;
|
||||
import net.minecraft.entity.player.PlayerInventory;
|
||||
import net.minecraft.item.ItemGroup;
|
||||
import net.minecraft.text.Text;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
import org.spongepowered.asm.mixin.injection.At;
|
||||
|
@ -31,9 +23,18 @@ import org.spongepowered.asm.mixin.injection.Inject;
|
|||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable;
|
||||
|
||||
import net.minecraft.client.gui.screen.ingame.AbstractInventoryScreen;
|
||||
import net.minecraft.client.gui.screen.ingame.CreativeInventoryScreen;
|
||||
import net.minecraft.container.Container;
|
||||
import net.minecraft.entity.player.PlayerInventory;
|
||||
import net.minecraft.item.ItemGroup;
|
||||
import net.minecraft.text.Text;
|
||||
|
||||
import net.fabricmc.fabric.impl.itemgroup.CreativeGuiExtensions;
|
||||
import net.fabricmc.fabric.impl.itemgroup.FabricCreativeGuiComponents;
|
||||
|
||||
@Mixin(CreativeInventoryScreen.class)
|
||||
public abstract class MixinCreativePlayerInventoryGui extends AbstractInventoryScreen implements CreativeGuiExtensions {
|
||||
|
||||
public MixinCreativePlayerInventoryGui(Container container_1, PlayerInventory playerInventory_1, Text textComponent_1) {
|
||||
super(container_1, playerInventory_1, textComponent_1);
|
||||
}
|
||||
|
@ -49,12 +50,12 @@ public abstract class MixinCreativePlayerInventoryGui extends AbstractInventoryS
|
|||
|
||||
private int fabric_getPageOffset(int page) {
|
||||
switch (page) {
|
||||
case 0:
|
||||
return 0;
|
||||
case 1:
|
||||
return 12;
|
||||
default:
|
||||
return 12 + ((12 - FabricCreativeGuiComponents.COMMON_GROUPS.size()) * (page - 1));
|
||||
case 0:
|
||||
return 0;
|
||||
case 1:
|
||||
return 12;
|
||||
default:
|
||||
return 12 + ((12 - FabricCreativeGuiComponents.COMMON_GROUPS.size()) * (page - 1));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -71,6 +72,7 @@ public abstract class MixinCreativePlayerInventoryGui extends AbstractInventoryS
|
|||
if (fabric_getPageOffset(fabric_currentPage + 1) >= ItemGroup.GROUPS.length) {
|
||||
return;
|
||||
}
|
||||
|
||||
fabric_currentPage++;
|
||||
fabric_updateSelection();
|
||||
}
|
||||
|
@ -80,6 +82,7 @@ public abstract class MixinCreativePlayerInventoryGui extends AbstractInventoryS
|
|||
if (fabric_currentPage == 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
fabric_currentPage--;
|
||||
fabric_updateSelection();
|
||||
}
|
||||
|
@ -94,9 +97,11 @@ public abstract class MixinCreativePlayerInventoryGui extends AbstractInventoryS
|
|||
if (type == FabricCreativeGuiComponents.Type.NEXT) {
|
||||
return !(fabric_getPageOffset(fabric_currentPage + 1) >= ItemGroup.GROUPS.length);
|
||||
}
|
||||
|
||||
if (type == FabricCreativeGuiComponents.Type.PREVIOUS) {
|
||||
return fabric_currentPage != 0;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
|
@ -119,7 +124,6 @@ public abstract class MixinCreativePlayerInventoryGui extends AbstractInventoryS
|
|||
|
||||
addButton(new FabricCreativeGuiComponents.ItemGroupButtonWidget(xpos + 10, ypos, FabricCreativeGuiComponents.Type.NEXT, this));
|
||||
addButton(new FabricCreativeGuiComponents.ItemGroupButtonWidget(xpos, ypos, FabricCreativeGuiComponents.Type.PREVIOUS, this));
|
||||
|
||||
}
|
||||
|
||||
@Inject(method = "setSelectedTab", at = @At("HEAD"), cancellable = true)
|
||||
|
@ -154,8 +158,8 @@ public abstract class MixinCreativePlayerInventoryGui extends AbstractInventoryS
|
|||
if (FabricCreativeGuiComponents.COMMON_GROUPS.contains(itemGroup)) {
|
||||
return true;
|
||||
}
|
||||
return fabric_currentPage == fabric_getOffsetPage(itemGroup.getIndex());
|
||||
|
||||
return fabric_currentPage == fabric_getOffsetPage(itemGroup.getIndex());
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -16,14 +16,16 @@
|
|||
|
||||
package net.fabricmc.fabric.mixin.itemgroup.client;
|
||||
|
||||
import net.fabricmc.fabric.impl.itemgroup.FabricCreativeGuiComponents;
|
||||
import net.minecraft.item.ItemGroup;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.Shadow;
|
||||
import org.spongepowered.asm.mixin.injection.At;
|
||||
import org.spongepowered.asm.mixin.injection.Inject;
|
||||
import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable;
|
||||
|
||||
import net.minecraft.item.ItemGroup;
|
||||
|
||||
import net.fabricmc.fabric.impl.itemgroup.FabricCreativeGuiComponents;
|
||||
|
||||
@Mixin(ItemGroup.class)
|
||||
public abstract class MixinItemGroup {
|
||||
@Shadow
|
||||
|
@ -47,7 +49,6 @@ public abstract class MixinItemGroup {
|
|||
} else {
|
||||
info.setReturnValue((getIndex() - 12) % (12 - FabricCreativeGuiComponents.COMMON_GROUPS.size()) - 4);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -16,15 +16,16 @@
|
|||
|
||||
package net.fabricmc.fabric.api.client.keybinding;
|
||||
|
||||
import net.fabricmc.fabric.mixin.client.keybinding.KeyCodeAccessor;
|
||||
import net.minecraft.client.options.KeyBinding;
|
||||
import net.minecraft.client.util.InputUtil;
|
||||
import net.minecraft.util.Identifier;
|
||||
|
||||
import net.fabricmc.fabric.mixin.client.keybinding.KeyCodeAccessor;
|
||||
|
||||
/**
|
||||
* Expanded version of {@link KeyBinding} for use by Fabric mods.
|
||||
* <p>
|
||||
* *ALL* instantiated FabricKeyBindings should be registered in
|
||||
*
|
||||
* <p>*ALL* instantiated FabricKeyBindings should be registered in
|
||||
* {@link KeyBindingRegistry#register(FabricKeyBinding)}!
|
||||
*/
|
||||
public class FabricKeyBinding extends KeyBinding {
|
||||
|
|
|
@ -16,16 +16,17 @@
|
|||
|
||||
package net.fabricmc.fabric.api.client.keybinding;
|
||||
|
||||
import net.fabricmc.fabric.impl.client.keybinding.KeyBindingRegistryImpl;
|
||||
import net.minecraft.client.options.KeyBinding;
|
||||
|
||||
import net.fabricmc.fabric.impl.client.keybinding.KeyBindingRegistryImpl;
|
||||
|
||||
/**
|
||||
* Interface for registering key bindings.
|
||||
*
|
||||
* @see KeyBinding
|
||||
*/
|
||||
public interface KeyBindingRegistry {
|
||||
static KeyBindingRegistry INSTANCE = KeyBindingRegistryImpl.INSTANCE;
|
||||
KeyBindingRegistry INSTANCE = KeyBindingRegistryImpl.INSTANCE;
|
||||
|
||||
/**
|
||||
* Add a new key binding category.
|
||||
|
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Reference in a new issue