From 13a3863832b692957896c654f68667c50bb2511b Mon Sep 17 00:00:00 2001 From: Demon000 Date: Sat, 15 Feb 2020 10:58:33 +0000 Subject: [PATCH] davinci: light: Avoid resetting state The handler function is called regardless of whether the value of the highest priority state changed. In case of the notification led, this translates to the breathing process being reset, which triggers my OCD. Change-Id: I4880b00602cbb739219871f1d7ce9ad85d87bc1b --- light/Light.cpp | 80 ++++++++++++++++++++++++++++++++++++------------- 1 file changed, 60 insertions(+), 20 deletions(-) diff --git a/light/Light.cpp b/light/Light.cpp index f16c82a..eb366f0 100644 --- a/light/Light.cpp +++ b/light/Light.cpp @@ -108,10 +108,21 @@ static void handleNotification(const LightState& state) { } } -static inline bool isLit(const LightState& state) { +static inline bool isStateLit(const LightState& state) { return state.color & 0x00ffffff; } +static inline bool isStateEqual(const LightState& first, const LightState& second) { + if (first.color == second.color && first.flashMode == second.flashMode && + first.flashOnMs == second.flashOnMs && + first.flashOffMs == second.flashOffMs && + first.brightnessMode == second.brightnessMode) { + return true; + } + + return false; +} + /* Keep sorted in the order of importance. */ static std::vector backends = { { Type::ATTENTION, handleNotification }, @@ -120,6 +131,40 @@ static std::vector backends = { { Type::BACKLIGHT, handleBacklight }, }; +static LightStateHandler findHandler(Type type) { + for (const LightBackend& backend : backends) { + if (backend.type == type) { + return backend.handler; + } + } + + return nullptr; +} + +static LightState findLitState(LightStateHandler handler) { + LightState emptyState; + + for (const LightBackend& backend : backends) { + if (backend.handler == handler) { + if (isStateLit(backend.state)) { + return backend.state; + } + + emptyState = backend.state; + } + } + + return emptyState; +} + +static void updateState(Type type, const LightState& state) { + for (LightBackend& backend : backends) { + if (backend.type == type) { + backend.state = state; + } + } +} + } // anonymous namespace namespace android { @@ -129,34 +174,29 @@ namespace V2_0 { namespace implementation { Return Light::setLight(Type type, const LightState& state) { - LightStateHandler handler = nullptr; - /* Lock global mutex until light state is updated. */ std::lock_guard lock(globalLock); - /* Update the cached state value for the current type. */ - for (LightBackend& backend : backends) { - if (backend.type == type) { - backend.state = state; - handler = backend.handler; - } - } - - /* If no handler has been found, then the type is not supported. */ + LightStateHandler handler = findHandler(type); if (!handler) { + /* If no handler has been found, then the type is not supported. */ return Status::LIGHT_NOT_SUPPORTED; } - /* Light up the type with the highest priority that matches the current handler. */ - for (LightBackend& backend : backends) { - if (handler == backend.handler && isLit(backend.state)) { - handler(backend.state); - return Status::SUCCESS; - } + /* Find the old state of the current handler. */ + LightState oldState = findLitState(handler); + + /* Update the cached state value for the current type. */ + updateState(type, state); + + /* Find the new state of the current handler. */ + LightState newState = findLitState(handler); + + if (isStateEqual(oldState, newState)) { + return Status::SUCCESS; } - /* If no type has been lit up, then turn off the hardware. */ - handler(state); + handler(newState); return Status::SUCCESS; }