diff --git a/data/images/misc/water.png b/data/images/misc/water.png new file mode 100644 index 00000000..8b92f9bc Binary files /dev/null and b/data/images/misc/water.png differ diff --git a/data/images/terrain/moon.png b/data/images/terrain/moon.png new file mode 100644 index 00000000..61cebbc7 Binary files /dev/null and b/data/images/terrain/moon.png differ diff --git a/data/images/terrain/sun.png b/data/images/terrain/sun.png new file mode 100644 index 00000000..d3433441 Binary files /dev/null and b/data/images/terrain/sun.png differ diff --git a/src/client/Minecraft.cpp b/src/client/Minecraft.cpp index 0ea8e9db..2a05eb2e 100755 --- a/src/client/Minecraft.cpp +++ b/src/client/Minecraft.cpp @@ -1156,6 +1156,10 @@ void Minecraft::init() FoliageColor::setUseTint(tint); GrassColor::setUseTint(tint); + bool sideTint = options.getBooleanValue(OPTIONS_TINTED_SIDE); + TileRenderer::setUseTint(sideTint); + + // Platform specific initialization here font = new Font(&options, "font/default8.png", textures); @@ -1408,7 +1412,7 @@ void Minecraft::_levelGenerated() if (level && level->dimension) { // For example, if you want FogType or any other option - level->dimension->FogType = options.getBooleanValue(OPTIONS_FOG_TYPE); + level->dimension->FogType = options.getIntValue(OPTIONS_FOG_TYPE); } diff --git a/src/client/Options.cpp b/src/client/Options.cpp index 78cef1a6..ee9aced2 100755 --- a/src/client/Options.cpp +++ b/src/client/Options.cpp @@ -68,6 +68,10 @@ OptionInt fogType("fogType", 0, 0, 2); OptionBool javaHud("javaHud", false); +OptionBool betaSky("betaSky", false); + +OptionBool tintedSide("tintedSide", false); + OptionBool blockOutline("blockOutline", false); OptionBool restoredAnims("restoredAnims", true); @@ -183,6 +187,10 @@ void Options::initTable() { // more options yay m_options[OPTIONS_FOG_TYPE] = &fogType; + m_options[OPTIONS_BETA_SKY] = &betaSky; + + m_options[OPTIONS_TINTED_SIDE] = &tintedSide; + m_options[OPTIONS_JAVA_HUD] = &javaHud; m_options[OPTIONS_AUTOJUMP] = &autoJump; diff --git a/src/client/Options.h b/src/client/Options.h index 7d1d3b40..826bfb30 100755 --- a/src/client/Options.h +++ b/src/client/Options.h @@ -90,6 +90,8 @@ enum OptionId { OPTIONS_FOG_TYPE, OPTIONS_JAVA_HUD, OPTIONS_RESTORED_ANIMS, + OPTIONS_TINTED_SIDE, + OPTIONS_BETA_SKY, // Should be last! OPTIONS_COUNT }; diff --git a/src/client/gui/Gui.cpp b/src/client/gui/Gui.cpp index 04892360..c9f63ea5 100755 --- a/src/client/gui/Gui.cpp +++ b/src/client/gui/Gui.cpp @@ -121,6 +121,9 @@ void Gui::render(float a, bool mouseFree, int xMouse, int yMouse) { if (!minecraft->options.getBooleanValue(OPTIONS_HIDEGUI)) { renderToolBar(a, ySlot, screenWidth); + font->drawShadow("Minecraft - Pocket Edition ", 2, 2, 0xffffffff); +// font->drawShadow("This is a demo, not the finished product", 2, 10 + 2, 0xffffffff); + glEnable(GL_BLEND); bool isChatting = (minecraft->screen && (dynamic_cast(minecraft->screen) || dynamic_cast(minecraft->screen))); unsigned int max = 10; diff --git a/src/client/gui/screens/OptionsScreen.cpp b/src/client/gui/screens/OptionsScreen.cpp index 88fbb634..9e537219 100755 --- a/src/client/gui/screens/OptionsScreen.cpp +++ b/src/client/gui/screens/OptionsScreen.cpp @@ -233,8 +233,10 @@ void OptionsScreen::generateOptionScreens() { .addOptionItem(OPTIONS_BAR_ON_TOP, minecraft) .addOptionItem(OPTIONS_RPI_CURSOR, minecraft) .addOptionItem(OPTIONS_FOLIAGE_TINT, minecraft) + .addOptionItem(OPTIONS_TINTED_SIDE, minecraft) .addOptionItem(OPTIONS_JAVA_HUD, minecraft) .addOptionItem(OPTIONS_FOG_TYPE, minecraft) + .addOptionItem(OPTIONS_BETA_SKY, minecraft) .addOptionItem(OPTIONS_RESTORED_ANIMS, minecraft); } diff --git a/src/client/renderer/GameRenderer.cpp b/src/client/renderer/GameRenderer.cpp index aab7f2ac..aab253ab 100755 --- a/src/client/renderer/GameRenderer.cpp +++ b/src/client/renderer/GameRenderer.cpp @@ -272,17 +272,6 @@ void GameRenderer::renderLevel(float a) { screenScissorArea.w, screenScissorArea.h); } - if(mc->options.getBooleanValue(OPTIONS_FANCY_GRAPHICS)) { - setupFog(-1); - TIMER_POP_PUSH("sky"); - glFogf(GL_FOG_START, renderDistance * 0.2f); - glFogf(GL_FOG_END, renderDistance *0.75); - levelRenderer->renderSky(a); - glFogf(GL_FOG_START, renderDistance * 0.6f); - glFogf(GL_FOG_END, renderDistance); - } - glEnable2(GL_FOG); - setupFog(1); if (mc->options.getBooleanValue(OPTIONS_AMBIENT_OCCLUSION)) { glShadeModel2(GL_SMOOTH); @@ -295,10 +284,29 @@ void GameRenderer::renderLevel(float a) { TIMER_POP_PUSH("culling"); mc->levelRenderer->cull(&frustum, a); mc->levelRenderer->updateDirtyChunks(cameraEntity, false); - + // this sky rendering code below was originally before the frustrum and culling stuff but sunset color breaks for some reason in that place, so i moved i after those two - shredder if(mc->options.getBooleanValue(OPTIONS_FANCY_GRAPHICS)) { + setupFog(-1); + TIMER_POP_PUSH("sky"); + // @TODO - EXTREME JANK BELOW, it works but i have to do heavy cleanup here, also to test if the glfogf commands even affect fog in anyway. + if(mc->options.getBooleanValue(OPTIONS_BETA_SKY) && (mc->options.getIntValue(OPTIONS_VIEW_DISTANCE) < 2)){ + levelRenderer->renderSky(a); // how java renders the sky instead of how pe doing prepareandrenderclouds. + } else if (!mc->options.getBooleanValue(OPTIONS_BETA_SKY)){ + glFogf(GL_FOG_START, renderDistance * 0.2f); + glFogf(GL_FOG_END, renderDistance *0.75); + + glFogf(GL_FOG_START, renderDistance * 0.6f); + glFogf(GL_FOG_END, renderDistance); + } + } + glEnable2(GL_FOG); + setupFog(1); + // MCPE renders clouds using this, but this method breaks 3d clouds and also breaks 2d clouds transparency viewed from above, add as a Legacy Sky or Fast Sky option. - shredder + if(!mc->options.getBooleanValue(OPTIONS_BETA_SKY)){ + if(mc->options.getBooleanValue(OPTIONS_FANCY_GRAPHICS)) { prepareAndRenderClouds(levelRenderer, a); } + } setupFog(0); glEnable2(GL_FOG); @@ -306,7 +314,9 @@ void GameRenderer::renderLevel(float a) { mc->textures->loadAndBindTexture("terrain.png"); Lighting::turnOff(); - glDisable2(GL_ALPHA_TEST); +// glDisable2(GL_ALPHA_TEST); // vanilla pe disables alpha test here, i renable it so grass side textures dont become opaque - shredder + glEnable2(GL_ALPHA_TEST); // + glDisable2(GL_BLEND); glEnable2(GL_CULL_FACE); TIMER_POP_PUSH("terrain-0"); @@ -374,11 +384,14 @@ void GameRenderer::renderLevel(float a) { } glDisable2(GL_FOG); - // - // setupFog(0); - // glEnable2(GL_FOG); - //// levelRenderer->renderClouds(a); - // glDisable2(GL_FOG); + // Normally this is commented out, but this is how java does it and should fix both 2d/3d clouds, a + if(mc->options.getBooleanValue(OPTIONS_BETA_SKY)){ + setupFog(0); + glEnable2(GL_FOG); + levelRenderer->renderClouds(a); + glDisable2(GL_FOG); + } + // SHREDDER END setupFog(1); if (zoom == 1 && !mc->options.getBooleanValue(OPTIONS_HIDEGUI)) { diff --git a/src/client/renderer/LevelRenderer.cpp b/src/client/renderer/LevelRenderer.cpp index 0c776825..6ce0d9ba 100755 --- a/src/client/renderer/LevelRenderer.cpp +++ b/src/client/renderer/LevelRenderer.cpp @@ -76,6 +76,9 @@ LevelRenderer::LevelRenderer( Minecraft* mc) //for (int i = 0; i < numListsOrBuffers; ++i) printf("bufId %d: %d\t", i, chunkBuffers[i]); glGenBuffers2(1, &skyBuffer); + glGenBuffers2(1, &voidBuffer); + glGenBuffers2(1, &starBuffer); + generateStars(); generateSky(); #else int maxChunksWidth = 1024 / CHUNK_SIZE; @@ -94,6 +97,8 @@ LevelRenderer::~LevelRenderer() #ifdef OPENGL_ES glDeleteBuffers(numListsOrBuffers, chunkBuffers); glDeleteBuffers(1, &skyBuffer); + glDeleteBuffers(1, &voidBuffer); + glDeleteBuffers(1, &starBuffer); delete[] chunkBuffers; #else glDeleteLists(numListsOrBuffers, chunkLists); @@ -121,6 +126,25 @@ void LevelRenderer::generateSky() { } t.end(true, skyBuffer); + + yy = (float) (-16); + t.begin(); + + // pretty much the same thing as the sky one above except uses inverted values to generate the void plane. + + voidVertexCount = 0; + for (int xx = -s * d; xx <= s * d; xx += s) { + for (int zz = -s * d; zz <= s * d; zz += s) { + t.vertex((float) xx + 0, yy, (float) zz + s); + t.vertex((float)(xx + s), yy, (float) zz + s); + t.vertex((float)(xx + s), yy, (float)(zz + 0)); + t.vertex((float) xx + 0, yy, (float)(zz + 0)); + //LOGI("x, z: %d, %d\n", xx, zz); + voidVertexCount += 4; + } + } + + t.end(true, voidBuffer); //LOGI("skyvertexcount: %d\n", skyVertexCount); //glEndList(); } @@ -146,10 +170,6 @@ void LevelRenderer::setLevel( Level* level ) level->addListener(this); allChanged(); } - if (mc->options.getBooleanValue(OPTIONS_AMBIENT_OCCLUSION)) { - mc->useAmbientOcclusion = !mc->useAmbientOcclusion; - allChanged(); - } } void LevelRenderer::allChanged() @@ -168,6 +188,9 @@ void LevelRenderer::allChanged() FoliageColor::setUseTint(tint); GrassColor::setUseTint(tint); + bool sideTint = mc->options.getBooleanValue(OPTIONS_TINTED_SIDE); + TileRenderer::setUseTint(sideTint); + int dist = (512 >> 3) << (3 - lastViewDistance); if (lastViewDistance <= 2 && mc->isPowerVR()) @@ -325,6 +348,37 @@ int LevelRenderer::render( Mob* player, int layer, float alpha ) allChanged(); } + bool SmoothLightState = mc->options.getBooleanValue(OPTIONS_AMBIENT_OCCLUSION); + if (SmoothLightState != mc->useAmbientOcclusion){ + mc->useAmbientOcclusion = SmoothLightState; + allChanged(); + } + + + bool tint = mc->options.getBooleanValue(OPTIONS_FOLIAGE_TINT); + if (tint != LastTint) { + LastTint = tint; + + + FoliageColor::setUseTint(tint); + GrassColor::setUseTint(tint); + + allChanged(); + } + + + bool sideTint = mc->options.getBooleanValue(OPTIONS_TINTED_SIDE); + + if (sideTint != LastSideTint) { + LastSideTint = sideTint; + + + TileRenderer::setUseTint(sideTint); + + allChanged(); + } + + TIMER_PUSH("sortchunks"); for (int i = 0; i < 10; i++) { @@ -513,14 +567,14 @@ void LevelRenderer::render(const AABB& b) const { Tesselator& t = Tesselator::instance; -// glColor4f2(1, 1, 1, 1); + // glColor4f2(1, 1, 1, 1); -// textures->loadAndBindTexture("terrain.png"); // uh need to check java - shredder + // textures->loadAndBindTexture("terrain.png"); // uh need to check java - shredder //t.begin(); -// t.color(255, 255, 255, 255); // again not needed, for some reason the vanilla source code tints it... white? maybe this was used for something else in MCPE's dev at one point? - shredder + // t.color(255, 255, 255, 255); // again not needed, for some reason the vanilla source code tints it... white? maybe this was used for something else in MCPE's dev at one point? - shredder -// t.offset(((Mob*)mc->player)->getPos(0).negated()); // why does this even exist normally, it just makes the thing... not render + // t.offset(((Mob*)mc->player)->getPos(0).negated()); // why does this even exist normally, it just makes the thing... not render t.begin(GL_LINE_STRIP); t.vertex(b.x0, b.y0, b.z0); @@ -1016,6 +1070,57 @@ std::string LevelRenderer::gatherStats1() { // int[] toRender = new int[50000]; // IntBuffer resultBuffer = MemoryTracker.createIntBuffer(64); + void LevelRenderer::generateStars() { + // ported from java beta again, + // converted the doubles into floats to be consistent, shouldnt affect much - shredder + + Random random = Random(10842L); + Tesselator& t = Tesselator::instance; + t.begin(); + starVertexCount = 0; + + for (int i = 0; i < 1500; i++) { + float d = random.nextFloat() * 2.0F - 1.0F; + float e = random.nextFloat() * 2.0F - 1.0F; + float f = random.nextFloat() * 2.0F - 1.0F; + float g = 0.25F + random.nextFloat() * 0.25F; + float h = d * d + e * e + f * f; + if (h < 1.0 && h > 0.01) { + h = 1.0 / Mth::sqrt(h); + d *= h; + e *= h; + f *= h; + float j = d * 100.0; + float k = e * 100.0; + float l = f * 100.0; + float m = Mth::atan2(d, f); + float n = Mth::sin(m); + float o = Mth::cos(m); + float p = Mth::atan2(Mth::sqrt(d * d + f * f), e); + float q = Mth::sin(p); + float r = Mth::cos(p); + float s = random.nextDouble() * Mth::PI * 2.0; + float t2 = Mth::sin(s); + float u = Mth::cos(s); + + for (int v = 0; v < 4; v++) { + float w = 0.0; + float x = ((v & 2) - 1) * g; + float y = ((v + 1 & 2) - 1) * g; + float aa = x * u - y * t2; + float ab = y * u + x * t2; + float ad = aa * q + w * r; + float ae = w * q - aa * r; + float af = ae * n - ab * o; + float ah = ab * n + ae * o; + t.vertex(j + af, k + ad, l + ah); + } + starVertexCount += 4; + } + } + + t.end(true, starBuffer); + } void LevelRenderer::renderSky(float alpha) { if (mc->level->dimension->foggy) return; @@ -1036,19 +1141,120 @@ void LevelRenderer::renderSky(float alpha) { } glColor4f2(sr, sg, Mth::Min(1.0f, sb), 1); - //Tesselator& t = Tesselator::instance; - + Tesselator& t = Tesselator::instance; + // @TODO shredder - should not enable or disable depth mask if using legacy sky because mcpe sky rendering is awful and will render clouds above terrain + if(mc->options.getBooleanValue(OPTIONS_BETA_SKY)){ + glDepthMask(false); + } glEnable2(GL_FOG); glColor4f2(sr, sg, sb, 1.0f); #ifdef OPENGL_ES drawArrayVT(skyBuffer, skyVertexCount); #endif - glEnable2(GL_TEXTURE_2D); + glDisable(GL_FOG); + glDisable(GL_ALPHA_TEST); + + // thanks to the mcpe 0.1 decomp project a bit for this part, was not getting the gl states correctly, gles is painful - shredder + + // Sunrise + glEnable(GL_BLEND); + glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); + + float* c = level->dimension->getSunriseColor(level->getTimeOfDay(alpha), alpha); + if (c != nullptr) + { + glDisable(GL_TEXTURE_2D); + + + glPushMatrix(); + glRotatef(90.0f, 1.0f, 0.0f, 0.0f); + glRotatef(level->getTimeOfDay(alpha) > 0.5f ? 180 : 0, 0.0f, 0.0f, 1.0f); + + t.begin(GL_TRIANGLE_FAN); + t.color(c[0], c[1], c[2], c[3]); + t.vertex(0.0f, 100.0f, 0.0f); + t.color(c[0], c[1], c[2], 0.0f); + + int steps = 16; + for (int i = 0; i <= steps; i++) + { + float a = i * 3.1415927f * 2.0f / steps; + float sin = Mth::sin(a); + float cos = Mth::cos(a); + t.vertex((sin * 120.0f), (cos * 120.0f), (-cos * 40.0f * c[3])); + } + + t.draw(); + glPopMatrix(); + } + + // gets the time of day and rotates the sun and moon png based on the time + glEnable(GL_TEXTURE_2D); + glBlendFunc(GL_ONE, GL_ONE); + glPushMatrix(); + + glColor4f(1.0f, 1.0f, 1.0f, 1.0f); + glTranslatef(sc.x, sc.y, sc.z); + glRotatef(0.0f, 0.0f, 0.0f, 1.0f); + glRotatef(level->getTimeOfDay(alpha) * 360.0f, 1.0f, 0.0f, 0.0f); + + float ss = 30.0f; + + + textures->loadAndBindTexture("terrain/sun.png"); + t.begin(); + t.vertexUV(-ss, 100.0f, -ss, 0.0f, 0.0f); + t.vertexUV(ss, 100.0f, -ss, 1.0f, 0.0f); + t.vertexUV(ss, 100.0f, ss, 1.0f, 1.0f); + t.vertexUV(-ss, 100.0f, ss, 0.0f, 1.0f); + t.draw(); + + ss = 20.0f; + textures->loadAndBindTexture("terrain/moon.png"); + t.begin(); + t.vertexUV(-ss, -100.0f, ss, 1.0f, 1.0f); + t.vertexUV(ss, -100.0f, ss, 0.0f, 1.0f); + t.vertexUV(ss, -100.0f, -ss, 0.0f, 0.0f); + t.vertexUV(-ss, -100.0f, -ss, 1.0f, 0.0f); + t.draw(); + + + glDisable(GL_TEXTURE_2D); + + float a = level->getStarBrightness(alpha); + if (a > 0.0f) + { + glColor4f(a, a, a, a); + drawArrayVT(starBuffer, starVertexCount); + } + + + glColor4f(1.0f, 1.0f, 1.0f, 1.0f); + glDisable(GL_BLEND); + glEnable(GL_ALPHA_TEST); + glEnable(GL_FOG); + glPopMatrix(); + + // ported over void plane (the blue bottom plane seen in java) because pocket edition lacks it @TODO test if it's buggy - shredder + + glColor3f(sc.x * 0.2f + 0.04f, sc.y * 0.2f + 0.04f, sc.z * 0.6f + 0.1f); + glDisable(GL_TEXTURE_2D); + drawArrayVT(voidBuffer, voidVertexCount); + glEnable(GL_TEXTURE_2D); + + // @TODO shredder - should not enable or disable depth mask if using legacy sky because mcpe sky rendering is awful and will render clouds above terrain + if(mc->options.getBooleanValue(OPTIONS_BETA_SKY)){ + glDepthMask(true); + } } void LevelRenderer::renderClouds( float alpha ) { //if (!mc->level->dimension->isNaturalDimension()) return; + if (mc->options.getBooleanValue(OPTIONS_FANCY_GRAPHICS)){ + renderAdvancedClouds(alpha); + return; + } glEnable2(GL_TEXTURE_2D); glDisable(GL_CULL_FACE); float yOffs = (float) (mc->player->yOld + (mc->player->y - mc->player->yOld) * alpha); @@ -1097,6 +1303,142 @@ void LevelRenderer::renderClouds( float alpha ) { glEnable(GL_CULL_FACE); } +void LevelRenderer::renderAdvancedClouds(float alpha) { + + // ported from java beta, tesselation code for the 3d clouds, renders broken if mcpe sky rendering option is used - shredder + + glDisable(GL_CULL_FACE); + + float px = mc->player->xOld + (mc->player->x - mc->player->xOld) * alpha; + float py = mc->player->yOld + (mc->player->y - mc->player->yOld) * alpha; + float pz = mc->player->zOld + (mc->player->z - mc->player->zOld) * alpha; + + Tesselator& t = Tesselator::instance; + float ss = 12.0f; + float h = 4.0f; + + float cloudTime = (float)ticks + alpha; + + double xo = (px + cloudTime * 0.03f) / ss; + double zo = pz / ss + 0.33f; + + float yy = 108.0f - py + 0.33f; + + int xWraps = Mth::floor(xo / 2048.0); + int zWraps = Mth::floor(zo / 2048.0); + xo -= xWraps * 2048; + zo -= zWraps * 2048; + + textures->loadAndBindTexture("environment/clouds.png"); + glEnable(GL_BLEND); + glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); + + Vec3 cc = level->getCloudColor(alpha); + float cr = cc.x; + float cg = cc.y; + float cb = cc.z; + + float uvScale = 1.0f / 256.0f; + float uo = (float)Mth::floor(xo) * uvScale; + float vo = (float)Mth::floor(zo) * uvScale; + + float xOffs = (float)(xo - Mth::floor(xo)); + float zOffs = (float)(zo - Mth::floor(zo)); + + int D = 8; + int radius = 3; + float e = 1.0f / 1024.0f; + + glPushMatrix(); + glScalef(ss, 1.0f, ss); + + for (int pass = 0; pass < 2; pass++) { + + if (pass == 0) glColorMask(false, false, false, false); + else glColorMask(true, true, true, true); + + for (int xPos = -radius + 1; xPos <= radius; xPos++) { + for (int zPos = -radius + 1; zPos <= radius; zPos++) { + t.begin(); + float xx = (float)(xPos * D); + float zz = (float)(zPos * D); + float xp = xx - xOffs; + float zp = zz - zOffs; + + + if (yy > -h - 1.0f) { + t.color(cr * 0.7f, cg * 0.7f, cb * 0.7f, 0.8f); + t.normal(0.0f, -1.0f, 0.0f); + t.vertexUV(xp + 0, yy + 0, zp + D, (xx + 0) * uvScale + uo, (zz + D) * uvScale + vo); + t.vertexUV(xp + D, yy + 0, zp + D, (xx + D) * uvScale + uo, (zz + D) * uvScale + vo); + t.vertexUV(xp + D, yy + 0, zp + 0, (xx + D) * uvScale + uo, (zz + 0) * uvScale + vo); + t.vertexUV(xp + 0, yy + 0, zp + 0, (xx + 0) * uvScale + uo, (zz + 0) * uvScale + vo); + } + + + if (yy <= h + 1.0f) { + t.color(cr, cg, cb, 0.8f); + t.normal(0.0f, 1.0f, 0.0f); + t.vertexUV(xp + 0, yy + h - e, zp + D, (xx + 0) * uvScale + uo, (zz + D) * uvScale + vo); + t.vertexUV(xp + D, yy + h - e, zp + D, (xx + D) * uvScale + uo, (zz + D) * uvScale + vo); + t.vertexUV(xp + D, yy + h - e, zp + 0, (xx + D) * uvScale + uo, (zz + 0) * uvScale + vo); + t.vertexUV(xp + 0, yy + h - e, zp + 0, (xx + 0) * uvScale + uo, (zz + 0) * uvScale + vo); + } + + t.color(cr * 0.9f, cg * 0.9f, cb * 0.9f, 0.8f); + + + if (xPos > -1) { + t.normal(-1.0f, 0.0f, 0.0f); + for (int i = 0; i < D; i++) { + t.vertexUV(xp + i + 0, yy + 0, zp + D, (xx + i + 0.5f) * uvScale + uo, (zz + D) * uvScale + vo); + t.vertexUV(xp + i + 0, yy + h, zp + D, (xx + i + 0.5f) * uvScale + uo, (zz + D) * uvScale + vo); + t.vertexUV(xp + i + 0, yy + h, zp + 0, (xx + i + 0.5f) * uvScale + uo, (zz + 0) * uvScale + vo); + t.vertexUV(xp + i + 0, yy + 0, zp + 0, (xx + i + 0.5f) * uvScale + uo, (zz + 0) * uvScale + vo); + } + } + if (xPos <= 1) { + t.normal(1.0f, 0.0f, 0.0f); + for (int i = 0; i < D; i++) { + t.vertexUV(xp + i + 1 - e, yy + 0, zp + D, (xx + i + 0.5f) * uvScale + uo, (zz + D) * uvScale + vo); + t.vertexUV(xp + i + 1 - e, yy + h, zp + D, (xx + i + 0.5f) * uvScale + uo, (zz + D) * uvScale + vo); + t.vertexUV(xp + i + 1 - e, yy + h, zp + 0, (xx + i + 0.5f) * uvScale + uo, (zz + 0) * uvScale + vo); + t.vertexUV(xp + i + 1 - e, yy + 0, zp + 0, (xx + i + 0.5f) * uvScale + uo, (zz + 0) * uvScale + vo); + } + } + + t.color(cr * 0.8f, cg * 0.8f, cb * 0.8f, 0.8f); + + + if (zPos > -1) { + t.normal(0.0f, 0.0f, -1.0f); + for (int i = 0; i < D; i++) { + t.vertexUV(xp + 0, yy + h, zp + i + 0, (xx + 0) * uvScale + uo, (zz + i + 0.5f) * uvScale + vo); + t.vertexUV(xp + D, yy + h, zp + i + 0, (xx + D) * uvScale + uo, (zz + i + 0.5f) * uvScale + vo); + t.vertexUV(xp + D, yy + 0, zp + i + 0, (xx + D) * uvScale + uo, (zz + i + 0.5f) * uvScale + vo); + t.vertexUV(xp + 0, yy + 0, zp + i + 0, (xx + 0) * uvScale + uo, (zz + i + 0.5f) * uvScale + vo); + } + } + if (zPos <= 1) { + t.normal(0.0f, 0.0f, 1.0f); + for (int i = 0; i < D; i++) { + t.vertexUV(xp + 0, yy + h, zp + i + 1 - e, (xx + 0) * uvScale + uo, (zz + i + 0.5f) * uvScale + vo); + t.vertexUV(xp + D, yy + h, zp + i + 1 - e, (xx + D) * uvScale + uo, (zz + i + 0.5f) * uvScale + vo); + t.vertexUV(xp + D, yy + 0, zp + i + 1 - e, (xx + D) * uvScale + uo, (zz + i + 0.5f) * uvScale + vo); + t.vertexUV(xp + 0, yy + 0, zp + i + 1 - e, (xx + 0) * uvScale + uo, (zz + i + 0.5f) * uvScale + vo); + } + } + t.endOverrideAndDraw(); + } + } + } + + glPopMatrix(); + glColor4f(1.0f, 1.0f, 1.0f, 1.0f); + glDisable(GL_BLEND); + glEnable(GL_CULL_FACE); +} + void LevelRenderer::playSound(const std::string& name, float x, float y, float z, float volume, float pitch) { // @todo: deny sounds here if sound is off (rather than waiting 'til SoundEngine) float dd = 16; @@ -1259,6 +1601,7 @@ void LevelRenderer::renderHitSelect( Player* player, const HitResult& h, int mod void LevelRenderer::onGraphicsReset() { + generateStars(); generateSky(); // Get new buffers diff --git a/src/client/renderer/LevelRenderer.h b/src/client/renderer/LevelRenderer.h index 2a9c7e23..2fa29c8a 100755 --- a/src/client/renderer/LevelRenderer.h +++ b/src/client/renderer/LevelRenderer.h @@ -43,7 +43,9 @@ public: void renderDebug(const AABB& b, float a) const; void renderSky(float alpha); + void generateStars(); void renderClouds(float alpha); + void renderAdvancedClouds(float alpha); void renderEntities(Vec3 cam, Culler* culler, float a); void renderSameAsLast(int layer, float alpha); void renderHit(Player* player, const HitResult& h, int mode, /*ItemInstance*/void* inventoryItem, float a); @@ -116,6 +118,9 @@ private: // shredder added again... int lastFogType; + bool LastTint; + bool LastSideTint; + int ticks; int starList, skyList, darkList; @@ -124,6 +129,12 @@ private: GLuint skyBuffer; int skyVertexCount; + GLuint voidBuffer; + int voidVertexCount; + + GLuint starBuffer; + int starVertexCount; + // /*public*/ std::vector renderableTileEntities; Textures* textures; // /*private*/ TileRenderer tileRenderer; diff --git a/src/client/renderer/TileRenderer.cpp b/src/client/renderer/TileRenderer.cpp index 8c1c91cf..e61334ca 100755 --- a/src/client/renderer/TileRenderer.cpp +++ b/src/client/renderer/TileRenderer.cpp @@ -19,8 +19,10 @@ #include "tileentity/TileEntityRenderer.h" #include "EntityTileRenderer.h" -TileRenderer::TileRenderer( LevelSource* level /* = NULL */ ) -: level(level), +bool TileRenderer::sideTinting = false; + +TileRenderer::TileRenderer(LevelSource* level /* = NULL */ ) + : level(level), fixedTexture(-1), xFlipTexture(false), noCulling(false), @@ -58,6 +60,11 @@ bool TileRenderer::tesselateBlockInWorld( Tile* tt, int x, int y, int z, float r float c2 = 0.8f; float c3 = 0.6f; + // added these to get biome color and save it before its overriden - shredder + float biomeR = r; + float biomeG = g; + float biomeB = b; + float r11 = c11 * r; float g11 = c11 * g; @@ -101,6 +108,10 @@ bool TileRenderer::tesselateBlockInWorld( Tile* tt, int x, int y, int z, float r if (tt->zz0 > 0) br = centerBrightness; t.color(r2 * br, g2 * br, b2 * br); renderNorth(tt, xf, yf, zf, tt->getTexture(level, x, y, z, 2)); + if ((tt->getTexture(level, x, y, z, 2) == 3) && sideTinting) { // checking if the texture from terrain.png is the normal grass side texture + t.color(c2 * br * biomeR, c2 * br * biomeG, c2 * br * biomeB); + renderNorth(tt, xf, yf, zf, 38); // rendering an extra face over the side of the cube that is a grayscale grass fringe tinted by t.color using biome colors, kinda inefficient + } changed = true; } @@ -109,6 +120,10 @@ bool TileRenderer::tesselateBlockInWorld( Tile* tt, int x, int y, int z, float r if (tt->zz1 < 1) br = centerBrightness; t.color(r2 * br, g2 * br, b2 * br); renderSouth(tt, xf, yf, zf, tt->getTexture(level, x, y, z, 3)); + if ((tt->getTexture(level, x, y, z, 3) == 3) && sideTinting){ // checking if the texture from terrain.png is the normal grass side texture + t.color(c2 * br * biomeR, c2 * br * biomeG, c2 * br * biomeB); + renderSouth(tt, xf, yf, zf, 38); // rendering an extra face over the side of the cube that is a grayscale grass fringe tinted by t.color using biome colors, kinda inefficient + } changed = true; } @@ -117,6 +132,10 @@ bool TileRenderer::tesselateBlockInWorld( Tile* tt, int x, int y, int z, float r if (tt->xx0 > 0) br = centerBrightness; t.color(r3 * br, g3 * br, b3 * br); renderWest(tt, xf, yf, zf, tt->getTexture(level, x, y, z, 4)); + if ((tt->getTexture(level, x, y, z, 4) == 3) && sideTinting) { // checking if the texture from terrain.png is the normal grass side texture + t.color(c2 * br * biomeR, c2 * br * biomeG, c2 * br * biomeB); + renderWest(tt, xf, yf, zf, 38); // rendering an extra face over the side of the cube that is a grayscale grass fringe tinted by t.color using biome colors, kinda inefficient + } changed = true; } @@ -125,6 +144,10 @@ bool TileRenderer::tesselateBlockInWorld( Tile* tt, int x, int y, int z, float r if (tt->xx1 < 1) br = centerBrightness; t.color(r3 * br, g3 * br, b3 * br); renderEast(tt, xf, yf, zf, tt->getTexture(level, x, y, z, 5)); + if ((tt->getTexture(level, x, y, z, 5) == 3) && sideTinting) { // checking if the texture from terrain.png is the normal grass side texture + t.color(c2 * br * biomeR, c2 * br * biomeG, c2 * br * biomeB); + renderEast(tt, xf, yf, zf, 38); // rendering an extra face over the side of the cube that is a grayscale grass fringe tinted by t.color using biome colors, kinda inefficient + } changed = true; } @@ -148,38 +171,38 @@ bool TileRenderer::tesselateInWorld( Tile* tt, int x, int y, int z ) return tesselateBlockInWorld(tt, x, y, z); } else if (shape == Tile::SHAPE_WATER) { return tesselateWaterInWorld(tt, x, y, z); - } else if (shape == Tile::SHAPE_CACTUS) { - return tesselateCactusInWorld(tt, x, y, z); + } else if (shape == Tile::SHAPE_CACTUS) { + return tesselateCactusInWorld(tt, x, y, z); } else if (shape == Tile::SHAPE_CROSS_TEXTURE) { return tesselateCrossInWorld(tt, x, y, z); } else if(shape == Tile::SHAPE_STEM) { return tesselateStemInWorld(tt, x, y, z); } else if (shape == Tile::SHAPE_ROWS) { - return tesselateRowInWorld(tt, x, y, z); + return tesselateRowInWorld(tt, x, y, z); } else if (shape == Tile::SHAPE_TORCH) { return tesselateTorchInWorld(tt, x, y, z); - } else if (shape == Tile::SHAPE_FIRE) { - return tesselateFireInWorld(tt, x, y, z); - //} else if (shape == Tile::SHAPE_RED_DUST) { - // return tesselateDustInWorld(tt, x, y, z); + } else if (shape == Tile::SHAPE_FIRE) { + return tesselateFireInWorld(tt, x, y, z); + //} else if (shape == Tile::SHAPE_RED_DUST) { + // return tesselateDustInWorld(tt, x, y, z); } else if (shape == Tile::SHAPE_LADDER) { return tesselateLadderInWorld(tt, x, y, z); } else if (shape == Tile::SHAPE_DOOR) { return tesselateDoorInWorld(tt, x, y, z); - //} else if (shape == Tile::SHAPE_RAIL) { - // return tesselateRailInWorld(tt, x, y, z); + //} else if (shape == Tile::SHAPE_RAIL) { + // return tesselateRailInWorld(tt, x, y, z); } else if (shape == Tile::SHAPE_STAIRS) { return tesselateStairsInWorld((StairTile*)tt, x, y, z); - } else if (shape == Tile::SHAPE_FENCE) { - return tesselateFenceInWorld((FenceTile*)tt, x, y, z); + } else if (shape == Tile::SHAPE_FENCE) { + return tesselateFenceInWorld((FenceTile*)tt, x, y, z); } else if (shape == Tile::SHAPE_FENCE_GATE) { return tesselateFenceGateInWorld((FenceGateTile*) tt, x, y, z); - //} else if (shape == Tile::SHAPE_LEVER) { - // return tesselateLeverInWorld(tt, x, y, z); - //} else if (shape == Tile::SHAPE_BED) { - // return tesselateBedInWorld(tt, x, y, z); - //} else if (shape == Tile::SHAPE_DIODE) { - // return tesselateDiodeInWorld(tt, x, y, z); + //} else if (shape == Tile::SHAPE_LEVER) { + // return tesselateLeverInWorld(tt, x, y, z); + //} else if (shape == Tile::SHAPE_BED) { + // return tesselateBedInWorld(tt, x, y, z); + //} else if (shape == Tile::SHAPE_DIODE) { + // return tesselateDiodeInWorld(tt, x, y, z); } else if (shape == Tile::SHAPE_IRON_FENCE) { return tesselateThinFenceInWorld((ThinFenceTile*) tt, x, y, z); } else if(shape == Tile::SHAPE_BED) { @@ -232,10 +255,10 @@ bool TileRenderer::tesselateFireInWorld( Tile* tt, int x, int y, int z ) int tex = tt->getTexture(0); if (fixedTexture >= 0) tex = fixedTexture; - + float br = tt->getBrightness( level, x, y, z ); t.color( br, br, br ); - + int xt = ((tex & 0xf) << 4); int yt = tex & 0xf0; @@ -340,82 +363,82 @@ bool TileRenderer::tesselateFireInWorld( Tile* tt, int x, int y, int z ) if ( Tile::fire->canBurn( level, x - 1, y, z ) ) { t.vertexUV( ( float )( x + r ), ( float )( y + h + yo ), ( float )( z + - 1.0f ), ( float )( u1 ), ( float )( v0 ) ); + 1.0f ), ( float )( u1 ), ( float )( v0 ) ); t.vertexUV( ( float )( x + 0.0f ), ( float )( y + 0.0f + yo ), ( float )( z + - 1.0f ), ( float )( u1 ), ( float )( v1 ) ); + 1.0f ), ( float )( u1 ), ( float )( v1 ) ); t.vertexUV( ( float )( x + 0.0f ), ( float )( y + 0.0f + yo ), ( float )( z + - 0.0f ), ( float )( u0 ), ( float )( v1 ) ); + 0.0f ), ( float )( u0 ), ( float )( v1 ) ); t.vertexUV( ( float )( x + r ), ( float )( y + h + yo ), ( float )( z + - 0.0f ), ( float )( u0 ), ( float )( v0 ) ); + 0.0f ), ( float )( u0 ), ( float )( v0 ) ); t.vertexUV( ( float )( x + r ), ( float )( y + h + yo ), ( float )( z + - 0.0f ), ( float )( u0 ), ( float )( v0 ) ); + 0.0f ), ( float )( u0 ), ( float )( v0 ) ); t.vertexUV( ( float )( x + 0.0f ), ( float )( y + 0.0f + yo ), ( float )( z + - 0.0f ), ( float )( u0 ), ( float )( v1 ) ); + 0.0f ), ( float )( u0 ), ( float )( v1 ) ); t.vertexUV( ( float )( x + 0.0f ), ( float )( y + 0.0f + yo ), ( float )( z + - 1.0f ), ( float )( u1 ), ( float )( v1 ) ); + 1.0f ), ( float )( u1 ), ( float )( v1 ) ); t.vertexUV( ( float )( x + r ), ( float )( y + h + yo ), ( float )( z + - 1.0f ), ( float )( u1 ), ( float )( v0 ) ); + 1.0f ), ( float )( u1 ), ( float )( v0 ) ); } if ( Tile::fire->canBurn( level, x + 1, y, z ) ) { t.vertexUV( ( float )( x + 1 - r ), ( float )( y + h + yo ), ( float )( z + - 0.0f ), ( float )( u0 ), ( float )( v0 ) ); + 0.0f ), ( float )( u0 ), ( float )( v0 ) ); t.vertexUV( ( float )( x + 1 - 0 ), ( float )( y + 0 + yo ), ( float )( z + - 0.0f ), ( float )( u0 ), ( float )( v1 ) ); + 0.0f ), ( float )( u0 ), ( float )( v1 ) ); t.vertexUV( ( float )( x + 1 - 0 ), ( float )( y + 0 + yo ), ( float )( z + - 1.0f ), ( float )( u1 ), ( float )( v1 ) ); + 1.0f ), ( float )( u1 ), ( float )( v1 ) ); t.vertexUV( ( float )( x + 1 - r ), ( float )( y + h + yo ), ( float )( z + - 1.0f ), ( float )( u1 ), ( float )( v0 ) ); + 1.0f ), ( float )( u1 ), ( float )( v0 ) ); t.vertexUV( ( float )( x + 1.0f - r ), ( float )( y + h + yo ), ( float )( z + - 1.0f ), ( float )( u1 ), ( float )( v0 ) ); + 1.0f ), ( float )( u1 ), ( float )( v0 ) ); t.vertexUV( ( float )( x + 1.0f - 0.0f ), ( float )( y + 0.0f + yo ), ( float )( z + - 1.0f ), ( float )( u1 ), ( float )( v1 ) ); + 1.0f ), ( float )( u1 ), ( float )( v1 ) ); t.vertexUV( ( float )( x + 1.0f - 0 ), ( float )( y + 0.0f + yo ), ( float )( z + - 0.0f ), ( float )( u0 ), ( float )( v1 ) ); + 0.0f ), ( float )( u0 ), ( float )( v1 ) ); t.vertexUV( ( float )( x + 1.0f - r ), ( float )( y + h + yo ), ( float )( z + - 0.0f ), ( float )( u0 ), ( float )( v0 ) ); + 0.0f ), ( float )( u0 ), ( float )( v0 ) ); } if ( Tile::fire->canBurn( level, x, y, z - 1 ) ) { t.vertexUV( ( float )( x + 0.0f ), ( float )( y + h + yo ), ( float )( z + - r ), ( float )( u1 ), ( float )( v0 ) ); + r ), ( float )( u1 ), ( float )( v0 ) ); t.vertexUV( ( float )( x + 0.0f ), ( float )( y + 0.0f + yo ), ( float )( z + - 0.0f ), ( float )( u1 ), ( float )( v1 ) ); + 0.0f ), ( float )( u1 ), ( float )( v1 ) ); t.vertexUV( ( float )( x + 1.0f ), ( float )( y + 0.0f + yo ), ( float )( z + - 0.0f ), ( float )( u0 ), ( float )( v1 ) ); + 0.0f ), ( float )( u0 ), ( float )( v1 ) ); t.vertexUV( ( float )( x + 1.0f ), ( float )( y + h + yo ), ( float )( z + - r ), ( float )( u0 ), ( float )( v0 ) ); + r ), ( float )( u0 ), ( float )( v0 ) ); t.vertexUV( ( float )( x + 1.0f ), ( float )( y + h + yo ), ( float )( z + - r ), ( float )( u0 ), ( float )( v0 ) ); + r ), ( float )( u0 ), ( float )( v0 ) ); t.vertexUV( ( float )( x + 1.0f ), ( float )( y + 0.0f + yo ), ( float )( z + - 0.0f ), ( float )( u0 ), ( float )( v1 ) ); + 0.0f ), ( float )( u0 ), ( float )( v1 ) ); t.vertexUV( ( float )( x + 0.0f ), ( float )( y + 0.0f + yo ), ( float )( z + - 0.0f ), ( float )( u1 ), ( float )( v1 ) ); + 0.0f ), ( float )( u1 ), ( float )( v1 ) ); t.vertexUV( ( float )( x + 0.0f ), ( float )( y + h + yo ), ( float )( z + - r ), ( float )( u1 ), ( float )( v0 ) ); + r ), ( float )( u1 ), ( float )( v0 ) ); } if ( Tile::fire->canBurn( level, x, y, z + 1 ) ) { t.vertexUV( ( float )( x + 1.0f ), ( float )( y + h + yo ), ( float )( z + 1.0f - - r ), ( float )( u0 ), ( float )( v0 ) ); + r ), ( float )( u0 ), ( float )( v0 ) ); t.vertexUV( ( float )( x + 1.0f ), ( float )( y + 0.0f + yo ), ( float )( z + 1.0f - - 0.0f ), ( float )( u0 ), ( float )( v1 ) ); + 0.0f ), ( float )( u0 ), ( float )( v1 ) ); t.vertexUV( ( float )( x + 0.0f ), ( float )( y + 0.0f + yo ), ( float )( z + 1.0f - - 0.0f ), ( float )( u1 ), ( float )( v1 ) ); + 0.0f ), ( float )( u1 ), ( float )( v1 ) ); t.vertexUV( ( float )( x + 0.0f ), ( float )( y + h + yo ), ( float )( z + 1.0f - - r ), ( float )( u1 ), ( float )( v0 ) ); + r ), ( float )( u1 ), ( float )( v0 ) ); t.vertexUV( ( float )( x + 0.0f ), ( float )( y + h + yo ), ( float )( z + 1.0f - - r ), ( float )( u1 ), ( float )( v0 ) ); + r ), ( float )( u1 ), ( float )( v0 ) ); t.vertexUV( ( float )( x + 0.0f ), ( float )( y + 0.0f + yo ), ( float )( z + 1.0f - - 0.0f ), ( float )( u1 ), ( float )( v1 ) ); + 0.0f ), ( float )( u1 ), ( float )( v1 ) ); t.vertexUV( ( float )( x + 1.0f ), ( float )( y + 0.0f + yo ), ( float )( z + 1.0f - - 0.0f ), ( float )( u0 ), ( float )( v1 ) ); + 0.0f ), ( float )( u0 ), ( float )( v1 ) ); t.vertexUV( ( float )( x + 1.0f ), ( float )( y + h + yo ), ( float )( z + 1.0f - - r ), ( float )( u0 ), ( float )( v0 ) ); + r ), ( float )( u0 ), ( float )( v0 ) ); } if ( Tile::fire->canBurn( level, x, y + 1.0f, z ) ) { @@ -440,13 +463,13 @@ bool TileRenderer::tesselateFireInWorld( Tile* tt, int x, int y, int z ) if ( ( ( x + y + z ) & 1 ) == 0 ) { t.vertexUV( ( float )( x0_ ), ( float )( y + h ), ( float )( z + - 0 ), ( float )( u1 ), ( float )( v0 ) ); + 0 ), ( float )( u1 ), ( float )( v0 ) ); t.vertexUV( ( float )( x0 ), ( float )( y + 0 ), ( float )( z + - 0 ), ( float )( u1 ), ( float )( v1 ) ); + 0 ), ( float )( u1 ), ( float )( v1 ) ); t.vertexUV( ( float )( x0 ), ( float )( y + 0 ), ( float )( z + - 1 ), ( float )( u0 ), ( float )( v1 ) ); + 1 ), ( float )( u0 ), ( float )( v1 ) ); t.vertexUV( ( float )( x0_ ), ( float )( y + h ), ( float )( z + - 1 ), ( float )( u0 ), ( float )( v0 ) ); + 1 ), ( float )( u0 ), ( float )( v0 ) ); u0 = (xt) / 256.0f; u1 = (xt + 15.99f) / 256.0f; @@ -454,24 +477,24 @@ bool TileRenderer::tesselateFireInWorld( Tile* tt, int x, int y, int z ) v1 = (yt + 15.99f) / 256.0f; t.vertexUV( ( float )( x1_ ), ( float )( y + h ), ( float )( z + - 1.0f ), ( float )( u1 ), ( float )( v0 ) ); + 1.0f ), ( float )( u1 ), ( float )( v0 ) ); t.vertexUV( ( float )( x1 ), ( float )( y + 0.0f ), ( float )( z + - 1.0f ), ( float )( u1 ), ( float )( v1 ) ); + 1.0f ), ( float )( u1 ), ( float )( v1 ) ); t.vertexUV( ( float )( x1 ), ( float )( y + 0.0f ), ( float )( z + - 0 ), ( float )( u0 ), ( float )( v1 ) ); + 0 ), ( float )( u0 ), ( float )( v1 ) ); t.vertexUV( ( float )( x1_ ), ( float )( y + h ), ( float )( z + - 0 ), ( float )( u0 ), ( float )( v0 ) ); + 0 ), ( float )( u0 ), ( float )( v0 ) ); } else { t.vertexUV( ( float )( x + 0.0f ), ( float )( y + - h ), ( float )( z1_ ), ( float )( u1 ), ( float )( v0 ) ); + h ), ( float )( z1_ ), ( float )( u1 ), ( float )( v0 ) ); t.vertexUV( ( float )( x + 0.0f ), ( float )( y + - 0.0f ), ( float )( z1 ), ( float )( u1 ), ( float )( v1 ) ); + 0.0f ), ( float )( z1 ), ( float )( u1 ), ( float )( v1 ) ); t.vertexUV( ( float )( x + 1.0f ), ( float )( y + - 0.0f ), ( float )( z1 ), ( float )( u0 ), ( float )( v1 ) ); + 0.0f ), ( float )( z1 ), ( float )( u0 ), ( float )( v1 ) ); t.vertexUV( ( float )( x + 1.0f ), ( float )( y + - h ), ( float )( z1_ ), ( float )( u0 ), ( float )( v0 ) ); + h ), ( float )( z1_ ), ( float )( u0 ), ( float )( v0 ) ); u0 = (xt) / 256.0f; u1 = (xt + 15.99f) / 256.0f; @@ -479,13 +502,13 @@ bool TileRenderer::tesselateFireInWorld( Tile* tt, int x, int y, int z ) v1 = (yt + 15.99f) / 256.0f; t.vertexUV( ( float )( x + 1.0f ), ( float )( y + - h ), ( float )( z0_ ), ( float )( u1 ), ( float )( v0 ) ); + h ), ( float )( z0_ ), ( float )( u1 ), ( float )( v0 ) ); t.vertexUV( ( float )( x + 1.0f ), ( float )( y + - 0.0f ), ( float )( z0 ), ( float )( u1 ), ( float )( v1 ) ); + 0.0f ), ( float )( z0 ), ( float )( u1 ), ( float )( v1 ) ); t.vertexUV( ( float )( x + 0.0f ), ( float )( y + - 0.0f ), ( float )( z0 ), ( float )( u0 ), ( float )( v1 ) ); + 0.0f ), ( float )( z0 ), ( float )( u0 ), ( float )( v1 ) ); t.vertexUV( ( float )( x + 0.0f ), ( float )( y + - h ), ( float )( z0_ ), ( float )( u0 ), ( float )( v0 ) ); + h ), ( float )( z0_ ), ( float )( u0 ), ( float )( v0 ) ); } } } @@ -958,46 +981,46 @@ float TileRenderer::getWaterHeight( int x, int y, int z, const Material* m ) } void TileRenderer::renderBlock(Tile* tt, LevelSource* level, int x, int y, int z) { - float c10 = 0.5f; - float c11 = 1; - float c2 = 0.8f; - float c3 = 0.6f; + float c10 = 0.5f; + float c11 = 1; + float c2 = 0.8f; + float c3 = 0.6f; - Tesselator& t = Tesselator::instance; - t.begin(); + Tesselator& t = Tesselator::instance; + t.begin(); - float center = tt->getBrightness(level, x, y, z); - float br = tt->getBrightness(level, x, y - 1, z); - if (br < center) br = center; + float center = tt->getBrightness(level, x, y, z); + float br = tt->getBrightness(level, x, y - 1, z); + if (br < center) br = center; - t.color(c10 * br, c10 * br, c10 * br); - renderFaceDown(tt, -0.5f, -0.5f, -0.5f, tt->getTexture(0)); + t.color(c10 * br, c10 * br, c10 * br); + renderFaceDown(tt, -0.5f, -0.5f, -0.5f, tt->getTexture(0)); - br = tt->getBrightness(level, x, y + 1, z); - if (br < center) br = center; - t.color(c11 * br, c11 * br, c11 * br); - renderFaceUp(tt, -0.5f, -0.5f, -0.5f, tt->getTexture(1)); + br = tt->getBrightness(level, x, y + 1, z); + if (br < center) br = center; + t.color(c11 * br, c11 * br, c11 * br); + renderFaceUp(tt, -0.5f, -0.5f, -0.5f, tt->getTexture(1)); - br = tt->getBrightness(level, x, y, z - 1); - if (br < center) br = center; - t.color(c2 * br, c2 * br, c2 * br); - renderNorth(tt, -0.5f, -0.5f, -0.5f, tt->getTexture(2)); + br = tt->getBrightness(level, x, y, z - 1); + if (br < center) br = center; + t.color(c2 * br, c2 * br, c2 * br); + renderNorth(tt, -0.5f, -0.5f, -0.5f, tt->getTexture(2)); - br = tt->getBrightness(level, x, y, z + 1); - if (br < center) br = center; - t.color(c2 * br, c2 * br, c2 * br); - renderSouth(tt, -0.5f, -0.5f, -0.5f, tt->getTexture(3)); + br = tt->getBrightness(level, x, y, z + 1); + if (br < center) br = center; + t.color(c2 * br, c2 * br, c2 * br); + renderSouth(tt, -0.5f, -0.5f, -0.5f, tt->getTexture(3)); - br = tt->getBrightness(level, x - 1, y, z); - if (br < center) br = center; - t.color(c3 * br, c3 * br, c3 * br); - renderWest(tt, -0.5f, -0.5f, -0.5f, tt->getTexture(4)); + br = tt->getBrightness(level, x - 1, y, z); + if (br < center) br = center; + t.color(c3 * br, c3 * br, c3 * br); + renderWest(tt, -0.5f, -0.5f, -0.5f, tt->getTexture(4)); - br = tt->getBrightness(level, x + 1, y, z); - if (br < center) br = center; - t.color(c3 * br, c3 * br, c3 * br); - renderEast(tt, -0.5f, -0.5f, -0.5f, tt->getTexture(5)); - t.draw(); + br = tt->getBrightness(level, x + 1, y, z); + if (br < center) br = center; + t.color(c3 * br, c3 * br, c3 * br); + renderEast(tt, -0.5f, -0.5f, -0.5f, tt->getTexture(5)); + t.draw(); } bool TileRenderer::tesselateBlockInWorldWithAmbienceOcclusion( Tile* tt, int pX, int pY, int pZ, float pBaseRed, float pBaseGreen, float pBaseBlue ) @@ -1197,6 +1220,15 @@ bool TileRenderer::tesselateBlockInWorldWithAmbienceOcclusion( Tile* tt, int pX, c4g *= ll4; c4b *= ll4; renderNorth(tt, (float) pX, (float) pY, (float) pZ, tt->getTexture(level, pX, pY, pZ, 2)); + if (tt->getTexture(level, pX, pY, pZ, 2) == 3 && sideTinting) + { + c1r *= pBaseRed; c1g *= pBaseGreen; c1b *= pBaseBlue; + c2r *= pBaseRed; c2g *= pBaseGreen; c2b *= pBaseBlue; + c3r *= pBaseRed; c3g *= pBaseGreen; c3b *= pBaseBlue; + c4r *= pBaseRed; c4g *= pBaseGreen; c4b *= pBaseBlue; + + renderNorth(tt, (float) pX, (float) pY, (float) pZ, 38); + } i = true; } if ((noCulling) || (tt->shouldRenderFace(level, pX, pY, pZ + 1, 3))) { @@ -1250,6 +1282,15 @@ bool TileRenderer::tesselateBlockInWorldWithAmbienceOcclusion( Tile* tt, int pX, c4g *= ll4; c4b *= ll4; renderSouth(tt, (float) pX, (float) pY, (float) pZ, tt->getTexture(level, pX, pY, pZ, 3)); + if (tt->getTexture(level, pX, pY, pZ, 3) == 3 && sideTinting) + { + c1r *= pBaseRed; c1g *= pBaseGreen; c1b *= pBaseBlue; + c2r *= pBaseRed; c2g *= pBaseGreen; c2b *= pBaseBlue; + c3r *= pBaseRed; c3g *= pBaseGreen; c3b *= pBaseBlue; + c4r *= pBaseRed; c4g *= pBaseGreen; c4b *= pBaseBlue; + + renderSouth(tt, (float) pX, (float) pY, (float) pZ, 38); + } i = true; } if ((noCulling) || (tt->shouldRenderFace(level, pX - 1, pY, pZ, 4))) { @@ -1302,6 +1343,15 @@ bool TileRenderer::tesselateBlockInWorldWithAmbienceOcclusion( Tile* tt, int pX, c4g *= ll4; c4b *= ll4; renderWest(tt, (float) pX, (float) pY, (float) pZ, tt->getTexture(level, pX, pY, pZ, 4)); + if (tt->getTexture(level, pX, pY, pZ, 4) == 3 && sideTinting) + { + c1r *= pBaseRed; c1g *= pBaseGreen; c1b *= pBaseBlue; + c2r *= pBaseRed; c2g *= pBaseGreen; c2b *= pBaseBlue; + c3r *= pBaseRed; c3g *= pBaseGreen; c3b *= pBaseBlue; + c4r *= pBaseRed; c4g *= pBaseGreen; c4b *= pBaseBlue; + + renderWest(tt, (float) pX, (float) pY, (float) pZ, 38); + } i = true; } if ((noCulling) || (tt->shouldRenderFace(level, pX + 1, pY, pZ, 5))) { @@ -1355,6 +1405,15 @@ bool TileRenderer::tesselateBlockInWorldWithAmbienceOcclusion( Tile* tt, int pX, c4b *= ll4; renderEast(tt, (float) pX, (float) pY, (float) pZ, tt->getTexture(level, pX, pY, pZ, 5)); + if (tt->getTexture(level, pX, pY, pZ, 5) == 3 && sideTinting) + { + c1r *= pBaseRed; c1g *= pBaseGreen; c1b *= pBaseBlue; + c2r *= pBaseRed; c2g *= pBaseGreen; c2b *= pBaseBlue; + c3r *= pBaseRed; c3g *= pBaseGreen; c3b *= pBaseBlue; + c4r *= pBaseRed; c4g *= pBaseGreen; c4b *= pBaseBlue; + + renderEast(tt, (float) pX, (float) pY, (float) pZ, 38); + } i = true; } applyAmbienceOcclusion = false; @@ -1362,124 +1421,124 @@ bool TileRenderer::tesselateBlockInWorldWithAmbienceOcclusion( Tile* tt, int pX, } bool TileRenderer::tesselateCactusInWorld(Tile* tt, int x, int y, int z) { - int col = tt->getColor(level, x, y, z); - float r = ((col >> 16) & 0xff) / 255.0f; - float g = ((col >> 8) & 0xff) / 255.0f; - float b = ((col) & 0xff) / 255.0f; - return tesselateCactusInWorld(tt, x, y, z, r, g, b); + int col = tt->getColor(level, x, y, z); + float r = ((col >> 16) & 0xff) / 255.0f; + float g = ((col >> 8) & 0xff) / 255.0f; + float b = ((col) & 0xff) / 255.0f; + return tesselateCactusInWorld(tt, x, y, z, r, g, b); } bool TileRenderer::tesselateCactusInWorld(Tile* tt, int x, int y, int z, float r, float g, float b) { - Tesselator& t = Tesselator::instance; + Tesselator& t = Tesselator::instance; - bool changed = false; - float c10 = 0.5f; - float c11 = 1; - float c2 = 0.8f; - float c3 = 0.6f; + bool changed = false; + float c10 = 0.5f; + float c11 = 1; + float c2 = 0.8f; + float c3 = 0.6f; - float r10 = c10 * r; - float r11 = c11 * r; - float r2 = c2 * r; - float r3 = c3 * r; + float r10 = c10 * r; + float r11 = c11 * r; + float r2 = c2 * r; + float r3 = c3 * r; - float g10 = c10 * g; - float g11 = c11 * g; - float g2 = c2 * g; - float g3 = c3 * g; + float g10 = c10 * g; + float g11 = c11 * g; + float g2 = c2 * g; + float g3 = c3 * g; - float b10 = c10 * b; - float b11 = c11 * b; - float b2 = c2 * b; - float b3 = c3 * b; + float b10 = c10 * b; + float b11 = c11 * b; + float b2 = c2 * b; + float b3 = c3 * b; - float s = 1 / 16.0f; + float s = 1 / 16.0f; const float X = (float)x; const float Y = (float)y; const float Z = (float)z; - float centerBrightness = tt->getBrightness(level, x, y, z); + float centerBrightness = tt->getBrightness(level, x, y, z); - if (noCulling || tt->shouldRenderFace(level, x, y - 1, z, 0)) { - float br = tt->getBrightness(level, x, y - 1, z); - // if (Tile::lightEmission[tt->id] > br*Level.MAX_BRIGHTNESS) br = -// Tile::lightEmission[tt->id]/Level.MAX_BRIGHTNESS; - t.color(r10 * br, g10 * br, b10 * br); - renderFaceDown(tt, X, Y, Z, tt->getTexture(level, x, y, z, 0)); - changed = true; - } + if (noCulling || tt->shouldRenderFace(level, x, y - 1, z, 0)) { + float br = tt->getBrightness(level, x, y - 1, z); + // if (Tile::lightEmission[tt->id] > br*Level.MAX_BRIGHTNESS) br = + // Tile::lightEmission[tt->id]/Level.MAX_BRIGHTNESS; + t.color(r10 * br, g10 * br, b10 * br); + renderFaceDown(tt, X, Y, Z, tt->getTexture(level, x, y, z, 0)); + changed = true; + } - if (noCulling || tt->shouldRenderFace(level, x, y + 1, z, 1)) { - float br = tt->getBrightness(level, x, y + 1, z); - if (tt->yy1 != 1 && !tt->material->isLiquid()) br = centerBrightness; - // if (Tile::lightEmission[tt->id] > br*Level.MAX_BRIGHTNESS) br = -// Tile::lightEmission[tt->id]/Level.MAX_BRIGHTNESS; - t.color(r11 * br, g11 * br, b11 * br); - renderFaceUp(tt, X, Y, Z, tt->getTexture(level, x, y, z, 1)); - changed = true; - } + if (noCulling || tt->shouldRenderFace(level, x, y + 1, z, 1)) { + float br = tt->getBrightness(level, x, y + 1, z); + if (tt->yy1 != 1 && !tt->material->isLiquid()) br = centerBrightness; + // if (Tile::lightEmission[tt->id] > br*Level.MAX_BRIGHTNESS) br = + // Tile::lightEmission[tt->id]/Level.MAX_BRIGHTNESS; + t.color(r11 * br, g11 * br, b11 * br); + renderFaceUp(tt, X, Y, Z, tt->getTexture(level, x, y, z, 1)); + changed = true; + } - if (noCulling || tt->shouldRenderFace(level, x, y, z - 1, 2)) { - float br = tt->getBrightness(level, x, y, z - 1); - if (tt->zz0 > 0) br = centerBrightness; - // if (Tile::lightEmission[tt->id] > br*Level.MAX_BRIGHTNESS) br = -// Tile::lightEmission[tt->id]/Level.MAX_BRIGHTNESS; - t.color(r2 * br, g2 * br, b2 * br); - t.addOffset(0, 0, s); - renderNorth(tt, X, Y, Z, tt->getTexture(level, x, y, z, 2)); - t.addOffset(0, 0, -s); - changed = true; - } + if (noCulling || tt->shouldRenderFace(level, x, y, z - 1, 2)) { + float br = tt->getBrightness(level, x, y, z - 1); + if (tt->zz0 > 0) br = centerBrightness; + // if (Tile::lightEmission[tt->id] > br*Level.MAX_BRIGHTNESS) br = + // Tile::lightEmission[tt->id]/Level.MAX_BRIGHTNESS; + t.color(r2 * br, g2 * br, b2 * br); + t.addOffset(0, 0, s); + renderNorth(tt, X, Y, Z, tt->getTexture(level, x, y, z, 2)); + t.addOffset(0, 0, -s); + changed = true; + } - if (noCulling || tt->shouldRenderFace(level, x, y, z + 1, 3)) { - float br = tt->getBrightness(level, x, y, z + 1); - if (tt->zz1 < 1) br = centerBrightness; - // if (Tile::lightEmission[tt->id] > br*Level.MAX_BRIGHTNESS) br = -// Tile::lightEmission[tt->id]/Level.MAX_BRIGHTNESS; - t.color(r2 * br, g2 * br, b2 * br); - t.addOffset(0, 0, -s); - renderSouth(tt, X, Y, Z, tt->getTexture(level, x, y, z, 3)); - t.addOffset(0, 0, s); - changed = true; - } + if (noCulling || tt->shouldRenderFace(level, x, y, z + 1, 3)) { + float br = tt->getBrightness(level, x, y, z + 1); + if (tt->zz1 < 1) br = centerBrightness; + // if (Tile::lightEmission[tt->id] > br*Level.MAX_BRIGHTNESS) br = + // Tile::lightEmission[tt->id]/Level.MAX_BRIGHTNESS; + t.color(r2 * br, g2 * br, b2 * br); + t.addOffset(0, 0, -s); + renderSouth(tt, X, Y, Z, tt->getTexture(level, x, y, z, 3)); + t.addOffset(0, 0, s); + changed = true; + } - if (noCulling || tt->shouldRenderFace(level, x - 1, y, z, 4)) { - float br = tt->getBrightness(level, x - 1, y, z); - if (tt->xx0 > 0) br = centerBrightness; - // if (Tile::lightEmission[tt->id] > br*Level.MAX_BRIGHTNESS) br = -// Tile::lightEmission[tt->id]/Level.MAX_BRIGHTNESS; - t.color(r3 * br, g3 * br, b3 * br); - t.addOffset(s, 0, 0); - renderWest(tt, X, Y, Z, tt->getTexture(level, x, y, z, 4)); - t.addOffset(-s, 0, 0); - changed = true; - } + if (noCulling || tt->shouldRenderFace(level, x - 1, y, z, 4)) { + float br = tt->getBrightness(level, x - 1, y, z); + if (tt->xx0 > 0) br = centerBrightness; + // if (Tile::lightEmission[tt->id] > br*Level.MAX_BRIGHTNESS) br = + // Tile::lightEmission[tt->id]/Level.MAX_BRIGHTNESS; + t.color(r3 * br, g3 * br, b3 * br); + t.addOffset(s, 0, 0); + renderWest(tt, X, Y, Z, tt->getTexture(level, x, y, z, 4)); + t.addOffset(-s, 0, 0); + changed = true; + } - if (noCulling || tt->shouldRenderFace(level, x + 1, y, z, 5)) { - float br = tt->getBrightness(level, x + 1, y, z); - if (tt->xx1 < 1) br = centerBrightness; - // if (Tile::lightEmission[tt->id] > br*Level.MAX_BRIGHTNESS) br = -// Tile::lightEmission[tt->id]/Level.MAX_BRIGHTNESS; - t.color(r3 * br, g3 * br, b3 * br); - t.addOffset(-s, 0, 0); - renderEast(tt, X, Y, Z, tt->getTexture(level, x, y, z, 5)); - t.addOffset(s, 0, 0); - changed = true; - } + if (noCulling || tt->shouldRenderFace(level, x + 1, y, z, 5)) { + float br = tt->getBrightness(level, x + 1, y, z); + if (tt->xx1 < 1) br = centerBrightness; + // if (Tile::lightEmission[tt->id] > br*Level.MAX_BRIGHTNESS) br = + // Tile::lightEmission[tt->id]/Level.MAX_BRIGHTNESS; + t.color(r3 * br, g3 * br, b3 * br); + t.addOffset(-s, 0, 0); + renderEast(tt, X, Y, Z, tt->getTexture(level, x, y, z, 5)); + t.addOffset(s, 0, 0); + changed = true; + } - return changed; + return changed; } bool TileRenderer::tesselateFenceInWorld(FenceTile* tt, int x, int y, int z) { - bool changed = true; + bool changed = true; - float a = 6 / 16.0f; - float b = 10 / 16.0f; - tt->setShape(a, 0, a, b, 1, b); - tesselateBlockInWorld(tt, x, y, z); + float a = 6 / 16.0f; + float b = 10 / 16.0f; + tt->setShape(a, 0, a, b, 1, b); + tesselateBlockInWorld(tt, x, y, z); - bool vertical = false; - bool horizontal = false; + bool vertical = false; + bool horizontal = false; bool l = tt->connectsTo(level, x - 1, y, z); bool r = tt->connectsTo(level, x + 1, y, z); @@ -1487,42 +1546,42 @@ bool TileRenderer::tesselateFenceInWorld(FenceTile* tt, int x, int y, int z) { bool d = tt->connectsTo(level, x, y, z + 1); if (l || r) vertical = true; - if (u || d) horizontal = true; + if (u || d) horizontal = true; - if (!vertical && !horizontal) vertical = true; + if (!vertical && !horizontal) vertical = true; - a = 7 / 16.0f; - b = 9 / 16.0f; - float h0 = 12 / 16.0f; - float h1 = 15 / 16.0f; + a = 7 / 16.0f; + b = 9 / 16.0f; + float h0 = 12 / 16.0f; + float h1 = 15 / 16.0f; - float x0 = l ? 0 : a; - float x1 = r ? 1 : b; - float z0 = u ? 0 : a; - float z1 = d ? 1 : b; + float x0 = l ? 0 : a; + float x1 = r ? 1 : b; + float z0 = u ? 0 : a; + float z1 = d ? 1 : b; - if (vertical) { - tt->setShape(x0, h0, a, x1, h1, b); - tesselateBlockInWorld(tt, x, y, z); - } - if (horizontal) { - tt->setShape(a, h0, z0, b, h1, z1); - tesselateBlockInWorld(tt, x, y, z); - } + if (vertical) { + tt->setShape(x0, h0, a, x1, h1, b); + tesselateBlockInWorld(tt, x, y, z); + } + if (horizontal) { + tt->setShape(a, h0, z0, b, h1, z1); + tesselateBlockInWorld(tt, x, y, z); + } - h0 = 6 / 16.0f; - h1 = 9 / 16.0f; - if (vertical) { - tt->setShape(x0, h0, a, x1, h1, b); - tesselateBlockInWorld(tt, x, y, z); - } - if (horizontal) { - tt->setShape(a, h0, z0, b, h1, z1); - tesselateBlockInWorld(tt, x, y, z); - } + h0 = 6 / 16.0f; + h1 = 9 / 16.0f; + if (vertical) { + tt->setShape(x0, h0, a, x1, h1, b); + tesselateBlockInWorld(tt, x, y, z); + } + if (horizontal) { + tt->setShape(a, h0, z0, b, h1, z1); + tesselateBlockInWorld(tt, x, y, z); + } - tt->setShape(0, 0, 0, 1, 1, 1); - return changed; + tt->setShape(0, 0, 0, 1, 1, 1); + return changed; } bool TileRenderer::tesselateFenceGateInWorld(FenceGateTile* tt, int x, int y, int z) { @@ -2308,7 +2367,7 @@ void TileRenderer::renderEast( Tile* tt, float x, float y, float z, int tex ) void TileRenderer::renderTile( Tile* tile, int data ) { Tesselator& t = Tesselator::instance; - + t.color(0xff, 0xff, 0xff); // i disabled this, this is normally enabled in normal mcpe see if this fits OPTION_NORMAL_LIGHTING - shredder int shape = tile->getRenderShape(); @@ -2324,7 +2383,7 @@ void TileRenderer::renderTile( Tile* tile, int data ) t.normal(0.0f, 1.0f, 0.0f); renderFaceUp(tile, 0, 0, 0, tile->getTexture(1, data)); - + t.normal(0.0f, 0.0f, -1.0f); renderNorth(tile, 0, 0, 0, tile->getTexture(2, data)); @@ -2403,110 +2462,110 @@ void TileRenderer::renderTile( Tile* tile, int data ) t.addOffset(s, 0, 0); t.draw(); t.offset(0, 0, 0);//0.5f, 0.5f, 0.5f); - } else if (shape == Tile::SHAPE_ROWS) { - t.begin(); - t.normal(0, -1, 0); - tesselateRowTexture(tile, data, -0.5f, -0.5f, -0.5f); + } else if (shape == Tile::SHAPE_ROWS) { + t.begin(); + t.normal(0, -1, 0); + tesselateRowTexture(tile, data, -0.5f, -0.5f, -0.5f); //} else if (shape == Tile::SHAPE_TORCH) { //// t.begin(); //// t.normal(0, -1, 0); /// tesselateTorch(tile, -0.5f, -0.5f, -0.5f, 0, 0); //// t.end(); - } else if (shape == Tile::SHAPE_ENTITYTILE_ANIMATED) { - EntityTileRenderer::instance->render(tile, data, 1.0f); - //glEnable(GL_RESCALE_NORMAL); - } else if (shape == Tile::SHAPE_STAIRS) { - t.addOffset(-0.5f, -0.5f, -0.5f); - t.begin(); - for (int i = 0; i < 2; i++) { - if (i == 0) tile->setShape(0, 0, 0, 1, 1, 0.5f); - if (i == 1) tile->setShape(0, 0, 0.5f, 1, 0.5f, 1); + } else if (shape == Tile::SHAPE_ENTITYTILE_ANIMATED) { + EntityTileRenderer::instance->render(tile, data, 1.0f); + //glEnable(GL_RESCALE_NORMAL); + } else if (shape == Tile::SHAPE_STAIRS) { + t.addOffset(-0.5f, -0.5f, -0.5f); + t.begin(); + for (int i = 0; i < 2; i++) { + if (i == 0) tile->setShape(0, 0, 0, 1, 1, 0.5f); + if (i == 1) tile->setShape(0, 0, 0.5f, 1, 0.5f, 1); - t.normal(0.0f, -1.0f, 0.0f); - renderFaceDown(tile, 0, 0, 0, tile->getTexture(0)); + t.normal(0.0f, -1.0f, 0.0f); + renderFaceDown(tile, 0, 0, 0, tile->getTexture(0)); - t.normal(0.0f, 1.0f, 0.0f); - renderFaceUp(tile, 0, 0, 0, tile->getTexture(1)); + t.normal(0.0f, 1.0f, 0.0f); + renderFaceUp(tile, 0, 0, 0, tile->getTexture(1)); - t.normal(0.0f, 0.0f, -1.0f); - renderNorth(tile, 0, 0, 0, tile->getTexture(2)); + t.normal(0.0f, 0.0f, -1.0f); + renderNorth(tile, 0, 0, 0, tile->getTexture(2)); - t.normal(0.0f, 0.0f, 1.0f); - renderSouth(tile, 0, 0, 0, tile->getTexture(3)); + t.normal(0.0f, 0.0f, 1.0f); + renderSouth(tile, 0, 0, 0, tile->getTexture(3)); - t.normal(-1.0f, 0.0f, 0.0f); - renderWest(tile, 0, 0, 0, tile->getTexture(4)); + t.normal(-1.0f, 0.0f, 0.0f); + renderWest(tile, 0, 0, 0, tile->getTexture(4)); - t.normal(1.0f, 0.0f, 0.0f); - renderEast(tile, 0, 0, 0, tile->getTexture(5)); - } - t.draw(); - t.addOffset(0.5f, 0.5f, 0.5f); + t.normal(1.0f, 0.0f, 0.0f); + renderEast(tile, 0, 0, 0, tile->getTexture(5)); } - else if (shape == Tile::SHAPE_FENCE) { - t.addOffset(-0.5f, -0.5f, -0.5f); - t.begin(); - for (int i = 0; i < 4; i++) { - float w = 2 / 16.0f; - if (i == 0) tile->setShape(0.5f - w, 0, 0, 0.5f + w, 1, w * 2); - if (i == 1) tile->setShape(0.5f - w, 0, 1 - w * 2, 0.5f + w, 1, 1); - w = 1 / 16.0f; - if (i == 2) tile->setShape(0.5f - w, 1 - w * 3, -w * 2, 0.5f + w, 1 - w, 1 + w * 2); - if (i == 3) tile->setShape(0.5f - w, 0.5f - w * 3, -w * 2, 0.5f + w, 0.5f - w, 1 + w * 2); + t.draw(); + t.addOffset(0.5f, 0.5f, 0.5f); + } + else if (shape == Tile::SHAPE_FENCE) { + t.addOffset(-0.5f, -0.5f, -0.5f); + t.begin(); + for (int i = 0; i < 4; i++) { + float w = 2 / 16.0f; + if (i == 0) tile->setShape(0.5f - w, 0, 0, 0.5f + w, 1, w * 2); + if (i == 1) tile->setShape(0.5f - w, 0, 1 - w * 2, 0.5f + w, 1, 1); + w = 1 / 16.0f; + if (i == 2) tile->setShape(0.5f - w, 1 - w * 3, -w * 2, 0.5f + w, 1 - w, 1 + w * 2); + if (i == 3) tile->setShape(0.5f - w, 0.5f - w * 3, -w * 2, 0.5f + w, 0.5f - w, 1 + w * 2); - t.normal(0.0f, -1.0f, 0.0f); - renderFaceDown(tile, 0, 0, 0, tile->getTexture(0)); + t.normal(0.0f, -1.0f, 0.0f); + renderFaceDown(tile, 0, 0, 0, tile->getTexture(0)); - t.normal(0.0f, 1.0f, 0.0f); - renderFaceUp(tile, 0, 0, 0, tile->getTexture(1)); + t.normal(0.0f, 1.0f, 0.0f); + renderFaceUp(tile, 0, 0, 0, tile->getTexture(1)); - t.normal(0.0f, 0.0f, -1.0f); - renderNorth(tile, 0, 0, 0, tile->getTexture(2)); + t.normal(0.0f, 0.0f, -1.0f); + renderNorth(tile, 0, 0, 0, tile->getTexture(2)); - t.normal(0.0f, 0.0f, 1.0f); - renderSouth(tile, 0, 0, 0, tile->getTexture(3)); + t.normal(0.0f, 0.0f, 1.0f); + renderSouth(tile, 0, 0, 0, tile->getTexture(3)); - t.normal(-1.0f, 0.0f, 0.0f); - renderWest(tile, 0, 0, 0, tile->getTexture(4)); + t.normal(-1.0f, 0.0f, 0.0f); + renderWest(tile, 0, 0, 0, tile->getTexture(4)); - t.normal(1.0f, 0.0f, 0.0f); - renderEast(tile, 0, 0, 0, tile->getTexture(5)); - } - t.draw(); - t.addOffset(0.5f, 0.5f, 0.5f); - tile->setShape(0, 0, 0, 1, 1, 1); - } else if (shape == Tile::SHAPE_FENCE_GATE) { - t.addOffset(-0.5f, -0.5f, -0.5f); - t.begin(); - for (int i = 0; i < 3; i++) { - float w = 1 / 16.0f; - if (i == 0) tile->setShape(0.5f - w, .3f, 0, 0.5f + w, 1, w * 2); - if (i == 1) tile->setShape(0.5f - w, .3f, 1 - w * 2, 0.5f + w, 1, 1); - if (i == 2) tile->setShape(0.5f - w, .5f, w * 2, 0.5f + w, 1 - w, 1 - w * 2); - - t.normal(0.0f, -1.0f, 0.0f); - renderFaceDown(tile, 0, 0, 0, tile->getTexture(0)); - - t.normal(0.0f, 1.0f, 0.0f); - renderFaceUp(tile, 0, 0, 0, tile->getTexture(1)); - - t.normal(0.0f, 0.0f, -1.0f); - renderNorth(tile, 0, 0, 0, tile->getTexture(2)); - - t.normal(0.0f, 0.0f, 1.0f); - renderSouth(tile, 0, 0, 0, tile->getTexture(3)); - - t.normal(-1.0f, 0.0f, 0.0f); - renderWest(tile, 0, 0, 0, tile->getTexture(4)); - - t.normal(1.0f, 0.0f, 0.0f); - renderEast(tile, 0, 0, 0, tile->getTexture(5)); - } - t.draw(); - t.addOffset(0.5f, 0.5f, 0.5f); - tile->setShape(0, 0, 0, 1, 1, 1); + t.normal(1.0f, 0.0f, 0.0f); + renderEast(tile, 0, 0, 0, tile->getTexture(5)); } + t.draw(); + t.addOffset(0.5f, 0.5f, 0.5f); + tile->setShape(0, 0, 0, 1, 1, 1); + } else if (shape == Tile::SHAPE_FENCE_GATE) { + t.addOffset(-0.5f, -0.5f, -0.5f); + t.begin(); + for (int i = 0; i < 3; i++) { + float w = 1 / 16.0f; + if (i == 0) tile->setShape(0.5f - w, .3f, 0, 0.5f + w, 1, w * 2); + if (i == 1) tile->setShape(0.5f - w, .3f, 1 - w * 2, 0.5f + w, 1, 1); + if (i == 2) tile->setShape(0.5f - w, .5f, w * 2, 0.5f + w, 1 - w, 1 - w * 2); + + t.normal(0.0f, -1.0f, 0.0f); + renderFaceDown(tile, 0, 0, 0, tile->getTexture(0)); + + t.normal(0.0f, 1.0f, 0.0f); + renderFaceUp(tile, 0, 0, 0, tile->getTexture(1)); + + t.normal(0.0f, 0.0f, -1.0f); + renderNorth(tile, 0, 0, 0, tile->getTexture(2)); + + t.normal(0.0f, 0.0f, 1.0f); + renderSouth(tile, 0, 0, 0, tile->getTexture(3)); + + t.normal(-1.0f, 0.0f, 0.0f); + renderWest(tile, 0, 0, 0, tile->getTexture(4)); + + t.normal(1.0f, 0.0f, 0.0f); + renderEast(tile, 0, 0, 0, tile->getTexture(5)); + } + t.draw(); + t.addOffset(0.5f, 0.5f, 0.5f); + tile->setShape(0, 0, 0, 1, 1, 1); + } } diff --git a/src/client/renderer/TileRenderer.h b/src/client/renderer/TileRenderer.h index 83351bd7..c463abf3 100755 --- a/src/client/renderer/TileRenderer.h +++ b/src/client/renderer/TileRenderer.h @@ -10,6 +10,7 @@ class ThinFenceTile; class StairTile; class LevelSource; class Material; +class Minecraft; class TileRenderer { @@ -60,6 +61,10 @@ public: void renderTile(Tile* tile, int data); void renderGuiTile(Tile* tile, int data); + static void setUseTint(bool value) { + sideTinting = value; + } + static bool canRender(int renderShape); private: float getWaterHeight(int x, int y, int z, const Material* m); @@ -68,6 +73,7 @@ private: int fixedTexture; bool xFlipTexture; bool noCulling; + static bool sideTinting; bool applyAmbienceOcclusion; float ll000, llx00, ll0y0, ll00z, llX00, ll0Y0, ll00Z; diff --git a/src/world/entity/animal/Sheep.cpp b/src/world/entity/animal/Sheep.cpp index 9039fa1d..52294344 100755 --- a/src/world/entity/animal/Sheep.cpp +++ b/src/world/entity/animal/Sheep.cpp @@ -1,5 +1,6 @@ #include "Sheep.h" #include "../../item/DyePowderItem.h" +#include "../../level/tile/TallGrass.h" #include "../../level/tile/LevelEvent.h" const float Sheep::COLOR[][3] = { @@ -198,7 +199,7 @@ void Sheep::updateAi() int yy = Mth::floor(y); int zz = Mth::floor(z); - if (/*(level->getTile(xx, yy, zz) == Tile::tallgrass->id && level->getData(xx, yy, zz) == TallGrass::TALL_GRASS) || */ level->getTile(xx, yy - 1, zz) == ((Tile*)Tile::grass)->id) { + if ((level->getTile(xx, yy, zz) == Tile::tallgrass->id && level->getData(xx, yy, zz) == TallGrass::TALL_GRASS) || level->getTile(xx, yy - 1, zz) == ((Tile*)Tile::grass)->id) { eatAnimationTick = EAT_ANIMATION_TICKS; level->broadcastEntityEvent(this, EntityEvent::EAT_GRASS); } @@ -208,11 +209,11 @@ void Sheep::updateAi() int zz = Mth::floor(z); bool ate = false; - /* if (level->getTile(xx, yy, zz) == Tile::tallgrass->id) { - level->levelEvent(LevelEvent::PARTICLES_DESTROY_BLOCK, xx, yy, zz, Tile::tallgrass->id + TallGrass::TALL_GRASS * 256); + if (level->getTile(xx, yy, zz) == Tile::tallgrass->id) { + level->levelEvent(NULL, LevelEvent::PARTICLES_DESTROY_BLOCK, xx, yy, zz, Tile::tallgrass->id + TallGrass::TALL_GRASS * 256); level->setTile(xx, yy, zz, 0); ate = true; - } else */if (level->getTile(xx, yy - 1, zz) == ((Tile*)Tile::grass)->id) { + } else if (level->getTile(xx, yy - 1, zz) == ((Tile*)Tile::grass)->id) { level->levelEvent(NULL, LevelEvent::PARTICLES_DESTROY_BLOCK, xx, yy - 1, zz, ((Tile*)Tile::grass)->id); level->setTile(xx, yy - 1, zz, Tile::dirt->id); ate = true; diff --git a/src/world/item/DyePowderItem.cpp b/src/world/item/DyePowderItem.cpp index 11c7964c..2252c9de 100755 --- a/src/world/item/DyePowderItem.cpp +++ b/src/world/item/DyePowderItem.cpp @@ -10,6 +10,7 @@ #include "../level/tile/ClothTile.h" #include "../level/tile/CropTile.h" #include "../level/tile/StemTile.h" +#include "../level/tile/TallGrass.h" const std::string DyePowderItem::COLOR_DESCS[] = { "black", "red", "green", "brown", "blue", "purple", "cyan", "silver", "gray", "pink", "lime", "yellow", "lightBlue", "magenta", "orange", "white" @@ -91,9 +92,9 @@ bool DyePowderItem::useOn( ItemInstance* itemInstance, Player* player, Level* le continue; if (level->getTile(xx, yy, zz) == 0) { - /*if (random.nextInt(10) != 0) { - level->setTileAndData(xx, yy, zz, Tile::tallgrass.id, TallGrass.TALL_GRASS); - } else*/ if (random.nextInt(3) != 0) { + if (random.nextInt(10) != 0) { + level->setTileAndData(xx, yy, zz, Tile::tallgrass->id, TallGrass::TALL_GRASS); + } else if (random.nextInt(3) != 0) { level->setTile(xx, yy, zz, Tile::flower->id); } else { level->setTile(xx, yy, zz, Tile::rose->id); diff --git a/src/world/item/ShearsItem.h b/src/world/item/ShearsItem.h index d73b2f54..30d4d57e 100755 --- a/src/world/item/ShearsItem.h +++ b/src/world/item/ShearsItem.h @@ -22,7 +22,7 @@ public: /*@Override*/ bool mineBlock(ItemInstance* itemInstance, int tile, int x, int y, int z/*, Mob* owner*/) { - if (tile == ((Tile*)Tile::leaves)->id || tile == Tile::web->id /*|| tile == Tile::tallgrass->id || tile == Tile::vine->id*/) { + if (tile == ((Tile*)Tile::leaves)->id || tile == Tile::web->id || tile == Tile::tallgrass->id /*|| tile == Tile::vine->id*/) { itemInstance->hurt(1);//, owner); return true; } diff --git a/src/world/level/FoliageColor.h b/src/world/level/FoliageColor.h index 98d77b7a..4d1a4467 100755 --- a/src/world/level/FoliageColor.h +++ b/src/world/level/FoliageColor.h @@ -43,7 +43,7 @@ public: } static int getDefaultColor() { - return 0xFFFFFF; + return 0x48b518; } private: diff --git a/src/world/level/Level.cpp b/src/world/level/Level.cpp index bb5ac0e0..14aa54ec 100755 --- a/src/world/level/Level.cpp +++ b/src/world/level/Level.cpp @@ -1174,7 +1174,14 @@ Vec3 Level::getSkyColor(Entity* source, float a) { float br = Mth::cos(td * Mth::PI * 2) * 2 + 0.5f; if (br < 0.0f) br = 0.0f; - if (br > 0.75f) br = 0.75f; //@note; was 1.0f + if (dimension->FogType == 1) // @TODO - probably make this not dependent on dimension type honestly - shredder + { + if (br > 1.0f) br = 1.0f; //@ uses the normal javasky color ramp when java sky type is choosen, + } else + { + if (br > 0.8f) br = 0.8f; //@note; was 1.0f + } + int xx = Mth::floor(source->x); int zz = Mth::floor(source->z); diff --git a/src/world/level/biome/Biome.cpp b/src/world/level/biome/Biome.cpp index 2c8638f5..4c09842c 100755 --- a/src/world/level/biome/Biome.cpp +++ b/src/world/level/biome/Biome.cpp @@ -9,6 +9,7 @@ #include "../../level/tile/TallGrass.h" #include "../../../util/Color.h" +#include "../GrassColor.h" Biome* Biome::rainForest = NULL; Biome* Biome::swampland = NULL; @@ -217,6 +218,26 @@ int Biome::getSkyColor( float temp ) return Color::getHSBColor(224 / 360.0f - temp * 0.05f, 0.50f + temp * 0.1f, 1.0f).getRGB(); } +float Biome::getDownfall() +{ + return downfall; +} + + +float Biome::getTemperature() +{ + return temperature; +} + + +int Biome::getGrassColor() +{ + float temp = Mth::clamp(getTemperature(), 0.0f, 1.0f); + float rain = Mth::clamp(getDownfall(), 0.0f, 1.0f); + + return GrassColor::get(temp, rain); +} + Biome::MobList& Biome::getMobs(const MobCategory& category) { if (&category == &MobCategory::monster) diff --git a/src/world/level/biome/Biome.h b/src/world/level/biome/Biome.h index 48a49d56..af44be4e 100755 --- a/src/world/level/biome/Biome.h +++ b/src/world/level/biome/Biome.h @@ -78,7 +78,13 @@ public: virtual float adjustScale(float scale); virtual float adjustDepth(float depth); + + virtual int getSkyColor(float temp); + virtual int getGrassColor(); + + virtual float getDownfall(); + virtual float getTemperature(); virtual MobList& getMobs(const MobCategory& category); virtual float getCreatureProbability(); @@ -88,6 +94,8 @@ public: char topMaterial; char material; int leafColor; + float temperature; + float downfall; private: static Biome* map[64*64]; }; diff --git a/src/world/level/levelgen/RandomLevelSource.cpp b/src/world/level/levelgen/RandomLevelSource.cpp index 3868faa4..4e3c4b28 100755 --- a/src/world/level/levelgen/RandomLevelSource.cpp +++ b/src/world/level/levelgen/RandomLevelSource.cpp @@ -419,7 +419,7 @@ void RandomLevelSource::postProcess(ChunkSource* parent, int xt, int zt) { FlowerFeature feature(Tile::mushroom2->id); feature.place(level, &random, x, y, z); } - /*int grassCount = 1; + int grassCount = 1; for (int i = 0; i < grassCount; i++) { int x = xo + random.nextInt(16) + 8; int y = random.nextInt(Level::genDepth); @@ -429,7 +429,7 @@ void RandomLevelSource::postProcess(ChunkSource* parent, int xt, int zt) { grassFeature->place(level, &random, x, y, z); delete grassFeature; } - }*/ + } for (int i = 0; i < 10; i++) { int x = xo + random.nextInt(16) + 8; int y = random.nextInt(128); diff --git a/src/world/level/tile/LeafTile.h b/src/world/level/tile/LeafTile.h index 53d98842..6095d126 100755 --- a/src/world/level/tile/LeafTile.h +++ b/src/world/level/tile/LeafTile.h @@ -60,6 +60,7 @@ public: return FoliageColor::getDefaultColor(); } + // return FoliageColor::getDefaultColor(); we need to hook this up with OPTION_FOLIAGE_TINT level->getBiomeSource()->getBiomeBlock(x, z, 1, 1); float temperature = level->getBiomeSource()->temperatures[0]; diff --git a/src/world/level/tile/TallGrass.cpp b/src/world/level/tile/TallGrass.cpp index 7a0350c2..b3fc6e65 100755 --- a/src/world/level/tile/TallGrass.cpp +++ b/src/world/level/tile/TallGrass.cpp @@ -1,8 +1,12 @@ #include "TallGrass.h" #include "../FoliageColor.h" +#include "../GrassColor.h" #include "../../entity/player/Player.h" #include "../../item/Item.h" #include "../../item/ShearsItem.h" +#include "../Level.h" +#include "../LevelSource.h" +#include "../biome/BiomeSource.h" TallGrass::TallGrass( int id, int tex ) : super(id, tex, Material::replaceable_plant) { float ss = 0.4f; @@ -17,9 +21,14 @@ int TallGrass::getTexture( int face, int data ) { } int TallGrass::getColor() { - /*double temp = 0.5; - double rain = 1.0; - return GrassColor.get(temp, rain);*/ + //double temp = 0.5; + //double rain = 1.0; + // converted to float for consistency - shredder + float temp = 0.5; + float rain = 1.0; + if (GrassColor::useTint){ + return GrassColor::get(temp, rain); + } return 0x339933; } @@ -31,7 +40,15 @@ int TallGrass::getColor( int auxData ) { int TallGrass::getColor( LevelSource* level, int x, int y, int z ) { int d = level->getData(x, y, z); if (d == DEAD_SHRUB) return 0xffffff; - + float temp = level->getBiomeSource()->temperatures[0]; // shredder added + float rain = level->getBiomeSource()->downfalls[0]; // shredder added + if (GrassColor::useTint){ + return GrassColor::get(temp, rain); + } + // @TODO port this function from beta 1.6.6 probably, for now im using biomesource to tint it directly above - shredder + //if (GrassColor::useTint){ + //return level->getBiome(x, z)->getGrassColor(); + //} return 0x339933;//level->getBiome(x, z)->getGrassColor(); }