diff --git a/src/renderer/editor/main.cpp b/src/renderer/editor/main.cpp index 43a2ffb4e..005e7c610 100644 --- a/src/renderer/editor/main.cpp +++ b/src/renderer/editor/main.cpp @@ -104,6 +104,14 @@ struct MaterialPlugin : public AssetBrowser::IPlugin { b = material->isDefined(alpha_cutout_define); if (ImGui::Checkbox("Is alpha cutout", &b)) material->setDefine(alpha_cutout_define, b); + if(b) + { + float tmp = material->getAlphaRef(); + if(ImGui::DragFloat("Alpha reference value", &tmp, 0.01f, 0.0f, 1.0f)) + { + material->setAlphaRef(tmp); + } + } } b = material->isBackfaceCulling(); diff --git a/src/renderer/material.cpp b/src/renderer/material.cpp index 565348ee9..294156293 100644 --- a/src/renderer/material.cpp +++ b/src/renderer/material.cpp @@ -19,6 +19,7 @@ namespace Lumix static const uint32 SHADOWMAP_HASH = crc32("shadowmap"); +static const float DEFAULT_ALPHA_REF_VALUE = 0.3f; Material::Material(const Path& path, ResourceManager& resource_manager, IAllocator& allocator) @@ -38,6 +39,7 @@ Material::Material(const Path& path, ResourceManager& resource_manager, IAllocat enableZTest(true); enableBackfaceCulling(true); + setAlphaRef(DEFAULT_ALPHA_REF_VALUE); for (int i = 0; i < MAX_TEXTURE_COUNT; ++i) { m_textures[i] = nullptr; @@ -202,6 +204,7 @@ bool Material::save(JsonSerializer& serializer) serializer.endArray(); serializer.serialize("backface_culling", isBackfaceCulling()); serializer.serialize("shininess", m_shininess); + serializer.serialize("alpha_ref", m_alpha_ref); serializer.beginArray("specular"); serializer.serializeArrayItem(m_specular.x); serializer.serializeArrayItem(m_specular.y); @@ -581,11 +584,21 @@ void Material::setRenderState(bool value, uint64 state, uint64 mask) } +void Material::setAlphaRef(float value) +{ + m_alpha_ref = value; + uint8 val = uint8(value * 255.0f); + m_render_states &= ~BGFX_STATE_ALPHA_REF_MASK; + m_render_states |= BGFX_STATE_ALPHA_REF(val); +} + + bool Material::load(FS::IFile& file) { PROFILE_FUNCTION(); m_render_states = BGFX_STATE_DEPTH_TEST_LEQUAL | BGFX_STATE_CULL_CW; + setAlphaRef(DEFAULT_ALPHA_REF_VALUE); m_uniforms.clear(); JsonSerializer serializer(file, JsonSerializer::READ, getPath(), m_allocator); serializer.deserializeObjectBegin(); @@ -611,6 +624,12 @@ bool Material::load(FS::IFile& file) return false; } } + else if (compareString(label, "alpha_ref") == 0) + { + serializer.deserialize(m_alpha_ref, 0.3f); + uint8 val = uint8(m_alpha_ref * 255.0f); + m_render_states |= BGFX_STATE_ALPHA_REF(val); + } else if (compareString(label, "alpha_blending") == 0) { if (serializer.isNextBoolean()) diff --git a/src/renderer/material.h b/src/renderer/material.h index 70c12afd9..a94f362d2 100644 --- a/src/renderer/material.h +++ b/src/renderer/material.h @@ -56,6 +56,8 @@ public: void setShininess(float value) { m_shininess = value; } Vec3 getSpecular() const { return m_specular; } void setSpecular(const Vec3& specular) { m_specular = specular; } + float getAlphaRef() const { return m_alpha_ref; } + void setAlphaRef(float value); uint64 getRenderStates() const { return m_render_states; } void setShader(Shader* shader); @@ -102,6 +104,7 @@ private: uint64 m_render_states; Vec3 m_specular; float m_shininess; + float m_alpha_ref; uint32 m_define_mask; }; diff --git a/src/renderer/pipeline.cpp b/src/renderer/pipeline.cpp index 9a54e2998..bf7fd031a 100644 --- a/src/renderer/pipeline.cpp +++ b/src/renderer/pipeline.cpp @@ -1817,7 +1817,7 @@ struct PipelineImpl : public Pipeline } } - for (int i = 0; i < material->getTextureCount(); ++i) + for (int i = 0; i < shader->getTextureSlotCount(); ++i) { Texture* texture = material->getTexture(i); if (!texture) continue; @@ -2023,7 +2023,7 @@ struct PipelineImpl : public Pipeline if (!isReady()) return; m_stats = {}; - m_render_state = BGFX_STATE_DEFAULT; + m_render_state = BGFX_STATE_RGB_WRITE | BGFX_STATE_ALPHA_WRITE | BGFX_STATE_DEPTH_WRITE | BGFX_STATE_MSAA; m_applied_camera = INVALID_COMPONENT; m_global_light_shadowmap = nullptr; m_stencil = BGFX_STENCIL_NONE;