From 780b4625424ee6b972c43e978b3cdc10b9d6bf9b Mon Sep 17 00:00:00 2001 From: Lais Andrade Date: Fri, 30 Aug 2024 15:55:27 +0100 Subject: Load vibration scale gain from system properties Update external vibration scaling library to load the scale gain used to define the scale factor for each level (low, medium, high). This allows vendor to configure the scale levels, similar to how they can also configure the haptic generator output gain. Bug: 356407380 Test: libvibrator_test Flag: android.os.vibrator.haptics_scale_v2_enabled Change-Id: I67753c32c00f706bbbdf50f999c222fb9ade4224 --- libs/vibrator/Android.bp | 1 + libs/vibrator/ExternalVibrationUtils.cpp | 22 +++++++++- libs/vibrator/tests/ExternalVibrationUtilsTest.cpp | 48 +++++++++++++++------- 3 files changed, 55 insertions(+), 16 deletions(-) diff --git a/libs/vibrator/Android.bp b/libs/vibrator/Android.bp index d3b3a734f9..22c196ef48 100644 --- a/libs/vibrator/Android.bp +++ b/libs/vibrator/Android.bp @@ -90,6 +90,7 @@ cc_library { ], shared_libs: [ + "libbase", "liblog", "libutils", "server_configurable_flags", diff --git a/libs/vibrator/ExternalVibrationUtils.cpp b/libs/vibrator/ExternalVibrationUtils.cpp index ca13afcbaf..4757bdbc6b 100644 --- a/libs/vibrator/ExternalVibrationUtils.cpp +++ b/libs/vibrator/ExternalVibrationUtils.cpp @@ -17,6 +17,10 @@ #include +#include +#include +#include + #include #include @@ -34,6 +38,21 @@ static constexpr float HAPTIC_MAX_AMPLITUDE_FLOAT = 1.0f; static constexpr float SCALE_GAMMA = 0.65f; // Same as VibrationEffect.SCALE_GAMMA static constexpr float SCALE_LEVEL_GAIN = 1.4f; // Same as VibrationConfig.DEFAULT_SCALE_LEVEL_GAIN +float getScaleLevelGain() { + static std::mutex gMutex; + static float gScaleLevelGain GUARDED_BY(gMutex) = 0; + std::lock_guard lock(gMutex); + if (gScaleLevelGain != 0) { + return gScaleLevelGain; + } + float scaleGain; + std::string value = ::android::base::GetProperty("vendor.vibrator.scale.level.gain", ""); + if (value.empty() || !::android::base::ParseFloat(value, &scaleGain) || scaleGain <= 1) { + scaleGain = SCALE_LEVEL_GAIN; + } + return gScaleLevelGain = scaleGain; +} + float getOldHapticScaleGamma(HapticLevel level) { switch (level) { case HapticLevel::VERY_LOW: @@ -79,7 +98,8 @@ float getHapticScaleFactor(HapticScale scale) { case HapticLevel::NONE: return 1.0f; default: - float scaleFactor = powf(SCALE_LEVEL_GAIN, static_cast(level)); + float scaleLevelGain = getScaleLevelGain(); + float scaleFactor = powf(scaleLevelGain, static_cast(level)); if (scaleFactor <= 0) { ALOGE("Invalid scale factor %.2f for level %d, using fallback to 1.0", scaleFactor, static_cast(level)); diff --git a/libs/vibrator/tests/ExternalVibrationUtilsTest.cpp b/libs/vibrator/tests/ExternalVibrationUtilsTest.cpp index 9369f80da3..e817263e36 100644 --- a/libs/vibrator/tests/ExternalVibrationUtilsTest.cpp +++ b/libs/vibrator/tests/ExternalVibrationUtilsTest.cpp @@ -14,6 +14,7 @@ * limitations under the License. */ +#include #include #include #include @@ -170,6 +171,12 @@ TEST_F_WITH_FLAGS( ExternalVibrationUtilsTest, TestScaleV2ToHapticLevel, // Value of fix_audio_coupled_haptics_scaling is not important, should work with either REQUIRES_FLAGS_ENABLED(ACONFIG_FLAG(FLAG_NS, haptics_scale_v2_enabled))) { + // Skip test on devices with custom scale level gain configured. + if (!::android::base::GetProperty("vendor.vibrator.scale.level.gain", "").empty()) { + GTEST_SKIP() << "system property for scale level gain is set, skip tests based on level"; + return; + } + float expectedVeryHigh[TEST_BUFFER_LENGTH] = { 1, -1, 0.8f, -0.38f }; scaleBuffer(HapticLevel::VERY_HIGH); EXPECT_FLOATS_NEARLY_EQ(expectedVeryHigh, mBuffer, TEST_BUFFER_LENGTH, TEST_TOLERANCE); @@ -191,6 +198,12 @@ TEST_F_WITH_FLAGS( ExternalVibrationUtilsTest, TestScaleV2ToScaleFactorUndefinedUsesHapticLevel, // Value of fix_audio_coupled_haptics_scaling is not important, should work with either REQUIRES_FLAGS_ENABLED(ACONFIG_FLAG(FLAG_NS, haptics_scale_v2_enabled))) { + // Skip test on devices with custom scale level gain configured. + if (!::android::base::GetProperty("vendor.vibrator.scale.level.gain", "").empty()) { + GTEST_SKIP() << "system property for scale level gain is set, skip tests based on level"; + return; + } + constexpr float adaptiveScaleNone = 1.0f; float expectedVeryHigh[TEST_BUFFER_LENGTH] = {1, -1, 0.8f, -0.38f}; scaleBuffer(HapticScale(HapticLevel::VERY_HIGH, -1.0f /* scaleFactor */, adaptiveScaleNone)); @@ -238,7 +251,7 @@ TEST_F_WITH_FLAGS(ExternalVibrationUtilsTest, TestAdaptiveScaleFactorAppliedAfte EXPECT_FLOATS_NEARLY_EQ(expectedMuted, mBuffer, TEST_BUFFER_LENGTH, TEST_TOLERANCE); // Haptic level scale up then adaptive scale down - float expectedVeryHigh[TEST_BUFFER_LENGTH] = { 0.2, -0.2, 0.16f, -0.13f }; + float expectedVeryHigh[TEST_BUFFER_LENGTH] = {0.2f, -0.2f, 0.16f, -0.13f}; scaleBuffer(HapticLevel::VERY_HIGH, 0.2f /* adaptiveScaleFactor */); EXPECT_FLOATS_NEARLY_EQ(expectedVeryHigh, mBuffer, TEST_BUFFER_LENGTH, TEST_TOLERANCE); @@ -276,7 +289,7 @@ TEST_F_WITH_FLAGS(ExternalVibrationUtilsTest, TestAdaptiveScaleFactorAppliedAfte EXPECT_FLOATS_NEARLY_EQ(expectedMuted, mBuffer, TEST_BUFFER_LENGTH, TEST_TOLERANCE); // Haptic level scale up then adaptive scale down - float expectedVeryHigh[TEST_BUFFER_LENGTH] = { 0.2, -0.2, 0.16f, -0.07f }; + float expectedVeryHigh[TEST_BUFFER_LENGTH] = {0.2f, -0.2f, 0.16f, -0.07f}; scaleBuffer(HapticLevel::VERY_HIGH, 0.2f /* adaptiveScaleFactor */); EXPECT_FLOATS_NEARLY_EQ(expectedVeryHigh, mBuffer, TEST_BUFFER_LENGTH, TEST_TOLERANCE); @@ -300,8 +313,8 @@ TEST_F_WITH_FLAGS( ExternalVibrationUtilsTest, TestAdaptiveScaleFactorUndefinedIgnoredScaleV2, // Value of fix_audio_coupled_haptics_scaling is not important, should work with either REQUIRES_FLAGS_ENABLED(ACONFIG_FLAG(FLAG_NS, haptics_scale_v2_enabled))) { - float expectedVeryHigh[TEST_BUFFER_LENGTH] = {1, -1, 0.8f, -0.38f}; - scaleBuffer(HapticLevel::VERY_HIGH, -1.0f /* adaptiveScaleFactor */); + float expectedVeryHigh[TEST_BUFFER_LENGTH] = {1, -1, 0.8, -0.38f}; + scaleBuffer(HapticScale(HapticLevel::HIGH, 2 /* scaleFactor */, -1 /* adaptiveScaleFactor */)); EXPECT_FLOATS_NEARLY_EQ(expectedVeryHigh, mBuffer, TEST_BUFFER_LENGTH, TEST_TOLERANCE); } @@ -312,27 +325,30 @@ TEST_F_WITH_FLAGS( // Adaptive scale mutes vibration float expectedMuted[TEST_BUFFER_LENGTH]; std::fill(std::begin(expectedMuted), std::end(expectedMuted), 0); - scaleBuffer(HapticLevel::VERY_HIGH, 0.0f /* adaptiveScaleFactor */); + scaleBuffer(HapticScale(HapticLevel::HIGH, 2 /* scaleFactor */, 0 /* adaptiveScaleFactor */)); EXPECT_FLOATS_NEARLY_EQ(expectedMuted, mBuffer, TEST_BUFFER_LENGTH, TEST_TOLERANCE); // Haptic level scale up then adaptive scale down - float expectedVeryHigh[TEST_BUFFER_LENGTH] = { 0.2, -0.2, 0.15f, -0.07f }; - scaleBuffer(HapticLevel::VERY_HIGH, 0.2f /* adaptiveScaleFactor */); + float expectedVeryHigh[TEST_BUFFER_LENGTH] = {0.2f, -0.2f, 0.16f, -0.07f}; + scaleBuffer( + HapticScale(HapticLevel::HIGH, 2 /* scaleFactor */, 0.2f /* adaptiveScaleFactor */)); EXPECT_FLOATS_NEARLY_EQ(expectedVeryHigh, mBuffer, TEST_BUFFER_LENGTH, TEST_TOLERANCE); // Haptic level scale up then adaptive scale up - float expectedHigh[TEST_BUFFER_LENGTH] = { 1.5f, -1.5f, 0.95f, -0.41f }; - scaleBuffer(HapticLevel::HIGH, 1.5f /* adaptiveScaleFactor */); + float expectedHigh[TEST_BUFFER_LENGTH] = {1.5f, -1.5f, 1.2f, -0.57f}; + scaleBuffer( + HapticScale(HapticLevel::HIGH, 2 /* scaleFactor */, 1.5f /* adaptiveScaleFactor */)); EXPECT_FLOATS_NEARLY_EQ(expectedHigh, mBuffer, TEST_BUFFER_LENGTH, TEST_TOLERANCE); // Haptic level scale down then adaptive scale down - float expectedLow[TEST_BUFFER_LENGTH] = { 0.42f, -0.42f, 0.21f, -0.08f }; - scaleBuffer(HapticLevel::LOW, 0.6f /* adaptiveScaleFactor */); + float expectedLow[TEST_BUFFER_LENGTH] = {0.3f, -0.3f, 0.15f, -0.06f}; + scaleBuffer( + HapticScale(HapticLevel::LOW, 0.5f /* scaleFactor */, 0.6f /* adaptiveScaleFactor */)); EXPECT_FLOATS_NEARLY_EQ(expectedLow, mBuffer, TEST_BUFFER_LENGTH, TEST_TOLERANCE); // Haptic level scale down then adaptive scale up - float expectedVeryLow[TEST_BUFFER_LENGTH] = { 1.02f, -1.02f, 0.51f, -0.2f }; - scaleBuffer(HapticLevel::VERY_LOW, 2 /* adaptiveScaleFactor */); + float expectedVeryLow[TEST_BUFFER_LENGTH] = {1.0f, -1.0f, 0.51f, -0.2f}; + scaleBuffer(HapticScale(HapticLevel::LOW, 0.5f /* scaleFactor */, 2 /* adaptiveScaleFactor */)); EXPECT_FLOATS_NEARLY_EQ(expectedVeryLow, mBuffer, TEST_BUFFER_LENGTH, TEST_TOLERANCE); } @@ -370,11 +386,13 @@ TEST_F_WITH_FLAGS( REQUIRES_FLAGS_ENABLED(ACONFIG_FLAG(FLAG_NS, haptics_scale_v2_enabled))) { // Scaled = { 0.2, -0.2, 0.15f, -0.07f }; float expectedClippedVeryHigh[TEST_BUFFER_LENGTH] = { 0.15f, -0.15f, 0.15f, -0.07f }; - scaleBuffer(HapticLevel::VERY_HIGH, 0.2f /* adaptiveScaleFactor */, 0.15f /* limit */); + scaleBuffer(HapticScale(HapticLevel::HIGH, 2 /* scaleFactor */, 0.2f /* adaptiveScaleFactor */), + 0.15f /* limit */); EXPECT_FLOATS_NEARLY_EQ(expectedClippedVeryHigh, mBuffer, TEST_BUFFER_LENGTH, TEST_TOLERANCE); // Scaled = { 1.02f, -1.02f, 0.51f, -0.2f } float expectedClippedVeryLow[TEST_BUFFER_LENGTH] = { 0.7f, -0.7f, 0.51f, -0.2f }; - scaleBuffer(HapticLevel::VERY_LOW, 2 /* adaptiveScaleFactor */, 0.7f /* limit */); + scaleBuffer(HapticScale(HapticLevel::LOW, 0.5 /* scaleFactor */, 2 /* adaptiveScaleFactor */), + 0.7f /* limit */); EXPECT_FLOATS_NEARLY_EQ(expectedClippedVeryLow, mBuffer, TEST_BUFFER_LENGTH, TEST_TOLERANCE); } -- cgit v1.2.3-59-g8ed1b