From 6447b5c0fabc406833d7c5bce90a7a1255f48a43 Mon Sep 17 00:00:00 2001 From: atdunbg Date: Fri, 9 Oct 2026 00:04:55 +0800 Subject: [PATCH] =?UTF-8?q?=E6=9D=90=E8=B4=A8=E8=A1=A8=E9=9D=A2=E5=8F=82?= =?UTF-8?q?=E6=95=B0=E6=8E=A5=E9=80=9A=EF=BC=9A=E6=96=B0=E5=A2=9E=20emissi?= =?UTF-8?q?veFactor=EF=BC=88=E6=97=A0=20emissive=20=E8=B4=B4=E5=9B=BE?= =?UTF-8?q?=E6=97=B6=E7=9A=84=E5=8F=91=E5=85=89=E5=85=A5=E5=8F=A3=EF=BC=8C?= =?UTF-8?q?glTF=20=E8=AF=AD=E4=B9=89=EF=BC=89=E5=85=A5=20UBO/YAML/?= =?UTF-8?q?=E7=BC=93=E5=AD=98=E9=94=AE/=E4=B8=A4=20shader=EF=BC=9BTransmis?= =?UTF-8?q?sion/Thickness=20=E6=9C=AA=E5=8B=BE=20Transparent=20=E6=97=B6?= =?UTF-8?q?=E7=A6=81=E7=94=A8=E7=BC=96=E8=BE=91=EF=BC=88=E4=B8=8D=E9=80=8F?= =?UTF-8?q?=E6=98=8E=E6=AE=B5=20shader=20=E4=B8=8D=E8=AF=BB=EF=BC=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- App/editor/panels/MaterialEditorPanel.cpp | 24 +++++++++++++++++++--- Engine/include/Engine/Renderer/Material.h | 4 ++++ Engine/src/Renderer/Material.cpp | 5 ++++- Engine/src/Renderer/MaterialAsset.cpp | 4 ++++ shaders/pbr/simple_shader.frag | 7 +++++-- shaders/pbr/simple_shader_translucent.frag | 6 ++++-- 6 files changed, 42 insertions(+), 8 deletions(-) diff --git a/App/editor/panels/MaterialEditorPanel.cpp b/App/editor/panels/MaterialEditorPanel.cpp index 30b8dfc..0be81ae 100644 --- a/App/editor/panels/MaterialEditorPanel.cpp +++ b/App/editor/panels/MaterialEditorPanel.cpp @@ -174,12 +174,23 @@ void MaterialEditorPanel::DrawAssetMode(const EditorContext& ctx) ImGui::DragFloat("Roughness", &p.factors.y, 0.01f, 0.0f, 1.0f)); EditParam(ImGui::ColorEdit4("Base Color", &p.baseColor.x)); EditParam(ImGui::DragFloat("IOR", &p.surface.x, 0.01f, 1.0f, 3.0f)); - EditParam(ImGui::DragFloat("Transmission", &p.surface.y, 0.01f, 0.0f, - 1.0f)); + // 发光 = emissiveFactor × emissive 贴图 × Strength(Emissive 槽 + // 兜底贴图恒黑,无贴图时颜色因子是唯一入口) + EditParam(ImGui::ColorEdit3("Emissive Color", &p.emissiveFactor.x)); EditParam(ImGui::DragFloat("Emissive Strength", &p.surface.z, 0.05f, 0.0f, 100.0f)); + // transmission/thickness 只有不透明段不读——透明 shader 专属 + //(未勾 Transparent 时禁用编辑,防"拖了没反应"的困惑) + ImGui::BeginDisabled(!trans); + EditParam(ImGui::DragFloat("Transmission", &p.surface.y, 0.01f, 0.0f, + 1.0f)); EditParam(ImGui::DragFloat("Thickness", &p.surface.w, 0.01f, 0.0f, 10.0f)); + ImGui::EndDisabled(); + if (!trans) + { + ImGui::TextDisabled("Transmission/Thickness need Transparent"); + } // ---- 纹理槽(变化 → 落盘 + waitIdle 重建)---- ImGui::SeparatorText("Textures"); @@ -303,9 +314,16 @@ void MaterialEditorPanel::DrawBuiltinMode(const EditorContext& ctx) ImGui::DragFloat("Roughness", &p.factors.y, 0.01f, 0.0f, 1.0f); ImGui::ColorEdit4("Base Color", &p.baseColor.x); ImGui::DragFloat("IOR", &p.surface.x, 0.01f, 1.0f, 3.0f); - ImGui::DragFloat("Transmission", &p.surface.y, 0.01f, 0.0f, 1.0f); + ImGui::ColorEdit3("Emissive Color", &p.emissiveFactor.x); ImGui::DragFloat("Emissive Strength", &p.surface.z, 0.05f, 0.0f, 100.0f); + ImGui::BeginDisabled(!trans); + ImGui::DragFloat("Transmission", &p.surface.y, 0.01f, 0.0f, 1.0f); ImGui::DragFloat("Thickness", &p.surface.w, 0.01f, 0.0f, 10.0f); + ImGui::EndDisabled(); + if (!trans) + { + ImGui::TextDisabled("Transmission/Thickness need Transparent"); + } ImGui::SeparatorText("Textures"); static constexpr const char* kSlotNames[Engine::Material::kSlotCount] = { "Albedo", "Normal", "MetallicRoughness", diff --git a/Engine/include/Engine/Renderer/Material.h b/Engine/include/Engine/Renderer/Material.h index d3f1c74..a191033 100644 --- a/Engine/include/Engine/Renderer/Material.h +++ b/Engine/include/Engine/Renderer/Material.h @@ -57,6 +57,10 @@ namespace Engine { glm::vec4 surface{1.5f, 0.0f, 1.0f, 0.0f}; // 杂项语义:x = unlit(KHR_materials_unlit,shader 早退直出 albedo) glm::vec4 misc{0.0f, 0.0f, 0.0f, 0.0f}; + // glTF emissiveFactor:自发光颜色(rgb;黑 = 不发光)。emissive + // 槽默认兜底纹理是纯黑,无贴图时 Emissive Strength 乘出来恒黑 + // ——无贴图想要发光就调这里(rgb × 贴图 × surface.z) + glm::vec4 emissiveFactor{0.0f, 0.0f, 0.0f, 0.0f}; // 每槽 KHR_texture_transform(glTF2 每个 textureInfo 独立声明 // offset/scale/rotation——烘焙单份顶点 UV 无法表达"一材质多槽 // 各异变换",收敛为 shader 侧线性式 uv' = A·uv + t,作用在本引擎 diff --git a/Engine/src/Renderer/Material.cpp b/Engine/src/Renderer/Material.cpp index b686626..8d7d641 100644 --- a/Engine/src/Renderer/Material.cpp +++ b/Engine/src/Renderer/Material.cpp @@ -84,7 +84,10 @@ namespace Engine ",s:" + std::to_string(params.surface.x) + "," + std::to_string(params.surface.y) + "," + std::to_string(params.surface.z) + - "," + std::to_string(params.surface.w); + "," + std::to_string(params.surface.w) + + ",e:" + std::to_string(params.emissiveFactor.x) + + "," + std::to_string(params.emissiveFactor.y) + + "," + std::to_string(params.emissiveFactor.z); // per-slot UV 变换 + unlit 入键:同一张贴图配不同变换是不同材质 //(KHR_texture_transform 测试模型:一张棋盘格被 82 个材质以不同 // 变换共享,键漏了会串成同一份) diff --git a/Engine/src/Renderer/MaterialAsset.cpp b/Engine/src/Renderer/MaterialAsset.cpp index 8df30bf..775db08 100644 --- a/Engine/src/Renderer/MaterialAsset.cpp +++ b/Engine/src/Renderer/MaterialAsset.cpp @@ -84,6 +84,8 @@ namespace Engine EmitVec4(out, data.params.baseColor); out << YAML::Key << "Surface" << YAML::Value; EmitVec4(out, data.params.surface); + out << YAML::Key << "EmissiveFactor" << YAML::Value; + EmitVec4(out, data.params.emissiveFactor); out << YAML::Key << "Misc" << YAML::Value; EmitVec4(out, data.params.misc); // per-slot UV 变换(KHR_texture_transform):6 槽各 A(4 分量) + T @@ -145,6 +147,8 @@ namespace Engine m["BaseColor"], MaterialParams{}.baseColor); out.params.surface = ReadVec4( m["Surface"], MaterialParams{}.surface); + out.params.emissiveFactor = ReadVec4( + m["EmissiveFactor"], MaterialParams{}.emissiveFactor); out.params.misc = ReadVec4( m["Misc"], MaterialParams{}.misc); for (u32 slot = 0; slot < Material::kSlotCount; ++slot) { diff --git a/shaders/pbr/simple_shader.frag b/shaders/pbr/simple_shader.frag index 04c1978..a2abbb4 100644 --- a/shaders/pbr/simple_shader.frag +++ b/shaders/pbr/simple_shader.frag @@ -46,6 +46,7 @@ layout(set = 1, binding = 6) uniform MaterialParams { vec4 baseColor; // glTF baseColorFactor:rgb 调色 albedo,a = BLEND 透明度 vec4 surface; // x = ior(F0 换算),y = transmission(不透明段恒 0 语义),z = 自发光强度,w = 体积厚度 vec4 misc; // x = unlit(KHR_materials_unlit,1 = 早退直出 albedo) + vec4 emissiveFactor; // 自发光颜色(rgb × emissiveMap × surface.z;黑 = 不发光) vec4 uvA[6]; // 每槽 UV 线性变换(KHR_texture_transform,v-up 空间)(a11,a12,a21,a22),槽序 = binding vec4 uvT[6]; // 每槽 UV 平移 (tx, ty, 0, 0) } matParams; @@ -166,8 +167,10 @@ void main() { matParams.factors.z) * matParams.factors.y, 0.045, 1.0); float metallic = clamp(mr.b * matParams.factors.x, 0.0, 1.0); - // 自发光强度(KHR_materials_emissive_strength,缺省 1) - vec3 emissive = texture(emissiveMap, ApplyUv(3, fragUV)).rgb * matParams.surface.z; + // 自发光强度(KHR_materials_emissive_strength,缺省 1); + // emissiveFactor = 颜色因子(无贴图时发光的入口——兜底贴图恒黑) + vec3 emissive = texture(emissiveMap, ApplyUv(3, fragUV)).rgb + * matParams.emissiveFactor.rgb * matParams.surface.z; vec3 N = MappedNormal(normalize(fragNormal), fragTangent, ApplyUv(1, fragUV)); vec3 V = normalize(ubo.cameraPos.xyz - fragWorldPos); diff --git a/shaders/pbr/simple_shader_translucent.frag b/shaders/pbr/simple_shader_translucent.frag index 78c9338..beb4130 100644 --- a/shaders/pbr/simple_shader_translucent.frag +++ b/shaders/pbr/simple_shader_translucent.frag @@ -46,7 +46,8 @@ layout(set = 1, binding = 6) uniform MaterialParams { vec4 baseColor; // glTF baseColorFactor:rgb 调色 albedo,a = BLEND 透明度 vec4 surface; // x = ior,y = transmission(KHR_materials_transmission),z = 自发光强度,w = 体积厚度 vec4 misc; // x = unlit(透射材质不会是 unlit,仅为与 simple_shader 布局一致) - vec4 uvA[6]; // 每槽 UV 线性变换(KHR_texture_transform,v-up 空间)(a11,a12,a21,a22) + vec4 emissiveFactor; // 自发光颜色(rgb × emissiveMap × surface.z;黑 = 不发光) + vec4 uvA[6]; // 每槽 UV 线性变换(KHR_texture_transform,v-up 空间)(a11,a12,a21,a22),槽序 = binding vec4 uvT[6]; // 每槽 UV 平移 (tx, ty, 0, 0) } matParams; @@ -159,7 +160,8 @@ void main() { 0.045, 1.0); float metallic = clamp(mr.b * matParams.factors.x, 0.0, 1.0); // 自发光强度(KHR_materials_emissive_strength,缺省 1) - vec3 emissive = texture(emissiveMap, ApplyUv(3, fragUV)).rgb * matParams.surface.z; + vec3 emissive = texture(emissiveMap, ApplyUv(3, fragUV)).rgb + * matParams.emissiveFactor.rgb * matParams.surface.z; // glTF 表面扩展:透射率(KHR_materials_transmission)/ // 折射率(ior,缺省 1.5)/ 体积厚度(KHR_materials_volume)