First batch of GetValues() overrides (#6852)

* Benchmarks and tests for Image and Constant GetValues

Signed-off-by: Mike Balfour <82224783+mbalfour-amzn@users.noreply.github.com>

* Verify GetValues for Perlin and Random Gradients

Signed-off-by: Mike Balfour <82224783+mbalfour-amzn@users.noreply.github.com>

* Standardized the assert format for GetValues().

Signed-off-by: Mike Balfour <82224783+mbalfour-amzn@users.noreply.github.com>

* More GetValues unit tests and test cleanup

Signed-off-by: Mike Balfour <82224783+mbalfour-amzn@users.noreply.github.com>

* Fixed typos

Signed-off-by: Mike Balfour <82224783+mbalfour-amzn@users.noreply.github.com>

* GetValues() unit tests for surface gradients.

Signed-off-by: Mike Balfour <82224783+mbalfour-amzn@users.noreply.github.com>

* Benchmarks for ShapeAreaFalloff Gradient

Signed-off-by: Mike Balfour <82224783+mbalfour-amzn@users.noreply.github.com>

* Added benchmarks for all remaining gradients and cleaned up the helper methods.

Signed-off-by: Mike Balfour <82224783+mbalfour-amzn@users.noreply.github.com>

* Renamed class for better report formatting.

Signed-off-by: Mike Balfour <82224783+mbalfour-amzn@users.noreply.github.com>

* Added missing Mocks dependencies for the Editor tests.

Signed-off-by: Mike Balfour <82224783+mbalfour-amzn@users.noreply.github.com>

* First batch of specific GetValues() overrides.
Each one is measurably faster than the generic version.  Also, in ShapeAreaFalloffGradient, I optimized and simplified the logic a bit, so GetValue() is marginally faster too.

Signed-off-by: Mike Balfour <82224783+mbalfour-amzn@users.noreply.github.com>
This commit is contained in:
Mike Balfour
2022-01-13 14:50:54 -06:00
committed by GitHub
parent 62e7483b0e
commit 79431f5e5f
10 changed files with 194 additions and 20 deletions
@@ -145,6 +145,22 @@ namespace GradientSignal
m_gradientTransform = newTransform;
}
float RandomGradientComponent::GetRandomValue(const AZ::Vector3& position, AZStd::size_t seed) const
{
// generating stable pseudo-random noise from a position based hash
float x = position.GetX();
float y = position.GetY();
AZStd::size_t result = 0;
AZStd::hash_combine<float>(result, x * seed + y);
AZStd::hash_combine<float>(result, y * seed + x);
AZStd::hash_combine<float>(result, x * y * seed);
// always returns [0.0,1.0]
return static_cast<float>(result % std::numeric_limits<AZ::u8>::max()) / static_cast<float>(std::numeric_limits<AZ::u8>::max());
}
float RandomGradientComponent::GetValue(const GradientSampleParams& sampleParams) const
{
@@ -158,23 +174,50 @@ namespace GradientSignal
if (!wasPointRejected)
{
//generating stable pseudo-random noise from a position based hash
float x = uvw.GetX();
float y = uvw.GetY();
AZStd::size_t result = 0;
const AZStd::size_t seed = m_configuration.m_randomSeed + AZStd::size_t(2); // Add 2 to avoid seeds 0 and 1, which can create strange patterns with this particular algorithm
const AZStd::size_t seed = m_configuration.m_randomSeed +
AZStd::size_t(2); // Add 2 to avoid seeds 0 and 1, which can create strange patterns with this particular algorithm
AZStd::hash_combine<float>(result, x * seed + y);
AZStd::hash_combine<float>(result, y * seed + x);
AZStd::hash_combine<float>(result, x * y * seed);
//always returns [0.0,1.0]
return static_cast<float>(result % std::numeric_limits<AZ::u8>::max()) / static_cast<float>(std::numeric_limits<AZ::u8>::max());
return GetRandomValue(uvw, seed);
}
return 0.0f;
}
void RandomGradientComponent::GetValues(AZStd::array_view<AZ::Vector3> positions, AZStd::array_view<float> outValues) const
{
if (positions.size() != outValues.size())
{
AZ_Assert(false, "input and output lists are different sizes (%zu vs %zu).", positions.size(), outValues.size());
return;
}
AZ::Vector3 uvw;
bool wasPointRejected = false;
const AZStd::size_t seed = m_configuration.m_randomSeed +
AZStd::size_t(2); // Add 2 to avoid seeds 0 and 1, which can create strange patterns with this particular algorithm
AZStd::shared_lock<decltype(m_transformMutex)> lock(m_transformMutex);
for (size_t index = 0; index < positions.size(); index++)
{
// The const_cast is necessary for now since array_view currently only supports const entries.
// If/when array_view is fixed to support non-const, or AZStd::span gets created, the const_cast can get removed.
auto& outValue = const_cast<float&>(outValues[index]);
m_gradientTransform.TransformPositionToUVW(positions[index], uvw, wasPointRejected);
if (!wasPointRejected)
{
outValue = GetRandomValue(uvw, seed);
}
else
{
outValue = 0.0f;
}
}
}
int RandomGradientComponent::GetRandomSeed() const
{
return m_configuration.m_randomSeed;