package zmaster587.advancedRocketry.client.render.planet; import java.util.LinkedList; import java.util.List; import java.util.Random; import org.lwjgl.opengl.GL11; import zmaster587.advancedRocketry.api.Configuration; import zmaster587.advancedRocketry.api.IPlanetaryProvider; import zmaster587.advancedRocketry.dimension.DimensionManager; import zmaster587.advancedRocketry.dimension.DimensionProperties; import zmaster587.advancedRocketry.event.RocketEventHandler; import zmaster587.advancedRocketry.inventory.TextureResources; import zmaster587.advancedRocketry.stations.SpaceObject; import zmaster587.advancedRocketry.stations.SpaceObjectManager; import net.minecraft.client.Minecraft; import net.minecraft.client.multiplayer.WorldClient; import net.minecraft.client.renderer.GLAllocation; import net.minecraft.client.renderer.OpenGlHelper; import net.minecraft.client.renderer.RenderHelper; import net.minecraft.client.renderer.Tessellator; import net.minecraft.util.MathHelper; import net.minecraft.util.ResourceLocation; import net.minecraft.util.Vec3; import net.minecraftforge.client.IRenderHandler; import net.minecraftforge.common.util.ForgeDirection; public class RenderPlanetarySky extends IRenderHandler { private int starGLCallList; private int glSkyList; private int glSkyList2; //Mostly vanilla code //TODO: make usable on other planets public RenderPlanetarySky() { this.starGLCallList = GLAllocation.generateDisplayLists(3); GL11.glPushMatrix(); GL11.glNewList(this.starGLCallList, GL11.GL_COMPILE); this.renderStars(); GL11.glEndList(); GL11.glPopMatrix(); Tessellator tessellator = Tessellator.instance; this.glSkyList = this.starGLCallList + 1; GL11.glNewList(this.glSkyList, GL11.GL_COMPILE); byte b2 = 64; int i = 256 / b2 + 2; float f = 16.0F; int j; int k; for (j = -b2 * i; j <= b2 * i; j += b2) { for (k = -b2 * i; k <= b2 * i; k += b2) { tessellator.startDrawingQuads(); tessellator.addVertex((double)(j + 0), (double)f, (double)(k + 0)); tessellator.addVertex((double)(j + b2), (double)f, (double)(k + 0)); tessellator.addVertex((double)(j + b2), (double)f, (double)(k + b2)); tessellator.addVertex((double)(j + 0), (double)f, (double)(k + b2)); tessellator.draw(); } } GL11.glEndList(); this.glSkyList2 = this.starGLCallList + 2; GL11.glNewList(this.glSkyList2, GL11.GL_COMPILE); f = -16.0F; tessellator.startDrawingQuads(); for (j = -b2 * i; j <= b2 * i; j += b2) { for (k = -b2 * i; k <= b2 * i; k += b2) { tessellator.addVertex((double)(j + b2), (double)f, (double)(k + 0)); tessellator.addVertex((double)(j + 0), (double)f, (double)(k + 0)); tessellator.addVertex((double)(j + 0), (double)f, (double)(k + b2)); tessellator.addVertex((double)(j + b2), (double)f, (double)(k + b2)); } } tessellator.draw(); GL11.glEndList(); } Minecraft mc = Minecraft.getMinecraft(); private void renderStars() { Random random = new Random(10842L); Tessellator tessellator = Tessellator.instance; tessellator.startDrawingQuads(); for (int i = 0; i < 2000; ++i) { double d0 = (double)(random.nextFloat() * 2.0F - 1.0F); double d1 = (double)(random.nextFloat() * 2.0F - 1.0F); double d2 = (double)(random.nextFloat() * 2.0F - 1.0F); double d3 = (double)(0.15F + random.nextFloat() * 0.1F); double d4 = d0 * d0 + d1 * d1 + d2 * d2; if (d4 < 1.0D && d4 > 0.01D) { d4 = 1.0D / Math.sqrt(d4); d0 *= d4; d1 *= d4; d2 *= d4; double d5 = d0 * 100.0D; double d6 = d1 * 100.0D; double d7 = d2 * 100.0D; double d8 = Math.atan2(d0, d2); double d9 = Math.sin(d8); double d10 = Math.cos(d8); double d11 = Math.atan2(Math.sqrt(d0 * d0 + d2 * d2), d1); double d12 = Math.sin(d11); double d13 = Math.cos(d11); double d14 = random.nextDouble() * Math.PI * 2.0D; double d15 = Math.sin(d14); double d16 = Math.cos(d14); for (int j = 0; j < 4; ++j) { double d17 = 0.0D; double d18 = (double)((j & 2) - 1) * d3; double d19 = (double)((j + 1 & 2) - 1) * d3; double d20 = d18 * d16 - d19 * d15; double d21 = d19 * d16 + d18 * d15; double d22 = d20 * d12 + d17 * d13; double d23 = d17 * d12 - d20 * d13; double d24 = d23 * d9 - d21 * d10; double d25 = d21 * d9 + d23 * d10; tessellator.addVertex(d5 + d24, d6 + d22, d7 + d25); } } } tessellator.draw(); } @Override public void render(float partialTicks, WorldClient world, Minecraft mc) { //TODO: properly handle this float atmosphere; int solarOrbitalDistance, planetOrbitalDistance = 0; double myPhi = 0, myTheta = 0, myPrevOrbitalTheta = 0, myRotationalPhi = 0;; boolean hasAtmosphere = false, isMoon; float parentAtmColor[] = new float[]{1f,1f,1f}; boolean isWarp = false; boolean isGasGiant = false; ForgeDirection travelDirection = null; ResourceLocation parentPlanetIcon = null; List<DimensionProperties> children; ForgeDirection axis = ForgeDirection.EAST; Vec3 sunColor; if(mc.theWorld.provider instanceof IPlanetaryProvider) { IPlanetaryProvider planetaryProvider = (IPlanetaryProvider)mc.theWorld.provider; DimensionProperties properties = (DimensionProperties)planetaryProvider.getDimensionProperties((int)mc.thePlayer.posX, (int)mc.thePlayer.posZ); atmosphere = planetaryProvider.getAtmosphereDensityFromHeight(mc.renderViewEntity.posY, (int)mc.thePlayer.posX, (int)mc.thePlayer.posZ); axis = getRotationAxis(properties, (int)mc.thePlayer.posX, (int)mc.thePlayer.posZ); myPhi = properties.orbitalPhi; myTheta = properties.orbitTheta; myRotationalPhi = properties.rotationalPhi; myPrevOrbitalTheta = properties.prevOrbitalTheta; children = new LinkedList<DimensionProperties>(); for (Integer i : properties.getChildPlanets()) { children.add(DimensionManager.getInstance().getDimensionProperties(i)); } solarOrbitalDistance = properties.getSolarOrbitalDistance(); if(isMoon = properties.isMoon()) { DimensionProperties parentProperties = properties.getParentProperties(); isGasGiant = parentProperties.isGasGiant(); hasAtmosphere = parentProperties.hasAtmosphere(); planetOrbitalDistance = properties.getParentOrbitalDistance(); parentAtmColor = parentProperties.skyColor; parentPlanetIcon = getTextureForPlanet(parentProperties); } sunColor = planetaryProvider.getSunColor((int)mc.thePlayer.posX, (int)mc.thePlayer.posZ); if(world.provider.dimensionId == Configuration.spaceDimId) { isWarp = properties.getParentPlanet() == SpaceObjectManager.WARPDIMID; if(isWarp) { SpaceObject station = (SpaceObject) SpaceObjectManager.getSpaceManager().getSpaceStationFromBlockCoords((int)mc.thePlayer.posX, (int)mc.thePlayer.posZ); travelDirection = station.getForwardDirection(); } } } else { children = new LinkedList<DimensionProperties>(); isMoon = false; hasAtmosphere = DimensionManager.overworldProperties.hasAtmosphere(); atmosphere = DimensionManager.overworldProperties.getAtmosphereDensityAtHeight(mc.renderViewEntity.posY); solarOrbitalDistance = DimensionManager.overworldProperties.orbitalDist; sunColor = Vec3.createVectorHelper(1, 1, 1); } GL11.glDisable(GL11.GL_TEXTURE_2D); Vec3 vec3 = Minecraft.getMinecraft().theWorld.getSkyColor(this.mc.renderViewEntity, partialTicks); float f1 = (float)vec3.xCoord; float f2 = (float)vec3.yCoord; float f3 = (float)vec3.zCoord; float f6; if (this.mc.gameSettings.anaglyph) { float f4 = (f1 * 30.0F + f2 * 59.0F + f3 * 11.0F) / 100.0F; float f5 = (f1 * 30.0F + f2 * 70.0F) / 100.0F; f6 = (f1 * 30.0F + f3 * 70.0F) / 100.0F; f1 = f4; f2 = f5; f3 = f6; } //Simulate atmospheric thickness f1 *= atmosphere; f2 *= atmosphere; f3 *= atmosphere; GL11.glColor3f(f1, f2, f3); Tessellator tessellator1 = Tessellator.instance; GL11.glDepthMask(false); GL11.glEnable(GL11.GL_FOG); GL11.glColor3f(f1, f2, f3); GL11.glCallList(this.glSkyList); GL11.glDisable(GL11.GL_FOG); GL11.glDisable(GL11.GL_ALPHA_TEST); GL11.glEnable(GL11.GL_BLEND); OpenGlHelper.glBlendFunc(770, 771, 1, 0); RenderHelper.disableStandardItemLighting(); float[] afloat = mc.theWorld.provider.calcSunriseSunsetColors(mc.theWorld.getCelestialAngle(partialTicks), partialTicks); float f7; float f8; float f9; float f10; if (afloat != null) { GL11.glDisable(GL11.GL_TEXTURE_2D); GL11.glShadeModel(GL11.GL_SMOOTH); GL11.glPushMatrix(); GL11.glRotatef(90.0F, 1.0F, 0.0F, 0.0F); GL11.glRotatef(MathHelper.sin(mc.theWorld.getCelestialAngleRadians(partialTicks)) < 0.0F ? 180.0F : 0.0F, 0.0F, 0.0F, 1.0F); GL11.glRotatef(90.0F, 0.0F, 0.0F, 1.0F); //Sim atmospheric thickness f6 = afloat[0]; f7 = afloat[1]; f8 = afloat[2]; float f11; if (this.mc.gameSettings.anaglyph) { f9 = (f6 * 30.0F + f7 * 59.0F + f8 * 11.0F) / 100.0F; f10 = (f6 * 30.0F + f7 * 70.0F) / 100.0F; f11 = (f6 * 30.0F + f8 * 70.0F) / 100.0F; f6 = f9; f7 = f10; f8 = f11; } tessellator1.startDrawing(6); tessellator1.setColorRGBA_F(f6, f7, f8, afloat[3] * atmosphere); tessellator1.addVertex(0.0D, 100.0D, 0.0D); byte b0 = 16; tessellator1.setColorRGBA_F(afloat[0], afloat[1], afloat[2], 0.0F); for (int j = 0; j <= b0; ++j) { f11 = (float)j * (float)Math.PI * 2.0F / (float)b0; float f12 = MathHelper.sin(f11); float f13 = MathHelper.cos(f11); tessellator1.addVertex((double)(f12 * 120.0F), (double)(f13 * 120.0F), (double)(-f13 * 40.0F * afloat[3])); } tessellator1.draw(); GL11.glPopMatrix(); GL11.glShadeModel(GL11.GL_FLAT); } GL11.glEnable(GL11.GL_TEXTURE_2D); OpenGlHelper.glBlendFunc(770, 1, 1, 0); GL11.glPushMatrix(); if(atmosphere > 0) f6 = 1.0F - (mc.theWorld.getRainStrength(partialTicks)*(atmosphere/100f)); else f6 = 1f; f7 = 0.0F; f8 = 0.0F; f9 = 0.0F; GL11.glColor4f(1.0F, 1.0F, 1.0F, f6); GL11.glTranslatef(f7, f8, f9); GL11.glRotatef(-90.0F, 0.0F, 1.0F, 0.0F); GL11.glRotatef((float)myRotationalPhi, 0f, 1f, 0f); GL11.glRotatef(isWarp ? 0 : mc.theWorld.getCelestialAngle(partialTicks) * 360.0F, axis.offsetX, axis.offsetY, axis.offsetZ); GL11.glDisable(GL11.GL_TEXTURE_2D); float f18 = mc.theWorld.getStarBrightness(partialTicks) * f6 * (atmosphere) + (1-atmosphere); if(mc.theWorld.isRaining()) f18 *= 1-mc.theWorld.getRainStrength(partialTicks); if (f18 > 0.0F) { GL11.glColor4f(f18, f18, f18, f18); GL11.glPushMatrix(); if(isWarp) { for(int i = -3; i < 5; i++) { GL11.glPushMatrix(); double magnitude = i*-100 + (((System.currentTimeMillis()) + 50) % 2000)/20f; GL11.glTranslated(-travelDirection.offsetZ*magnitude, 0, travelDirection.offsetX*magnitude); GL11.glCallList(this.starGLCallList); GL11.glPopMatrix(); } //GL11.glTranslated(((System.currentTimeMillis()/10) + 50) % 100, 0, 0); } else { GL11.glCallList(this.starGLCallList); //Extra stars for low ATM if(atmosphere < 0.5) { GL11.glColor4f(f18, f18, f18, f18/2f); GL11.glPushMatrix(); GL11.glRotatef(-90, 0, 1, 0); GL11.glCallList(this.starGLCallList); GL11.glPopMatrix(); } if(atmosphere < 0.25) { GL11.glColor4f(f18, f18, f18, f18/4f); GL11.glPushMatrix(); GL11.glRotatef(90, 0, 1, 0); GL11.glCallList(this.starGLCallList); GL11.glPopMatrix(); } GL11.glColor4f(f18, f18, f18, f18); } GL11.glPopMatrix(); } GL11.glEnable(GL11.GL_TEXTURE_2D); mc.renderEngine.bindTexture(TextureResources.locationSunPng); float multiplier = atmosphere > 1 ? (2-atmosphere) : 1f; multiplier *= 1-mc.theWorld.getRainStrength(partialTicks); if(!isWarp) { //Set sun color and distance tessellator1.startDrawingQuads(); f10 = 30f*(202-solarOrbitalDistance)/100f; //multiplier = 2; tessellator1.setColorOpaque_F((float)sunColor.xCoord * multiplier, (float)sunColor.yCoord * multiplier, (float)sunColor.zCoord * multiplier); tessellator1.addVertexWithUV((double)(-f10), 100.0D, (double)(-f10), 0.0D, 0.0D); tessellator1.addVertexWithUV((double)f10, 100.0D, (double)(-f10), 1.0D, 0.0D); tessellator1.addVertexWithUV((double)f10, 100.0D, (double)f10, 1.0D, 1.0D); tessellator1.addVertexWithUV((double)(-f10), 100.0D, (double)f10, 0.0D, 1.0D); tessellator1.draw(); } f10 = 20.0F; if(isMoon) { GL11.glPushMatrix(); GL11.glRotatef((float)myPhi, 0f, 0f, 1f); GL11.glRotatef((float)((partialTicks*myTheta + ((1-partialTicks)*myPrevOrbitalTheta)) * 180F/Math.PI), 1f, 0f, 0f); renderPlanet(tessellator1, parentPlanetIcon, planetOrbitalDistance, multiplier, hasAtmosphere, parentAtmColor, isGasGiant); GL11.glPopMatrix(); } for(DimensionProperties moons : children) { GL11.glPushMatrix(); GL11.glRotatef((float)moons.orbitalPhi, 0f, 0f, 1f); GL11.glRotatef((float)((partialTicks*moons.orbitTheta + ((1-partialTicks)*moons.prevOrbitalTheta)) * 180F/Math.PI), 1f, 0f, 0f); renderPlanet(tessellator1, moons.getPlanetIcon(), moons.getParentOrbitalDistance()*(1/moons.gravitationalMultiplier), multiplier, moons.hasAtmosphere(), moons.skyColor, isGasGiant); GL11.glPopMatrix(); } GL11.glEnable(GL11.GL_FOG); GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F); GL11.glDisable(GL11.GL_BLEND); GL11.glEnable(GL11.GL_ALPHA_TEST); GL11.glPopMatrix(); GL11.glDisable(GL11.GL_TEXTURE_2D); GL11.glColor3f(0.0F, 0.0F, 0.0F); double d0 = this.mc.thePlayer.getPosition(partialTicks).yCoord - mc.theWorld.getHorizon(); if (d0 < 0.0D) { GL11.glPushMatrix(); GL11.glTranslatef(0.0F, 12.0F, 0.0F); GL11.glCallList(this.glSkyList2); GL11.glPopMatrix(); f8 = 1.0F; f9 = -((float)(d0 + 65.0D)); f10 = -f8; tessellator1.startDrawingQuads(); tessellator1.setColorRGBA_I(0, 255); tessellator1.addVertex((double)(-f8), (double)f9, (double)f8); tessellator1.addVertex((double)f8, (double)f9, (double)f8); tessellator1.addVertex((double)f8, (double)f10, (double)f8); tessellator1.addVertex((double)(-f8), (double)f10, (double)f8); tessellator1.addVertex((double)(-f8), (double)f10, (double)(-f8)); tessellator1.addVertex((double)f8, (double)f10, (double)(-f8)); tessellator1.addVertex((double)f8, (double)f9, (double)(-f8)); tessellator1.addVertex((double)(-f8), (double)f9, (double)(-f8)); tessellator1.addVertex((double)f8, (double)f10, (double)(-f8)); tessellator1.addVertex((double)f8, (double)f10, (double)f8); tessellator1.addVertex((double)f8, (double)f9, (double)f8); tessellator1.addVertex((double)f8, (double)f9, (double)(-f8)); tessellator1.addVertex((double)(-f8), (double)f9, (double)(-f8)); tessellator1.addVertex((double)(-f8), (double)f9, (double)f8); tessellator1.addVertex((double)(-f8), (double)f10, (double)f8); tessellator1.addVertex((double)(-f8), (double)f10, (double)(-f8)); tessellator1.addVertex((double)(-f8), (double)f10, (double)(-f8)); tessellator1.addVertex((double)(-f8), (double)f10, (double)f8); tessellator1.addVertex((double)f8, (double)f10, (double)f8); tessellator1.addVertex((double)f8, (double)f10, (double)(-f8)); tessellator1.draw(); } if (mc.theWorld.provider.isSkyColored()) { GL11.glColor3f(f1 * 0.2F + 0.04F, f2 * 0.2F + 0.04F, f3 * 0.6F + 0.1F); } else { GL11.glColor3f(f1, f2, f3); } //Blackness @ bottom of world //GL11.glPushMatrix(); //GL11.glTranslatef(0.0F, -((float)(d0 - 16.0D)), 0.0F); //GL11.glCallList(this.glSkyList2); //GL11.glPopMatrix(); GL11.glEnable(GL11.GL_TEXTURE_2D); GL11.glDepthMask(true); RocketEventHandler.onPostWorldRender(partialTicks); } protected ForgeDirection getRotationAxis(DimensionProperties properties, int posX, int posZ) { return ForgeDirection.EAST; } protected ResourceLocation getTextureForPlanet(DimensionProperties properties) { return properties.getPlanetIcon(); } protected ResourceLocation getTextureForPlanetLEO(DimensionProperties properties) { return properties.getPlanetIcon(); } protected void renderPlanet(Tessellator tessellator1, ResourceLocation icon, float planetOrbitalDistance, float alphaMultiplier, boolean hasAtmosphere, float[] skyColor, boolean gasGiant) { //GL11.glDisable(GL11.GL_BLEND); GL11.glPushAttrib(GL11.GL_ALL_ATTRIB_BITS); GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA); mc.renderEngine.bindTexture(icon); //int k = mc.theWorld.getMoonPhase(); //int l = k % 4; //int i1 = k / 4 % 2; //Set planet Orbiting distance; size float f10 = 10f*(200-planetOrbitalDistance)/100f; float f14 = 1f;//(float)(l + 0) / 4.0F; float f15 = 0f;//(float)(i1 + 0) / 2.0F; float f16 = f15;//(float)(l + 1) / 4.0F; float f17 = f14;//(float)(i1 + 1) / 2.0F; //TODO: draw sky planets tessellator1.startDrawingQuads(); tessellator1.setColorRGBA_F(1f, 1f, 1f, alphaMultiplier); tessellator1.addVertexWithUV((double)(-f10), -100.0D, (double)f10, (double)f16, (double)f17); tessellator1.addVertexWithUV((double)f10, -100.0D, (double)f10, (double)f14, (double)f17); tessellator1.addVertexWithUV((double)f10, -100.0D, (double)(-f10), (double)f14, (double)f15); tessellator1.addVertexWithUV((double)(-f10), -100.0D, (double)(-f10), (double)f16, (double)f15); tessellator1.draw(); //GL11.glEnable(GL11.GL_BLEND); GL11.glPopAttrib(); //Draw atmosphere if applicable if(hasAtmosphere) { tessellator1.startDrawingQuads(); mc.renderEngine.bindTexture(DimensionProperties.getAtmosphereResource()); tessellator1.setColorRGBA_F(skyColor[0], skyColor[1], skyColor[2], alphaMultiplier); tessellator1.addVertexWithUV((double)(-f10), -100.0D, (double)f10, (double)f16, (double)f17); tessellator1.addVertexWithUV((double)f10, -100.0D, (double)f10, (double)f14, (double)f17); tessellator1.addVertexWithUV((double)f10, -100.0D, (double)(-f10), (double)f14, (double)f15); tessellator1.addVertexWithUV((double)(-f10), -100.0D, (double)(-f10), (double)f16, (double)f15); tessellator1.draw(); } tessellator1.setColorRGBA_F(1f, 1f, 1f, 1f); } }