From 3077afc0a2039cd4c8d64d9df62ed9b2ba6463dc Mon Sep 17 00:00:00 2001 From: numzero Date: Sun, 22 Nov 2020 16:29:31 +0300 Subject: Store stars in a single static mesh buffer --- src/client/sky.cpp | 199 +++++++++++++++++++++++------------------------------ 1 file changed, 86 insertions(+), 113 deletions(-) (limited to 'src/client/sky.cpp') diff --git a/src/client/sky.cpp b/src/client/sky.cpp index 2e0cbca86..29a0545ab 100644 --- a/src/client/sky.cpp +++ b/src/client/sky.cpp @@ -1,6 +1,7 @@ /* Minetest Copyright (C) 2010-2013 celeron55, Perttu Ahola +Copyright (C) 2020 numzero, Lobachevskiy Vitaliy This program is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by @@ -34,16 +35,7 @@ with this program; if not, write to the Free Software Foundation, Inc., #include "config.h" using namespace irr::core; -Sky::Sky(s32 id, ITextureSource *tsrc) : - scene::ISceneNode(RenderingEngine::get_scene_manager()->getRootSceneNode(), - RenderingEngine::get_scene_manager(), id) -{ - setAutomaticCulling(scene::EAC_OFF); - m_box.MaxEdge.set(0, 0, 0); - m_box.MinEdge.set(0, 0, 0); - - // Create material - +static video::SMaterial baseMaterial() { video::SMaterial mat; mat.Lighting = false; #if ENABLE_GLES @@ -56,14 +48,29 @@ Sky::Sky(s32 id, ITextureSource *tsrc) : mat.TextureLayer[0].TextureWrapU = video::ETC_CLAMP_TO_EDGE; mat.TextureLayer[0].TextureWrapV = video::ETC_CLAMP_TO_EDGE; mat.BackfaceCulling = false; + return mat; +}; + +Sky::Sky(s32 id, ITextureSource *tsrc) : + scene::ISceneNode(RenderingEngine::get_scene_manager()->getRootSceneNode(), + RenderingEngine::get_scene_manager(), id) +{ + setAutomaticCulling(scene::EAC_OFF); + m_box.MaxEdge.set(0, 0, 0); + m_box.MinEdge.set(0, 0, 0); + + // Create materials - m_materials[0] = mat; + m_materials[0] = baseMaterial(); + m_materials[0].MaterialType = video::EMT_TRANSPARENT_ALPHA_CHANNEL; + m_materials[0].Lighting = true; + m_materials[0].ColorMaterial = video::ECM_NONE; - m_materials[1] = mat; + m_materials[1] = baseMaterial(); //m_materials[1].MaterialType = video::EMT_TRANSPARENT_VERTEX_ALPHA; m_materials[1].MaterialType = video::EMT_TRANSPARENT_ALPHA_CHANNEL; - m_materials[2] = mat; + m_materials[2] = baseMaterial(); m_materials[2].setTexture(0, tsrc->getTextureForMesh("sunrisebg.png")); m_materials[2].MaterialType = video::EMT_TRANSPARENT_ALPHA_CHANNEL; //m_materials[2].MaterialType = video::EMT_TRANSPARENT_ADD_COLOR; @@ -80,7 +87,7 @@ Sky::Sky(s32 id, ITextureSource *tsrc) : tsrc->getTexture(m_moon_params.tonemap) : NULL; if (m_sun_texture) { - m_materials[3] = mat; + m_materials[3] = baseMaterial(); m_materials[3].setTexture(0, m_sun_texture); m_materials[3].MaterialType = video::EMT_TRANSPARENT_ALPHA_CHANNEL; // Disables texture filtering @@ -92,7 +99,7 @@ Sky::Sky(s32 id, ITextureSource *tsrc) : m_materials[3].Lighting = true; } if (m_moon_texture) { - m_materials[4] = mat; + m_materials[4] = baseMaterial(); m_materials[4].setTexture(0, m_moon_texture); m_materials[4].MaterialType = video::EMT_TRANSPARENT_ALPHA_CHANNEL; // Disables texture filtering @@ -105,7 +112,7 @@ Sky::Sky(s32 id, ITextureSource *tsrc) : } for (int i = 5; i < 11; i++) { - m_materials[i] = mat; + m_materials[i] = baseMaterial(); m_materials[i].Lighting = true; m_materials[i].MaterialType = video::EMT_SOLID; } @@ -673,13 +680,12 @@ void Sky::draw_moon(video::IVideoDriver *driver, float moonsize, const video::SC c = video::SColor(255, 255, 255, 255); draw_sky_body(vertices, -d, d, c); place_sky_body(vertices, -90, wicked_time_of_day * 360 - 90); - driver->drawIndexedTriangleFan(&vertices[0], 4, indices, 2); + driver->drawIndexedTriangleList(&vertices[0], 4, indices, 2); } } void Sky::draw_stars(video::IVideoDriver * driver, float wicked_time_of_day) { - driver->setMaterial(m_materials[1]); // Tune values so that stars first appear just after the sun // disappears over the horizon, and disappear just before the sun // appears over the horizon. @@ -687,87 +693,19 @@ void Sky::draw_stars(video::IVideoDriver * driver, float wicked_time_of_day) // to time 4000. float tod = wicked_time_of_day < 0.5f ? wicked_time_of_day : (1.0f - wicked_time_of_day); - float starbrightness = clamp((0.25f - fabsf(tod)) * 20.0f, 0.0f, 1.0f); - - float f = starbrightness; - float d = (0.006 / 2) * m_star_params.scale; - - video::SColor starcolor = m_star_params.starcolor; - starcolor.setAlpha(f * m_star_params.starcolor.getAlpha()); - - // Stars are only drawn when not fully transparent - if (m_star_params.starcolor.getAlpha() < 1) + float starbrightness = (0.25f - fabsf(tod)) * 20.0f; + int alpha = clamp(starbrightness * m_star_params.starcolor.getAlpha(), 0, 255); + if (!alpha) // Stars are only drawn when not fully transparent return; -#if ENABLE_GLES - u16 *indices = new u16[m_star_params.count * 3]; - video::S3DVertex *vertices = - new video::S3DVertex[m_star_params.count * 3]; - for (u32 i = 0; i < m_star_params.count; i++) { - indices[i * 3 + 0] = i * 3 + 0; - indices[i * 3 + 1] = i * 3 + 1; - indices[i * 3 + 2] = i * 3 + 2; - v3f r = m_stars[i]; - core::CMatrix4 a; - a.buildRotateFromTo(v3f(0, 1, 0), r); - v3f p = v3f(-d, 1, -d); - v3f p1 = v3f(d, 1, 0); - v3f p2 = v3f(-d, 1, d); - a.rotateVect(p); - a.rotateVect(p1); - a.rotateVect(p2); - p.rotateXYBy(wicked_time_of_day * 360 - 90); - p1.rotateXYBy(wicked_time_of_day * 360 - 90); - p2.rotateXYBy(wicked_time_of_day * 360 - 90); - vertices[i * 3 + 0].Pos = p; - vertices[i * 3 + 0].Color = starcolor; - vertices[i * 3 + 1].Pos = p1; - vertices[i * 3 + 1].Color = starcolor; - vertices[i * 3 + 2].Pos = p2; - vertices[i * 3 + 2].Color = starcolor; - } - driver->drawIndexedTriangleList(vertices, m_star_params.count * 3, - indices, m_star_params.count); - delete[] indices; - delete[] vertices; -#else - u16 *indices = new u16[m_star_params.count * 4]; - video::S3DVertex *vertices = - new video::S3DVertex[m_star_params.count * 4]; - for (u32 i = 0; i < m_star_params.count; i++) { - indices[i * 4 + 0] = i * 4 + 0; - indices[i * 4 + 1] = i * 4 + 1; - indices[i * 4 + 2] = i * 4 + 2; - indices[i * 4 + 3] = i * 4 + 3; - v3f r = m_stars[i]; - core::CMatrix4 a; - a.buildRotateFromTo(v3f(0, 1, 0), r); - v3f p = v3f(-d, 1, -d); - v3f p1 = v3f(d, 1, -d); - v3f p2 = v3f(d, 1, d); - v3f p3 = v3f(-d, 1, d); - a.rotateVect(p); - a.rotateVect(p1); - a.rotateVect(p2); - a.rotateVect(p3); - p.rotateXYBy(wicked_time_of_day * 360 - 90); - p1.rotateXYBy(wicked_time_of_day * 360 - 90); - p2.rotateXYBy(wicked_time_of_day * 360 - 90); - p3.rotateXYBy(wicked_time_of_day * 360 - 90); - vertices[i * 4 + 0].Pos = p; - vertices[i * 4 + 0].Color = starcolor; - vertices[i * 4 + 1].Pos = p1; - vertices[i * 4 + 1].Color = starcolor; - vertices[i * 4 + 2].Pos = p2; - vertices[i * 4 + 2].Color = starcolor; - vertices[i * 4 + 3].Pos = p3; - vertices[i * 4 + 3].Color = starcolor; - } - driver->drawVertexPrimitiveList(vertices, m_star_params.count * 4, - indices, m_star_params.count, video::EVT_STANDARD, - scene::EPT_QUADS, video::EIT_16BIT); - delete[] indices; - delete[] vertices; -#endif + + m_materials[0].DiffuseColor = video::SColor(alpha, 0, 0, 0); + m_materials[0].EmissiveColor = m_star_params.starcolor; + auto sky_rotation = core::matrix4().setRotationAxisRadians(2.0f * M_PI * (wicked_time_of_day - 0.25f), v3f(0.0f, 0.0f, 1.0f)); + auto world_matrix = driver->getTransform(video::ETS_WORLD); + driver->setTransform(video::ETS_WORLD, world_matrix * sky_rotation); + driver->setMaterial(m_materials[0]); + driver->drawMeshBuffer(m_stars.get()); + driver->setTransform(video::ETS_WORLD, world_matrix); } void Sky::draw_sky_body(std::array &vertices, float pos_1, float pos_2, const video::SColor &c) @@ -822,7 +760,7 @@ void Sky::setSunTexture(std::string sun_texture, m_sun_texture = tsrc->getTextureForMesh(m_sun_params.texture); if (m_sun_texture) { - m_materials[3] = m_materials[0]; + m_materials[3] = baseMaterial(); m_materials[3].setTexture(0, m_sun_texture); m_materials[3].MaterialType = video:: EMT_TRANSPARENT_ALPHA_CHANNEL; @@ -870,7 +808,7 @@ void Sky::setMoonTexture(std::string moon_texture, m_moon_texture = tsrc->getTextureForMesh(m_moon_params.texture); if (m_moon_texture) { - m_materials[4] = m_materials[0]; + m_materials[4] = baseMaterial(); m_materials[4].setTexture(0, m_moon_texture); m_materials[4].MaterialType = video:: EMT_TRANSPARENT_ALPHA_CHANNEL; @@ -892,19 +830,54 @@ void Sky::setStarCount(u16 star_count, bool force_update) // Allow force updating star count at game init. if (m_star_params.count != star_count || force_update) { m_star_params.count = star_count; - m_stars.clear(); - // Rebuild the stars surrounding the camera - for (u16 i = 0; i < star_count; i++) { - v3f star = v3f( - myrand_range(-10000, 10000), - myrand_range(-10000, 10000), - myrand_range(-10000, 10000) - ); - - star.normalize(); - m_stars.emplace_back(star); - } + updateStars(); + } +} + +void Sky::updateStars() { + m_stars.reset(new scene::SMeshBuffer()); + // Stupid IrrLicht doesn’t allow non-indexed rendering, and indexed quad + // rendering is slow due to lack of hardware support. So as indices are + // 16-bit and there are 4 vertices per star... the limit is 2^16/4 = 0x4000. + // That should be well enough actually. + if (m_star_params.count > 0x4000) { + warningstream << "Requested " << m_star_params.count << " stars but " << 0x4000 << " is the max\n"; + m_star_params.count = 0x4000; + } + m_stars->Vertices.reallocate(4 * m_star_params.count); + m_stars->Indices.reallocate(6 * m_star_params.count); + + float d = (0.006 / 2) * m_star_params.scale; + for (u16 i = 0; i < m_star_params.count; i++) { + v3f r = v3f( + myrand_range(-10000, 10000), + myrand_range(-10000, 10000), + myrand_range(-10000, 10000) + ); + core::CMatrix4 a; + a.buildRotateFromTo(v3f(0, 1, 0), r); + v3f p = v3f(-d, 1, -d); + v3f p1 = v3f(d, 1, -d); + v3f p2 = v3f(d, 1, d); + v3f p3 = v3f(-d, 1, d); + a.rotateVect(p); + a.rotateVect(p1); + a.rotateVect(p2); + a.rotateVect(p3); + m_stars->Vertices.push_back(video::S3DVertex(p, {}, {}, {})); + m_stars->Vertices.push_back(video::S3DVertex(p1, {}, {}, {})); + m_stars->Vertices.push_back(video::S3DVertex(p2, {}, {}, {})); + m_stars->Vertices.push_back(video::S3DVertex(p3, {}, {}, {})); + } + for (u16 i = 0; i < m_star_params.count; i++) { + m_stars->Indices.push_back(i * 4 + 0); + m_stars->Indices.push_back(i * 4 + 1); + m_stars->Indices.push_back(i * 4 + 2); + m_stars->Indices.push_back(i * 4 + 2); + m_stars->Indices.push_back(i * 4 + 3); + m_stars->Indices.push_back(i * 4 + 0); } + m_stars->setHardwareMappingHint(scene::EHM_STATIC); } void Sky::setSkyColors(const SkyColor &sky_color) @@ -936,7 +909,7 @@ void Sky::addTextureToSkybox(std::string texture, int material_id, // Keep a list of texture names handy. m_sky_params.textures.emplace_back(texture); video::ITexture *result = tsrc->getTextureForMesh(texture); - m_materials[material_id+5] = m_materials[0]; + m_materials[material_id+5] = baseMaterial(); m_materials[material_id+5].setTexture(0, result); m_materials[material_id+5].MaterialType = video::EMT_SOLID; } -- cgit v1.2.3 From 560627eef8c02f8201e639c75fcd5301d3a33077 Mon Sep 17 00:00:00 2001 From: numzero Date: Sun, 22 Nov 2020 16:41:36 +0300 Subject: Reuse seed when updating stars The only currently relevant parameter is scale which can now be changed without resetting stars position --- src/client/sky.cpp | 8 +++++--- src/client/sky.h | 1 + 2 files changed, 6 insertions(+), 3 deletions(-) (limited to 'src/client/sky.cpp') diff --git a/src/client/sky.cpp b/src/client/sky.cpp index 29a0545ab..cc9fb7d36 100644 --- a/src/client/sky.cpp +++ b/src/client/sky.cpp @@ -830,6 +830,7 @@ void Sky::setStarCount(u16 star_count, bool force_update) // Allow force updating star count at game init. if (m_star_params.count != star_count || force_update) { m_star_params.count = star_count; + m_seed = (u64)myrand() << 32 | myrand(); updateStars(); } } @@ -847,12 +848,13 @@ void Sky::updateStars() { m_stars->Vertices.reallocate(4 * m_star_params.count); m_stars->Indices.reallocate(6 * m_star_params.count); + PcgRandom rgen(m_seed); float d = (0.006 / 2) * m_star_params.scale; for (u16 i = 0; i < m_star_params.count; i++) { v3f r = v3f( - myrand_range(-10000, 10000), - myrand_range(-10000, 10000), - myrand_range(-10000, 10000) + rgen.range(-10000, 10000), + rgen.range(-10000, 10000), + rgen.range(-10000, 10000) ); core::CMatrix4 a; a.buildRotateFromTo(v3f(0, 1, 0), r); diff --git a/src/client/sky.h b/src/client/sky.h index 176545015..9f859f961 100644 --- a/src/client/sky.h +++ b/src/client/sky.h @@ -179,6 +179,7 @@ private: bool m_default_tint = true; + u64 m_seed = 0; irr_ptr m_stars; video::ITexture *m_sun_texture; -- cgit v1.2.3 From d7cf40a0ce996985cff20a156c56437f8b64c772 Mon Sep 17 00:00:00 2001 From: numzero Date: Sun, 22 Nov 2020 16:44:00 +0300 Subject: Replace TriangleFan as poorly supported --- src/client/sky.cpp | 22 +++++++++++----------- 1 file changed, 11 insertions(+), 11 deletions(-) (limited to 'src/client/sky.cpp') diff --git a/src/client/sky.cpp b/src/client/sky.cpp index cc9fb7d36..dda59dd11 100644 --- a/src/client/sky.cpp +++ b/src/client/sky.cpp @@ -209,7 +209,7 @@ void Sky::render() const f32 t = 1.0f; const f32 o = 0.0f; - static const u16 indices[4] = {0, 1, 2, 3}; + static const u16 indices[6] = {0, 1, 2, 0, 2, 3}; video::S3DVertex vertices[4]; driver->setMaterial(m_materials[1]); @@ -251,7 +251,7 @@ void Sky::render() vertex.Pos.rotateXZBy(180); } } - driver->drawIndexedTriangleFan(&vertices[0], 4, indices, 2); + driver->drawIndexedTriangleList(&vertices[0], 4, indices, 2); } } @@ -277,7 +277,7 @@ void Sky::render() // Switch from -Z (south) to +Z (north) vertex.Pos.rotateXZBy(-180); } - driver->drawIndexedTriangleFan(&vertices[0], 4, indices, 2); + driver->drawIndexedTriangleList(&vertices[0], 4, indices, 2); } } @@ -308,7 +308,7 @@ void Sky::render() // Switch from -Z (south) to -X (west) vertex.Pos.rotateXZBy(-90); } - driver->drawIndexedTriangleFan(&vertices[0], 4, indices, 2); + driver->drawIndexedTriangleList(&vertices[0], 4, indices, 2); } // Draw sun @@ -344,7 +344,7 @@ void Sky::render() // Switch from -Z (south) to +Z (north) vertex.Pos.rotateXZBy(-180); } - driver->drawIndexedTriangleFan(&vertices[0], 4, indices, 2); + driver->drawIndexedTriangleList(&vertices[0], 4, indices, 2); } // Draw bottom far cloudy fog thing in front of sun, moon and stars @@ -353,7 +353,7 @@ void Sky::render() vertices[1] = video::S3DVertex( 1, -1.0, -1, 0, 1, 0, c, o, t); vertices[2] = video::S3DVertex( 1, -1.0, 1, 0, 1, 0, c, o, o); vertices[3] = video::S3DVertex(-1, -1.0, 1, 0, 1, 0, c, t, o); - driver->drawIndexedTriangleFan(&vertices[0], 4, indices, 2); + driver->drawIndexedTriangleList(&vertices[0], 4, indices, 2); } } } @@ -597,7 +597,7 @@ void Sky::draw_sun(video::IVideoDriver *driver, float sunsize, const video::SCol * wicked_time_of_day: current time of day, to know where should be the sun in the sky */ { - static const u16 indices[4] = {0, 1, 2, 3}; + static const u16 indices[] = {0, 1, 2, 0, 2, 3}; std::array vertices; if (!m_sun_texture) { driver->setMaterial(m_materials[1]); @@ -615,7 +615,7 @@ void Sky::draw_sun(video::IVideoDriver *driver, float sunsize, const video::SCol for (int i = 0; i < 4; i++) { draw_sky_body(vertices, -sunsizes[i], sunsizes[i], colors[i]); place_sky_body(vertices, 90, wicked_time_of_day * 360 - 90); - driver->drawIndexedTriangleFan(&vertices[0], 4, indices, 2); + driver->drawIndexedTriangleList(&vertices[0], 4, indices, 2); } } else { driver->setMaterial(m_materials[3]); @@ -627,7 +627,7 @@ void Sky::draw_sun(video::IVideoDriver *driver, float sunsize, const video::SCol c = video::SColor(255, 255, 255, 255); draw_sky_body(vertices, -d, d, c); place_sky_body(vertices, 90, wicked_time_of_day * 360 - 90); - driver->drawIndexedTriangleFan(&vertices[0], 4, indices, 2); + driver->drawIndexedTriangleList(&vertices[0], 4, indices, 2); } } @@ -644,7 +644,7 @@ void Sky::draw_moon(video::IVideoDriver *driver, float moonsize, const video::SC * the sky */ { - static const u16 indices[4] = {0, 1, 2, 3}; + static const u16 indices[] = {0, 1, 2, 0, 2, 3}; std::array vertices; if (!m_moon_texture) { driver->setMaterial(m_materials[1]); @@ -668,7 +668,7 @@ void Sky::draw_moon(video::IVideoDriver *driver, float moonsize, const video::SC for (int i = 0; i < 4; i++) { draw_sky_body(vertices, moonsizes_1[i], moonsizes_2[i], colors[i]); place_sky_body(vertices, -90, wicked_time_of_day * 360 - 90); - driver->drawIndexedTriangleFan(&vertices[0], 4, indices, 2); + driver->drawIndexedTriangleList(&vertices[0], 4, indices, 2); } } else { driver->setMaterial(m_materials[4]); -- cgit v1.2.3 From cdcf7dca7c9afb329d49f2016964f77ac379ed67 Mon Sep 17 00:00:00 2001 From: numzero Date: Sun, 22 Nov 2020 18:25:41 +0300 Subject: Sky: support GLES2 IrrLicht built-in shader is broken, have to write my own --- client/shaders/stars_shader/opengl_fragment.glsl | 6 ++++++ client/shaders/stars_shader/opengl_vertex.glsl | 4 ++++ src/client/game.cpp | 8 +++++++- src/client/sky.cpp | 15 ++++++++------- src/client/sky.h | 8 ++++++-- 5 files changed, 31 insertions(+), 10 deletions(-) create mode 100644 client/shaders/stars_shader/opengl_fragment.glsl create mode 100644 client/shaders/stars_shader/opengl_vertex.glsl (limited to 'src/client/sky.cpp') diff --git a/client/shaders/stars_shader/opengl_fragment.glsl b/client/shaders/stars_shader/opengl_fragment.glsl new file mode 100644 index 000000000..a9ed741bf --- /dev/null +++ b/client/shaders/stars_shader/opengl_fragment.glsl @@ -0,0 +1,6 @@ +uniform vec4 starColor; + +void main(void) +{ + gl_FragColor = starColor; +} diff --git a/client/shaders/stars_shader/opengl_vertex.glsl b/client/shaders/stars_shader/opengl_vertex.glsl new file mode 100644 index 000000000..77c401f34 --- /dev/null +++ b/client/shaders/stars_shader/opengl_vertex.glsl @@ -0,0 +1,4 @@ +void main(void) +{ + gl_Position = mWorldViewProj * inVertexPosition; +} diff --git a/src/client/game.cpp b/src/client/game.cpp index b7bb0a330..2001f0487 100644 --- a/src/client/game.cpp +++ b/src/client/game.cpp @@ -424,6 +424,7 @@ class GameGlobalShaderConstantSetter : public IShaderConstantSetter CachedVertexShaderSetting m_animation_timer_vertex; CachedPixelShaderSetting m_animation_timer_pixel; CachedPixelShaderSetting m_day_light; + CachedPixelShaderSetting m_star_color; CachedPixelShaderSetting m_eye_position_pixel; CachedVertexShaderSetting m_eye_position_vertex; CachedPixelShaderSetting m_minimap_yaw; @@ -456,6 +457,7 @@ public: m_animation_timer_vertex("animationTimer"), m_animation_timer_pixel("animationTimer"), m_day_light("dayLight"), + m_star_color("starColor"), m_eye_position_pixel("eyePosition"), m_eye_position_vertex("eyePosition"), m_minimap_yaw("yawVec"), @@ -507,6 +509,10 @@ public: sunlight.b }; m_day_light.set(dnc, services); + video::SColorf star_color = m_sky->getCurrentStarColor(); + float clr[4] = {star_color.r, star_color.g, star_color.b, star_color.a}; + m_star_color.set(clr, services); + u32 animation_timer = porting::getTimeMs() % 1000000; float animation_timer_f = (float)animation_timer / 100000.f; m_animation_timer_vertex.set(&animation_timer_f, services); @@ -1363,7 +1369,7 @@ bool Game::createClient(const GameStartData &start_data) /* Skybox */ - sky = new Sky(-1, texture_src); + sky = new Sky(-1, texture_src, shader_src); scsf->setSky(sky); skybox = NULL; // This is used/set later on in the main run loop diff --git a/src/client/sky.cpp b/src/client/sky.cpp index dda59dd11..3fc5a95b4 100644 --- a/src/client/sky.cpp +++ b/src/client/sky.cpp @@ -51,7 +51,7 @@ static video::SMaterial baseMaterial() { return mat; }; -Sky::Sky(s32 id, ITextureSource *tsrc) : +Sky::Sky(s32 id, ITextureSource *tsrc, IShaderSource *ssrc) : scene::ISceneNode(RenderingEngine::get_scene_manager()->getRootSceneNode(), RenderingEngine::get_scene_manager(), id) { @@ -59,10 +59,12 @@ Sky::Sky(s32 id, ITextureSource *tsrc) : m_box.MaxEdge.set(0, 0, 0); m_box.MinEdge.set(0, 0, 0); + m_enable_shaders = g_settings->getBool("enable_shaders"); + // Create materials m_materials[0] = baseMaterial(); - m_materials[0].MaterialType = video::EMT_TRANSPARENT_ALPHA_CHANNEL; + m_materials[0].MaterialType = ssrc->getShaderInfo(ssrc->getShader("stars_shader", TILE_MATERIAL_ALPHA, 0)).material; m_materials[0].Lighting = true; m_materials[0].ColorMaterial = video::ECM_NONE; @@ -694,12 +696,11 @@ void Sky::draw_stars(video::IVideoDriver * driver, float wicked_time_of_day) float tod = wicked_time_of_day < 0.5f ? wicked_time_of_day : (1.0f - wicked_time_of_day); float starbrightness = (0.25f - fabsf(tod)) * 20.0f; - int alpha = clamp(starbrightness * m_star_params.starcolor.getAlpha(), 0, 255); - if (!alpha) // Stars are only drawn when not fully transparent + m_star_color = m_star_params.starcolor; + m_star_color.a = clamp(starbrightness * m_star_color.a, 0.0f, 1.0f); + if (m_star_color.a <= 0.0f) // Stars are only drawn when not fully transparent return; - - m_materials[0].DiffuseColor = video::SColor(alpha, 0, 0, 0); - m_materials[0].EmissiveColor = m_star_params.starcolor; + m_materials[0].DiffuseColor = m_materials[0].EmissiveColor = m_star_color.toSColor(); auto sky_rotation = core::matrix4().setRotationAxisRadians(2.0f * M_PI * (wicked_time_of_day - 0.25f), v3f(0.0f, 0.0f, 1.0f)); auto world_matrix = driver->getTransform(video::ETS_WORLD); driver->setTransform(video::ETS_WORLD, world_matrix * sky_rotation); diff --git a/src/client/sky.h b/src/client/sky.h index 9f859f961..10e1cd976 100644 --- a/src/client/sky.h +++ b/src/client/sky.h @@ -22,6 +22,7 @@ with this program; if not, write to the Free Software Foundation, Inc., #include "camera.h" #include "irrlichttypes_extrabloated.h" #include "irr_ptr.h" +#include "shader.h" #include "skyparams.h" #pragma once @@ -35,7 +36,7 @@ class Sky : public scene::ISceneNode { public: //! constructor - Sky(s32 id, ITextureSource *tsrc); + Sky(s32 id, ITextureSource *tsrc, IShaderSource *ssrc); virtual void OnRegisterSceneNode(); @@ -102,6 +103,8 @@ public: void clearSkyboxTextures() { m_sky_params.textures.clear(); } void addTextureToSkybox(std::string texture, int material_id, ITextureSource *tsrc); + const video::SColorf &getCurrentStarColor() const { return m_star_color; } + private: aabb3f m_box; video::SMaterial m_materials[SKY_MATERIAL_COUNT]; @@ -155,6 +158,7 @@ private: bool m_clouds_enabled = true; // Initialised to true, reset only by set_sky API bool m_directional_colored_fog; bool m_in_clouds = true; // Prevent duplicating bools to remember old values + bool m_enable_shaders = false; video::SColorf m_bgcolor_bright_f = video::SColorf(1.0f, 1.0f, 1.0f, 1.0f); video::SColorf m_skycolor_bright_f = video::SColorf(1.0f, 1.0f, 1.0f, 1.0f); @@ -181,6 +185,7 @@ private: u64 m_seed = 0; irr_ptr m_stars; + video::SColorf m_star_color; video::ITexture *m_sun_texture; video::ITexture *m_moon_texture; @@ -188,7 +193,6 @@ private: video::ITexture *m_moon_tonemap; void updateStars(); - void updateStarsColor(video::SColor color); void draw_sun(video::IVideoDriver *driver, float sunsize, const video::SColor &suncolor, const video::SColor &suncolor2, float wicked_time_of_day); -- cgit v1.2.3 From c158e20e5beab1037c905fe96b2a56baccddaec7 Mon Sep 17 00:00:00 2001 From: numzero Date: Sun, 22 Nov 2020 19:49:38 +0300 Subject: Provide fallback star color for GLES 2 with MT shaders disabled --- src/client/sky.cpp | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) (limited to 'src/client/sky.cpp') diff --git a/src/client/sky.cpp b/src/client/sky.cpp index 3fc5a95b4..0fccf067c 100644 --- a/src/client/sky.cpp +++ b/src/client/sky.cpp @@ -849,6 +849,7 @@ void Sky::updateStars() { m_stars->Vertices.reallocate(4 * m_star_params.count); m_stars->Indices.reallocate(6 * m_star_params.count); + video::SColor fallback_color = m_star_params.starcolor; // used on GLES 2 “without shaders” PcgRandom rgen(m_seed); float d = (0.006 / 2) * m_star_params.scale; for (u16 i = 0; i < m_star_params.count; i++) { @@ -867,10 +868,10 @@ void Sky::updateStars() { a.rotateVect(p1); a.rotateVect(p2); a.rotateVect(p3); - m_stars->Vertices.push_back(video::S3DVertex(p, {}, {}, {})); - m_stars->Vertices.push_back(video::S3DVertex(p1, {}, {}, {})); - m_stars->Vertices.push_back(video::S3DVertex(p2, {}, {}, {})); - m_stars->Vertices.push_back(video::S3DVertex(p3, {}, {}, {})); + m_stars->Vertices.push_back(video::S3DVertex(p, {}, fallback_color, {})); + m_stars->Vertices.push_back(video::S3DVertex(p1, {}, fallback_color, {})); + m_stars->Vertices.push_back(video::S3DVertex(p2, {}, fallback_color, {})); + m_stars->Vertices.push_back(video::S3DVertex(p3, {}, fallback_color, {})); } for (u16 i = 0; i < m_star_params.count; i++) { m_stars->Indices.push_back(i * 4 + 0); -- cgit v1.2.3 From 8689e00fca2cf55594d53f4e112f0d7b6676c8b0 Mon Sep 17 00:00:00 2001 From: numzero Date: Mon, 23 Nov 2020 01:04:31 +0300 Subject: Fix style --- src/client/sky.cpp | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) (limited to 'src/client/sky.cpp') diff --git a/src/client/sky.cpp b/src/client/sky.cpp index 0fccf067c..180d43066 100644 --- a/src/client/sky.cpp +++ b/src/client/sky.cpp @@ -35,7 +35,8 @@ with this program; if not, write to the Free Software Foundation, Inc., #include "config.h" using namespace irr::core; -static video::SMaterial baseMaterial() { +static video::SMaterial baseMaterial() +{ video::SMaterial mat; mat.Lighting = false; #if ENABLE_GLES @@ -836,7 +837,8 @@ void Sky::setStarCount(u16 star_count, bool force_update) } } -void Sky::updateStars() { +void Sky::updateStars() +{ m_stars.reset(new scene::SMeshBuffer()); // Stupid IrrLicht doesn’t allow non-indexed rendering, and indexed quad // rendering is slow due to lack of hardware support. So as indices are -- cgit v1.2.3 From 868749b4f8e898be0c01f892ea78d859d054c17e Mon Sep 17 00:00:00 2001 From: sfan5 Date: Thu, 26 Nov 2020 22:17:11 +0100 Subject: Return star color calculation to what it previously was --- src/client/sky.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src/client/sky.cpp') diff --git a/src/client/sky.cpp b/src/client/sky.cpp index 180d43066..9a2614eda 100644 --- a/src/client/sky.cpp +++ b/src/client/sky.cpp @@ -698,7 +698,7 @@ void Sky::draw_stars(video::IVideoDriver * driver, float wicked_time_of_day) float tod = wicked_time_of_day < 0.5f ? wicked_time_of_day : (1.0f - wicked_time_of_day); float starbrightness = (0.25f - fabsf(tod)) * 20.0f; m_star_color = m_star_params.starcolor; - m_star_color.a = clamp(starbrightness * m_star_color.a, 0.0f, 1.0f); + m_star_color.a *= clamp(starbrightness, 0.0f, 1.0f); if (m_star_color.a <= 0.0f) // Stars are only drawn when not fully transparent return; m_materials[0].DiffuseColor = m_materials[0].EmissiveColor = m_star_color.toSColor(); -- cgit v1.2.3