• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2011 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #ifndef RECOVERY_UI_H
18 #define RECOVERY_UI_H
19 
20 #include <linux/input.h>
21 #include <pthread.h>
22 #include <time.h>
23 
24 #include <string>
25 
26 // Abstract class for controlling the user interface during recovery.
27 class RecoveryUI {
28  public:
29   RecoveryUI();
30 
~RecoveryUI()31   virtual ~RecoveryUI() {}
32 
33   // Initializes the object; called before anything else. UI texts will be initialized according to
34   // the given locale. Returns true on success.
35   virtual bool Init(const std::string& locale);
36 
37   // Shows a stage indicator. Called immediately after Init().
38   virtual void SetStage(int current, int max) = 0;
39 
40   // Sets the overall recovery state ("background image").
41   enum Icon { NONE, INSTALLING_UPDATE, ERASING, NO_COMMAND, ERROR };
42   virtual void SetBackground(Icon icon) = 0;
43   virtual void SetSystemUpdateText(bool security_update) = 0;
44 
45   // --- progress indicator ---
46   enum ProgressType { EMPTY, INDETERMINATE, DETERMINATE };
47   virtual void SetProgressType(ProgressType determinate) = 0;
48 
49   // Shows a progress bar and define the scope of the next operation:
50   //   portion - fraction of the progress bar the next operation will use
51   //   seconds - expected time interval (progress bar moves at this minimum rate)
52   virtual void ShowProgress(float portion, float seconds) = 0;
53 
54   // Sets progress bar position (0.0 - 1.0 within the scope defined by the last call to
55   // ShowProgress).
56   virtual void SetProgress(float fraction) = 0;
57 
58   // --- text log ---
59 
60   virtual void ShowText(bool visible) = 0;
61 
62   virtual bool IsTextVisible() = 0;
63 
64   virtual bool WasTextEverVisible() = 0;
65 
66   // Writes a message to the on-screen log (shown if the user has toggled on the text display).
67   // Print() will also dump the message to stdout / log file, while PrintOnScreenOnly() not.
68   virtual void Print(const char* fmt, ...) __printflike(2, 3) = 0;
69   virtual void PrintOnScreenOnly(const char* fmt, ...) __printflike(2, 3) = 0;
70 
71   virtual void ShowFile(const char* filename) = 0;
72 
73   // --- key handling ---
74 
75   // Waits for a key and return it. May return -1 after timeout.
76   virtual int WaitKey();
77 
78   virtual bool IsKeyPressed(int key);
79   virtual bool IsLongPress();
80 
81   // Returns true if you have the volume up/down and power trio typical of phones and tablets, false
82   // otherwise.
83   virtual bool HasThreeButtons();
84 
85   // Returns true if it has a power key.
86   virtual bool HasPowerKey() const;
87 
88   // Returns true if it supports touch inputs.
89   virtual bool HasTouchScreen() const;
90 
91   // Erases any queued-up keys.
92   virtual void FlushKeys();
93 
94   // Called on each key press, even while operations are in progress. Return value indicates whether
95   // an immediate operation should be triggered (toggling the display, rebooting the device), or if
96   // the key should be enqueued for use by the main thread.
97   enum KeyAction { ENQUEUE, TOGGLE, REBOOT, IGNORE };
98   virtual KeyAction CheckKey(int key, bool is_long_press);
99 
100   // Called when a key is held down long enough to have been a long-press (but before the key is
101   // released). This means that if the key is eventually registered (released without any other keys
102   // being pressed in the meantime), CheckKey will be called with 'is_long_press' true.
103   virtual void KeyLongPress(int key);
104 
105   // Normally in recovery there's a key sequence that triggers immediate reboot of the device,
106   // regardless of what recovery is doing (with the default CheckKey implementation, it's pressing
107   // the power button 7 times in row). Call this to enable or disable that feature. It is enabled by
108   // default.
109   virtual void SetEnableReboot(bool enabled);
110 
111   // --- menu display ---
112 
113   // Display some header text followed by a menu of items, which appears at the top of the screen
114   // (in place of any scrolling ui_print() output, if necessary).
115   virtual void StartMenu(const char* const* headers, const char* const* items,
116                          int initial_selection) = 0;
117 
118   // Sets the menu highlight to the given index, wrapping if necessary. Returns the actual item
119   // selected.
120   virtual int SelectMenu(int sel) = 0;
121 
122   // Ends menu mode, resetting the text overlay so that ui_print() statements will be displayed.
123   virtual void EndMenu() = 0;
124 
125  protected:
126   void EnqueueKey(int key_code);
127 
128   // The locale that's used to show the rendered texts.
129   std::string locale_;
130   bool rtl_locale_;
131 
132   // The normal and dimmed brightness percentages (default: 50 and 25, which means 50% and 25% of
133   // the max_brightness). Because the absolute values may vary across devices. These two values can
134   // be configured via subclassing. Setting brightness_normal_ to 0 to disable screensaver.
135   unsigned int brightness_normal_;
136   unsigned int brightness_dimmed_;
137 
138   // Whether we should listen for touch inputs (default: false).
139   bool touch_screen_allowed_;
140 
141  private:
142   // The sensitivity when detecting a swipe.
143   const int kTouchLowThreshold;
144   const int kTouchHighThreshold;
145 
146   // Key event input queue
147   pthread_mutex_t key_queue_mutex;
148   pthread_cond_t key_queue_cond;
149   int key_queue[256], key_queue_len;
150   char key_pressed[KEY_MAX + 1];  // under key_queue_mutex
151   int key_last_down;              // under key_queue_mutex
152   bool key_long_press;            // under key_queue_mutex
153   int key_down_count;             // under key_queue_mutex
154   bool enable_reboot;             // under key_queue_mutex
155   int rel_sum;
156 
157   int consecutive_power_keys;
158   int last_key;
159 
160   bool has_power_key;
161   bool has_up_key;
162   bool has_down_key;
163   bool has_touch_screen;
164 
165   // Touch event related variables. See the comments in RecoveryUI::OnInputEvent().
166   int touch_slot_;
167   int touch_X_;
168   int touch_Y_;
169   int touch_start_X_;
170   int touch_start_Y_;
171   bool touch_finger_down_;
172   bool touch_swiping_;
173   bool is_bootreason_recovery_ui_;
174 
175   struct key_timer_t {
176     RecoveryUI* ui;
177     int key_code;
178     int count;
179   };
180 
181   pthread_t input_thread_;
182 
183   void OnKeyDetected(int key_code);
184   void OnTouchDetected(int dx, int dy);
185   int OnInputEvent(int fd, uint32_t epevents);
186   void ProcessKey(int key_code, int updown);
187 
188   bool IsUsbConnected();
189 
190   static void* time_key_helper(void* cookie);
191   void time_key(int key_code, int count);
192 
193   void SetLocale(const std::string&);
194 
195   enum class ScreensaverState { DISABLED, NORMAL, DIMMED, OFF };
196   ScreensaverState screensaver_state_;
197   // The following two contain the absolute values computed from brightness_normal_ and
198   // brightness_dimmed_ respectively.
199   unsigned int brightness_normal_value_;
200   unsigned int brightness_dimmed_value_;
201   bool InitScreensaver();
202 };
203 
204 #endif  // RECOVERY_UI_H
205