package pneumaticCraft.client.render.pneumaticArmor; import java.util.ArrayList; import java.util.List; import net.minecraft.block.Block; import net.minecraft.client.gui.FontRenderer; import net.minecraft.client.renderer.entity.RenderManager; import net.minecraft.client.resources.I18n; import net.minecraft.entity.Entity; import net.minecraft.entity.player.EntityPlayer; import net.minecraft.inventory.IInventory; import net.minecraft.item.ItemStack; import net.minecraft.tileentity.TileEntity; import net.minecraft.util.Vec3; import net.minecraft.world.World; import net.minecraftforge.client.event.MouseEvent; import org.lwjgl.opengl.GL11; import pneumaticCraft.api.client.pneumaticHelmet.IBlockTrackEntry; import pneumaticCraft.api.client.pneumaticHelmet.IHackableBlock; import pneumaticCraft.client.gui.widget.GuiAnimatedStat; import pneumaticCraft.client.render.RenderProgressBar; import pneumaticCraft.client.render.pneumaticArmor.blockTracker.BlockTrackEntryInventory; import pneumaticCraft.client.render.pneumaticArmor.blockTracker.BlockTrackEntryList; import pneumaticCraft.client.render.pneumaticArmor.hacking.HackableHandler; import pneumaticCraft.common.CommonHUDHandler; import pneumaticCraft.common.network.NetworkHandler; import pneumaticCraft.common.network.PacketDescriptionPacketRequest; import pneumaticCraft.common.network.PacketHackingBlockStart; import cpw.mods.fml.client.FMLClientHandler; public class RenderBlockTarget{ private final World world; private final int blockX; private final int blockY; private final int blockZ; private final RenderBlockArrows arrowRenderer = new RenderBlockArrows(); public int ticksExisted = 0; public final GuiAnimatedStat stat; private final EntityPlayer player; private boolean playerIsLooking; public List<String> textList = new ArrayList<String>(); private int hackTime; private final BlockTrackUpgradeHandler blockTracker; private TileEntity te; public RenderBlockTarget(World world, EntityPlayer player, int x, int y, int z, TileEntity te, BlockTrackUpgradeHandler blockTracker){ this.world = world; this.player = player; blockX = x; blockY = y; blockZ = z; this.te = te; this.blockTracker = blockTracker; // oldTicksExisted = entity.ticksExisted; String title = world.getBlock(x, y, z).getLocalizedName(); if(title.contains(".name")) { try { ItemStack stack = world.getBlock(x, y, z).getPickBlock(FMLClientHandler.instance().getClient().objectMouseOver, world, x, y, z, FMLClientHandler.instance().getClientPlayerEntity()); if(stack != null) title = stack.getDisplayName(); } catch(Throwable e) {} } if(title.contains(".name")) { if(te instanceof IInventory) { try { title = I18n.format(((IInventory)te).getInventoryName()); } catch(Throwable e) { BlockTrackEntryInventory.addTileEntityToBlackList(te, e); } } } stat = new GuiAnimatedStat(null, title, "", 20, -20, 0x3000AA00, null, false); stat.setMinDimensionsAndReset(0, 0); } public void setTileEntity(TileEntity te){ this.te = te; } public boolean isTargetStillValid(){ return getApplicableEntries().size() > 0; } public List<IBlockTrackEntry> getApplicableEntries(){ return BlockTrackEntryList.instance.getEntriesForCoordinate(world, blockX, blockY, blockZ, te); } public boolean isSameTarget(World world, int x, int y, int z){ return blockX == x && blockY == y && blockZ == z; } public Block getBlock(){ return world.getBlock(blockX, blockY, blockZ); } public double getDistanceToEntity(Entity entity){ return entity.getDistance(blockX + 0.5D, blockY + 0.5D, blockZ + 0.5D); } public void update(){ if(te != null && te.isInvalid()) te = null; stat.update(); List<IBlockTrackEntry> applicableTrackEntries = getApplicableEntries(); if(CommonHUDHandler.getHandlerForPlayer().ticksExisted % 100 == 0) { boolean sentUpdate = false; for(IBlockTrackEntry entry : applicableTrackEntries) { if(entry.shouldBeUpdatedFromServer(te)) { if(!sentUpdate) { NetworkHandler.sendToServer(new PacketDescriptionPacketRequest(blockX, blockY, blockZ)); sentUpdate = true; } } } } playerIsLooking = isPlayerLookingAtTarget(); arrowRenderer.ticksExisted++; if(!getBlock().isAir(world, blockX, blockY, blockZ)) { textList = new ArrayList<String>(); if(ticksExisted > 120) { stat.closeWindow(); for(IBlockTrackEntry entry : applicableTrackEntries) { if(blockTracker.countBlockTrackersOfType(entry) <= entry.spamThreshold()) { stat.openWindow(); break; } } if(playerIsLooking) { stat.openWindow(); addBlockTrackInfo(textList); } stat.setText(textList); } else if(ticksExisted < -30) { stat.closeWindow(); stat.setText(textList); } } if(hackTime > 0) { IHackableBlock hackableBlock = HackableHandler.getHackableForCoord(world, blockX, blockY, blockZ, player); if(hackableBlock != null) { hackTime++;// = Math.min(hackTime + 1, hackableBlock.getHackTime(world, blockX, blockY, blockZ, player)); } else { hackTime = 0; } } } public void render(float partialTicks){ double x = blockX + 0.5D; double y = blockY + 0.5D; double z = blockZ + 0.5D; GL11.glDisable(GL11.GL_TEXTURE_2D); GL11.glPushMatrix(); GL11.glClear(GL11.GL_DEPTH_BUFFER_BIT); float red = 0.5F; float green = 0.5F; float blue = 1.0F; float alpha = 0.5F; GL11.glTranslated(x, y, z); // for some reason the blend function resets... that's why this line is // here. GL11.glEnable(GL11.GL_BLEND); GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA); if(!getBlock().isAir(world, blockX, blockY, blockZ)) arrowRenderer.render(world, blockX, blockY, blockZ, partialTicks); int targetAcquireProgress = (int)((ticksExisted - 50) / 0.7F); GL11.glRotatef(180.0F - RenderManager.instance.playerViewY, 0.0F, 1.0F, 0.0F); GL11.glRotatef(180.0F - RenderManager.instance.playerViewX, 1.0F, 0.0F, 0.0F); if(ticksExisted <= 120 && ticksExisted > 50) { GL11.glColor4d(0, 1, 0, 0.8D); RenderProgressBar.render(0D, 0.4D, 1.8D, 0.9D, 0, targetAcquireProgress); } GL11.glEnable(GL11.GL_TEXTURE_2D); if(!getBlock().isAir(world, blockX, blockY, blockZ)) { FontRenderer fontRenderer = RenderManager.instance.getFontRenderer(); GL11.glColor4d(red, green, blue, alpha); if(ticksExisted > 120) { GL11.glScaled(0.02D, 0.02D, 0.02D); stat.render(-1, -1, partialTicks); } else if(ticksExisted > 50) { GL11.glScaled(0.02D, 0.02D, 0.02D); fontRenderer.drawString("Acquiring Target...", 0, 0, 0x7F7F7F); fontRenderer.drawString(targetAcquireProgress + "%", 37, 28, 0x002F00); } else if(ticksExisted < -30) { GL11.glScaled(0.03D, 0.03D, 0.03D); stat.render(-1, -1, partialTicks); fontRenderer.drawString("Lost Target!", 0, 0, 0xFF0000); } } GL11.glPopMatrix(); } public boolean isInitialized(){ return ticksExisted >= 120; } public void addBlockTrackInfo(List<String> textList){ for(IBlockTrackEntry blockTrackEntry : getApplicableEntries()) blockTrackEntry.addInformation(world, blockX, blockY, blockZ, te, textList); } public boolean isPlayerLooking(){ return playerIsLooking; } private boolean isPlayerLookingAtTarget(){ Vec3 vec3 = player.getLook(1.0F).normalize(); Vec3 vec31 = Vec3.createVectorHelper(blockX + 0.5D - player.posX, blockY + 0.5D - player.posY + player.getEyeHeight(), blockZ + 0.5D - player.posZ); double d0 = vec31.lengthVector(); vec31 = vec31.normalize(); double d1 = vec3.dotProduct(vec31); return d1 > 1.0D - 0.025D / d0; } public void hack(){ if(isInitialized() && isPlayerLookingAtTarget()) { IHackableBlock block = HackableHandler.getHackableForCoord(world, blockX, blockY, blockZ, player); if(block != null && (hackTime == 0 || hackTime > block.getHackTime(world, blockX, blockY, blockZ, player))) NetworkHandler.sendToServer(new PacketHackingBlockStart(blockX, blockY, blockZ)); } } public void onHackConfirmServer(){ hackTime = 1; } public int getHackTime(){ return hackTime; } public boolean scroll(MouseEvent event){ if(isInitialized() && isPlayerLookingAtTarget()) { return stat.handleMouseWheel(event.dwheel); } return false; } }