Merge branch 'Muzz-Triplanar-Features' into 1.10
This commit is contained in:
@@ -4,6 +4,7 @@
|
||||
|
||||
#include "MaterialGenerator.h"
|
||||
#include "Engine/Content/Assets/MaterialFunction.h"
|
||||
#include "Engine/Visject/ShaderStringBuilder.h"
|
||||
|
||||
void MaterialGenerator::ProcessGroupMaterial(Box* box, Node* node, Value& value)
|
||||
{
|
||||
@@ -643,6 +644,136 @@ void MaterialGenerator::ProcessGroupMaterial(Box* box, Node* node, Value& value)
|
||||
value = writeLocal(ValueType::Float3, String::Format(TEXT("float3({0}, {1}, {2})"), innerMask.Value, outerMask.Value, mask.Value), node);
|
||||
break;
|
||||
}
|
||||
// Shift HSV
|
||||
case 50:
|
||||
{
|
||||
const auto color = tryGetValue(node->GetBox(0), Value::One).AsFloat4();
|
||||
if (!color.IsValid())
|
||||
{
|
||||
value = Value::Zero;
|
||||
break;
|
||||
}
|
||||
const auto hue = tryGetValue(node->GetBox(1), node->Values[0]).AsFloat();
|
||||
const auto saturation = tryGetValue(node->GetBox(2), node->Values[1]).AsFloat();
|
||||
const auto val = tryGetValue(node->GetBox(3), node->Values[2]).AsFloat();
|
||||
auto result = writeLocal(Value::InitForZero(ValueType::Float4), node);
|
||||
|
||||
const String hsvAdjust = ShaderStringBuilder()
|
||||
.Code(TEXT(R"(
|
||||
{
|
||||
float3 rgb = %COLOR%.rgb;
|
||||
float minc = min(min(rgb.r, rgb.g), rgb.b);
|
||||
float maxc = max(max(rgb.r, rgb.g), rgb.b);
|
||||
float delta = maxc - minc;
|
||||
|
||||
float3 grb = float3(rgb.g - rgb.b, rgb.r - rgb.b, rgb.b - rgb.g);
|
||||
float3 cmps = float3(maxc == rgb.r, maxc == rgb.g, maxc == rgb.b);
|
||||
float h = dot(grb * rcp(delta), cmps);
|
||||
h += 6.0 * (h < 0);
|
||||
h = frac(h * (1.0/6.0) * step(0, delta) + %HUE% * 0.5);
|
||||
|
||||
float s = saturate(delta * rcp(maxc + step(maxc, 0)) * (1.0 + %SATURATION%));
|
||||
float v = maxc * (1.0 + %VALUE%);
|
||||
|
||||
float3 k = float3(1.0, 2.0 / 3.0, 1.0 / 3.0);
|
||||
%RESULT% = float4(v * lerp(1.0, saturate(abs(frac(h + k) * 6.0 - 3.0) - 1.0), s), %COLOR%.a);
|
||||
}
|
||||
)"))
|
||||
.Replace(TEXT("%COLOR%"), color.Value)
|
||||
.Replace(TEXT("%HUE%"), hue.Value)
|
||||
.Replace(TEXT("%SATURATION%"), saturation.Value)
|
||||
.Replace(TEXT("%VALUE%"), val.Value)
|
||||
.Replace(TEXT("%RESULT%"), result.Value)
|
||||
.Build();
|
||||
_writer.Write(*hsvAdjust);
|
||||
value = result;
|
||||
break;
|
||||
}
|
||||
// Color Blend
|
||||
case 51:
|
||||
{
|
||||
const auto baseColor = tryGetValue(node->GetBox(0), Value::One).AsFloat4();
|
||||
const auto blendColor = tryGetValue(node->GetBox(1), Value::One).AsFloat4();
|
||||
const auto blendAmount = tryGetValue(node->GetBox(2), node->Values[1]).AsFloat();
|
||||
const auto blendMode = node->Values[0].AsInt;
|
||||
auto result = writeLocal(Value::InitForZero(ValueType::Float4), node);
|
||||
|
||||
String blendFormula;
|
||||
switch (blendMode)
|
||||
{
|
||||
case 0: // Normal
|
||||
blendFormula = TEXT("blend");
|
||||
break;
|
||||
case 1: // Add
|
||||
blendFormula = TEXT("base + blend");
|
||||
break;
|
||||
case 2: // Subtract
|
||||
blendFormula = TEXT("base - blend");
|
||||
break;
|
||||
case 3: // Multiply
|
||||
blendFormula = TEXT("base * blend");
|
||||
break;
|
||||
case 4: // Screen
|
||||
blendFormula = TEXT("1.0 - (1.0 - base) * (1.0 - blend)");
|
||||
break;
|
||||
case 5: // Overlay
|
||||
blendFormula = TEXT("base <= 0.5 ? 2.0 * base * blend : 1.0 - 2.0 * (1.0 - base) * (1.0 - blend)");
|
||||
break;
|
||||
case 6: // Linear Burn
|
||||
blendFormula = TEXT("base + blend - 1.0");
|
||||
break;
|
||||
case 7: // Linear Light
|
||||
blendFormula = TEXT("blend < 0.5 ? max(base + (2.0 * blend) - 1.0, 0.0) : min(base + 2.0 * (blend - 0.5), 1.0)");
|
||||
break;
|
||||
case 8: // Darken
|
||||
blendFormula = TEXT("min(base, blend)");
|
||||
break;
|
||||
case 9: // Lighten
|
||||
blendFormula = TEXT("max(base, blend)");
|
||||
break;
|
||||
case 10: // Difference
|
||||
blendFormula = TEXT("abs(base - blend)");
|
||||
break;
|
||||
case 11: // Exclusion
|
||||
blendFormula = TEXT("base + blend - (2.0 * base * blend)");
|
||||
break;
|
||||
case 12: // Divide
|
||||
blendFormula = TEXT("base / (blend + 0.000001)");
|
||||
break;
|
||||
case 13: // Hard Light
|
||||
blendFormula = TEXT("blend <= 0.5 ? 2.0 * base * blend : 1.0 - 2.0 * (1.0 - base) * (1.0 - blend)");
|
||||
break;
|
||||
case 14: // Pin Light
|
||||
blendFormula = TEXT("blend <= 0.5 ? min(base, 2.0 * blend) : max(base, 2.0 * (blend - 0.5))");
|
||||
break;
|
||||
case 15: // Hard Mix
|
||||
blendFormula = TEXT("step(1.0 - base, blend)");
|
||||
break;
|
||||
default:
|
||||
blendFormula = TEXT("blend");
|
||||
break;
|
||||
}
|
||||
|
||||
const String blendImpl = ShaderStringBuilder()
|
||||
.Code(TEXT(R"(
|
||||
{
|
||||
float3 base = %BASE%.rgb;
|
||||
float3 blend = %BLEND%.rgb;
|
||||
float alpha = %BASE%.a;
|
||||
float3 final = %BLEND_FORMULA%;
|
||||
%RESULT% = float4(lerp(base, final, %AMOUNT%), alpha);
|
||||
}
|
||||
)"))
|
||||
.Replace(TEXT("%BASE%"), baseColor.Value)
|
||||
.Replace(TEXT("%BLEND%"), blendColor.Value)
|
||||
.Replace(TEXT("%AMOUNT%"), blendAmount.Value)
|
||||
.Replace(TEXT("%BLEND_FORMULA%"), *blendFormula)
|
||||
.Replace(TEXT("%RESULT%"), result.Value)
|
||||
.Build();
|
||||
_writer.Write(*blendImpl);
|
||||
value = result;
|
||||
break;
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user