77
88#include < services.hpp>
99
10+ #include " chprintf.h"
1011#include " hal.h"
12+ #include " robots/include/sabo_robot.hpp"
1113#include " sabo_cover_ui_display.hpp"
1214#include " sabo_cover_ui_display_driver_uc1698.hpp"
1315
@@ -127,6 +129,111 @@ const char* SaboCoverUIController::ButtonIDToString(const ButtonID id) {
127129 }
128130}
129131
132+ /* *
133+ * @brief Handle the boot sequence
134+ *
135+ */
136+ void SaboCoverUIController::HandleBootSequence () {
137+ auto boot_screen = display_->GetBootScreen ();
138+ if (boot_screen == nullptr ) return ;
139+
140+ // All boot steps done...
141+ if (current_boot_step_ >= boot_steps_.size ()) {
142+ if (boot_screen->GetAnimationState () == SaboScreenBoot::AnimationState::NONE) {
143+ display_->SetBootStatus (" Ready to mow" , 100 );
144+ boot_screen->StartForwardAnimation ();
145+ } else if (boot_screen->GetAnimationState () == SaboScreenBoot::AnimationState::DONE) {
146+ display_->ShowMainScreen ();
147+ }
148+ return ;
149+ }
150+
151+ BootStep& step = boot_steps_[current_boot_step_];
152+ systime_t now = chVTGetSystemTimeX ();
153+ uint32_t elapsed_ms = TIME_I2MS (now - step.last_action_time );
154+
155+ switch (step.state ) {
156+ case BootStepState::WAIT:
157+ step.state = BootStepState::RUNNING;
158+ step.last_action_time = now;
159+ display_->SetBootStatus (step.name , (current_boot_step_ * 100 ) / boot_steps_.size ());
160+ break ;
161+
162+ case BootStepState::RUNNING:
163+ if (elapsed_ms >= 1000 ) {
164+ if (step.test_func ()) {
165+ step.state = BootStepState::DONE;
166+ current_boot_step_++;
167+ boot_step_retry_count_ = 0 ;
168+ } else {
169+ boot_step_retry_count_++;
170+ if (boot_step_retry_count_ < BOOT_STEP_RETRIES) {
171+ etl::string<48 > fail_msg;
172+ chsnprintf (fail_msg.data (), fail_msg.max_size (), " %s (%d/%d)" , step.name , boot_step_retry_count_,
173+ BOOT_STEP_RETRIES);
174+ display_->SetBootStatus (fail_msg, (current_boot_step_ * 100 ) / boot_steps_.size ());
175+ step.last_action_time = now;
176+ } else {
177+ etl::string<48 > fail_msg = step.name ;
178+ fail_msg += " failed!" ;
179+ display_->SetBootStatus (fail_msg, (current_boot_step_ * 100 ) / boot_steps_.size ());
180+ step.state = BootStepState::ERROR;
181+ step.last_action_time = now;
182+ }
183+ }
184+ }
185+ break ;
186+
187+ case BootStepState::ERROR:
188+ if (elapsed_ms >= 60000 || cabo_->IsAnyButtonPressed ()) {
189+ step.state = BootStepState::DONE;
190+ current_boot_step_++;
191+ boot_step_retry_count_ = 0 ;
192+ }
193+ break ;
194+
195+ case BootStepState::DONE:
196+ // NOP. Next step get handled in next tick
197+ break ;
198+ }
199+ }
200+
201+ bool SaboCoverUIController::TestIMU () {
202+ return imu_service.IsFound ();
203+ }
204+
205+ bool SaboCoverUIController::TestCharger () {
206+ Robot* robot = GetRobot ();
207+ if (!robot) return false ;
208+
209+ auto * sabo = static_cast <SaboRobot*>(robot);
210+ if (!sabo) return false ;
211+
212+ const CHARGER_STATUS status = sabo->GetChargerStatus ();
213+ // TODO: Why do I get COMMS_ERROR here?
214+ // return status != CHARGER_STATUS::FAULT && status != CHARGER_STATUS::COMMS_ERROR;
215+ return status != CHARGER_STATUS::FAULT;
216+ }
217+
218+ bool SaboCoverUIController::TestGPS () {
219+ return true ;
220+ }
221+
222+ bool SaboCoverUIController::TestLeftESC () {
223+ auto esc_state = diff_drive.GetLeftESCState ();
224+ return esc_state.status == MotorDriver::ESCState::ESCStatus::ESC_STATUS_OK;
225+ }
226+
227+ bool SaboCoverUIController::TestRightESC () {
228+ auto esc_state = diff_drive.GetRightESCState ();
229+ return esc_state.status == MotorDriver::ESCState::ESCStatus::ESC_STATUS_OK;
230+ }
231+
232+ bool SaboCoverUIController::TestMowerESC () {
233+ auto esc_state = mower_service.GetESCState ();
234+ return esc_state.status == MotorDriver::ESCState::ESCStatus::ESC_STATUS_OK;
235+ }
236+
130237void SaboCoverUIController::ThreadFunc () {
131238 if (display_) {
132239 display_->Start ();
@@ -139,6 +246,10 @@ void SaboCoverUIController::ThreadFunc() {
139246 if (cabo_->IsReady () && display_) {
140247 display_->Tick ();
141248 if (cabo_->IsAnyButtonPressed ()) display_->WakeUp ();
249+
250+ if (current_boot_step_ <= boot_steps_.size () && display_->GetActiveScreen ()->GetScreenId () == ScreenId::BOOT) {
251+ HandleBootSequence ();
252+ }
142253 }
143254
144255 // ----- Debug -----
0 commit comments