diff --git a/src/main/java/eu/crushedpixel/replaymod/ReplayMod.java b/src/main/java/eu/crushedpixel/replaymod/ReplayMod.java index 4eef912f..e749e4df 100755 --- a/src/main/java/eu/crushedpixel/replaymod/ReplayMod.java +++ b/src/main/java/eu/crushedpixel/replaymod/ReplayMod.java @@ -10,10 +10,7 @@ import eu.crushedpixel.replaymod.localization.LocalizedResourcePack; import eu.crushedpixel.replaymod.online.authentication.AuthenticationHandler; import eu.crushedpixel.replaymod.recording.ConnectionEventHandler; import eu.crushedpixel.replaymod.registry.*; -import eu.crushedpixel.replaymod.renderer.InvisibilityRender; -import eu.crushedpixel.replaymod.renderer.PathPreviewRenderer; -import eu.crushedpixel.replaymod.renderer.SafeEntityRenderer; -import eu.crushedpixel.replaymod.renderer.SpectatorRenderer; +import eu.crushedpixel.replaymod.renderer.*; import eu.crushedpixel.replaymod.replay.ReplayHandler; import eu.crushedpixel.replaymod.replay.ReplayProcess; import eu.crushedpixel.replaymod.replay.ReplaySender; @@ -80,6 +77,7 @@ public class ReplayMod { public static SpectatorRenderer spectatorRenderer; public static TooltipRenderer tooltipRenderer; public static PathPreviewRenderer pathPreviewRenderer; + public static CustomObjectRenderer customObjectRenderer; public static SoundHandler soundHandler = new SoundHandler(); public static CrosshairRenderHandler crosshairRenderHandler; @@ -140,6 +138,10 @@ public class ReplayMod { FMLCommonHandler.instance().bus().register(pathPreviewRenderer); MinecraftForge.EVENT_BUS.register(pathPreviewRenderer); + customObjectRenderer = new CustomObjectRenderer(); + FMLCommonHandler.instance().bus().register(customObjectRenderer); + MinecraftForge.EVENT_BUS.register(customObjectRenderer); + crosshairRenderHandler = new CrosshairRenderHandler(); FMLCommonHandler.instance().bus().register(crosshairRenderHandler); MinecraftForge.EVENT_BUS.register(crosshairRenderHandler); @@ -182,7 +184,6 @@ public class ReplayMod { }, "localizedResourcePackLoader"); localizedResourcePackLoader.start(); - /* boolean auth = false; try { @@ -198,7 +199,6 @@ public class ReplayMod { } */ - if (System.getProperty("replaymod.render.file") != null) { final File file = new File(System.getProperty("replaymod.render.file")); if (!file.exists()) { diff --git a/src/main/java/eu/crushedpixel/replaymod/holders/CustomImageObject.java b/src/main/java/eu/crushedpixel/replaymod/holders/CustomImageObject.java new file mode 100644 index 00000000..057a1a34 --- /dev/null +++ b/src/main/java/eu/crushedpixel/replaymod/holders/CustomImageObject.java @@ -0,0 +1,57 @@ +package eu.crushedpixel.replaymod.holders; + +import eu.crushedpixel.replaymod.registry.ResourceHelper; +import lombok.Getter; +import net.minecraft.client.Minecraft; +import net.minecraft.client.renderer.texture.DynamicTexture; +import net.minecraft.util.ResourceLocation; + +import javax.imageio.ImageIO; +import java.awt.image.BufferedImage; +import java.io.File; +import java.io.IOException; + +public class CustomImageObject { + + public CustomImageObject(Position position, String name, File imageSource) throws IOException { + BufferedImage bufferedImage = ImageIO.read(imageSource); + + this.textureWidth = bufferedImage.getWidth(); + this.textureHeight = bufferedImage.getHeight(); + + float w; + float h; + + if(bufferedImage.getWidth() > bufferedImage.getHeight()) { + w = 1; + h = (bufferedImage.getHeight()/(float)bufferedImage.getWidth()); + } else { + w = (bufferedImage.getWidth()/(float)bufferedImage.getHeight()); + h = 1; + } + + this.position = new ExtendedPosition(position.getX(), position.getY(), position.getZ(), w, h); + this.name = name; + + this.resourceLocation = new ResourceLocation("customImages/"+imageSource.getAbsolutePath()); + this.dynamicTexture = new DynamicTexture(bufferedImage); + } + + @Getter private ExtendedPosition position; + @Getter private String name; + + private ResourceLocation resourceLocation; + private DynamicTexture dynamicTexture; + + @Getter private float textureWidth, textureHeight; + + public ResourceLocation getResourceLocation() { + if(!ResourceHelper.isRegistered(resourceLocation)) { + ResourceHelper.registerResource(resourceLocation); + Minecraft.getMinecraft().getTextureManager().loadTexture(resourceLocation, dynamicTexture); + dynamicTexture.updateDynamicTexture(); + } + + return resourceLocation; + } +} diff --git a/src/main/java/eu/crushedpixel/replaymod/holders/ExtendedPosition.java b/src/main/java/eu/crushedpixel/replaymod/holders/ExtendedPosition.java new file mode 100644 index 00000000..aeb95974 --- /dev/null +++ b/src/main/java/eu/crushedpixel/replaymod/holders/ExtendedPosition.java @@ -0,0 +1,18 @@ +package eu.crushedpixel.replaymod.holders; + +import lombok.Data; + +@Data +public class ExtendedPosition extends Position { + + public ExtendedPosition(double x, double y, double z, float width, float height) { + super(x, y, z, 0, 0); + this.width = width; + this.height = height; + } + + private float anchorX, anchorY; + private float width, height; + private float scale = 1f; + +} diff --git a/src/main/java/eu/crushedpixel/replaymod/registry/ResourceHelper.java b/src/main/java/eu/crushedpixel/replaymod/registry/ResourceHelper.java index ab1c7578..7532d4fd 100755 --- a/src/main/java/eu/crushedpixel/replaymod/registry/ResourceHelper.java +++ b/src/main/java/eu/crushedpixel/replaymod/registry/ResourceHelper.java @@ -23,7 +23,11 @@ public class ResourceHelper { } public static void registerResource(ResourceLocation loc) { - openResources.add(loc); + if(!openResources.contains(loc)) openResources.add(loc); + } + + public static boolean isRegistered(ResourceLocation loc) { + return openResources.contains(loc); } public static void freeResource(ResourceLocation loc) { diff --git a/src/main/java/eu/crushedpixel/replaymod/renderer/CustomObjectRenderer.java b/src/main/java/eu/crushedpixel/replaymod/renderer/CustomObjectRenderer.java new file mode 100644 index 00000000..76944372 --- /dev/null +++ b/src/main/java/eu/crushedpixel/replaymod/renderer/CustomObjectRenderer.java @@ -0,0 +1,112 @@ +package eu.crushedpixel.replaymod.renderer; + +import eu.crushedpixel.replaymod.holders.CustomImageObject; +import eu.crushedpixel.replaymod.holders.ExtendedPosition; +import eu.crushedpixel.replaymod.replay.ReplayHandler; +import net.minecraft.client.Minecraft; +import net.minecraft.client.renderer.GlStateManager; +import net.minecraft.client.renderer.Tessellator; +import net.minecraft.client.renderer.WorldRenderer; +import net.minecraft.entity.Entity; +import net.minecraftforge.client.event.RenderWorldLastEvent; +import net.minecraftforge.fml.common.eventhandler.SubscribeEvent; +import org.lwjgl.opengl.GL11; + +/** + * Allows users to render custom images in the World. + */ +public class CustomObjectRenderer { + + private static final Minecraft mc = Minecraft.getMinecraft(); + + @SubscribeEvent + public void renderCustomObjects(RenderWorldLastEvent event) { + if(!ReplayHandler.isInReplay()) return; + + Entity entity = ReplayHandler.getCameraEntity(); + if(entity == null) return; + + double doubleX = entity.posX; + double doubleY = entity.posY; + double doubleZ = entity.posZ; + + GlStateManager.pushAttrib(); + GlStateManager.pushMatrix(); + + GlStateManager.disableLighting(); + GlStateManager.enableBlend(); + + GlStateManager.disableTexture2D(); + + //do stuff here + for(CustomImageObject object : ReplayHandler.getCustomImageObjects()) { + drawCustomImageObject(doubleX, doubleY, doubleZ, object); + } + + GlStateManager.enableTexture2D(); + GlStateManager.enableLighting(); + + GlStateManager.disableBlend(); + GlStateManager.popAttrib(); + GlStateManager.popMatrix(); + } + + private void drawCustomImageObject(double playerX, double playerY, double playerZ, CustomImageObject customImageObject) { + GlStateManager.pushMatrix(); + GlStateManager.enableTexture2D(); + GlStateManager.enableLighting(); + GlStateManager.disableLighting(); + GlStateManager.enableAlpha(); + + GlStateManager.disableBlend(); + + Tessellator tessellator = Tessellator.getInstance(); + WorldRenderer renderer = tessellator.getWorldRenderer(); + + mc.renderEngine.bindTexture(customImageObject.getResourceLocation()); + + ExtendedPosition objectPosition = customImageObject.getPosition(); + + double x = objectPosition.getX() - playerX; + double y = objectPosition.getY() - playerY; + double z = objectPosition.getZ() - playerZ; + + GL11.glNormal3f(0, 1, 0); + + GlStateManager.translate(x, y + 1.4, z); + + GlStateManager.rotate(-objectPosition.getYaw(), 0, 1, 0); + GlStateManager.rotate(objectPosition.getRoll(), 0, 0, 1); + GlStateManager.rotate(objectPosition.getPitch(), 1, 0, 0); + + renderer.setColorRGBA_F(1, 1, 1, 0.5f); + + float width = objectPosition.getWidth() * objectPosition.getScale(); + float height = objectPosition.getHeight() * objectPosition.getScale(); + + float minX = -width/2 + objectPosition.getAnchorX(); + float maxX = width/2 + objectPosition.getAnchorX(); + float minY = -height/2 + objectPosition.getAnchorY(); + float maxY = height/2 + objectPosition.getAnchorY(); + + renderer.startDrawingQuads(); + + renderer.addVertexWithUV(minX, minY, 0, 1, 1); + renderer.addVertexWithUV(minX, maxY, 0, 1, 0); + renderer.addVertexWithUV(maxX, maxY, 0, 0, 0); + renderer.addVertexWithUV(maxX, minY, 0, 0, 1); + + renderer.addVertexWithUV(maxX, maxY, 0, 0, 0); + renderer.addVertexWithUV(minX, maxY, 0, 1, 0); + renderer.addVertexWithUV(minX, minY, 0, 1, 1); + renderer.addVertexWithUV(maxX, minY, 0, 0, 1); + + tessellator.draw(); + renderer.setTranslation(0, 0, 0); + + GlStateManager.disableAlpha(); + GlStateManager.disableTexture2D(); + GlStateManager.enableLighting(); + GlStateManager.popMatrix(); + } +} diff --git a/src/main/java/eu/crushedpixel/replaymod/replay/ReplayHandler.java b/src/main/java/eu/crushedpixel/replaymod/replay/ReplayHandler.java index 77639bd2..62c0bdfe 100755 --- a/src/main/java/eu/crushedpixel/replaymod/replay/ReplayHandler.java +++ b/src/main/java/eu/crushedpixel/replaymod/replay/ReplayHandler.java @@ -52,6 +52,8 @@ public class ReplayHandler { private static KeyframeSet[] keyframeRepository = new KeyframeSet[]{}; + private static List customImageObjects = new ArrayList(); + /** * The file currently being played. */ @@ -734,4 +736,12 @@ public class ReplayHandler { setRealTimelineCursor(newCursorPos); } + + public static List getCustomImageObjects() { + return customImageObjects; + } + + public static void addCustomImageObject(CustomImageObject object) { + customImageObjects.add(object); + } }