mirror of
https://github.com/GTNewHorizons/StructureLib.git
synced 2026-11-09 15:04:56 +00:00
Compare commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
68c5436496 | ||
|
|
c4eb372cfb | ||
|
|
2446ad2db7 | ||
|
|
906961b6c8 | ||
|
|
393045d4f2 | ||
|
|
74baa66f52 | ||
|
|
24928454fd | ||
|
|
34ceda8ccc | ||
|
|
c78c61f45e | ||
|
|
fbf8cfd82c | ||
|
|
4c42e5f2a2 | ||
|
|
6795b18259 |
No files matched your search
@@ -0,0 +1,27 @@
|
||||
# This workflow will build a Java project with Gradle
|
||||
# For more information see: https://help.github.com/actions/language-and-framework-guides/building-and-testing-java-with-gradle
|
||||
|
||||
name: Java CI with Gradle
|
||||
|
||||
on:
|
||||
push:
|
||||
branches: [ master ]
|
||||
pull_request:
|
||||
branches: [ master ]
|
||||
|
||||
jobs:
|
||||
build:
|
||||
|
||||
runs-on: ubuntu-latest
|
||||
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- name: Set up JDK 8
|
||||
uses: actions/setup-java@v2
|
||||
with:
|
||||
java-version: '8'
|
||||
distribution: 'adopt'
|
||||
- name: Grant execute permission for gradlew
|
||||
run: chmod +x gradlew
|
||||
- name: Build with Gradle
|
||||
run: ./gradlew build
|
||||
+10
-3
@@ -51,15 +51,22 @@ task deobfJar(type: Jar) {
|
||||
classifier = 'deobf'
|
||||
}
|
||||
|
||||
task sourceJar(type: Jar) {
|
||||
from sourceSets.main.allSource
|
||||
classifier = 'sources'
|
||||
}
|
||||
|
||||
artifacts {
|
||||
archives deobfJar
|
||||
archives jar
|
||||
archives sourceJar
|
||||
}
|
||||
|
||||
install.dependsOn reobf
|
||||
|
||||
idea {
|
||||
module {
|
||||
inheritOutputDirs = false
|
||||
outputDir = compileJava.destinationDir
|
||||
testOutputDir = compileTestJava.destinationDir
|
||||
outputDir = new File(compileJava.destinationDir.parentFile.parentFile, "idea")
|
||||
testOutputDir = new File(compileTestJava.destinationDir.parentFile.parentFile, "ideaTest")
|
||||
}
|
||||
}
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
modGroup = com.gtnewhorizon
|
||||
modVersion = 1.0.0
|
||||
modVersion = 1.0.7
|
||||
modBaseName = StructureLib
|
||||
|
||||
forgeVersion = 1.7.10-10.13.4.1614-1.7.10
|
||||
@@ -0,0 +1,68 @@
|
||||
package com.gtnewhorizon.structurelib;
|
||||
|
||||
import cpw.mods.fml.client.event.ConfigChangedEvent;
|
||||
import cpw.mods.fml.common.FMLCommonHandler;
|
||||
import cpw.mods.fml.common.eventhandler.SubscribeEvent;
|
||||
import net.minecraftforge.common.config.ConfigCategory;
|
||||
import net.minecraftforge.common.config.Configuration;
|
||||
import net.minecraftforge.common.config.Property;
|
||||
|
||||
import java.io.File;
|
||||
import java.util.Map;
|
||||
|
||||
public enum ConfigurationHandler {
|
||||
INSTANCE;
|
||||
|
||||
private Configuration config;
|
||||
private int maxCoexistingHologram;
|
||||
private boolean removeCollidingHologram;
|
||||
|
||||
ConfigurationHandler() {
|
||||
FMLCommonHandler.instance().bus().register(this);
|
||||
}
|
||||
|
||||
void init(File f) {
|
||||
config = new Configuration(f, ConfigurationVersion.latest().getVersionMarker());
|
||||
ConfigurationVersion.migrateToLatest(config);
|
||||
loadConfig();
|
||||
setLanguageKeys();
|
||||
}
|
||||
|
||||
private void setLanguageKeys() {
|
||||
for (String categoryName : config.getCategoryNames()) {
|
||||
ConfigCategory category = config.getCategory(categoryName);
|
||||
category.setLanguageKey("structurelib.config." + categoryName);
|
||||
for (Map.Entry<String, Property> entry : category.entrySet()) {
|
||||
entry.getValue().setLanguageKey(String.format("%s.%s", category.getLanguagekey(), entry.getKey()));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void loadConfig() {
|
||||
maxCoexistingHologram = config.getInt("maxCoexisting", "client.hologram", 1, 1, 100, "An attempt will be made to prune old holograms when a new hologram is about to be projected");
|
||||
removeCollidingHologram = config.getBoolean("removeColliding", "client.hologram", true, "An attempt will be made to remove an existing hologram if it collides with a new hologram.");
|
||||
|
||||
if (config.hasChanged()) {
|
||||
config.save();
|
||||
}
|
||||
}
|
||||
|
||||
@SubscribeEvent
|
||||
public void onConfigChange(ConfigChangedEvent.PostConfigChangedEvent e) {
|
||||
if (e.modID.equals(StructureLibAPI.MOD_ID)) {
|
||||
loadConfig();
|
||||
}
|
||||
}
|
||||
|
||||
public int getMaxCoexistingHologram() {
|
||||
return maxCoexistingHologram;
|
||||
}
|
||||
|
||||
public boolean isRemoveCollidingHologram() {
|
||||
return removeCollidingHologram;
|
||||
}
|
||||
|
||||
Configuration getConfig() {
|
||||
return config;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,44 @@
|
||||
package com.gtnewhorizon.structurelib;
|
||||
|
||||
import net.minecraftforge.common.config.Configuration;
|
||||
|
||||
import javax.annotation.Nullable;
|
||||
import java.util.Arrays;
|
||||
import java.util.Objects;
|
||||
|
||||
enum ConfigurationVersion {
|
||||
V1 {
|
||||
@Override
|
||||
protected void step(Configuration c) {
|
||||
}
|
||||
};
|
||||
|
||||
private static final ConfigurationVersion[] VALUES = values();
|
||||
|
||||
private final String versionMarker;
|
||||
|
||||
ConfigurationVersion() {
|
||||
this.versionMarker = name();
|
||||
}
|
||||
|
||||
public static void migrateToLatest(Configuration c) {
|
||||
for (int i = identify(c).ordinal() + 1; i < VALUES.length; i++) {
|
||||
VALUES[i].step(c);
|
||||
}
|
||||
}
|
||||
|
||||
public static ConfigurationVersion latest() {
|
||||
return VALUES[VALUES.length - 1];
|
||||
}
|
||||
|
||||
public static ConfigurationVersion identify(Configuration c) {
|
||||
return Arrays.stream(VALUES).filter(v -> Objects.equals(c.getLoadedConfigVersion(), v.getVersionMarker())).findFirst().orElse(V1);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public String getVersionMarker() {
|
||||
return versionMarker;
|
||||
}
|
||||
|
||||
protected abstract void step(Configuration c);
|
||||
}
|
||||
@@ -0,0 +1,28 @@
|
||||
package com.gtnewhorizon.structurelib;
|
||||
|
||||
import cpw.mods.fml.client.IModGuiFactory;
|
||||
import net.minecraft.client.Minecraft;
|
||||
import net.minecraft.client.gui.GuiScreen;
|
||||
|
||||
import java.util.Set;
|
||||
|
||||
public class GuiFactory implements IModGuiFactory {
|
||||
@Override
|
||||
public void initialize(Minecraft minecraftInstance) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public Class<? extends GuiScreen> mainConfigGuiClass() {
|
||||
return GuiModConfig.class;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Set<RuntimeOptionCategoryElement> runtimeGuiCategories() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public RuntimeOptionGuiHandler getHandlerFor(RuntimeOptionCategoryElement element) {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,25 @@
|
||||
package com.gtnewhorizon.structurelib;
|
||||
|
||||
import cpw.mods.fml.client.config.GuiConfig;
|
||||
import cpw.mods.fml.client.config.IConfigElement;
|
||||
import net.minecraft.client.gui.GuiScreen;
|
||||
import net.minecraftforge.common.config.ConfigElement;
|
||||
import net.minecraftforge.common.config.Configuration;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
public class GuiModConfig extends GuiConfig {
|
||||
public GuiModConfig(GuiScreen guiScreen) {
|
||||
super(guiScreen, getConfigElements(), StructureLibAPI.MOD_ID, false, false, GuiConfig.getAbridgedConfigPath(ConfigurationHandler.INSTANCE.getConfig().toString()));
|
||||
}
|
||||
|
||||
@SuppressWarnings("rawtypes")
|
||||
private static List<IConfigElement> getConfigElements() {
|
||||
final Configuration config = ConfigurationHandler.INSTANCE.getConfig();
|
||||
return config.getCategoryNames().stream()
|
||||
.filter(name -> name.indexOf('.') == -1)
|
||||
.map(name -> new ConfigElement(config.getCategory(name)))
|
||||
.collect(Collectors.toList());
|
||||
}
|
||||
}
|
||||
@@ -1,8 +1,9 @@
|
||||
package com.gtnewhorizon.structurelib;
|
||||
|
||||
import com.gtnewhorizon.structurelib.alignment.AlignmentMessage;
|
||||
import com.gtnewhorizon.structurelib.net.AlignmentMessage;
|
||||
import com.gtnewhorizon.structurelib.block.BlockHint;
|
||||
import com.gtnewhorizon.structurelib.item.ItemBlockHint;
|
||||
import com.gtnewhorizon.structurelib.item.ItemConstructableTrigger;
|
||||
import com.gtnewhorizon.structurelib.item.ItemFrontRotationTool;
|
||||
import com.gtnewhorizon.structurelib.proxy.CommonProxy;
|
||||
import com.gtnewhorizon.structurelib.util.XSTR;
|
||||
@@ -25,15 +26,14 @@ import org.apache.logging.log4j.Logger;
|
||||
/**
|
||||
* This class does not contain a stable API. Refrain from using this class.
|
||||
*/
|
||||
@Mod(modid = StructureLib.MOD_ID, name = "StructureLib", version = "${version}", acceptableRemoteVersions = "*")
|
||||
@Mod(modid = StructureLibAPI.MOD_ID, name = "StructureLib", version = "${version}", acceptableRemoteVersions = "*", guiFactory = "com.gtnewhorizon.structurelib.GuiFactory")
|
||||
public class StructureLib {
|
||||
public static boolean DEBUG_MODE = true;
|
||||
public static boolean DEBUG_MODE = Boolean.getBoolean("structurelib.debug");
|
||||
public static Logger LOGGER = LogManager.getLogger("StructureLib");
|
||||
public static final String MOD_ID = "structurelib";
|
||||
|
||||
@SidedProxy(serverSide = "com.gtnewhorizon.structurelib.proxy.CommonProxy", clientSide = "com.gtnewhorizon.structurelib.proxy.ClientProxy")
|
||||
static CommonProxy proxy;
|
||||
static SimpleNetworkWrapper net = NetworkRegistry.INSTANCE.newSimpleChannel(MOD_ID);
|
||||
static SimpleNetworkWrapper net = NetworkRegistry.INSTANCE.newSimpleChannel(StructureLibAPI.MOD_ID);
|
||||
|
||||
static {
|
||||
net.registerMessage(AlignmentMessage.ServerHandler.class, AlignmentMessage.AlignmentQuery.class, 0, Side.SERVER);
|
||||
@@ -45,6 +45,7 @@ public class StructureLib {
|
||||
static Block blockHint;
|
||||
static Item itemBlockHint;
|
||||
static Item itemFrontRotationTool;
|
||||
static Item itemConstructableTrigger;
|
||||
public static final CreativeTabs creativeTab = new CreativeTabs("structurelib") {
|
||||
@Override
|
||||
@SideOnly(Side.CLIENT)
|
||||
@@ -55,9 +56,12 @@ public class StructureLib {
|
||||
|
||||
@Mod.EventHandler
|
||||
public void preInit(FMLPreInitializationEvent e) {
|
||||
ConfigurationHandler.INSTANCE.init(e.getSuggestedConfigurationFile());
|
||||
GameRegistry.registerBlock(blockHint = new BlockHint(), ItemBlockHint.class, "blockhint");
|
||||
itemBlockHint = ItemBlock.getItemFromBlock(StructureLibAPI.getBlockHint());
|
||||
GameRegistry.registerItem(itemFrontRotationTool = new ItemFrontRotationTool(), itemFrontRotationTool.getUnlocalizedName());
|
||||
GameRegistry.registerItem(itemConstructableTrigger = new ItemConstructableTrigger(), itemConstructableTrigger.getUnlocalizedName());
|
||||
proxy.preInit(e);
|
||||
}
|
||||
|
||||
public static void addClientSideChatMessages(String... messages) {
|
||||
|
||||
@@ -1,17 +1,59 @@
|
||||
package com.gtnewhorizon.structurelib;
|
||||
|
||||
import com.gtnewhorizon.structurelib.alignment.AlignmentMessage;
|
||||
import com.gtnewhorizon.structurelib.net.AlignmentMessage;
|
||||
import com.gtnewhorizon.structurelib.alignment.IAlignmentProvider;
|
||||
import com.gtnewhorizon.structurelib.alignment.enumerable.ExtendedFacing;
|
||||
import cpw.mods.fml.common.network.NetworkRegistry;
|
||||
import net.minecraft.block.Block;
|
||||
import net.minecraft.entity.player.EntityPlayer;
|
||||
import net.minecraft.entity.player.EntityPlayerMP;
|
||||
import net.minecraft.item.Item;
|
||||
import net.minecraft.item.ItemStack;
|
||||
import net.minecraft.util.IIcon;
|
||||
import net.minecraft.world.World;
|
||||
|
||||
import static com.gtnewhorizon.structurelib.StructureLib.proxy;
|
||||
|
||||
/**
|
||||
* A stable interface into the structure lib's internals. Backwards compatibility is maintained to the maximum extend possible.
|
||||
*/
|
||||
public class StructureLibAPI {
|
||||
public static final String MOD_ID = "structurelib";
|
||||
public static final int HINT_BLOCK_META_GENERIC_0 = 0;
|
||||
public static final int HINT_BLOCK_META_GENERIC_1 = 1;
|
||||
public static final int HINT_BLOCK_META_GENERIC_2 = 2;
|
||||
public static final int HINT_BLOCK_META_GENERIC_3 = 3;
|
||||
public static final int HINT_BLOCK_META_GENERIC_4 = 4;
|
||||
public static final int HINT_BLOCK_META_GENERIC_5 = 5;
|
||||
public static final int HINT_BLOCK_META_GENERIC_6 = 6;
|
||||
public static final int HINT_BLOCK_META_GENERIC_7 = 7;
|
||||
public static final int HINT_BLOCK_META_GENERIC_8 = 8;
|
||||
public static final int HINT_BLOCK_META_GENERIC_9 = 9;
|
||||
public static final int HINT_BLOCK_META_GENERIC_10 = 10;
|
||||
public static final int HINT_BLOCK_META_GENERIC_11 = 11;
|
||||
public static final int HINT_BLOCK_META_DEFAULT = 12;
|
||||
public static final int HINT_BLOCK_META_AIR = 13;
|
||||
public static final int HINT_BLOCK_META_NOT_AIR = 14;
|
||||
public static final int HINT_BLOCK_META_ERROR = 15;
|
||||
|
||||
/**
|
||||
* Start a batch of hinting. All hints particles generated during one batch will be considered to belong to one hologram.
|
||||
*
|
||||
* You don't need to call this unless your constructable tool didn't call {@link com.gtnewhorizon.structurelib.alignment.constructable.ConstructableUtility#handle(ItemStack, EntityPlayer, World, int, int, int, int)}
|
||||
*/
|
||||
public static void startHinting(World w) {
|
||||
proxy.startHinting(w);
|
||||
}
|
||||
|
||||
/**
|
||||
* Start current batch of hinting. All hints particles generated during one batch will be considered to belong to one hologram.
|
||||
*
|
||||
* You don't need to call this unless your constructable tool didn't call {@link com.gtnewhorizon.structurelib.alignment.constructable.ConstructableUtility#handle(ItemStack, EntityPlayer, World, int, int, int, int)}
|
||||
*/
|
||||
public static void endHinting(World w) {
|
||||
proxy.endHinting(w);
|
||||
}
|
||||
|
||||
public static void hintParticleTinted(World w, int x, int y, int z, IIcon[] icons, short[] RGBa) {
|
||||
proxy.hintParticleTinted(w, x, y, z, icons, RGBa);
|
||||
}
|
||||
@@ -28,22 +70,45 @@ public class StructureLibAPI {
|
||||
proxy.hintParticle(w, x, y, z, block, meta);
|
||||
}
|
||||
|
||||
/**
|
||||
* Query the ExtendedFacing of this tile entity.
|
||||
* The ExtendedFacing will later be set onto given tile entity via {@link com.gtnewhorizon.structurelib.alignment.IAlignment#setExtendedFacing(ExtendedFacing)}
|
||||
* upon arrival of server reply.
|
||||
* @throws IllegalArgumentException if is not tile entity or provided a null alignment
|
||||
*/
|
||||
public static void queryAlignment(IAlignmentProvider provider) {
|
||||
StructureLib.net.sendToServer(new AlignmentMessage.AlignmentQuery(provider));
|
||||
}
|
||||
|
||||
/**
|
||||
* Send the ExtendedFacing of this Tile Entity to all players. Can be called on server side only.
|
||||
* @throws IllegalArgumentException if is not tile entity or provided a null alignment
|
||||
*/
|
||||
public static void sendAlignment(IAlignmentProvider provider) {
|
||||
StructureLib.net.sendToAll(new AlignmentMessage.AlignmentData(provider));
|
||||
}
|
||||
|
||||
/**
|
||||
* Send the ExtendedFacing of this Tile Entity to given player. Can be called on server side only.
|
||||
* @throws IllegalArgumentException if is not tile entity or provided a null alignment
|
||||
*/
|
||||
public static void sendAlignment(IAlignmentProvider provider, EntityPlayerMP player) {
|
||||
StructureLib.net.sendTo(new AlignmentMessage.AlignmentData(provider), player);
|
||||
}
|
||||
|
||||
/**
|
||||
* Send the ExtendedFacing of this Tile Entity to all players around target point. Can be called on server side only.
|
||||
* @throws IllegalArgumentException if is not tile entity or provided a null alignment
|
||||
*/
|
||||
public static void sendAlignment(IAlignmentProvider provider, NetworkRegistry.TargetPoint targetPoint) {
|
||||
StructureLib.net.sendToAllAround(new AlignmentMessage.AlignmentData(provider), targetPoint);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Send the ExtendedFacing of this Tile Entity to all players in that dimension. Can be called on server side only.
|
||||
* @throws IllegalArgumentException if is not tile entity or provided a null alignment
|
||||
*/
|
||||
public static void sendAlignment(IAlignmentProvider provider, World dimension) {
|
||||
StructureLib.net.sendToDimension(new AlignmentMessage.AlignmentData(provider), dimension.provider.dimensionId);
|
||||
}
|
||||
|
||||
@@ -54,7 +54,7 @@ public interface IAlignment extends IAlignmentLimits,IAlignmentProvider {
|
||||
default boolean toolSetDirection(ForgeDirection direction){
|
||||
if(direction==null || direction==ForgeDirection.UNKNOWN){
|
||||
for (int i = 0,j=getDirection().ordinal()+1, valuesLength = Direction.VALUES.length; i < valuesLength; i++) {
|
||||
if(toolSetDirection(Direction.VALUES[j%valuesLength].getForgeDirection())){
|
||||
if (toolSetDirection(Direction.VALUES[(j + i) % valuesLength].getForgeDirection())) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
@@ -90,8 +90,8 @@ public interface IAlignment extends IAlignmentLimits,IAlignmentProvider {
|
||||
int flips = Flip.VALUES.length;
|
||||
int rotations = Rotation.VALUES.length;
|
||||
for (int ii = 0,jj=getFlip().ordinal(); ii < flips; ii++) {
|
||||
for (int i = 0,j=getRotation().ordinal()+1; i < rotations; i++) {
|
||||
if(checkedSetExtendedFacing(ExtendedFacing.of(getDirection(),Rotation.VALUES[j%rotations],Flip.VALUES[jj%flips]))){
|
||||
for (int i = 1, j = getRotation().ordinal(); i < rotations; i++) {
|
||||
if (checkedSetExtendedFacing(ExtendedFacing.of(getDirection(), Rotation.VALUES[(j + i) % rotations], Flip.VALUES[(jj + ii) % flips]))) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
@@ -112,8 +112,8 @@ public interface IAlignment extends IAlignmentLimits,IAlignmentProvider {
|
||||
|
||||
default boolean toolSetFlip(Flip flip){
|
||||
if(flip==null){
|
||||
for (int i = 0,j=getFlip().ordinal()+1, valuesLength = Flip.VALUES.length; i < valuesLength; i++) {
|
||||
if(toolSetFlip(Flip.VALUES[j%valuesLength])){
|
||||
for (int i = 1, j = getFlip().ordinal(), valuesLength = Flip.VALUES.length; i < valuesLength; i++) {
|
||||
if (checkedSetFlip(Flip.VALUES[(j + i) % valuesLength])) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
@@ -134,7 +134,7 @@ public interface IAlignment extends IAlignmentLimits,IAlignmentProvider {
|
||||
default boolean toolSetExtendedFacing(ExtendedFacing extendedFacing){
|
||||
if(extendedFacing==null){
|
||||
for (int i = 0,j=getExtendedFacing().ordinal()+1, valuesLength = ExtendedFacing.VALUES.length; i < valuesLength; i++) {
|
||||
if(toolSetExtendedFacing(ExtendedFacing.VALUES[j%valuesLength])){
|
||||
if (checkedSetExtendedFacing(ExtendedFacing.VALUES[(j + i)%valuesLength])){
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
+8
@@ -1,6 +1,7 @@
|
||||
package com.gtnewhorizon.structurelib.alignment.constructable;
|
||||
|
||||
import com.gtnewhorizon.structurelib.StructureLib;
|
||||
import com.gtnewhorizon.structurelib.StructureLibAPI;
|
||||
import com.gtnewhorizon.structurelib.alignment.IAlignment;
|
||||
import com.gtnewhorizon.structurelib.alignment.enumerable.ExtendedFacing;
|
||||
import net.minecraft.entity.player.EntityPlayer;
|
||||
@@ -17,6 +18,13 @@ public class ConstructableUtility {
|
||||
}
|
||||
|
||||
public static boolean handle(ItemStack aStack, EntityPlayer aPlayer, World aWorld, int aX, int aY, int aZ, int aSide) {
|
||||
StructureLibAPI.startHinting(aWorld);
|
||||
boolean ret = handle0(aStack, aPlayer, aWorld, aX, aY, aZ, aSide);
|
||||
StructureLibAPI.endHinting(aWorld);
|
||||
return ret;
|
||||
}
|
||||
|
||||
private static boolean handle0(ItemStack aStack, EntityPlayer aPlayer, World aWorld, int aX, int aY, int aZ, int aSide) {
|
||||
TileEntity tTileEntity = aWorld.getTileEntity(aX, aY, aZ);
|
||||
if (tTileEntity == null || aPlayer instanceof FakePlayer) {
|
||||
return aPlayer instanceof EntityPlayerMP;
|
||||
|
||||
+4
@@ -14,6 +14,10 @@ import java.util.HashMap;
|
||||
public interface IMultiblockInfoContainer<T> {
|
||||
HashMap<String, IMultiblockInfoContainer<?>> MULTIBLOCK_MAP = new HashMap<>();
|
||||
|
||||
/**
|
||||
* There is no specific loading phase restriction, but you should generally not call it before the tile entity is
|
||||
* properly registered.
|
||||
*/
|
||||
static <T extends TileEntity> void registerTileClass(Class<T> clazz, IMultiblockInfoContainer<?> info) {
|
||||
MULTIBLOCK_MAP.put(clazz.getCanonicalName(), info);
|
||||
}
|
||||
|
||||
@@ -0,0 +1,5 @@
|
||||
/**
|
||||
* All public stuff in this package and its subpackages are considered part of the public API.
|
||||
* Backwards compatibility is maintained to the maximum extend possible.
|
||||
*/
|
||||
package com.gtnewhorizon.structurelib.alignment;
|
||||
@@ -1,6 +1,7 @@
|
||||
package com.gtnewhorizon.structurelib.block;
|
||||
|
||||
import com.gtnewhorizon.structurelib.StructureLib;
|
||||
import com.gtnewhorizon.structurelib.StructureLibAPI;
|
||||
import cpw.mods.fml.relauncher.Side;
|
||||
import cpw.mods.fml.relauncher.SideOnly;
|
||||
import net.minecraft.block.Block;
|
||||
@@ -26,22 +27,22 @@ public class BlockHint extends Block {
|
||||
@Override
|
||||
public void registerBlockIcons(IIconRegister aIconRegister) {
|
||||
//super.registerBlockIcons(aIconRegister);
|
||||
hint[0] = aIconRegister.registerIcon(StructureLib.MOD_ID + ":iconsets/HINT_0");
|
||||
hint[1] = aIconRegister.registerIcon(StructureLib.MOD_ID + ":iconsets/HINT_1");
|
||||
hint[2] = aIconRegister.registerIcon(StructureLib.MOD_ID + ":iconsets/HINT_2");
|
||||
hint[3] = aIconRegister.registerIcon(StructureLib.MOD_ID + ":iconsets/HINT_3");
|
||||
hint[4] = aIconRegister.registerIcon(StructureLib.MOD_ID + ":iconsets/HINT_4");
|
||||
hint[5] = aIconRegister.registerIcon(StructureLib.MOD_ID + ":iconsets/HINT_5");
|
||||
hint[6] = aIconRegister.registerIcon(StructureLib.MOD_ID + ":iconsets/HINT_6");
|
||||
hint[7] = aIconRegister.registerIcon(StructureLib.MOD_ID + ":iconsets/HINT_7");
|
||||
hint[8] = aIconRegister.registerIcon(StructureLib.MOD_ID + ":iconsets/HINT_8");
|
||||
hint[9] = aIconRegister.registerIcon(StructureLib.MOD_ID + ":iconsets/HINT_9");
|
||||
hint[10] = aIconRegister.registerIcon(StructureLib.MOD_ID + ":iconsets/HINT_10");
|
||||
hint[11] = aIconRegister.registerIcon(StructureLib.MOD_ID + ":iconsets/HINT_11");
|
||||
hint[12] = aIconRegister.registerIcon(StructureLib.MOD_ID + ":iconsets/HINT_DEFAULT");
|
||||
hint[13] = aIconRegister.registerIcon(StructureLib.MOD_ID + ":iconsets/HINT_AIR");
|
||||
hint[14] = aIconRegister.registerIcon(StructureLib.MOD_ID + ":iconsets/HINT_NOAIR");
|
||||
hint[15] = aIconRegister.registerIcon(StructureLib.MOD_ID + ":iconsets/HINT_ERROR");
|
||||
hint[0] = aIconRegister.registerIcon(StructureLibAPI.MOD_ID + ":iconsets/HINT_0");
|
||||
hint[1] = aIconRegister.registerIcon(StructureLibAPI.MOD_ID + ":iconsets/HINT_1");
|
||||
hint[2] = aIconRegister.registerIcon(StructureLibAPI.MOD_ID + ":iconsets/HINT_2");
|
||||
hint[3] = aIconRegister.registerIcon(StructureLibAPI.MOD_ID + ":iconsets/HINT_3");
|
||||
hint[4] = aIconRegister.registerIcon(StructureLibAPI.MOD_ID + ":iconsets/HINT_4");
|
||||
hint[5] = aIconRegister.registerIcon(StructureLibAPI.MOD_ID + ":iconsets/HINT_5");
|
||||
hint[6] = aIconRegister.registerIcon(StructureLibAPI.MOD_ID + ":iconsets/HINT_6");
|
||||
hint[7] = aIconRegister.registerIcon(StructureLibAPI.MOD_ID + ":iconsets/HINT_7");
|
||||
hint[8] = aIconRegister.registerIcon(StructureLibAPI.MOD_ID + ":iconsets/HINT_8");
|
||||
hint[9] = aIconRegister.registerIcon(StructureLibAPI.MOD_ID + ":iconsets/HINT_9");
|
||||
hint[10] = aIconRegister.registerIcon(StructureLibAPI.MOD_ID + ":iconsets/HINT_10");
|
||||
hint[11] = aIconRegister.registerIcon(StructureLibAPI.MOD_ID + ":iconsets/HINT_11");
|
||||
hint[12] = aIconRegister.registerIcon(StructureLibAPI.MOD_ID + ":iconsets/HINT_DEFAULT");
|
||||
hint[13] = aIconRegister.registerIcon(StructureLibAPI.MOD_ID + ":iconsets/HINT_AIR");
|
||||
hint[14] = aIconRegister.registerIcon(StructureLibAPI.MOD_ID + ":iconsets/HINT_NOAIR");
|
||||
hint[15] = aIconRegister.registerIcon(StructureLibAPI.MOD_ID + ":iconsets/HINT_ERROR");
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
+12
-5
@@ -1,6 +1,7 @@
|
||||
package com.gtnewhorizon.structurelib.entity.fx;
|
||||
|
||||
import com.gtnewhorizon.structurelib.StructureLib;
|
||||
import com.gtnewhorizon.structurelib.proxy.ClientProxy;
|
||||
import cpw.mods.fml.relauncher.Side;
|
||||
import cpw.mods.fml.relauncher.SideOnly;
|
||||
import net.minecraft.block.Block;
|
||||
@@ -12,11 +13,11 @@ import net.minecraft.world.World;
|
||||
import org.lwjgl.opengl.GL11;
|
||||
|
||||
@SideOnly(Side.CLIENT)
|
||||
public class BlockHint extends EntityFX {
|
||||
public class EntityFXBlockHint extends EntityFX {
|
||||
private IIcon[] icons;
|
||||
private short[] mRGBa = {255,255,255,0};
|
||||
|
||||
public BlockHint(World world){
|
||||
public EntityFXBlockHint(World world){
|
||||
this(world,0,0,0, Blocks.stone,0);
|
||||
}
|
||||
|
||||
@@ -28,7 +29,7 @@ public class BlockHint extends EntityFX {
|
||||
* @param z
|
||||
* @param icons DOWN, UP, NORTH, SOUTH, WEST, EAST
|
||||
*/
|
||||
public BlockHint(World world, int x, int y, int z, IIcon[] icons) {
|
||||
public EntityFXBlockHint(World world, int x, int y, int z, IIcon[] icons) {
|
||||
super(world, x + .25, y + .5, z + .25);
|
||||
particleGravity = 0;
|
||||
prevPosX = posX;
|
||||
@@ -39,7 +40,7 @@ public class BlockHint extends EntityFX {
|
||||
this.icons=icons;
|
||||
}
|
||||
|
||||
public BlockHint(World world, int x, int y, int z, Block block, int meta) {
|
||||
public EntityFXBlockHint(World world, int x, int y, int z, Block block, int meta) {
|
||||
super(world, x+.25, y+.5, z+.25);
|
||||
particleGravity = 0;
|
||||
prevPosX = posX;
|
||||
@@ -53,7 +54,7 @@ public class BlockHint extends EntityFX {
|
||||
}
|
||||
}
|
||||
|
||||
public BlockHint withColorTint(short[] coloure){
|
||||
public EntityFXBlockHint withColorTint(short[] coloure){
|
||||
this.mRGBa =coloure;
|
||||
return this;
|
||||
}
|
||||
@@ -130,4 +131,10 @@ public class BlockHint extends EntityFX {
|
||||
public boolean shouldRenderInPass(int pass) {
|
||||
return pass==2;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setDead() {
|
||||
super.setDead();
|
||||
ClientProxy.onHintDead(this);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,37 @@
|
||||
package com.gtnewhorizon.structurelib.item;
|
||||
|
||||
import com.gtnewhorizon.structurelib.StructureLib;
|
||||
import com.gtnewhorizon.structurelib.alignment.constructable.ConstructableUtility;
|
||||
import net.minecraft.entity.player.EntityPlayer;
|
||||
import net.minecraft.item.Item;
|
||||
import net.minecraft.item.ItemStack;
|
||||
import net.minecraft.world.World;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import static com.gtnewhorizon.structurelib.StructureLibAPI.MOD_ID;
|
||||
import static net.minecraft.util.EnumChatFormatting.BLUE;
|
||||
import static net.minecraft.util.StatCollector.translateToLocal;
|
||||
|
||||
public class ItemConstructableTrigger extends Item {
|
||||
public ItemConstructableTrigger() {
|
||||
setUnlocalizedName("structurelib.constructableTrigger");
|
||||
setTextureName(MOD_ID + ":itemConstructableTrigger");
|
||||
setCreativeTab(StructureLib.creativeTab);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onItemUseFirst(ItemStack stack, EntityPlayer player, World world, int x, int y, int z, int side, float hitX, float hitY, float hitZ) {
|
||||
return ConstructableUtility.handle(stack, player, world, x, y, z, side);
|
||||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
@Override
|
||||
public void addInformation(ItemStack aStack, EntityPlayer ep, List aList, boolean boo) {
|
||||
aList.add(translateToLocal("item.structurelib.constructableTrigger.desc.0"));//Triggers Constructable Interface
|
||||
aList.add(BLUE + translateToLocal("item.structurelib.constructableTrigger.desc.1"));//Shows multiblock construction details,
|
||||
aList.add(BLUE + translateToLocal("item.structurelib.constructableTrigger.desc.2"));//just Use on a multiblock controller.
|
||||
aList.add(BLUE + translateToLocal("item.structurelib.constructableTrigger.desc.3"));//(Sneak Use in creative to build)
|
||||
aList.add(BLUE + translateToLocal("item.structurelib.constructableTrigger.desc.4"));//Quantity affects tier/mode/type
|
||||
}
|
||||
}
|
||||
@@ -12,7 +12,7 @@ import net.minecraft.world.World;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import static com.gtnewhorizon.structurelib.StructureLib.MOD_ID;
|
||||
import static com.gtnewhorizon.structurelib.StructureLibAPI.MOD_ID;
|
||||
import static net.minecraft.util.StatCollector.translateToLocal;
|
||||
|
||||
public class ItemFrontRotationTool extends Item {
|
||||
|
||||
+3
-1
@@ -1,6 +1,8 @@
|
||||
package com.gtnewhorizon.structurelib.alignment;
|
||||
package com.gtnewhorizon.structurelib.net;
|
||||
|
||||
import com.gtnewhorizon.structurelib.StructureLib;
|
||||
import com.gtnewhorizon.structurelib.alignment.IAlignment;
|
||||
import com.gtnewhorizon.structurelib.alignment.IAlignmentProvider;
|
||||
import com.gtnewhorizon.structurelib.alignment.enumerable.ExtendedFacing;
|
||||
import cpw.mods.fml.common.network.ByteBufUtils;
|
||||
import cpw.mods.fml.common.network.simpleimpl.IMessage;
|
||||
@@ -1,7 +1,12 @@
|
||||
package com.gtnewhorizon.structurelib.proxy;
|
||||
|
||||
import com.gtnewhorizon.structurelib.entity.fx.BlockHint;
|
||||
import com.google.common.collect.BiMap;
|
||||
import com.google.common.collect.HashBiMap;
|
||||
import com.gtnewhorizon.structurelib.ConfigurationHandler;
|
||||
import com.gtnewhorizon.structurelib.entity.fx.EntityFXBlockHint;
|
||||
import com.gtnewhorizon.structurelib.entity.fx.WeightlessParticleFX;
|
||||
import cpw.mods.fml.common.event.FMLPreInitializationEvent;
|
||||
import cpw.mods.fml.common.eventhandler.SubscribeEvent;
|
||||
import net.minecraft.block.Block;
|
||||
import net.minecraft.client.Minecraft;
|
||||
import net.minecraft.client.gui.GuiNewChat;
|
||||
@@ -10,57 +15,173 @@ import net.minecraft.entity.player.EntityPlayer;
|
||||
import net.minecraft.util.ChatComponentText;
|
||||
import net.minecraft.util.IIcon;
|
||||
import net.minecraft.world.World;
|
||||
import net.minecraftforge.common.MinecraftForge;
|
||||
import net.minecraftforge.event.world.WorldEvent;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Iterator;
|
||||
import java.util.LinkedList;
|
||||
import java.util.List;
|
||||
|
||||
import static com.gtnewhorizon.structurelib.StructureLib.RANDOM;
|
||||
|
||||
public class ClientProxy extends CommonProxy {
|
||||
@Override
|
||||
public void hintParticleTinted(World w, int x, int y, int z, IIcon[] icons, short[] RGBa) {
|
||||
Minecraft.getMinecraft().effectRenderer.addEffect(new BlockHint(w, x, y, z, icons).withColorTint(RGBa));
|
||||
@Override
|
||||
public void hintParticleTinted(World w, int x, int y, int z, IIcon[] icons, short[] RGBa) {
|
||||
EntityFXBlockHint hint = new EntityFXBlockHint(w, x, y, z, icons).withColorTint(RGBa);
|
||||
Minecraft.getMinecraft().effectRenderer.addEffect(hint);
|
||||
ensureHinting();
|
||||
if (ConfigurationHandler.INSTANCE.isRemoveCollidingHologram()) {
|
||||
HintParticleInfo info = new HintParticleInfo(x, y, z, currentHints);
|
||||
EntityFXBlockHint dupe = allHints.inverse().get(info);
|
||||
if (dupe != null) {
|
||||
List<EntityFXBlockHint> owner = allHints.get(dupe).owner;
|
||||
// in case someone forget to call endHinting
|
||||
if (owner != currentHints) {
|
||||
hintOwners.remove(owner);
|
||||
owner.forEach(EntityFXBlockHint::setDead);
|
||||
owner.clear();
|
||||
}
|
||||
}
|
||||
allHints.forcePut(hint, info);
|
||||
}
|
||||
currentHints.add(hint);
|
||||
|
||||
EntityFX particle = new WeightlessParticleFX(w, x + RANDOM.nextFloat() * 0.5F, y + RANDOM.nextFloat() * 0.5F, z + RANDOM.nextFloat() * 0.5F, 0, 0, 0);
|
||||
particle.setRBGColorF(0, 0.6F * RANDOM.nextFloat(), 0.8f);
|
||||
Minecraft.getMinecraft().effectRenderer.addEffect(particle);
|
||||
}
|
||||
EntityFX particle = new WeightlessParticleFX(w, x + RANDOM.nextFloat() * 0.5F, y + RANDOM.nextFloat() * 0.5F, z + RANDOM.nextFloat() * 0.5F, 0, 0, 0);
|
||||
particle.setRBGColorF(0, 0.6F * RANDOM.nextFloat(), 0.8f);
|
||||
Minecraft.getMinecraft().effectRenderer.addEffect(particle);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void hintParticleTinted(World w, int x, int y, int z, Block block, int meta, short[] RGBa) {
|
||||
hintParticleTinted(w, x, y, z, createIIconFromBlock(block, meta), RGBa);
|
||||
}
|
||||
@Override
|
||||
public void hintParticleTinted(World w, int x, int y, int z, Block block, int meta, short[] RGBa) {
|
||||
hintParticleTinted(w, x, y, z, createIIconFromBlock(block, meta), RGBa);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void hintParticle(World w, int x, int y, int z, IIcon[] icons) {
|
||||
hintParticleTinted(w, x, y, z, icons, new short[]{255, 255, 255, 0});
|
||||
}
|
||||
@Override
|
||||
public void hintParticle(World w, int x, int y, int z, IIcon[] icons) {
|
||||
hintParticleTinted(w, x, y, z, icons, new short[]{255, 255, 255, 0});
|
||||
}
|
||||
|
||||
@Override
|
||||
public void hintParticle(World w, int x, int y, int z, Block block, int meta) {
|
||||
hintParticleTinted(w, x, y, z, createIIconFromBlock(block, meta), new short[]{255, 255, 255, 0});
|
||||
}
|
||||
@Override
|
||||
public void hintParticle(World w, int x, int y, int z, Block block, int meta) {
|
||||
hintParticleTinted(w, x, y, z, createIIconFromBlock(block, meta), new short[]{255, 255, 255, 0});
|
||||
}
|
||||
|
||||
private static IIcon[] createIIconFromBlock(Block block, int meta) {
|
||||
IIcon[] ret = new IIcon[6];
|
||||
for (int i = 0; i < 6; i++) {
|
||||
block.getIcon(i, meta);
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
private static IIcon[] createIIconFromBlock(Block block, int meta) {
|
||||
IIcon[] ret = new IIcon[6];
|
||||
for (int i = 0; i < 6; i++) {
|
||||
ret[i] = block.getIcon(i, meta);
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void addClientSideChatMessages(String... messages) {
|
||||
GuiNewChat chat = Minecraft.getMinecraft().ingameGUI.getChatGUI();
|
||||
for (String s : messages) {
|
||||
chat.printChatMessage(new ChatComponentText(s));
|
||||
}
|
||||
}
|
||||
@Override
|
||||
public void addClientSideChatMessages(String... messages) {
|
||||
GuiNewChat chat = Minecraft.getMinecraft().ingameGUI.getChatGUI();
|
||||
for (String s : messages) {
|
||||
chat.printChatMessage(new ChatComponentText(s));
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public EntityPlayer getCurrentPlayer() {
|
||||
return Minecraft.getMinecraft().thePlayer;
|
||||
}
|
||||
@Override
|
||||
public EntityPlayer getCurrentPlayer() {
|
||||
return Minecraft.getMinecraft().thePlayer;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isCurrentPlayer(EntityPlayer player) {
|
||||
return player == Minecraft.getMinecraft().thePlayer;
|
||||
}
|
||||
@Override
|
||||
public boolean isCurrentPlayer(EntityPlayer player) {
|
||||
return player == Minecraft.getMinecraft().thePlayer;
|
||||
}
|
||||
|
||||
private static final BiMap<EntityFXBlockHint, HintParticleInfo> allHints = HashBiMap.create();
|
||||
private static final List<List<EntityFXBlockHint>> hintOwners = new ArrayList<>();
|
||||
private static List<EntityFXBlockHint> currentHints;
|
||||
|
||||
public static void onHintDead(EntityFXBlockHint fx) {
|
||||
if (ConfigurationHandler.INSTANCE.isRemoveCollidingHologram())
|
||||
allHints.remove(fx);
|
||||
for (Iterator<List<EntityFXBlockHint>> iterator = hintOwners.iterator(); iterator.hasNext(); ) {
|
||||
List<EntityFXBlockHint> list = iterator.next();
|
||||
if (list.remove(fx)) {
|
||||
if (list.isEmpty())
|
||||
iterator.remove();
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void startHinting(World w) {
|
||||
if (!w.isRemote)
|
||||
return;
|
||||
if (currentHints != null)
|
||||
hintOwners.add(currentHints);
|
||||
currentHints = new LinkedList<>();
|
||||
}
|
||||
|
||||
private void ensureHinting() {
|
||||
if (currentHints == null)
|
||||
currentHints = new LinkedList<>();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void endHinting(World w) {
|
||||
if (!w.isRemote)
|
||||
return;
|
||||
while (!hintOwners.isEmpty() && hintOwners.size() >= ConfigurationHandler.INSTANCE.getMaxCoexistingHologram()) {
|
||||
List<EntityFXBlockHint> list = hintOwners.remove(0);
|
||||
list.forEach(EntityFXBlockHint::setDead);
|
||||
list.clear();
|
||||
}
|
||||
if (!currentHints.isEmpty())
|
||||
hintOwners.add(currentHints);
|
||||
currentHints = null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void preInit(FMLPreInitializationEvent e) {
|
||||
MinecraftForge.EVENT_BUS.register(new ForgeEventHandler());
|
||||
}
|
||||
|
||||
private static class HintParticleInfo {
|
||||
private final int x, y, z;
|
||||
private final List<EntityFXBlockHint> owner;
|
||||
|
||||
public HintParticleInfo(int x, int y, int z, List<EntityFXBlockHint> owner) {
|
||||
this.x = x;
|
||||
this.y = y;
|
||||
this.z = z;
|
||||
this.owner = owner;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (this == o) return true;
|
||||
if (o == null || getClass() != o.getClass()) return false;
|
||||
|
||||
HintParticleInfo that = (HintParticleInfo) o;
|
||||
|
||||
if (x != that.x) return false;
|
||||
if (y != that.y) return false;
|
||||
return z == that.z;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
int result = x;
|
||||
result = 31 * result + y;
|
||||
result = 31 * result + z;
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
public static class ForgeEventHandler {
|
||||
@SubscribeEvent
|
||||
public void onWorldLoad(WorldEvent.Load e) {
|
||||
if (e.world.isRemote) {
|
||||
allHints.clear();
|
||||
hintOwners.clear();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,5 +1,6 @@
|
||||
package com.gtnewhorizon.structurelib.proxy;
|
||||
|
||||
import cpw.mods.fml.common.event.FMLPreInitializationEvent;
|
||||
import net.minecraft.block.Block;
|
||||
import net.minecraft.entity.player.EntityPlayer;
|
||||
import net.minecraft.util.IIcon;
|
||||
@@ -18,4 +19,8 @@ public class CommonProxy {
|
||||
}
|
||||
public void addClientSideChatMessages(String... messages){
|
||||
}
|
||||
public void startHinting(World w) {}
|
||||
public void endHinting(World w) {}
|
||||
|
||||
public void preInit(FMLPreInitializationEvent e) {}
|
||||
}
|
||||
@@ -165,4 +165,8 @@ public interface IStructureDefinition<T> {
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
static <T> StructureDefinition.Builder<T> builder() {
|
||||
return StructureDefinition.builder();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,14 @@
|
||||
package com.gtnewhorizon.structurelib.structure;
|
||||
|
||||
/**
|
||||
* Implement this and use {@link StructureUtility#withContext(IStructureElement)} in case you need to record some
|
||||
* temporary states that don't need to live in your main context, which would usually live for the whole lifetime of the
|
||||
* structure than just during structure check. Usually just save some few bytes, but becomes non trivial if you need to
|
||||
* record too much stuff.
|
||||
*
|
||||
* You will have to reset the context yourself though. The API can't guess when the old context becomes invalid.
|
||||
* @param <CTX> the temporary state context
|
||||
*/
|
||||
public interface IWithExtendedContext<CTX> {
|
||||
CTX getCurrentContext();
|
||||
}
|
||||
@@ -0,0 +1,38 @@
|
||||
package com.gtnewhorizon.structurelib.structure;
|
||||
|
||||
import net.minecraft.item.ItemStack;
|
||||
import net.minecraft.world.World;
|
||||
|
||||
import java.util.function.Function;
|
||||
|
||||
class LazyStructureElement<T> implements IStructureElementDeferred<T> {
|
||||
private Function<T, IStructureElement<T>> to;
|
||||
private IStructureElement<T> elem;
|
||||
|
||||
public LazyStructureElement(Function<T, IStructureElement<T>> to) {
|
||||
this.to = to;
|
||||
}
|
||||
|
||||
private IStructureElement<T> get(T t) {
|
||||
if (to != null) {
|
||||
elem = to.apply(t);
|
||||
to = null;
|
||||
}
|
||||
return elem;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean check(T t, World world, int x, int y, int z) {
|
||||
return get(t).check(t, world, x, y, z);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean placeBlock(T t, World world, int x, int y, int z, ItemStack trigger) {
|
||||
return get(t).placeBlock(t, world, x, y, z, trigger);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean spawnHint(T t, World world, int x, int y, int z, ItemStack trigger) {
|
||||
return get(t).spawnHint(t, world, x, y, z, trigger);
|
||||
}
|
||||
}
|
||||
@@ -51,7 +51,8 @@ public class StructureDefinition<T> implements IStructureDefinition<T> {
|
||||
|
||||
/**
|
||||
* Adds shape
|
||||
* +- is air/no air checks
|
||||
* + is anything but air
|
||||
* - is air checks
|
||||
* space bar is skip
|
||||
* ~ is also skip (but marks controller position, optional and logically it is a space...)
|
||||
* rest needs to be defined
|
||||
|
||||
@@ -5,15 +5,27 @@ import com.gtnewhorizon.structurelib.alignment.enumerable.ExtendedFacing;
|
||||
import com.gtnewhorizon.structurelib.structure.adders.IBlockAdder;
|
||||
import com.gtnewhorizon.structurelib.structure.adders.ITileAdder;
|
||||
import com.gtnewhorizon.structurelib.util.Vec3Impl;
|
||||
import cpw.mods.fml.common.registry.GameRegistry;
|
||||
import net.minecraft.block.Block;
|
||||
import net.minecraft.init.Blocks;
|
||||
import net.minecraft.item.ItemStack;
|
||||
import net.minecraft.tileentity.TileEntity;
|
||||
import net.minecraft.util.IIcon;
|
||||
import net.minecraft.world.World;
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
|
||||
import java.util.*;
|
||||
import java.util.Collection;
|
||||
import java.util.Collections;
|
||||
import java.util.Comparator;
|
||||
import java.util.HashMap;
|
||||
import java.util.HashSet;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
import java.util.TreeMap;
|
||||
import java.util.TreeSet;
|
||||
import java.util.function.BiFunction;
|
||||
import java.util.function.BiPredicate;
|
||||
import java.util.function.Consumer;
|
||||
import java.util.function.Function;
|
||||
import java.util.function.Supplier;
|
||||
@@ -175,6 +187,98 @@ public class StructureUtility {
|
||||
|
||||
//region block
|
||||
|
||||
/**
|
||||
* Denote a block using unlocalized names. This can be useful to get around mod loading order issues.
|
||||
* <p>
|
||||
* While no immediate error will be thrown, client code should ensure said mod is loaded and
|
||||
* said mod is present, otherwise bad things will happen later!
|
||||
*/
|
||||
public static <T> IStructureElement<T> ofBlockUnlocalizedName(String modid, String unlocalizedName, int meta) {
|
||||
if (StringUtils.isBlank(unlocalizedName)) throw new IllegalArgumentException();
|
||||
if (meta < 0) throw new IllegalArgumentException();
|
||||
if (meta > 15) throw new IllegalArgumentException();
|
||||
if (StringUtils.isBlank(modid)) throw new IllegalArgumentException();
|
||||
return new IStructureElement<T>() {
|
||||
private Block block;
|
||||
|
||||
private Block getBlock() {
|
||||
if (block == null)
|
||||
block = GameRegistry.findBlock(modid, unlocalizedName);
|
||||
return block;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean check(T t, World world, int x, int y, int z) {
|
||||
return world.getBlock(x, y, z) != getBlock() && world.getBlockMetadata(x, y, z) == meta;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean spawnHint(T t, World world, int x, int y, int z, ItemStack trigger) {
|
||||
StructureLibAPI.hintParticle(world, x, y, z, getBlock(), meta);
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean placeBlock(T t, World world, int x, int y, int z, ItemStack trigger) {
|
||||
world.setBlock(x, y, z, getBlock(), meta, 2);
|
||||
return true;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Similiar to the other overload, but allows client code to specify a fallback in case said block was not found later
|
||||
* when the element got called.
|
||||
*
|
||||
* This is slightly different to using the other overload and another element in a {@link #ofChain(IStructureElement[])},
|
||||
* as that combination would cause crash, where this won't.
|
||||
*/
|
||||
public static <T> IStructureElement<T> ofBlockUnlocalizedName(String modid, String unlocalizedName, int meta, IStructureElement<T> fallback) {
|
||||
if (StringUtils.isBlank(unlocalizedName)) throw new IllegalArgumentException();
|
||||
if (meta < 0) throw new IllegalArgumentException();
|
||||
if (meta > 15) throw new IllegalArgumentException();
|
||||
if (StringUtils.isBlank(modid)) throw new IllegalArgumentException();
|
||||
if (fallback == null) throw new IllegalArgumentException();
|
||||
return new IStructureElement<T>() {
|
||||
private Block block;
|
||||
private boolean initialized;
|
||||
|
||||
private boolean init() {
|
||||
if (!initialized) {
|
||||
block = GameRegistry.findBlock(modid, unlocalizedName);
|
||||
initialized = true;
|
||||
}
|
||||
return block != null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean check(T t, World world, int x, int y, int z) {
|
||||
if (init())
|
||||
return world.getBlock(x, y, z) != block && world.getBlockMetadata(x, y, z) == meta;
|
||||
else
|
||||
return fallback.check(t, world, x, y, z);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean spawnHint(T t, World world, int x, int y, int z, ItemStack trigger) {
|
||||
if (init()) {
|
||||
StructureLibAPI.hintParticle(world, x, y, z, block, meta);
|
||||
return true;
|
||||
} else
|
||||
return fallback.spawnHint(t, world, x, y, z, trigger);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean placeBlock(T t, World world, int x, int y, int z, ItemStack trigger) {
|
||||
if (init()) {
|
||||
world.setBlock(x, y, z, block, meta, 2);
|
||||
return true;
|
||||
} else
|
||||
return fallback.placeBlock(t, world, x, y, z, trigger);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Does not allow Block duplicates (with different meta)
|
||||
*/
|
||||
@@ -558,6 +662,26 @@ public class StructureUtility {
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
public static <T, E> IStructureElementNoPlacement<T> ofSpecificTileAdder(BiPredicate<T, E> iTileAdder, Class<E> tileClass, Block hintBlock, int hintMeta) {
|
||||
if (iTileAdder == null || hintBlock == null || tileClass == null) {
|
||||
throw new IllegalArgumentException();
|
||||
}
|
||||
return new IStructureElementNoPlacement<T>() {
|
||||
@Override
|
||||
public boolean check(T t, World world, int x, int y, int z) {
|
||||
TileEntity tileEntity = world.getTileEntity(x, y, z);
|
||||
// This used to check if it's a GT tile. Since this is now an standalone mod we no longer do this
|
||||
return tileClass.isInstance(tileEntity) && iTileAdder.test(t, tileClass.cast(tileEntity));
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean spawnHint(T t, World world, int x, int y, int z, ItemStack trigger) {
|
||||
StructureLibAPI.hintParticle(world, x, y, z, hintBlock, hintMeta);
|
||||
return true;
|
||||
}
|
||||
};
|
||||
}
|
||||
// No more hatch adder. Implement it via tile adder. We could of course add a wrapper around it in gregtech, but not any more in this standalone mod.
|
||||
|
||||
//endregion
|
||||
@@ -640,8 +764,51 @@ public class StructureUtility {
|
||||
return ofChain(elementChain.toArray(new IStructureElement[0]));
|
||||
}
|
||||
|
||||
// region context
|
||||
public static <CTX, T extends IWithExtendedContext<CTX>, E extends IStructureElement<CTX>> IStructureElement<T> withContext(E elem) {
|
||||
return new IStructureElement<T>() {
|
||||
@Override
|
||||
public boolean check(T t, World world, int x, int y, int z) {
|
||||
return elem.check(t.getCurrentContext(), world, x, y, z);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean spawnHint(T t, World world, int x, int y, int z, ItemStack trigger) {
|
||||
return elem.spawnHint(t.getCurrentContext(), world, x, y, z, trigger);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean placeBlock(T t, World world, int x, int y, int z, ItemStack trigger) {
|
||||
return elem.placeBlock(t.getCurrentContext(), world, x, y, z, trigger);
|
||||
}
|
||||
};
|
||||
}
|
||||
//endregion
|
||||
|
||||
//region defer
|
||||
|
||||
/**
|
||||
* Similar to defer, but caches the first returned element returned and won't call it again.
|
||||
* Initialization is not thread safe.
|
||||
*/
|
||||
public static <T> IStructureElementDeferred<T> lazy(Supplier<IStructureElement<T>> to) {
|
||||
if (to == null) {
|
||||
throw new IllegalArgumentException();
|
||||
}
|
||||
return new LazyStructureElement<>(t -> to.get());
|
||||
}
|
||||
|
||||
/**
|
||||
* Similar to defer, but caches the first returned element returned and won't call it again.
|
||||
* Initialization is not thread safe.
|
||||
*/
|
||||
public static <T> IStructureElementDeferred<T> lazy(Function<T, IStructureElement<T>> to) {
|
||||
if (to == null) {
|
||||
throw new IllegalArgumentException();
|
||||
}
|
||||
return new LazyStructureElement<>(to);
|
||||
}
|
||||
|
||||
public static <T> IStructureElementDeferred<T> defer(Supplier<IStructureElement<T>> to) {
|
||||
if (to == null) {
|
||||
throw new IllegalArgumentException();
|
||||
@@ -1269,4 +1436,5 @@ public class StructureUtility {
|
||||
}
|
||||
return shape;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
/**
|
||||
* All public stuff in this package and its subpackages are considered part of the public API.
|
||||
* Backwards compatibility is maintained to the maximum extend possible.
|
||||
*/
|
||||
package com.gtnewhorizon.structurelib.structure;
|
||||
@@ -15,11 +15,18 @@ tile.structurelib.blockhint.13.name=Hint air
|
||||
tile.structurelib.blockhint.14.name=Hint no air
|
||||
tile.structurelib.blockhint.15.name=Hint error
|
||||
|
||||
item.structurelib.frontRotationTool.name=Front Rotation Tool
|
||||
item.structurelib.frontRotationTool.name=Front Rotation Tool (Standalone)
|
||||
item.structurelib.frontRotationTool.desc.0=Triggers Front Rotation Interface
|
||||
item.structurelib.frontRotationTool.desc.1=Rotates only the front panel,
|
||||
item.structurelib.frontRotationTool.desc.2=which allows structure rotation.
|
||||
|
||||
item.structurelib.constructableTrigger.name=Multiblock Structure Hologram Projector
|
||||
item.structurelib.constructableTrigger.desc.0=Triggers Constructable Interface
|
||||
item.structurelib.constructableTrigger.desc.1=Shows multiblock construction details,
|
||||
item.structurelib.constructableTrigger.desc.2=just Use on a multiblock controller.
|
||||
item.structurelib.constructableTrigger.desc.3=(Sneak Use in creative to build)
|
||||
item.structurelib.constructableTrigger.desc.4=Quantity affects tier/mode/type
|
||||
|
||||
structurelib.blockhint.desc.0=Helps while building
|
||||
structurelib.blockhint.0.name=Hint 1 dot
|
||||
structurelib.blockhint.1.name=Hint 2 dot
|
||||
@@ -42,4 +49,13 @@ structurelib.blockhint.14.name=Hint no air
|
||||
structurelib.blockhint.desc.4=Make sure it does not contain Air material.
|
||||
structurelib.blockhint.15.name=Hint error
|
||||
structurelib.blockhint.desc.5=ERROR, what did u expect?
|
||||
itemGroup.structurelib=StructureLib
|
||||
itemGroup.structurelib=StructureLib
|
||||
|
||||
structurelib.config.client=Client Side Configurations
|
||||
structurelib.config.client.tooltip=Configurations that only changes how the game looks like, but not how it functions.
|
||||
structurelib.config.client.hologram=Hologram Configurations
|
||||
structurelib.config.client.hologram.tooltip=Configurations that changes how the hologram got projected into the world by default.
|
||||
structurelib.config.client.hologram.maxCoexisting=Max Coexisting Holograms
|
||||
structurelib.config.client.hologram.maxCoexisting.tooltip=Number of holograms that can coexist. Usually all hints generated by one right click belongs to one hologram. An attempt will be made to prune old holograms when a new hologram is about to be projected and this limit would be exceeded.
|
||||
structurelib.config.client.hologram.removeColliding=Remove Colliding Holograms
|
||||
structurelib.config.client.hologram.removeColliding.tooltip=Whether an attempt will be made to remove any existing hologram that collides with a new hologram.
|
||||
@@ -0,0 +1,52 @@
|
||||
tile.structurelib.blockhint.0.name=提示方块:1号
|
||||
tile.structurelib.blockhint.1.name=提示方块:2号
|
||||
tile.structurelib.blockhint.2.name=提示方块:3号
|
||||
tile.structurelib.blockhint.3.name=提示方块:4号
|
||||
tile.structurelib.blockhint.4.name=提示方块:5号
|
||||
tile.structurelib.blockhint.5.name=提示方块:6号
|
||||
tile.structurelib.blockhint.6.name=提示方块:7号
|
||||
tile.structurelib.blockhint.7.name=提示方块:8号
|
||||
tile.structurelib.blockhint.8.name=提示方块:9号
|
||||
tile.structurelib.blockhint.9.name=提示方块:10号
|
||||
tile.structurelib.blockhint.10.name=提示方块:11号
|
||||
tile.structurelib.blockhint.11.name=提示方块:12号
|
||||
tile.structurelib.blockhint.12.name=提示方块:一般
|
||||
tile.structurelib.blockhint.13.name=提示方块:空气
|
||||
tile.structurelib.blockhint.14.name=提示方块:非空气
|
||||
tile.structurelib.blockhint.15.name=提示方块:错误
|
||||
|
||||
item.structurelib.frontRotationTool.name=正面旋转扳手 (StructureLib)
|
||||
item.structurelib.frontRotationTool.desc.0=可以旋转/翻转多方块主机
|
||||
item.structurelib.frontRotationTool.desc.1=旋转/翻转多方块主机时,会
|
||||
item.structurelib.frontRotationTool.desc.2=带动机器结构一起旋转/翻转。
|
||||
|
||||
item.structurelib.constructableTrigger.name=多方块机器蓝图 (StructureLib)
|
||||
item.structurelib.constructableTrigger.desc.0=可以显示多方块机器的结构
|
||||
item.structurelib.constructableTrigger.desc.1=只能在多方块主机上使用,将会显示机器
|
||||
item.structurelib.constructableTrigger.desc.2=结构的细节。 (译者注:请搭高使用)
|
||||
item.structurelib.constructableTrigger.desc.3= (创造模式下潜行右键可以直接完成搭建)
|
||||
item.structurelib.constructableTrigger.desc.4=手中蓝图数量会影响显示的机器等级/模式/类型
|
||||
|
||||
structurelib.blockhint.desc.0=帮助你搭建机器
|
||||
structurelib.blockhint.0.name=提示方块:1号
|
||||
structurelib.blockhint.1.name=提示方块:2号
|
||||
structurelib.blockhint.2.name=提示方块:3号
|
||||
structurelib.blockhint.3.name=提示方块:4号
|
||||
structurelib.blockhint.4.name=提示方块:5号
|
||||
structurelib.blockhint.5.name=提示方块:6号
|
||||
structurelib.blockhint.6.name=提示方块:7号
|
||||
structurelib.blockhint.7.name=提示方块:8号
|
||||
structurelib.blockhint.8.name=提示方块:9号
|
||||
structurelib.blockhint.9.name=提示方块:10号
|
||||
structurelib.blockhint.10.name=提示方块:11号
|
||||
structurelib.blockhint.11.name=提示方块:12号
|
||||
structurelib.blockhint.desc.1=特定方块们的占位符。
|
||||
structurelib.blockhint.12.name=提示方块:一般
|
||||
structurelib.blockhint.desc.2=一般通用占位符。
|
||||
structurelib.blockhint.13.name=提示方块:空气
|
||||
structurelib.blockhint.desc.3=确保这里是空气方块。
|
||||
structurelib.blockhint.14.name=提示方块:非空气
|
||||
structurelib.blockhint.desc.4=确保这里不是空气方块。
|
||||
structurelib.blockhint.15.name=提示方块:错误
|
||||
structurelib.blockhint.desc.5=ERROR,你想要做什么?
|
||||
itemGroup.structurelib=StructureLib
|
||||
Binary file not shown.
|
After Width: | Height: | Size: 667 B |
Reference in new issue
Block a user