Merge branch '1.12.2' into 4.3-dev

This commit is contained in:
Electroblob77
2020-03-25 14:29:53 +00:00
31 changed files with 175 additions and 116 deletions
@@ -94,7 +94,7 @@ public final class Settings {
/** <b>[Server-only]</b> List of dimension ids in which to generate wizard towers. */
public int[] towerDimensions = {0};
/** <b>[Server-only]</b> The rarity of wizard towers, used by the world generator. Larger numbers are rarer. */
public int towerRarity = 900;
public int towerRarity = 700;
/** <b>[Server-only]</b> List of structure file locations for wizard towers without loot chests. */
public ResourceLocation[] towerFiles = {new ResourceLocation(Wizardry.MODID, "wizard_tower_0"),
new ResourceLocation(Wizardry.MODID, "wizard_tower_1"),
@@ -108,7 +108,7 @@ public final class Settings {
/** <b>[Server-only]</b> List of dimension ids in which to generate obelisks. */
public int[] obeliskDimensions = {0, -1};
/** <b>[Server-only]</b> The rarity of obelisks, used by the world generator. Larger numbers are rarer. */
public int obeliskRarity = 800;
public int obeliskRarity = 600;
/** <b>[Server-only]</b> List of structure file locations for obelisks. */
public ResourceLocation[] obeliskFiles = {new ResourceLocation(Wizardry.MODID, "obelisk_0"),
new ResourceLocation(Wizardry.MODID, "obelisk_1"),
@@ -118,7 +118,7 @@ public final class Settings {
/** <b>[Server-only]</b> List of dimension ids in which to generate shrines. */
public int[] shrineDimensions = {0, -1};
/** <b>[Server-only]</b> The rarity of shrines, used by the world generator. Larger numbers are rarer. */
public int shrineRarity = 1500;
public int shrineRarity = 1100;
/** <b>[Server-only]</b> List of structure file locations for shrines. */
public ResourceLocation[] shrineFiles = {new ResourceLocation(Wizardry.MODID, "shrine_0"),
new ResourceLocation(Wizardry.MODID, "shrine_1"),
@@ -168,8 +168,6 @@ public final class Settings {
public boolean playerBlockDamage = true;
/** <b>[Server-only]</b> Whether to revert to the old wand upgrade system, which only requires tomes of arcana. */
public boolean legacyWandLevelling = false;
/** <b>[Server-only]</b> Whether to replace Minecraft's own fireballs with wizardry fireballs. */
public boolean replaceVanillaFireballs = true;
/** <b>[Server-only]</b> Whether to replace Minecraft's distance-based fall damage calculation with an equivalent,
* velocity-based one. */
public boolean replaceVanillaFallDamage = true;
@@ -272,7 +270,9 @@ public final class Settings {
* effect.
*/
public boolean slowTimeAffectsPlayers = true;
/** <b>[Synchronised]</b> Chance of 'misreading' an undiscovered spell and triggering a forfeit instead. */
/** <b>[Synchronised]</b> Whether to replace Minecraft's own fireballs with wizardry fireballs. */
public boolean replaceVanillaFireballs = true;
/** <b>[Synchronised]</b> Chance of 'misreading' an undiscovered spell and triggering a forfeit instead. */
public double forfeitChance = 0.2;
// Client-only settings. These settings only affect client-side code and hence are not synced. Each client obeys
@@ -46,7 +46,7 @@ import java.util.Calendar;
*/
@Mod(modid = Wizardry.MODID, name = Wizardry.NAME, version = Wizardry.VERSION, acceptedMinecraftVersions = "[1.12.2]",
guiFactory = "electroblob.wizardry.WizardryGuiFactory", dependencies = "required-after:forge@[14.23.5.2814,)")
guiFactory = "electroblob.wizardry.WizardryGuiFactory", dependencies = "required-after:forge@[14.23.5.2814,);after:antiqueatlas@[4.6,)")
public class Wizardry {
@@ -64,7 +64,7 @@ public class Wizardry {
* 1.x.x represents Minecraft 1.7.x versions, 2.x.x represents Minecraft 1.10.x versions, 3.x.x represents Minecraft
* 1.11.x versions, and so on.
*/
public static final String VERSION = "4.2.9";
public static final String VERSION = "4.2.10";
// IDEA: Triggering of inbuilt Forge events in relevant places?
// IDEA: Abstract the vanilla particles behind the particle builder
@@ -420,7 +420,7 @@ public final class WizardryEventHandler {
@SubscribeEvent // Priority doesn't matter here, we're only setting event fields so if it's cancelled it won't matter
public static void onLivingFallEvent(LivingFallEvent event){
// Why is fall damage based on distance fallen? Why? Who on earth came up with that? It makes no sense whatsoever!
if(Wizardry.settings.replaceVanillaFallDamage && !Loader.isModLoaded("speedbasedfalldamage")){
if(!event.getEntity().world.isRemote && Wizardry.settings.replaceVanillaFallDamage && !Loader.isModLoaded("speedbasedfalldamage")){
// We want to keep the fall damage EXACTLY THE SAME for free, uninterrupted falls, but fix the weirdness
// caused when something else changes the entity's velocity
// All living entities have a gravity of 0.08b/t^2
@@ -13,6 +13,7 @@ import net.minecraft.client.Minecraft;
import net.minecraft.client.audio.PositionedSoundRecord;
import net.minecraft.client.gui.GuiScreen;
import net.minecraft.client.renderer.GlStateManager;
import net.minecraft.client.resources.I18n;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.item.ItemStack;
import org.lwjgl.input.Keyboard;
@@ -32,9 +33,7 @@ public class GuiSpellBook extends GuiScreen {
this.spell = Spell.byMetadata(stack.getItemDamage());
}
/**
* Draws the screen and all the components in it.
*/
@Override
public void drawScreen(int par1, int par2, float par3){
int xPos = this.width / 2 - xSize / 2;
@@ -69,22 +68,18 @@ public class GuiSpellBook extends GuiScreen {
0x777777);
}
//this.fontRenderer.drawString("-------------------", xPos + 17, yPos + 35, 0);
// Novice is usually white but this doesn't show up
String tier = I18n.format("gui.ebwizardry:spell_book.tier", spell.getTier() == Tier.NOVICE ?
"\u00A77" + spell.getTier().getDisplayName() : spell.getTier().getDisplayNameWithFormatting());
this.fontRenderer.drawString(tier, xPos + 17, yPos + 45, 0);
if(spell.getTier() == Tier.NOVICE){
// Novice is usually white but this doesn't show up.
this.fontRenderer.drawString("Tier: \u00A77" + Tier.NOVICE.getDisplayName(), xPos + 17, yPos + 45, 0);
}else{
this.fontRenderer.drawString("Tier: " + spell.getTier().getDisplayNameWithFormatting(), xPos + 17, yPos + 45, 0);
}
String element = "Element: " + spell.getElement().getFormattingCode() + spell.getElement().getDisplayName();
if(!discovered) element = "Element: ?";
String element = I18n.format("gui.ebwizardry:spell_book.element", spell.getElement().getFormattingCode() + spell.getElement().getDisplayName());
if(!discovered) element = I18n.format("gui.ebwizardry:spell_book.element_undiscovered");
this.fontRenderer.drawString(element, xPos + 17, yPos + 57, 0);
String manaCost = "Mana Cost: " + spell.getCost();
if(spell.isContinuous) manaCost = "Mana Cost: " + spell.getCost() + "/second";
if(!discovered) manaCost = "Mana Cost: ?";
String manaCost = I18n.format("gui.ebwizardry:spell_book.mana_cost", spell.getCost());
if(spell.isContinuous) manaCost = I18n.format("gui.ebwizardry:spell_book.mana_cost_continuous", spell.getCost());
if(!discovered) manaCost = I18n.format("gui.ebwizardry:spell_book.mana_cost_undiscovered");
this.fontRenderer.drawString(manaCost, xPos + 17, yPos + 69, 0);
if(discovered){
@@ -95,6 +90,7 @@ public class GuiSpellBook extends GuiScreen {
}
}
@Override
public void initGui(){
super.initGui();
Keyboard.enableRepeatEvents(true);
@@ -103,6 +99,7 @@ public class GuiSpellBook extends GuiScreen {
this.mc.getSoundHandler().playSound(PositionedSoundRecord.getMasterRecord(WizardrySounds.MISC_BOOK_OPEN, 1));
}
@Override
public void onGuiClosed(){
super.onGuiClosed();
Keyboard.enableRepeatEvents(false);
@@ -68,7 +68,7 @@ public class EnchantmentMagicProtection extends Enchantment {
public enum Type {
MAGIC("magic", 1, 5, 8, s -> s instanceof IElementalDamage),
MAGIC("magic", 1, 5, 8, s -> s instanceof IElementalDamage || s.isMagicDamage()),
FROST("frost", 2, 10, 8, s -> s instanceof IElementalDamage && ((IElementalDamage)s).getType() == MagicDamage.DamageType.FROST),
SHOCK("shock", 2, 10, 8, s -> s instanceof IElementalDamage && ((IElementalDamage)s).getType() == MagicDamage.DamageType.SHOCK);
// Fire already exists, and the other types aren't used enough to be worth having
@@ -10,6 +10,7 @@ import electroblob.wizardry.util.WizardryUtilities;
import net.minecraft.entity.EntityLivingBase;
import net.minecraft.entity.MoverType;
import net.minecraft.potion.PotionEffect;
import net.minecraft.util.DamageSource;
import net.minecraft.util.EnumFacing;
import net.minecraft.util.math.AxisAlignedBB;
import net.minecraft.util.math.Vec3d;
@@ -61,10 +62,9 @@ public class EntityIceSpike extends EntityMagicConstruct {
if(!this.world.isRemote){
for(Object entity : this.world.getEntitiesWithinAABBExcludingEntity(this, this.getEntityBoundingBox())){
if(entity instanceof EntityLivingBase && this.isValidTarget((EntityLivingBase)entity)){
DamageSource source = this.getCaster() == null ? DamageSource.MAGIC : MagicDamage.causeDirectMagicDamage(this.getCaster(), DamageType.FROST);
// Potion effect only gets added if the damage succeeded.
if(((EntityLivingBase)entity).attackEntityFrom(
MagicDamage.causeDirectMagicDamage(this.getCaster(), DamageType.FROST),
Spells.ice_spikes.getProperty(Spell.DAMAGE).floatValue() * this.damageMultiplier))
if(((EntityLivingBase)entity).attackEntityFrom(source, Spells.ice_spikes.getProperty(Spell.DAMAGE).floatValue() * this.damageMultiplier))
((EntityLivingBase)entity).addPotionEffect(new PotionEffect(WizardryPotions.frost,
Spells.ice_spikes.getProperty(Spell.EFFECT_DURATION).intValue(),
Spells.ice_spikes.getProperty(Spell.EFFECT_STRENGTH).intValue()));
@@ -503,7 +503,6 @@ public class EntityWizard extends EntityCreature implements INpc, IMerchant, ISp
ItemStack anySpellBook = new ItemStack(WizardryItems.spell_book, 1, OreDictionary.WILDCARD_VALUE);
ItemStack crystalStack = new ItemStack(WizardryItems.magic_crystal, 5);
// NOTE: For wizardry 1.2, increase the number of uses of this trade. The default is 7, for reference.
this.trades.add(new MerchantRecipe(anySpellBook, crystalStack));
this.addRandomRecipes(3);
@@ -9,7 +9,6 @@ import electroblob.wizardry.util.MagicDamage.DamageType;
import electroblob.wizardry.util.ParticleBuilder;
import electroblob.wizardry.util.WizardryUtilities;
import net.minecraft.entity.Entity;
import net.minecraft.entity.EntityLiving;
import net.minecraft.entity.EntityLivingBase;
import net.minecraft.init.Blocks;
import net.minecraft.potion.PotionEffect;
@@ -48,13 +47,7 @@ public class EntityIceball extends EntityMagicProjectile {
}else{
boolean flag = true;
if(this.getThrower() != null && this.getThrower() instanceof EntityLiving){
flag = net.minecraftforge.event.ForgeEventFactory.getMobGriefingEvent(this.world, this.getThrower());
}
if(flag){
if(this.getThrower() == null || WizardryUtilities.canDamageBlocks(this.getThrower(), world)){
BlockPos pos = rayTrace.getBlockPos();
@@ -3,6 +3,7 @@ package electroblob.wizardry.entity.projectile;
import electroblob.wizardry.Wizardry;
import electroblob.wizardry.registry.Spells;
import electroblob.wizardry.spell.Spell;
import electroblob.wizardry.util.WizardryUtilities;
import io.netty.buffer.ByteBuf;
import net.minecraft.entity.projectile.EntityLargeFireball;
import net.minecraft.nbt.NBTTagCompound;
@@ -50,7 +51,7 @@ public class EntityLargeMagicFireball extends EntityMagicFireball {
protected void onImpact(RayTraceResult rayTrace){
if(!world.isRemote){
boolean flag = net.minecraftforge.event.ForgeEventFactory.getMobGriefingEvent(this.world, this.thrower);
boolean flag = this.getThrower() == null || WizardryUtilities.canDamageBlocks(this.getThrower(), world);
this.world.newExplosion(null, this.posX, this.posY, this.posZ, getExplosionPower() * blastMultiplier, flag, flag);
}
@@ -6,9 +6,9 @@ import electroblob.wizardry.spell.Spell;
import electroblob.wizardry.util.MagicDamage;
import electroblob.wizardry.util.MagicDamage.DamageType;
import electroblob.wizardry.util.ParticleBuilder;
import electroblob.wizardry.util.WizardryUtilities;
import io.netty.buffer.ByteBuf;
import net.minecraft.entity.Entity;
import net.minecraft.entity.EntityLiving;
import net.minecraft.entity.EntityLivingBase;
import net.minecraft.entity.projectile.EntitySmallFireball;
import net.minecraft.init.Blocks;
@@ -84,13 +84,7 @@ public class EntityMagicFireball extends EntityMagicProjectile {
}else{
boolean flag = true;
if(this.getThrower() != null && this.getThrower() instanceof EntityLiving){
flag = net.minecraftforge.event.ForgeEventFactory.getMobGriefingEvent(this.world, this.getThrower());
}
if(flag){
if(this.getThrower() == null || WizardryUtilities.canDamageBlocks(this.getThrower(), world)){
BlockPos blockpos = rayTrace.getBlockPos().offset(rayTrace.sideHit);
@@ -1,11 +1,17 @@
package electroblob.wizardry.integration.antiqueatlas;
import electroblob.wizardry.Wizardry;
import hunternif.mc.atlas.AntiqueAtlasMod;
import hunternif.mc.atlas.api.AtlasAPI;
import hunternif.mc.atlas.marker.GlobalMarkersData;
import hunternif.mc.atlas.marker.Marker;
import hunternif.mc.atlas.registry.MarkerType;
import net.minecraft.util.ResourceLocation;
import net.minecraft.world.World;
import net.minecraftforge.event.world.WorldEvent;
import net.minecraftforge.fml.common.Loader;
import net.minecraftforge.fml.common.Mod;
import net.minecraftforge.fml.common.eventhandler.SubscribeEvent;
/**
* This class handles all of wizardry's integration with the <i>Antique Atlas</i> mod. This class contains only the code
@@ -15,6 +21,7 @@ import net.minecraftforge.fml.common.Loader;
* @since Wizardry 4.2
* @author Electroblob
*/
@Mod.EventBusSubscriber
public class WizardryAntiqueAtlasIntegration {
public static final String ANTIQUE_ATLAS_MOD_ID = "antiqueatlas";
@@ -38,7 +45,7 @@ public class WizardryAntiqueAtlasIntegration {
* {@link electroblob.wizardry.Settings#autoTowerMarkers} is enabled. Server side only! */
public static void markTower(World world, int x, int z){
if(enabled() && Wizardry.settings.autoTowerMarkers){
AtlasAPI.getMarkerAPI().putGlobalMarker(world, false, TOWER_MARKER.toString().replace(':', '.'), "integration.antiqueatlas.marker." + TOWER_MARKER.toString(), x, z);
AtlasAPI.getMarkerAPI().putGlobalMarker(world, false, TOWER_MARKER.toString(), "integration.antiqueatlas.marker." + TOWER_MARKER.toString().replace(':', '.'), x, z);
}
}
@@ -46,7 +53,7 @@ public class WizardryAntiqueAtlasIntegration {
* {@link electroblob.wizardry.Settings#autoObeliskMarkers} is enabled. Server side only! */
public static void markObelisk(World world, int x, int z){
if(enabled() && Wizardry.settings.autoObeliskMarkers){
AtlasAPI.getMarkerAPI().putGlobalMarker(world, false, OBELISK_MARKER.toString().replace(':', '.'), "integration.antiqueatlas.marker." + OBELISK_MARKER.toString(), x, z);
AtlasAPI.getMarkerAPI().putGlobalMarker(world, false, OBELISK_MARKER.toString(), "integration.antiqueatlas.marker." + OBELISK_MARKER.toString().replace(':', '.'), x, z);
}
}
@@ -54,7 +61,7 @@ public class WizardryAntiqueAtlasIntegration {
* {@link electroblob.wizardry.Settings#autoShrineMarkers} is enabled. Server side only! */
public static void markShrine(World world, int x, int z){
if(enabled() && Wizardry.settings.autoShrineMarkers){
AtlasAPI.getMarkerAPI().putGlobalMarker(world, false, SHRINE_MARKER.toString().replace(':', '.'), "integration.antiqueatlas.marker." + SHRINE_MARKER.toString(), x, z);
AtlasAPI.getMarkerAPI().putGlobalMarker(world, false, SHRINE_MARKER.toString(), "integration.antiqueatlas.marker." + SHRINE_MARKER.toString().replace(':', '.'), x, z);
}
}
@@ -68,4 +75,21 @@ public class WizardryAntiqueAtlasIntegration {
AtlasAPI.getMarkerAPI().registerMarker(new MarkerType(OBELISK_MARKER, new ResourceLocation(Wizardry.MODID, "textures/integration/antiqueatlas/obelisk.png")));
}
@SubscribeEvent
public static void onWorldLoadEvent(WorldEvent.Load event){
if(!enabled()) return;
// Backwards compatibility for existing markers using the old translation key format (with colons)
GlobalMarkersData data = AntiqueAtlasMod.globalMarkersData.getData();
for(Marker marker : data.getMarkersInDimension(event.getWorld().provider.getDimension())){
if(marker.getLabel().contains(":")){
// Remove old-format markers and replace them with new ones
data.removeMarker(marker.getId());
AtlasAPI.getMarkerAPI().putGlobalMarker(event.getWorld(), marker.isVisibleAhead(), marker.getType(),
marker.getLabel().replace(':', '.'), marker.getX(), marker.getZ());
}
}
}
}
@@ -1,8 +1,10 @@
package electroblob.wizardry.misc;
import electroblob.wizardry.util.WizardryUtilities;
import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.nbt.NBTUtil;
import net.minecraft.network.PacketBuffer;
import net.minecraft.village.MerchantRecipe;
import net.minecraft.village.MerchantRecipeList;
import net.minecraftforge.oredict.OreDictionary;
@@ -46,12 +48,42 @@ public class WildcardTradeList extends MerchantRecipeList {
}
private boolean areItemStacksExactlyEqual(ItemStack stack1, ItemStack stack2){
// Added to allow wildcards; this line is the only actual change.
// Added to allow wildcards
if((stack1.getItemDamage() == OreDictionary.WILDCARD_VALUE || stack2.getItemDamage() == OreDictionary.WILDCARD_VALUE)
// Can't use ItemStack.areItemsEqualIgnoreDurability because that only works for items with durability, not subtypes.
&& stack1.getItem() == stack2.getItem()) return true;
return ItemStack.areItemsEqual(stack1, stack2) && (!stack2.hasTagCompound() || stack1.hasTagCompound() && NBTUtil.areNBTEquals(stack2.getTagCompound(), stack1.getTagCompound(), false));
}
@Override
public void writeToBuf(PacketBuffer buffer){
buffer.writeByte((byte)(this.size() & 255));
// Trick the client into thinking this is a normal item
for(MerchantRecipe merchantrecipe : this){
ItemStack itemToBuy = merchantrecipe.getItemToBuy();
if(itemToBuy.getMetadata() == OreDictionary.WILDCARD_VALUE) itemToBuy = WizardryUtilities.copyWithMeta(itemToBuy, 0);
buffer.writeItemStack(itemToBuy);
ItemStack itemToSell = merchantrecipe.getItemToSell();
if(itemToSell.getMetadata() == OreDictionary.WILDCARD_VALUE) itemToSell = WizardryUtilities.copyWithMeta(itemToSell, 0);
buffer.writeItemStack(itemToSell);
ItemStack secondItemToBuy = merchantrecipe.getSecondItemToBuy();
buffer.writeBoolean(!secondItemToBuy.isEmpty());
if(!secondItemToBuy.isEmpty()){
if(secondItemToBuy.getMetadata() == OreDictionary.WILDCARD_VALUE) secondItemToBuy = WizardryUtilities.copyWithMeta(secondItemToBuy, 0);
buffer.writeItemStack(secondItemToBuy);
}
buffer.writeBoolean(merchantrecipe.isRecipeDisabled());
buffer.writeInt(merchantrecipe.getToolUses());
buffer.writeInt(merchantrecipe.getMaxTradeUses());
}
}
}
@@ -56,6 +56,7 @@ public class PacketSyncSettings implements IMessageHandler<Message, IMessage> {
settings.discoveryMode = buf.readBoolean();
settings.creativeBypassesArcaneLock = buf.readBoolean();
settings.slowTimeAffectsPlayers = buf.readBoolean();
settings.replaceVanillaFireballs = buf.readBoolean();
settings.forfeitChance = buf.readFloat();
}
@@ -64,6 +65,7 @@ public class PacketSyncSettings implements IMessageHandler<Message, IMessage> {
buf.writeBoolean(settings.discoveryMode);
buf.writeBoolean(settings.creativeBypassesArcaneLock);
buf.writeBoolean(settings.slowTimeAffectsPlayers);
buf.writeBoolean(settings.replaceVanillaFireballs);
buf.writeFloat((float)settings.forfeitChance); // Configs don't have floats but this can only be 0-1 anyway
}
}
@@ -4,6 +4,7 @@ import electroblob.wizardry.util.ParticleBuilder;
import electroblob.wizardry.util.SpellModifiers;
import electroblob.wizardry.util.WizardryUtilities;
import net.minecraft.entity.Entity;
import net.minecraft.entity.EntityLiving;
import net.minecraft.entity.EntityLivingBase;
import net.minecraft.item.EnumAction;
import net.minecraft.util.EnumFacing;
@@ -19,6 +20,11 @@ public class HealAlly extends SpellRay {
addProperties(HEALTH);
}
@Override
public boolean canBeCastBy(EntityLiving npc, boolean override){
return false;
}
@Override
protected boolean onEntityHit(World world, Entity target, Vec3d hit, EntityLivingBase caster, Vec3d origin, int ticksInUse, SpellModifiers modifiers){
@@ -201,6 +201,8 @@ public class Possession extends SpellRay {
*/
public boolean possess(EntityPlayer possessor, EntityLiving target, int duration){
if(possessor.isSneaking()) return false;
if(WizardData.get(possessor) != null){
WizardData.get(possessor).setVariable(POSSESSEE_KEY, target);
@@ -683,11 +685,13 @@ public class Possession extends SpellRay {
if(possessee != null){
if(possessee.canPickUpLoot() && possessee.getHeldItemMainhand().isEmpty()){
possessee.setHeldItem(EnumHand.MAIN_HAND, event.getItem().getItem());
}else{
event.setCanceled(true);
}
event.setCanceled(true);
// if(possessee.canPickUpLoot() && possessee.getHeldItemMainhand().isEmpty()){
// possessee.setHeldItem(EnumHand.MAIN_HAND, event.getItem().getItem());
// }else{
// event.setCanceled(true);
// }
}
}
@@ -24,6 +24,7 @@ import net.minecraft.inventory.EntityEquipmentSlot;
import net.minecraft.inventory.EntityEquipmentSlot.Type;
import net.minecraft.item.Item;
import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.network.datasync.DataParameter;
import net.minecraft.server.MinecraftServer;
import net.minecraft.util.*;
@@ -795,6 +796,20 @@ public final class WizardryUtilities {
return false;
}
/**
* Returns a new {@link ItemStack} that is identical to the supplied one, except with the metadata changed to the
* new value given.
* @param toCopy The stack to copy
* @param newMetadata The new metadata value
* @return The resulting {@link ItemStack}
*/
public static ItemStack copyWithMeta(ItemStack toCopy, int newMetadata){
ItemStack copy = new ItemStack(toCopy.getItem(), toCopy.getCount(), newMetadata);
NBTTagCompound compound = toCopy.getTagCompound();
if(compound != null) copy.setTagCompound(compound.copy());
return copy;
}
/**
* Checks if the given player is opped on the given server. If the server is a singleplayer or LAN server, this
* means they have cheats enabled.
@@ -144,6 +144,9 @@ public abstract class WorldGenSurfaceStructure implements IWorldGenerator {
// Estimate a starting height for searching for the floor
BlockPos centre = world.getTopSolidOrLiquidBlock(new BlockPos(origin.add(size.getX()/2, 0, size.getZ()/2)));
// Check if we're at the top of the world, and if so just randomise the y pos (accounts for 'cavern' dimensions)
if(centre.getY() >= world.getActualHeight()) centre = new BlockPos(centre.getX(), random.nextInt(world.getActualHeight()), centre.getZ());
Integer startingHeight = WizardryUtilities.getNearestSurface(world, centre, EnumFacing.UP, 32, true,
WizardryUtilities.SurfaceCriteria.COLLIDABLE_IGNORING_TREES);