mirror of
https://github.com/GTNewHorizons/StructureLib.git
synced 2026-11-09 15:04:56 +00:00
Compare commits
3
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
95d1533342 | ||
|
|
19179ec894 | ||
|
|
d8b301457f |
No files matched your search
@@ -5,6 +5,7 @@ import static com.gtnewhorizon.structurelib.StructureLib.PANIC_MODE;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
import java.util.function.Consumer;
|
||||
import java.util.function.Predicate;
|
||||
|
||||
@@ -42,6 +43,30 @@ public interface IStructureElement<T> {
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns a human-readable description of what block(s) this element accepts. Used for diagnostic messages when
|
||||
* structure checks fail (e.g. "expected Input Bus at (1, 2, 3)").
|
||||
* <p>
|
||||
* Unlike {@link #getBlocksToPlace}, which returns the full set of concrete block variants for autoplacing (e.g.
|
||||
* every tier of Input Bus), this method returns <b>category-level</b> descriptions suitable for display to the
|
||||
* player (e.g. just "Input Bus"). It also requires no parameters, no world, trigger item, or environment, making it
|
||||
* usable in contexts where those are unavailable.
|
||||
* <p>
|
||||
* Implementations should return <b>lang keys</b> (e.g. {@code "tile.blockGlass.name"}) rather than pre-translated
|
||||
* display names. The caller is responsible for translating these keys on the client side via
|
||||
* {@code StatCollector.translateToLocal()}. If a key has no matching translation, {@code translateToLocal} returns
|
||||
* the input string unchanged, so pre-translated fallback strings also work.
|
||||
*
|
||||
* @param context the context object (e.g. the multiblock controller), used to determine state-dependent
|
||||
* descriptions
|
||||
* @return a list of accepted block descriptions as lang keys (or display names as fallback), or null if no
|
||||
* description is available
|
||||
*/
|
||||
@Nullable
|
||||
default List<String> getDescription(T context) {
|
||||
return null;
|
||||
}
|
||||
|
||||
boolean spawnHint(T t, World world, int x, int y, int z, ItemStack trigger);
|
||||
|
||||
boolean placeBlock(T t, World world, int x, int y, int z, ItemStack trigger);
|
||||
@@ -204,6 +229,12 @@ public interface IStructureElement<T> {
|
||||
public boolean spawnHint(T t, World world, int x, int y, int z, ItemStack trigger) {
|
||||
return IStructureElement.this.spawnHint(t, world, x, y, z, trigger);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public List<String> getDescription(T context) {
|
||||
return IStructureElement.this.getDescription(context);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
@@ -1,7 +1,9 @@
|
||||
package com.gtnewhorizon.structurelib.structure;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.LinkedHashSet;
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
import java.util.function.Consumer;
|
||||
import java.util.function.Predicate;
|
||||
|
||||
@@ -61,6 +63,19 @@ public interface IStructureElementChain<T> extends IStructureElement<T> {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
default List<String> getDescription(T context) {
|
||||
Set<String> descriptions = new LinkedHashSet<>();
|
||||
for (IStructureElement<T> fallback : fallbacks()) {
|
||||
List<String> desc = fallback.getDescription(context);
|
||||
if (desc != null) {
|
||||
descriptions.addAll(desc);
|
||||
}
|
||||
}
|
||||
return descriptions.isEmpty() ? null : new ArrayList<>(descriptions);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
default BlocksToPlace getBlocksToPlace(T t, World world, int x, int y, int z, ItemStack trigger,
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
package com.gtnewhorizon.structurelib.structure;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.function.Consumer;
|
||||
import java.util.function.Function;
|
||||
|
||||
@@ -65,4 +66,10 @@ class LazyStructureElement<T> implements IStructureElementDeferred<T> {
|
||||
AutoPlaceEnvironment env) {
|
||||
return get(t).survivalPlaceBlock(t, world, x, y, z, trigger, env);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public List<String> getDescription(T context) {
|
||||
return elem != null ? elem.getDescription(context) : null;
|
||||
}
|
||||
}
|
||||
@@ -707,6 +707,29 @@ public class StructureUtility {
|
||||
public static <T, TIER> IStructureElement<T> ofBlocksTiered(ITierConverter<TIER> tierExtractor,
|
||||
@Nullable List<Pair<Block, Integer>> allKnownTiers, @Nullable TIER notSet, BiConsumer<T, TIER> setter,
|
||||
Function<T, TIER> getter) {
|
||||
List<String> descriptions = null;
|
||||
if (allKnownTiers != null) {
|
||||
descriptions = new java.util.ArrayList<>();
|
||||
for (Pair<Block, Integer> tier : allKnownTiers) {
|
||||
Item item = Item.getItemFromBlock(tier.getLeft());
|
||||
if (item != null) {
|
||||
descriptions.add(new ItemStack(item, 1, tier.getRight()).getUnlocalizedName() + ".name");
|
||||
}
|
||||
}
|
||||
}
|
||||
return ofBlocksTiered(tierExtractor, allKnownTiers, notSet, setter, getter, descriptions);
|
||||
}
|
||||
|
||||
/**
|
||||
* Like {@link #ofBlocksTiered(ITierConverter, List, Object, BiConsumer, Function)}, but with an explicit
|
||||
* description that will be returned by {@link IStructureElement#getDescription(Object)}.
|
||||
*
|
||||
* @param description the description lang keys to attach to this element, or null for no description
|
||||
* @see #ofBlocksTiered(ITierConverter, List, Object, BiConsumer, Function)
|
||||
*/
|
||||
public static <T, TIER> IStructureElement<T> ofBlocksTiered(ITierConverter<TIER> tierExtractor,
|
||||
@Nullable List<Pair<Block, Integer>> allKnownTiers, @Nullable TIER notSet, BiConsumer<T, TIER> setter,
|
||||
Function<T, TIER> getter, @Nullable List<String> description) {
|
||||
List<Pair<Block, Integer>> hints = allKnownTiers == null ? Collections.emptyList() : allKnownTiers;
|
||||
if (hints.stream().anyMatch(Objects::isNull)) throw new IllegalArgumentException();
|
||||
IStructureElementCheckOnly<T> check = ofBlocksTiered(tierExtractor, notSet, setter, getter);
|
||||
@@ -785,6 +808,24 @@ public class StructureUtility {
|
||||
env.getActor(),
|
||||
env.getChatter());
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public List<String> getDescription(T context) {
|
||||
TIER currentTier = getter.apply(context);
|
||||
if (Objects.equals(currentTier, notSet)) return description;
|
||||
|
||||
for (Pair<Block, Integer> pair : hints) {
|
||||
TIER pairTier = tierExtractor.convert(pair.getKey(), pair.getValue());
|
||||
if (!Objects.equals(pairTier, currentTier)) continue;
|
||||
Item item = Item.getItemFromBlock(pair.getKey());
|
||||
if (item == null) continue;
|
||||
return Collections
|
||||
.singletonList(new ItemStack(item, 1, pair.getValue()).getUnlocalizedName() + ".name");
|
||||
}
|
||||
return description;
|
||||
}
|
||||
|
||||
};
|
||||
}
|
||||
|
||||
@@ -1408,6 +1449,14 @@ public class StructureUtility {
|
||||
AutoPlaceEnvironment env) {
|
||||
return BlocksToPlace.create(block, meta);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public List<String> getDescription(T context) {
|
||||
Item item = Item.getItemFromBlock(block);
|
||||
if (item == null) return null;
|
||||
return Collections.singletonList(new ItemStack(item, 1, meta).getUnlocalizedName() + ".name");
|
||||
}
|
||||
};
|
||||
} else {
|
||||
return new IStructureElement<T>() {
|
||||
@@ -1487,6 +1536,14 @@ public class StructureUtility {
|
||||
AutoPlaceEnvironment env) {
|
||||
return BlocksToPlace.create(block, meta);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public List<String> getDescription(T context) {
|
||||
Item item = Item.getItemFromBlock(block);
|
||||
if (item == null) return null;
|
||||
return Collections.singletonList(new ItemStack(item, 1, meta).getUnlocalizedName() + ".name");
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -1529,6 +1586,14 @@ public class StructureUtility {
|
||||
// there is getSubItems on ItemBlock, but it's client only
|
||||
return BlocksToPlace.create(defaultBlock, defaultMeta);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public List<String> getDescription(T context) {
|
||||
Item item = Item.getItemFromBlock(block);
|
||||
if (item == null) return null;
|
||||
return Collections.singletonList(new ItemStack(item, 1, 0).getUnlocalizedName() + ".name");
|
||||
}
|
||||
};
|
||||
} else {
|
||||
return new IStructureElement<T>() {
|
||||
@@ -1561,6 +1626,14 @@ public class StructureUtility {
|
||||
// there is getSubItems on ItemBlock, but it's client only
|
||||
return BlocksToPlace.create(defaultBlock, defaultMeta);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public List<String> getDescription(T context) {
|
||||
Item item = Item.getItemFromBlock(block);
|
||||
if (item == null) return null;
|
||||
return Collections.singletonList(new ItemStack(item, 1, 0).getUnlocalizedName() + ".name");
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -1824,6 +1897,71 @@ public class StructureUtility {
|
||||
AutoPlaceEnvironment env) {
|
||||
return element.survivalPlaceBlock(t, world, x, y, z, trigger, env);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public List<String> getDescription(T context) {
|
||||
return element.getDescription(context);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Wraps an element and overrides its description. Useful for providing human-readable names to elements whose
|
||||
* underlying implementation doesn't provide a description (e.g. tiered block elements).
|
||||
*
|
||||
* @param description the description to use, or null to clear any existing description
|
||||
* @param element the element to wrap
|
||||
*/
|
||||
public static <B extends IStructureElement<T>, T> IStructureElement<T> withDescription(
|
||||
@Nullable List<String> description, B element) {
|
||||
return new IStructureElement<T>() {
|
||||
|
||||
@Override
|
||||
public boolean check(T t, World world, int x, int y, int z) {
|
||||
return element.check(t, world, x, y, z);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean couldBeValid(T t, World world, int x, int y, int z, ItemStack trigger) {
|
||||
return element.couldBeValid(t, world, x, y, z, trigger);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean placeBlock(T t, World world, int x, int y, int z, ItemStack trigger) {
|
||||
return element.placeBlock(t, world, x, y, z, trigger);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean spawnHint(T t, World world, int x, int y, int z, ItemStack trigger) {
|
||||
return element.spawnHint(t, world, x, y, z, trigger);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public BlocksToPlace getBlocksToPlace(T t, World world, int x, int y, int z, ItemStack trigger,
|
||||
AutoPlaceEnvironment env) {
|
||||
return element.getBlocksToPlace(t, world, x, y, z, trigger, env);
|
||||
}
|
||||
|
||||
@Override
|
||||
@Deprecated
|
||||
public PlaceResult survivalPlaceBlock(T t, World world, int x, int y, int z, ItemStack trigger,
|
||||
IItemSource s, EntityPlayerMP actor, Consumer<IChatComponent> chatter) {
|
||||
return element.survivalPlaceBlock(t, world, x, y, z, trigger, s, actor, chatter);
|
||||
}
|
||||
|
||||
@Override
|
||||
public PlaceResult survivalPlaceBlock(T t, World world, int x, int y, int z, ItemStack trigger,
|
||||
AutoPlaceEnvironment env) {
|
||||
return element.survivalPlaceBlock(t, world, x, y, z, trigger, env);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public List<String> getDescription(T context) {
|
||||
return description;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
@@ -1880,6 +2018,12 @@ public class StructureUtility {
|
||||
AutoPlaceEnvironment env) {
|
||||
return element.survivalPlaceBlock(t, world, x, y, z, trigger, env);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public List<String> getDescription(T context) {
|
||||
return element.getDescription(context);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
@@ -1949,6 +2093,12 @@ public class StructureUtility {
|
||||
if (predicate.test(t)) return downstream.survivalPlaceBlock(t, world, x, y, z, trigger, env);
|
||||
return placeResultWhenDisabled;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public List<String> getDescription(T context) {
|
||||
return downstream.getDescription(context);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
@@ -2046,6 +2196,12 @@ public class StructureUtility {
|
||||
AutoPlaceEnvironment env) {
|
||||
return elem.survivalPlaceBlock(t.getCurrentContext(), world, x, y, z, trigger, env);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public List<String> getDescription(T context) {
|
||||
return elem.getDescription(context.getCurrentContext());
|
||||
}
|
||||
};
|
||||
}
|
||||
// endregion
|
||||
@@ -2883,6 +3039,12 @@ public class StructureUtility {
|
||||
warnNoExplicitSubChannel(env.getActor());
|
||||
return backing.survivalPlaceBlock(t, world, x, y, z, newTrigger, env);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public List<String> getDescription(T context) {
|
||||
return backing.getDescription(context);
|
||||
}
|
||||
};
|
||||
}
|
||||
// endregion
|
||||
|
||||
Reference in new issue
Block a user