From 75657a188d2c9d09fbe3fee5bd8381b56e8aaa50 Mon Sep 17 00:00:00 2001 From: Turanszki Janos Date: Wed, 8 Apr 2020 00:10:06 +0100 Subject: [PATCH] terrain updates #104 --- Editor/MeshWindow.cpp | 220 ++++++++++++++++++++++------- Editor/MeshWindow.h | 9 +- WickedEngine/objectHF.hlsli | 266 +++++++++++++++++++++++++----------- WickedEngine/wiRenderer.cpp | 2 +- WickedEngine/wiVersion.cpp | 2 +- 5 files changed, 368 insertions(+), 131 deletions(-) diff --git a/Editor/MeshWindow.cpp b/Editor/MeshWindow.cpp index 1d9f9e646..280550959 100644 --- a/Editor/MeshWindow.cpp +++ b/Editor/MeshWindow.cpp @@ -318,48 +318,66 @@ MeshWindow::MeshWindow(EditorComponent* editor) : GUI(&editor->GetGUI()) terrainMat3Combo->SetTooltip("Choose a sub terrain blend material."); meshWindow->AddWidget(terrainMat3Combo); - terrainFromHeightMapButton = new wiButton("Create Terrain From Heightmap"); - terrainFromHeightMapButton->SetTooltip("Load a heightmap texture, where the red channel corresponds to terrain height and the resolution to dimensions"); - terrainFromHeightMapButton->SetSize(XMFLOAT2(200, 20)); - terrainFromHeightMapButton->SetPos(XMFLOAT2(x + 180, y += step)); - terrainFromHeightMapButton->OnClick([=](wiEventArgs args) { + terrainGenButton = new wiButton("Generate Terrain..."); + terrainGenButton->SetTooltip("Generate terrain meshes."); + terrainGenButton->SetSize(XMFLOAT2(200, 20)); + terrainGenButton->SetPos(XMFLOAT2(x + 180, y += step)); + terrainGenButton->OnClick([=](wiEventArgs args) { - wiHelper::FileDialogParams params; - wiHelper::FileDialogResult result; - params.type = wiHelper::FileDialogParams::OPEN; - params.description = "Texture"; - params.extensions.push_back("dds"); - params.extensions.push_back("png"); - params.extensions.push_back("jpg"); - params.extensions.push_back("tga"); - wiHelper::FileDialog(params, result); + if (terrainGenWindow != nullptr) + { + GUI->RemoveWidget(terrainGenWindow); + delete terrainGenWindow; + terrainGenWindow = nullptr; + } + if (this->rgb != nullptr) + { + stbi_image_free(this->rgb); + this->rgb = nullptr; + } - if (result.ok) { - string fileName = result.filenames.front(); + terrainGenWindow = new wiWindow(GUI, "Terrain Gen"); + terrainGenWindow->SetSize(XMFLOAT2(260, 130)); + GUI->AddWidget(terrainGenWindow); - Scene& scene = wiScene::GetScene(); - Entity entity = scene.Entity_CreateObject("editorTerrain"); - ObjectComponent& object = *scene.objects.GetComponent(entity); - object.meshID = scene.Entity_CreateMesh("terrainMesh"); - MeshComponent& mesh = *scene.meshes.GetComponent(object.meshID); - const int channelCount = 4; - int width, height, bpp; - unsigned char* rgb = stbi_load(fileName.c_str(), &width, &height, &bpp, channelCount); + float xx = 20; + float yy = 0; + float stepstep = 25; + float heihei = 20; - mesh.vertex_positions.resize(width * height); - mesh.vertex_normals.resize(width * height); - mesh.vertex_colors.resize(width * height); + + + Scene& scene = wiScene::GetScene(); + Entity entity = scene.Entity_CreateObject("editorTerrain"); + ObjectComponent& object = *scene.objects.GetComponent(entity); + object.meshID = scene.Entity_CreateMesh("terrainMesh"); + MeshComponent* mesh = scene.meshes.GetComponent(object.meshID); + mesh->SetTerrain(true); + mesh->subsets.emplace_back(); + mesh->subsets.back().materialID = scene.Entity_CreateMaterial("terrainMaterial"); + mesh->subsets.back().indexOffset = 0; + MaterialComponent* material = scene.materials.GetComponent(mesh->subsets.back().materialID); + material->SetUseVertexColors(true); + + auto generate_mesh = [=] (int width, int height, unsigned char* rgb = nullptr, + int channelCount = 4, float heightmap_scale = 1) + { + mesh->vertex_positions.resize(width * height); + mesh->vertex_normals.resize(width * height); + mesh->vertex_colors.resize(width * height); for (int i = 0; i < width; ++i) { for (int j = 0; j < height; ++j) { size_t index = size_t(i + j * width); - mesh.vertex_positions[index] = XMFLOAT3((float)i - (float)width * 0.5f, (float)rgb[index * channelCount] - 127.0f, (float)j - (float)height * 0.5f); - mesh.vertex_colors[index] = wiColor::Red().rgba; + mesh->vertex_positions[index] = XMFLOAT3((float)i - (float)width * 0.5f, 0, (float)j - (float)height * 0.5f); + if (rgb != nullptr) + mesh->vertex_positions[index].y = ((float)rgb[index * channelCount] - 127.0f) * heightmap_scale; + mesh->vertex_colors[index] = wiColor::Red().rgba; } } - mesh.indices.resize((width - 1) * (height - 1) * 6); + mesh->indices.resize((width - 1) * (height - 1) * 6); size_t counter = 0; for (int x = 0; x < width - 1; x++) { @@ -370,31 +388,105 @@ MeshWindow::MeshWindow(EditorComponent* editor) : GUI(&editor->GetGUI()) int topLeft = x + (y + 1) * width; int topRight = (x + 1) + (y + 1) * width; - mesh.indices[counter++] = topLeft; - mesh.indices[counter++] = lowerLeft; - mesh.indices[counter++] = lowerRight; + mesh->indices[counter++] = topLeft; + mesh->indices[counter++] = lowerLeft; + mesh->indices[counter++] = lowerRight; - mesh.indices[counter++] = topLeft; - mesh.indices[counter++] = lowerRight; - mesh.indices[counter++] = topRight; + mesh->indices[counter++] = topLeft; + mesh->indices[counter++] = lowerRight; + mesh->indices[counter++] = topRight; } } - mesh.subsets.emplace_back(); - mesh.subsets.back().materialID = scene.Entity_CreateMaterial("terrainMaterial"); - mesh.subsets.back().indexOffset = 0; - mesh.subsets.back().indexCount = (uint32_t)mesh.indices.size(); + mesh->subsets.back().indexCount = (uint32_t)mesh->indices.size(); - mesh.ComputeNormals(MeshComponent::COMPUTE_NORMALS_SMOOTH_FAST); + mesh->ComputeNormals(MeshComponent::COMPUTE_NORMALS_SMOOTH_FAST); + }; + generate_mesh(128, 128); + + editor->ClearSelected(); + wiScene::PickResult pick; + pick.entity = entity; + pick.subsetIndex = 0; + editor->AddSelected(pick); + SetEntity(object.meshID); - editor->ClearSelected(); - wiScene::PickResult pick; - pick.entity = entity; - pick.subsetIndex = 0; - editor->AddSelected(pick); - SetEntity(entity); - } + + wiSlider* dimXSlider; + wiSlider* dimYSlider; + wiSlider* dimZSlider; + + dimXSlider = new wiSlider(16, 1024, 128, 1024 - 16, "X: "); + dimXSlider->SetTooltip("Terrain mesh grid resolution on X axis"); + dimXSlider->SetSize(XMFLOAT2(200, heihei)); + dimXSlider->SetPos(XMFLOAT2(xx, yy += stepstep)); + terrainGenWindow->AddWidget(dimXSlider); + + dimYSlider = new wiSlider(0, 1, 0.5f, 10000, "Y: "); + dimYSlider->SetTooltip("Terrain mesh grid heightmap scale on Y axis"); + dimYSlider->SetSize(XMFLOAT2(200, heihei)); + dimYSlider->SetPos(XMFLOAT2(xx, yy += stepstep)); + terrainGenWindow->AddWidget(dimYSlider); + + dimZSlider = new wiSlider(16, 1024, 128, 1024 - 16, "Z: "); + dimZSlider->SetTooltip("Terrain mesh grid resolution on Z axis"); + dimZSlider->SetSize(XMFLOAT2(200, heihei)); + dimZSlider->SetPos(XMFLOAT2(xx, yy += stepstep)); + terrainGenWindow->AddWidget(dimZSlider); + + dimXSlider->OnSlide([=](wiEventArgs args) { + this->width = (int)dimXSlider->GetValue(); + this->height = (int)dimZSlider->GetValue(); + generate_mesh(this->width, this->height); + }); + dimZSlider->OnSlide([=](wiEventArgs args) { + this->width = (int)dimXSlider->GetValue(); + this->height = (int)dimZSlider->GetValue(); + generate_mesh(this->width, this->height); + }); + dimYSlider->OnSlide([=](wiEventArgs args) { + generate_mesh(this->width, this->height, this->rgb, this->channelCount, args.fValue); + }); + + wiButton* heightmapButton = new wiButton("Load Heightmap..."); + heightmapButton->SetTooltip("Load a heightmap texture, where the red channel corresponds to terrain height and the resolution to dimensions"); + heightmapButton->SetSize(XMFLOAT2(200, heihei)); + heightmapButton->SetPos(XMFLOAT2(xx, yy += stepstep)); + heightmapButton->OnClick([=](wiEventArgs args) { + + wiHelper::FileDialogParams params; + wiHelper::FileDialogResult result; + params.type = wiHelper::FileDialogParams::OPEN; + params.description = "Texture"; + params.extensions.push_back("dds"); + params.extensions.push_back("png"); + params.extensions.push_back("jpg"); + params.extensions.push_back("tga"); + wiHelper::FileDialog(params, result); + + if (result.ok) { + string fileName = result.filenames.front(); + + if (this->rgb != nullptr) + { + stbi_image_free(this->rgb); + this->rgb = nullptr; + } + + int bpp; + this->rgb = stbi_load(fileName.c_str(), &this->width, &this->height, &bpp, channelCount); + + generate_mesh(width, height, rgb, channelCount, dimYSlider->GetValue()); + } + }); + terrainGenWindow->AddWidget(heightmapButton); + + terrainGenWindow->Translate(XMFLOAT3( + terrainGenButton->translation.x + terrainGenButton->scale.x + 10, + terrainGenButton->translation.y, + 0) + ); }); - meshWindow->AddWidget(terrainFromHeightMapButton); + meshWindow->AddWidget(terrainGenButton); @@ -404,12 +496,23 @@ MeshWindow::MeshWindow(EditorComponent* editor) : GUI(&editor->GetGUI()) SetEntity(INVALID_ENTITY); } - MeshWindow::~MeshWindow() { meshWindow->RemoveWidgets(true); GUI->RemoveWidget(meshWindow); delete meshWindow; + + if (terrainGenWindow != nullptr) + { + GUI->RemoveWidget(terrainGenWindow); + delete terrainGenWindow; + terrainGenWindow = nullptr; + } + if (this->rgb != nullptr) + { + stbi_image_free(this->rgb); + this->rgb = nullptr; + } } void MeshWindow::SetEntity(Entity entity) @@ -420,6 +523,21 @@ void MeshWindow::SetEntity(Entity entity) const MeshComponent* mesh = scene.meshes.GetComponent(entity); + if (mesh == nullptr || !mesh->IsTerrain()) + { + if (terrainGenWindow != nullptr) + { + GUI->RemoveWidget(terrainGenWindow); + delete terrainGenWindow; + terrainGenWindow = nullptr; + } + if (this->rgb != nullptr) + { + stbi_image_free(this->rgb); + this->rgb = nullptr; + } + } + if (mesh != nullptr) { const NameComponent& name = *scene.names.GetComponent(entity); @@ -497,5 +615,5 @@ void MeshWindow::SetEntity(Entity entity) meshWindow->SetEnabled(false); } - terrainFromHeightMapButton->SetEnabled(true); + terrainGenButton->SetEnabled(true); } diff --git a/Editor/MeshWindow.h b/Editor/MeshWindow.h index 7d67e9c57..3566df1c4 100644 --- a/Editor/MeshWindow.h +++ b/Editor/MeshWindow.h @@ -41,6 +41,13 @@ public: wiComboBox* terrainMat1Combo; wiComboBox* terrainMat2Combo; wiComboBox* terrainMat3Combo; - wiButton* terrainFromHeightMapButton; + wiButton* terrainGenButton; + + wiWindow* terrainGenWindow = nullptr; + + // heightmap texture: + unsigned char* rgb = nullptr; + const int channelCount = 4; + int width = 0, height = 0; }; diff --git a/WickedEngine/objectHF.hlsli b/WickedEngine/objectHF.hlsli index d03002ea2..43e4aa2f5 100644 --- a/WickedEngine/objectHF.hlsli +++ b/WickedEngine/objectHF.hlsli @@ -815,7 +815,7 @@ GBUFFEROutputType_Thin main(PIXELINPUT input) blend_weights /= blend_weights.x + blend_weights.y + blend_weights.z + blend_weights.w; float3 triplanar = abs(surface.N); triplanar /= triplanar.x + triplanar.y + triplanar.z; - float4 sam_x, sam_y, sam_z; + float4 sam, sam_x, sam_y, sam_z; float2 uv_x, uv_y, uv_z; [branch] @@ -824,25 +824,53 @@ GBUFFEROutputType_Thin main(PIXELINPUT input) uv_x = surface.P.yz * g_xMaterial.texMulAdd.xy + g_xMaterial.texMulAdd.zw; uv_y = surface.P.xz * g_xMaterial.texMulAdd.xy + g_xMaterial.texMulAdd.zw; uv_z = surface.P.xy * g_xMaterial.texMulAdd.xy + g_xMaterial.texMulAdd.zw; - sam_x = texture_basecolormap.Sample(sampler_objectshader, uv_x); - sam_y = texture_basecolormap.Sample(sampler_objectshader, uv_y); - sam_z = texture_basecolormap.Sample(sampler_objectshader, uv_z); - sam_x.rgb = DEGAMMA(sam_x.rgb); - sam_y.rgb = DEGAMMA(sam_y.rgb); - sam_z.rgb = DEGAMMA(sam_z.rgb); - color += (sam_x * triplanar.x + sam_y * triplanar.y + sam_z * triplanar.z) * g_xMaterial.baseColor * blend_weights.x; - sam_x = texture_surfacemap.Sample(sampler_objectshader, uv_x); - sam_y = texture_surfacemap.Sample(sampler_objectshader, uv_y); - sam_z = texture_surfacemap.Sample(sampler_objectshader, uv_z); - surface_occlusion_roughness_metallic_reflectance += (sam_x * triplanar.x + sam_y * triplanar.y + sam_z * triplanar.z) * - float4(1, g_xMaterial.roughness, g_xMaterial.metalness, g_xMaterial.reflectance) * blend_weights.x; - sam_x.xyz = texture_normalmap.Sample(sampler_objectshader, uv_x).rgb; - sam_y.xyz = texture_normalmap.Sample(sampler_objectshader, uv_y).rgb; - sam_z.xyz = texture_normalmap.Sample(sampler_objectshader, uv_z).rgb; - bumpColor = (sam_x.xyz * triplanar.x + sam_y.xyz * triplanar.y + sam_z.xyz * triplanar.z); - bumpColor = bumpColor.rgb * 2 - 1; - bumpColor.g *= g_xMaterial.normalMapFlip; - triplanar_normal += normalize(lerp(surface.N, mul(bumpColor, TBN), g_xMaterial.normalMapStrength)) * blend_weights.x; + + [branch] + if (g_xMaterial.uvset_baseColorMap >= 0) + { + sam_x = texture_basecolormap.Sample(sampler_objectshader, uv_x); + sam_y = texture_basecolormap.Sample(sampler_objectshader, uv_y); + sam_z = texture_basecolormap.Sample(sampler_objectshader, uv_z); + sam_x.rgb = DEGAMMA(sam_x.rgb); + sam_y.rgb = DEGAMMA(sam_y.rgb); + sam_z.rgb = DEGAMMA(sam_z.rgb); + sam = (sam_x * triplanar.x + sam_y * triplanar.y + sam_z * triplanar.z); + } + else + { + sam = 1; + } + color += sam * g_xMaterial.baseColor * blend_weights.x; + + [branch] + if (g_xMaterial.uvset_surfaceMap >= 0) + { + sam_x = texture_surfacemap.Sample(sampler_objectshader, uv_x); + sam_y = texture_surfacemap.Sample(sampler_objectshader, uv_y); + sam_z = texture_surfacemap.Sample(sampler_objectshader, uv_z); + sam = (sam_x * triplanar.x + sam_y * triplanar.y + sam_z * triplanar.z); + } + else + { + sam = 1; + } + surface_occlusion_roughness_metallic_reflectance += sam * float4(1, g_xMaterial.roughness, g_xMaterial.metalness, g_xMaterial.reflectance) * blend_weights.x; + + [branch] + if (g_xMaterial.uvset_normalMap >= 0) + { + sam_x.xyz = texture_normalmap.Sample(sampler_objectshader, uv_x).rgb; + sam_y.xyz = texture_normalmap.Sample(sampler_objectshader, uv_y).rgb; + sam_z.xyz = texture_normalmap.Sample(sampler_objectshader, uv_z).rgb; + bumpColor = (sam_x.xyz * triplanar.x + sam_y.xyz * triplanar.y + sam_z.xyz * triplanar.z); + bumpColor = bumpColor.rgb * 2 - 1; + bumpColor.g *= g_xMaterial.normalMapFlip; + triplanar_normal += normalize(lerp(surface.N, mul(bumpColor, TBN), g_xMaterial.normalMapStrength)) * blend_weights.x; + } + else + { + triplanar_normal += surface.N * blend_weights.x; + } } [branch] @@ -851,25 +879,53 @@ GBUFFEROutputType_Thin main(PIXELINPUT input) uv_x = surface.P.yz * g_xMaterial_blend1.texMulAdd.xy + g_xMaterial_blend1.texMulAdd.zw; uv_y = surface.P.xz * g_xMaterial_blend1.texMulAdd.xy + g_xMaterial_blend1.texMulAdd.zw; uv_z = surface.P.xy * g_xMaterial_blend1.texMulAdd.xy + g_xMaterial_blend1.texMulAdd.zw; - sam_x = texture_blend1_basecolormap.Sample(sampler_objectshader, uv_x); - sam_y = texture_blend1_basecolormap.Sample(sampler_objectshader, uv_y); - sam_z = texture_blend1_basecolormap.Sample(sampler_objectshader, uv_z); - sam_x.rgb = DEGAMMA(sam_x.rgb); - sam_y.rgb = DEGAMMA(sam_y.rgb); - sam_z.rgb = DEGAMMA(sam_z.rgb); - color += (sam_x * triplanar.x + sam_y * triplanar.y + sam_z * triplanar.z) * g_xMaterial_blend1.baseColor * blend_weights.y; - sam_x = texture_blend1_surfacemap.Sample(sampler_objectshader, uv_x); - sam_y = texture_blend1_surfacemap.Sample(sampler_objectshader, uv_y); - sam_z = texture_blend1_surfacemap.Sample(sampler_objectshader, uv_z); - surface_occlusion_roughness_metallic_reflectance += (sam_x * triplanar.x + sam_y * triplanar.y + sam_z * triplanar.z) * - float4(1, g_xMaterial_blend1.roughness, g_xMaterial_blend1.metalness, g_xMaterial_blend1.reflectance) * blend_weights.y; - sam_x.xyz = texture_blend1_normalmap.Sample(sampler_objectshader, uv_x).rgb; - sam_y.xyz = texture_blend1_normalmap.Sample(sampler_objectshader, uv_y).rgb; - sam_z.xyz = texture_blend1_normalmap.Sample(sampler_objectshader, uv_z).rgb; - bumpColor = (sam_x.xyz * triplanar.x + sam_y.xyz * triplanar.y + sam_z.xyz * triplanar.z); - bumpColor = bumpColor.rgb * 2 - 1; - bumpColor.g *= g_xMaterial_blend1.normalMapFlip; - triplanar_normal += normalize(lerp(surface.N, mul(bumpColor, TBN), g_xMaterial_blend1.normalMapStrength)) * blend_weights.y; + + [branch] + if (g_xMaterial_blend1.uvset_baseColorMap >= 0) + { + sam_x = texture_blend1_basecolormap.Sample(sampler_objectshader, uv_x); + sam_y = texture_blend1_basecolormap.Sample(sampler_objectshader, uv_y); + sam_z = texture_blend1_basecolormap.Sample(sampler_objectshader, uv_z); + sam_x.rgb = DEGAMMA(sam_x.rgb); + sam_y.rgb = DEGAMMA(sam_y.rgb); + sam_z.rgb = DEGAMMA(sam_z.rgb); + sam = (sam_x * triplanar.x + sam_y * triplanar.y + sam_z * triplanar.z); + } + else + { + sam = 1; + } + color += sam * g_xMaterial_blend1.baseColor * blend_weights.y; + + [branch] + if (g_xMaterial_blend1.uvset_surfaceMap >= 0) + { + sam_x = texture_blend1_surfacemap.Sample(sampler_objectshader, uv_x); + sam_y = texture_blend1_surfacemap.Sample(sampler_objectshader, uv_y); + sam_z = texture_blend1_surfacemap.Sample(sampler_objectshader, uv_z); + sam = (sam_x * triplanar.x + sam_y * triplanar.y + sam_z * triplanar.z); + } + else + { + sam = 1; + } + surface_occlusion_roughness_metallic_reflectance += sam * float4(1, g_xMaterial_blend1.roughness, g_xMaterial_blend1.metalness, g_xMaterial_blend1.reflectance) * blend_weights.y; + + [branch] + if (g_xMaterial_blend1.uvset_normalMap >= 0) + { + sam_x.xyz = texture_blend1_normalmap.Sample(sampler_objectshader, uv_x).rgb; + sam_y.xyz = texture_blend1_normalmap.Sample(sampler_objectshader, uv_y).rgb; + sam_z.xyz = texture_blend1_normalmap.Sample(sampler_objectshader, uv_z).rgb; + bumpColor = (sam_x.xyz * triplanar.x + sam_y.xyz * triplanar.y + sam_z.xyz * triplanar.z); + bumpColor = bumpColor.rgb * 2 - 1; + bumpColor.g *= g_xMaterial_blend1.normalMapFlip; + triplanar_normal += normalize(lerp(surface.N, mul(bumpColor, TBN), g_xMaterial_blend1.normalMapStrength)) * blend_weights.y; + } + else + { + triplanar_normal += surface.N * blend_weights.y; + } } [branch] @@ -878,25 +934,53 @@ GBUFFEROutputType_Thin main(PIXELINPUT input) uv_x = surface.P.yz * g_xMaterial_blend2.texMulAdd.xy + g_xMaterial_blend2.texMulAdd.zw; uv_y = surface.P.xz * g_xMaterial_blend2.texMulAdd.xy + g_xMaterial_blend2.texMulAdd.zw; uv_z = surface.P.xy * g_xMaterial_blend2.texMulAdd.xy + g_xMaterial_blend2.texMulAdd.zw; - sam_x = texture_blend2_basecolormap.Sample(sampler_objectshader, uv_x); - sam_y = texture_blend2_basecolormap.Sample(sampler_objectshader, uv_y); - sam_z = texture_blend2_basecolormap.Sample(sampler_objectshader, uv_z); - sam_x.rgb = DEGAMMA(sam_x.rgb); - sam_y.rgb = DEGAMMA(sam_y.rgb); - sam_z.rgb = DEGAMMA(sam_z.rgb); - color += (sam_x * triplanar.x + sam_y * triplanar.y + sam_z * triplanar.z) * g_xMaterial_blend2.baseColor * blend_weights.z; - sam_x = texture_blend2_surfacemap.Sample(sampler_objectshader, uv_x); - sam_y = texture_blend2_surfacemap.Sample(sampler_objectshader, uv_y); - sam_z = texture_blend2_surfacemap.Sample(sampler_objectshader, uv_z); - surface_occlusion_roughness_metallic_reflectance += (sam_x * triplanar.x + sam_y * triplanar.y + sam_z * triplanar.z) * - float4(1, g_xMaterial_blend2.roughness, g_xMaterial_blend2.metalness, g_xMaterial_blend2.reflectance) * blend_weights.z; - sam_x.xyz = texture_blend2_normalmap.Sample(sampler_objectshader, uv_x).rgb; - sam_y.xyz = texture_blend2_normalmap.Sample(sampler_objectshader, uv_y).rgb; - sam_z.xyz = texture_blend2_normalmap.Sample(sampler_objectshader, uv_z).rgb; - bumpColor = (sam_x.xyz * triplanar.x + sam_y.xyz * triplanar.y + sam_z.xyz * triplanar.z); - bumpColor = bumpColor.rgb * 2 - 1; - bumpColor.g *= g_xMaterial_blend2.normalMapFlip; - triplanar_normal += normalize(lerp(surface.N, mul(bumpColor, TBN), g_xMaterial_blend2.normalMapStrength)) * blend_weights.z; + + [branch] + if (g_xMaterial_blend2.uvset_baseColorMap >= 0) + { + sam_x = texture_blend2_basecolormap.Sample(sampler_objectshader, uv_x); + sam_y = texture_blend2_basecolormap.Sample(sampler_objectshader, uv_y); + sam_z = texture_blend2_basecolormap.Sample(sampler_objectshader, uv_z); + sam_x.rgb = DEGAMMA(sam_x.rgb); + sam_y.rgb = DEGAMMA(sam_y.rgb); + sam_z.rgb = DEGAMMA(sam_z.rgb); + sam = (sam_x * triplanar.x + sam_y * triplanar.y + sam_z * triplanar.z); + } + else + { + sam = 1; + } + color += sam * g_xMaterial_blend2.baseColor * blend_weights.z; + + [branch] + if (g_xMaterial_blend2.uvset_surfaceMap >= 0) + { + sam_x = texture_blend2_surfacemap.Sample(sampler_objectshader, uv_x); + sam_y = texture_blend2_surfacemap.Sample(sampler_objectshader, uv_y); + sam_z = texture_blend2_surfacemap.Sample(sampler_objectshader, uv_z); + sam = (sam_x * triplanar.x + sam_y * triplanar.y + sam_z * triplanar.z); + } + else + { + sam = 1; + } + surface_occlusion_roughness_metallic_reflectance += sam * float4(1, g_xMaterial_blend2.roughness, g_xMaterial_blend2.metalness, g_xMaterial_blend2.reflectance) * blend_weights.z; + + [branch] + if (g_xMaterial_blend2.uvset_normalMap >= 0) + { + sam_x.xyz = texture_blend2_normalmap.Sample(sampler_objectshader, uv_x).rgb; + sam_y.xyz = texture_blend2_normalmap.Sample(sampler_objectshader, uv_y).rgb; + sam_z.xyz = texture_blend2_normalmap.Sample(sampler_objectshader, uv_z).rgb; + bumpColor = (sam_x.xyz * triplanar.x + sam_y.xyz * triplanar.y + sam_z.xyz * triplanar.z); + bumpColor = bumpColor.rgb * 2 - 1; + bumpColor.g *= g_xMaterial_blend2.normalMapFlip; + triplanar_normal += normalize(lerp(surface.N, mul(bumpColor, TBN), g_xMaterial_blend2.normalMapStrength)) * blend_weights.z; + } + else + { + triplanar_normal += surface.N * blend_weights.z; + } } [branch] @@ -905,25 +989,53 @@ GBUFFEROutputType_Thin main(PIXELINPUT input) uv_x = surface.P.yz * g_xMaterial_blend3.texMulAdd.xy + g_xMaterial_blend3.texMulAdd.zw; uv_y = surface.P.xz * g_xMaterial_blend3.texMulAdd.xy + g_xMaterial_blend3.texMulAdd.zw; uv_z = surface.P.xy * g_xMaterial_blend3.texMulAdd.xy + g_xMaterial_blend3.texMulAdd.zw; - sam_x = texture_blend3_basecolormap.Sample(sampler_objectshader, uv_x); - sam_y = texture_blend3_basecolormap.Sample(sampler_objectshader, uv_y); - sam_z = texture_blend3_basecolormap.Sample(sampler_objectshader, uv_z); - sam_x.rgb = DEGAMMA(sam_x.rgb); - sam_y.rgb = DEGAMMA(sam_y.rgb); - sam_z.rgb = DEGAMMA(sam_z.rgb); - color += (sam_x * triplanar.x + sam_y * triplanar.y + sam_z * triplanar.z) * g_xMaterial_blend3.baseColor * blend_weights.w; - sam_x = texture_blend3_surfacemap.Sample(sampler_objectshader, uv_x); - sam_y = texture_blend3_surfacemap.Sample(sampler_objectshader, uv_y); - sam_z = texture_blend3_surfacemap.Sample(sampler_objectshader, uv_z); - surface_occlusion_roughness_metallic_reflectance += (sam_x * triplanar.x + sam_y * triplanar.y + sam_z * triplanar.z) * - float4(1, g_xMaterial_blend3.roughness, g_xMaterial_blend3.metalness, g_xMaterial_blend3.reflectance) * blend_weights.w; - sam_x.xyz = texture_blend3_normalmap.Sample(sampler_objectshader, uv_x).rgb; - sam_y.xyz = texture_blend3_normalmap.Sample(sampler_objectshader, uv_y).rgb; - sam_z.xyz = texture_blend3_normalmap.Sample(sampler_objectshader, uv_z).rgb; - bumpColor = (sam_x.xyz * triplanar.x + sam_y.xyz * triplanar.y + sam_z.xyz * triplanar.z); - bumpColor = bumpColor.rgb * 2 - 1; - bumpColor.g *= g_xMaterial_blend3.normalMapFlip; - triplanar_normal += normalize(lerp(surface.N, mul(bumpColor, TBN), g_xMaterial_blend3.normalMapStrength)) * blend_weights.w; + + [branch] + if (g_xMaterial_blend3.uvset_baseColorMap >= 0) + { + sam_x = texture_blend3_basecolormap.Sample(sampler_objectshader, uv_x); + sam_y = texture_blend3_basecolormap.Sample(sampler_objectshader, uv_y); + sam_z = texture_blend3_basecolormap.Sample(sampler_objectshader, uv_z); + sam_x.rgb = DEGAMMA(sam_x.rgb); + sam_y.rgb = DEGAMMA(sam_y.rgb); + sam_z.rgb = DEGAMMA(sam_z.rgb); + sam = (sam_x * triplanar.x + sam_y * triplanar.y + sam_z * triplanar.z); + } + else + { + sam = 1; + } + color += sam * g_xMaterial_blend3.baseColor * blend_weights.w; + + [branch] + if (g_xMaterial_blend3.uvset_surfaceMap >= 0) + { + sam_x = texture_blend3_surfacemap.Sample(sampler_objectshader, uv_x); + sam_y = texture_blend3_surfacemap.Sample(sampler_objectshader, uv_y); + sam_z = texture_blend3_surfacemap.Sample(sampler_objectshader, uv_z); + sam = (sam_x * triplanar.x + sam_y * triplanar.y + sam_z * triplanar.z); + } + else + { + sam = 1; + } + surface_occlusion_roughness_metallic_reflectance += sam * float4(1, g_xMaterial_blend3.roughness, g_xMaterial_blend3.metalness, g_xMaterial_blend3.reflectance) * blend_weights.w; + + [branch] + if (g_xMaterial_blend3.uvset_normalMap >= 0) + { + sam_x.xyz = texture_blend3_normalmap.Sample(sampler_objectshader, uv_x).rgb; + sam_y.xyz = texture_blend3_normalmap.Sample(sampler_objectshader, uv_y).rgb; + sam_z.xyz = texture_blend3_normalmap.Sample(sampler_objectshader, uv_z).rgb; + bumpColor = (sam_x.xyz * triplanar.x + sam_y.xyz * triplanar.y + sam_z.xyz * triplanar.z); + bumpColor = bumpColor.rgb * 2 - 1; + bumpColor.g *= g_xMaterial_blend3.normalMapFlip; + triplanar_normal += normalize(lerp(surface.N, mul(bumpColor, TBN), g_xMaterial_blend3.normalMapStrength)) * blend_weights.w; + } + else + { + triplanar_normal += surface.N * blend_weights.w; + } } color.a = 1; diff --git a/WickedEngine/wiRenderer.cpp b/WickedEngine/wiRenderer.cpp index 45e0a4c22..4ac7b98d3 100644 --- a/WickedEngine/wiRenderer.cpp +++ b/WickedEngine/wiRenderer.cpp @@ -3505,7 +3505,7 @@ void RenderMeshes(const RenderQueue& renderQueue, RENDERPASS renderPass, uint32_ blendmat.GetSurfaceMap(), }; device->BindResources(PS, res, TEXSLOT_RENDERER_BLEND3_BASECOLORMAP, arraysize(res), cmd); - device->BindConstantBuffer(PS, &blendmat.constantBuffer, CB_GETBINDSLOT(MaterialCB_Blend3) + 3, cmd); + device->BindConstantBuffer(PS, &blendmat.constantBuffer, CB_GETBINDSLOT(MaterialCB_Blend3), cmd); } } diff --git a/WickedEngine/wiVersion.cpp b/WickedEngine/wiVersion.cpp index 25b09cf8f..fbbbc180c 100644 --- a/WickedEngine/wiVersion.cpp +++ b/WickedEngine/wiVersion.cpp @@ -9,7 +9,7 @@ namespace wiVersion // minor features, major updates const int minor = 39; // minor bug fixes, alterations, refactors, updates - const int revision = 42; + const int revision = 43; long GetVersion()