diff --git a/screen_ui.cpp b/screen_ui.cpp index b8f6ea28..d65d656b 100644 --- a/screen_ui.cpp +++ b/screen_ui.cpp @@ -14,6 +14,8 @@ * limitations under the License. */ +#include "screen_ui.h" + #include #include #include @@ -34,13 +36,12 @@ #include #include -#include #include +#include +#include #include "common.h" #include "device.h" -#include "minui/minui.h" -#include "screen_ui.h" #include "ui.h" // Return the current time as a double (including fractions of a second). @@ -54,7 +55,7 @@ ScreenRecoveryUI::ScreenRecoveryUI() : kMarginWidth(RECOVERY_UI_MARGIN_WIDTH), kMarginHeight(RECOVERY_UI_MARGIN_HEIGHT), kAnimationFps(RECOVERY_UI_ANIMATION_FPS), - density_(static_cast(android::base::GetIntProperty("ro.sf.lcd_density", 160)) / 160.f), + kDensity(static_cast(android::base::GetIntProperty("ro.sf.lcd_density", 160)) / 160.f), currentIcon(NONE), progressBarType(EMPTY), progressScopeStart(0), @@ -66,7 +67,6 @@ ScreenRecoveryUI::ScreenRecoveryUI() text_(nullptr), text_col_(0), text_row_(0), - text_top_(0), show_text(false), show_text_ever(false), menu_headers_(nullptr), @@ -80,6 +80,8 @@ ScreenRecoveryUI::ScreenRecoveryUI() intro_done(false), stage(-1), max_stage(-1), + locale_(""), + rtl_locale_(false), updateMutex(PTHREAD_MUTEX_INITIALIZER) {} GRSurface* ScreenRecoveryUI::GetCurrentFrame() const { @@ -105,7 +107,7 @@ GRSurface* ScreenRecoveryUI::GetCurrentText() const { } int ScreenRecoveryUI::PixelsFromDp(int dp) const { - return dp * density_; + return dp * kDensity; } // Here's the intended layout: @@ -368,7 +370,7 @@ void ScreenRecoveryUI::draw_screen_locked() { // Display from the bottom up, until we hit the top of the screen, the bottom of the menu, or // we've displayed the entire text buffer. SetColor(LOG); - int row = (text_top_ + text_rows_ - 1) % text_rows_; + int row = text_row_; size_t count = 0; for (int ty = gr_fb_height() - kMarginHeight - char_height_; ty >= y && count < text_rows_; ty -= char_height_, ++count) { @@ -497,6 +499,7 @@ bool ScreenRecoveryUI::InitTextParams() { bool ScreenRecoveryUI::Init(const std::string& locale) { RecoveryUI::Init(locale); + if (!InitTextParams()) { return false; } @@ -510,7 +513,9 @@ bool ScreenRecoveryUI::Init(const std::string& locale) { file_viewer_text_ = Alloc2d(text_rows_, text_cols_ + 1); text_col_ = text_row_ = 0; - text_top_ = 1; + + // Set up the locale info. + SetLocale(locale); LoadBitmap("icon_error", &error_icon); @@ -643,7 +648,6 @@ void ScreenRecoveryUI::PrintV(const char* fmt, bool copy_to_stdout, va_list ap) text_[text_row_][text_col_] = '\0'; text_col_ = 0; text_row_ = (text_row_ + 1) % text_rows_; - if (text_row_ == text_top_) text_top_ = (text_top_ + 1) % text_rows_; } if (*ptr != '\n') text_[text_row_][text_col_++] = *ptr; } @@ -673,8 +677,6 @@ void ScreenRecoveryUI::PutChar(char ch) { if (ch == '\n' || text_col_ >= text_cols_) { text_col_ = 0; ++text_row_; - - if (text_row_ == text_top_) text_top_ = (text_top_ + 1) % text_rows_; } pthread_mutex_unlock(&updateMutex); } @@ -683,7 +685,6 @@ void ScreenRecoveryUI::ClearText() { pthread_mutex_lock(&updateMutex); text_col_ = 0; text_row_ = 0; - text_top_ = 1; for (size_t i = 0; i < text_rows_; ++i) { memset(text_[i], 0, text_cols_ + 1); } @@ -750,7 +751,6 @@ void ScreenRecoveryUI::ShowFile(const char* filename) { char** old_text = text_; size_t old_text_col = text_col_; size_t old_text_row = text_row_; - size_t old_text_top = text_top_; // Swap in the alternate screen and clear it. text_ = file_viewer_text_; @@ -762,7 +762,6 @@ void ScreenRecoveryUI::ShowFile(const char* filename) { text_ = old_text; text_col_ = old_text_col; text_row_ = old_text_row; - text_top_ = old_text_top; } void ScreenRecoveryUI::StartMenu(const char* const* headers, const char* const* items, @@ -841,3 +840,23 @@ void ScreenRecoveryUI::KeyLongPress(int) { // will change color to indicate a successful long press. Redraw(); } + +void ScreenRecoveryUI::SetLocale(const std::string& new_locale) { + locale_ = new_locale; + rtl_locale_ = false; + + if (!new_locale.empty()) { + size_t underscore = new_locale.find('_'); + // lang has the language prefix prior to '_', or full string if '_' doesn't exist. + std::string lang = new_locale.substr(0, underscore); + + // A bit cheesy: keep an explicit list of supported RTL languages. + if (lang == "ar" || // Arabic + lang == "fa" || // Persian (Farsi) + lang == "he" || // Hebrew (new language code) + lang == "iw" || // Hebrew (old language code) + lang == "ur") { // Urdu + rtl_locale_ = true; + } + } +} diff --git a/screen_ui.h b/screen_ui.h index 8231a2ba..eaac2a6e 100644 --- a/screen_ui.h +++ b/screen_ui.h @@ -32,6 +32,17 @@ struct GRSurface; // (shows an icon + a progress bar, text logging, menu, etc.) class ScreenRecoveryUI : public RecoveryUI { public: + enum UIElement { + HEADER, + MENU, + MENU_SEL_BG, + MENU_SEL_BG_ACTIVE, + MENU_SEL_FG, + LOG, + TEXT_FILL, + INFO + }; + ScreenRecoveryUI(); bool Init(const std::string& locale) override; @@ -67,16 +78,6 @@ class ScreenRecoveryUI : public RecoveryUI { void Redraw(); - enum UIElement { - HEADER, - MENU, - MENU_SEL_BG, - MENU_SEL_BG_ACTIVE, - MENU_SEL_FG, - LOG, - TEXT_FILL, - INFO - }; void SetColor(UIElement e) const; protected: @@ -89,68 +90,7 @@ class ScreenRecoveryUI : public RecoveryUI { const int kAnimationFps; // The scale factor from dp to pixels. 1.0 for mdpi, 4.0 for xxxhdpi. - const float density_; - - Icon currentIcon; - - // The layout to use. - int layout_; - - GRSurface* error_icon; - - GRSurface* erasing_text; - GRSurface* error_text; - GRSurface* installing_text; - GRSurface* no_command_text; - - GRSurface** introFrames; - GRSurface** loopFrames; - - GRSurface* progressBarEmpty; - GRSurface* progressBarFill; - GRSurface* stageMarkerEmpty; - GRSurface* stageMarkerFill; - - ProgressType progressBarType; - - float progressScopeStart, progressScopeSize, progress; - double progressScopeTime, progressScopeDuration; - - // true when both graphics pages are the same (except for the progress bar). - bool pagesIdentical; - - size_t text_cols_, text_rows_; - - // Log text overlay, displayed when a magic key is pressed. - char** text_; - size_t text_col_, text_row_, text_top_; - - bool show_text; - bool show_text_ever; // has show_text ever been true? - - std::vector menu_; - const char* const* menu_headers_; - bool show_menu; - int menu_items, menu_sel; - - // An alternate text screen, swapped with 'text_' when we're viewing a log file. - char** file_viewer_text_; - - pthread_t progress_thread_; - - // Number of intro frames and loop frames in the animation. - size_t intro_frames; - size_t loop_frames; - - size_t current_frame; - bool intro_done; - - int stage, max_stage; - - int char_width_; - int char_height_; - - pthread_mutex_t updateMutex; + const float kDensity; virtual bool InitTextParams(); @@ -191,6 +131,74 @@ class ScreenRecoveryUI : public RecoveryUI { // Similar to DrawTextLines() to draw multiple text lines, but additionally wraps long lines. // Returns the offset it should be moving along Y-axis. int DrawWrappedTextLines(int x, int y, const char* const* lines) const; + + Icon currentIcon; + + // The layout to use. + int layout_; + + GRSurface* error_icon; + + GRSurface* erasing_text; + GRSurface* error_text; + GRSurface* installing_text; + GRSurface* no_command_text; + + GRSurface** introFrames; + GRSurface** loopFrames; + + GRSurface* progressBarEmpty; + GRSurface* progressBarFill; + GRSurface* stageMarkerEmpty; + GRSurface* stageMarkerFill; + + ProgressType progressBarType; + + float progressScopeStart, progressScopeSize, progress; + double progressScopeTime, progressScopeDuration; + + // true when both graphics pages are the same (except for the progress bar). + bool pagesIdentical; + + size_t text_cols_, text_rows_; + + // Log text overlay, displayed when a magic key is pressed. + char** text_; + size_t text_col_, text_row_; + + bool show_text; + bool show_text_ever; // has show_text ever been true? + + std::vector menu_; + const char* const* menu_headers_; + bool show_menu; + int menu_items, menu_sel; + + // An alternate text screen, swapped with 'text_' when we're viewing a log file. + char** file_viewer_text_; + + pthread_t progress_thread_; + + // Number of intro frames and loop frames in the animation. + size_t intro_frames; + size_t loop_frames; + + size_t current_frame; + bool intro_done; + + int stage, max_stage; + + int char_width_; + int char_height_; + + // The locale that's used to show the rendered texts. + std::string locale_; + bool rtl_locale_; + + pthread_mutex_t updateMutex; + + private: + void SetLocale(const std::string&); }; #endif // RECOVERY_UI_H diff --git a/ui.cpp b/ui.cpp index e80d7ed0..baf6d108 100644 --- a/ui.cpp +++ b/ui.cpp @@ -50,9 +50,7 @@ static constexpr const char* BRIGHTNESS_FILE = "/sys/class/leds/lcd-backlight/br static constexpr const char* MAX_BRIGHTNESS_FILE = "/sys/class/leds/lcd-backlight/max_brightness"; RecoveryUI::RecoveryUI() - : locale_(""), - rtl_locale_(false), - brightness_normal_(50), + : brightness_normal_(50), brightness_dimmed_(25), touch_screen_allowed_(false), kTouchLowThreshold(RECOVERY_UI_TOUCH_LOW_THRESHOLD), @@ -132,10 +130,7 @@ bool RecoveryUI::InitScreensaver() { return true; } -bool RecoveryUI::Init(const std::string& locale) { - // Set up the locale info. - SetLocale(locale); - +bool RecoveryUI::Init(const std::string& /* locale */) { ev_init(std::bind(&RecoveryUI::OnInputEvent, this, std::placeholders::_1, std::placeholders::_2), touch_screen_allowed_); @@ -574,23 +569,3 @@ void RecoveryUI::SetEnableReboot(bool enabled) { enable_reboot = enabled; pthread_mutex_unlock(&key_queue_mutex); } - -void RecoveryUI::SetLocale(const std::string& new_locale) { - this->locale_ = new_locale; - this->rtl_locale_ = false; - - if (!new_locale.empty()) { - size_t underscore = new_locale.find('_'); - // lang has the language prefix prior to '_', or full string if '_' doesn't exist. - std::string lang = new_locale.substr(0, underscore); - - // A bit cheesy: keep an explicit list of supported RTL languages. - if (lang == "ar" || // Arabic - lang == "fa" || // Persian (Farsi) - lang == "he" || // Hebrew (new language code) - lang == "iw" || // Hebrew (old language code) - lang == "ur") { // Urdu - rtl_locale_ = true; - } - } -} diff --git a/ui.h b/ui.h index 3d9afece..4086023a 100644 --- a/ui.h +++ b/ui.h @@ -26,6 +26,27 @@ // Abstract class for controlling the user interface during recovery. class RecoveryUI { public: + enum Icon { + NONE, + INSTALLING_UPDATE, + ERASING, + NO_COMMAND, + ERROR + }; + + enum ProgressType { + EMPTY, + INDETERMINATE, + DETERMINATE + }; + + enum KeyAction { + ENQUEUE, + TOGGLE, + REBOOT, + IGNORE + }; + RecoveryUI(); virtual ~RecoveryUI() {} @@ -38,12 +59,10 @@ class RecoveryUI { virtual void SetStage(int current, int max) = 0; // Sets the overall recovery state ("background image"). - enum Icon { NONE, INSTALLING_UPDATE, ERASING, NO_COMMAND, ERROR }; virtual void SetBackground(Icon icon) = 0; virtual void SetSystemUpdateText(bool security_update) = 0; // --- progress indicator --- - enum ProgressType { EMPTY, INDETERMINATE, DETERMINATE }; virtual void SetProgressType(ProgressType determinate) = 0; // Shows a progress bar and define the scope of the next operation: @@ -94,7 +113,6 @@ class RecoveryUI { // Called on each key press, even while operations are in progress. Return value indicates whether // an immediate operation should be triggered (toggling the display, rebooting the device), or if // the key should be enqueued for use by the main thread. - enum KeyAction { ENQUEUE, TOGGLE, REBOOT, IGNORE }; virtual KeyAction CheckKey(int key, bool is_long_press); // Called when a key is held down long enough to have been a long-press (but before the key is @@ -125,10 +143,6 @@ class RecoveryUI { protected: void EnqueueKey(int key_code); - // The locale that's used to show the rendered texts. - std::string locale_; - bool rtl_locale_; - // The normal and dimmed brightness percentages (default: 50 and 25, which means 50% and 25% of // the max_brightness). Because the absolute values may vary across devices. These two values can // be configured via subclassing. Setting brightness_normal_ to 0 to disable screensaver. @@ -139,10 +153,35 @@ class RecoveryUI { bool touch_screen_allowed_; private: + enum class ScreensaverState { + DISABLED, + NORMAL, + DIMMED, + OFF + }; + + struct key_timer_t { + RecoveryUI* ui; + int key_code; + int count; + }; + // The sensitivity when detecting a swipe. const int kTouchLowThreshold; const int kTouchHighThreshold; + void OnKeyDetected(int key_code); + void OnTouchDetected(int dx, int dy); + int OnInputEvent(int fd, uint32_t epevents); + void ProcessKey(int key_code, int updown); + + bool IsUsbConnected(); + + static void* time_key_helper(void* cookie); + void time_key(int key_code, int count); + + bool InitScreensaver(); + // Key event input queue pthread_mutex_t key_queue_mutex; pthread_cond_t key_queue_cond; @@ -172,33 +211,14 @@ class RecoveryUI { bool touch_swiping_; bool is_bootreason_recovery_ui_; - struct key_timer_t { - RecoveryUI* ui; - int key_code; - int count; - }; - pthread_t input_thread_; - void OnKeyDetected(int key_code); - void OnTouchDetected(int dx, int dy); - int OnInputEvent(int fd, uint32_t epevents); - void ProcessKey(int key_code, int updown); - - bool IsUsbConnected(); - - static void* time_key_helper(void* cookie); - void time_key(int key_code, int count); - - void SetLocale(const std::string&); - - enum class ScreensaverState { DISABLED, NORMAL, DIMMED, OFF }; ScreensaverState screensaver_state_; + // The following two contain the absolute values computed from brightness_normal_ and // brightness_dimmed_ respectively. unsigned int brightness_normal_value_; unsigned int brightness_dimmed_value_; - bool InitScreensaver(); }; #endif // RECOVERY_UI_H diff --git a/wear_ui.cpp b/wear_ui.cpp index 1859b131..e2ee4880 100644 --- a/wear_ui.cpp +++ b/wear_ui.cpp @@ -133,7 +133,7 @@ void WearRecoveryUI::draw_screen_locked() { // display from the bottom up, until we hit the top of the // screen, the bottom of the menu, or we've displayed the // entire text buffer. - int row = (text_top_ + text_rows_ - 1) % text_rows_; + int row = text_row_; size_t count = 0; for (int ty = gr_fb_height() - char_height_ - kMarginHeight; ty > y + 2 && count < text_rows_; ty -= char_height_, ++count) {