From 31c84d4559f763cbe2777c0682b72d6cf35e9027 Mon Sep 17 00:00:00 2001
From: LinFor <linfor@gmail.com>
Date: Tue, 22 Dec 2020 09:31:14 +0300
Subject: [PATCH] FTDI EVE custom user menus (#20518)

---
 .../screens/custom_user_menus.cpp             | 215 ++++++++++++++++++
 .../ftdi_eve_touch_ui/screens/main_menu.cpp   |  64 +++++-
 .../lib/ftdi_eve_touch_ui/screens/screens.cpp | 157 +++++++------
 .../lib/ftdi_eve_touch_ui/screens/screens.h   | 203 ++++++++++-------
 4 files changed, 481 insertions(+), 158 deletions(-)
 create mode 100644 Marlin/src/lcd/extui/lib/ftdi_eve_touch_ui/screens/custom_user_menus.cpp

diff --git a/Marlin/src/lcd/extui/lib/ftdi_eve_touch_ui/screens/custom_user_menus.cpp b/Marlin/src/lcd/extui/lib/ftdi_eve_touch_ui/screens/custom_user_menus.cpp
new file mode 100644
index 00000000000..4132226977d
--- /dev/null
+++ b/Marlin/src/lcd/extui/lib/ftdi_eve_touch_ui/screens/custom_user_menus.cpp
@@ -0,0 +1,215 @@
+/**
+ * Marlin 3D Printer Firmware
+ * Copyright (c) 2020 MarlinFirmware [https://github.com/MarlinFirmware/Marlin]
+ *
+ * Based on Sprinter and grbl.
+ * Copyright (c) 2011 Camiel Gubbels / Erik van der Zalm
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program.  If not, see <https://www.gnu.org/licenses/>.
+ *
+ */
+
+#include "../config.h"
+
+#if BOTH(TOUCH_UI_FTDI_EVE, CUSTOM_USER_MENUS) && NONE(TOUCH_UI_LULZBOT_BIO, TOUCH_UI_COCOA_PRESS)
+
+#include "screens.h"
+
+using namespace FTDI;
+using namespace ExtUI;
+using namespace Theme;
+
+#define _ITEM_TAG(N) (10+N)
+#define _USER_DESC(N) USER_DESC_##N
+#define _USER_GCODE(N) USER_GCODE_##N
+#define _USER_ITEM(N) .tag(_ITEM_TAG(N)).button(USER_ITEM_POS(N), _USER_DESC(N))
+#define _USER_ACTION(N) case _ITEM_TAG(N): injectCommands_P(PSTR(_USER_GCODE(N))); TERN_(USER_SCRIPT_RETURN, GOTO_SCREEN(StatusScreen)); break;
+
+#define _HAS_1(N) (defined(USER_DESC_##N) && defined(USER_GCODE_##N))
+#define HAS_USER_ITEM(V...) DO(HAS,||,V)
+
+void CustomUserMenus::onRedraw(draw_mode_t what) {
+  if (what & BACKGROUND) {
+    CommandProcessor cmd;
+    cmd.cmd(CLEAR_COLOR_RGB(Theme::bg_color))
+       .cmd(CLEAR(true, true, true));
+  }
+
+  #if HAS_USER_ITEM(16, 17, 18, 19, 20)
+    #define _MORE_THAN_FIFTEEN 1
+  #else
+    #define _MORE_THAN_FIFTEEN 0
+  #endif
+  #if _MORE_THAN_FIFTEEN || HAS_USER_ITEM(11, 12, 13, 14, 15)
+    #define _MORE_THAN_TEN 1
+  #else
+    #define _MORE_THAN_TEN 0
+  #endif
+
+  #ifdef TOUCH_UI_PORTRAIT
+    #define GRID_ROWS 11
+    #define GRID_COLS (1 + _MORE_THAN_TEN)
+    #define USER_ITEM_POS(N) BTN_POS((1+((N-1)/10)), ((N-1) % 10 + 1)), BTN_SIZE(1,1)
+    #define BACK_POS         BTN_POS(1,11), BTN_SIZE(1,1)
+  #else
+    #if _MORE_THAN_TEN || HAS_USER_ITEM(6, 7, 8, 9, 10)
+      #define _MORE_THAN_FIVE 1
+    #else
+      #define _MORE_THAN_FIVE 0
+    #endif
+    #define GRID_ROWS 6
+    #define GRID_COLS (1 + _MORE_THAN_FIVE + _MORE_THAN_TEN + _MORE_THAN_FIFTEEN)
+    #define USER_ITEM_POS(N) BTN_POS((1+((N-1)/5)), ((N-1) % 5 + 1)), BTN_SIZE(1,1)
+    #define BACK_POS         BTN_POS(1,6), BTN_SIZE(GRID_COLS,1)
+  #endif
+
+  if (what & FOREGROUND) {
+    CommandProcessor cmd;
+    cmd.colors(normal_btn)
+       .font(Theme::font_medium)
+       #if HAS_USER_ITEM(1)
+        _USER_ITEM(1)
+       #endif
+       #if HAS_USER_ITEM(2)
+        _USER_ITEM(2)
+       #endif
+       #if HAS_USER_ITEM(3)
+        _USER_ITEM(3)
+       #endif
+       #if HAS_USER_ITEM(4)
+        _USER_ITEM(4)
+       #endif
+       #if HAS_USER_ITEM(5)
+        _USER_ITEM(5)
+       #endif
+       #if HAS_USER_ITEM(6)
+        _USER_ITEM(6)
+       #endif
+       #if HAS_USER_ITEM(7)
+        _USER_ITEM(7)
+       #endif
+       #if HAS_USER_ITEM(8)
+        _USER_ITEM(8)
+       #endif
+       #if HAS_USER_ITEM(9)
+        _USER_ITEM(9)
+       #endif
+       #if HAS_USER_ITEM(10)
+        _USER_ITEM(10)
+       #endif
+       #if HAS_USER_ITEM(11)
+        _USER_ITEM(11)
+       #endif
+       #if HAS_USER_ITEM(12)
+        _USER_ITEM(12)
+       #endif
+       #if HAS_USER_ITEM(13)
+        _USER_ITEM(13)
+       #endif
+       #if HAS_USER_ITEM(14)
+        _USER_ITEM(14)
+       #endif
+       #if HAS_USER_ITEM(15)
+        _USER_ITEM(15)
+       #endif
+       #if HAS_USER_ITEM(16)
+        _USER_ITEM(16)
+       #endif
+       #if HAS_USER_ITEM(17)
+        _USER_ITEM(17)
+       #endif
+       #if HAS_USER_ITEM(18)
+        _USER_ITEM(18)
+       #endif
+       #if HAS_USER_ITEM(19)
+        _USER_ITEM(19)
+       #endif
+       #if HAS_USER_ITEM(20)
+        _USER_ITEM(20)
+       #endif
+      .colors(action_btn)
+      .tag(1).button(BACK_POS, GET_TEXT_F(MSG_BACK));
+  }
+}
+
+bool CustomUserMenus::onTouchEnd(uint8_t tag) {
+  switch (tag) {
+    #if HAS_USER_ITEM(1)
+      _USER_ACTION(1)
+    #endif
+    #if HAS_USER_ITEM(2)
+      _USER_ACTION(2)
+    #endif
+    #if HAS_USER_ITEM(3)
+      _USER_ACTION(3)
+    #endif
+    #if HAS_USER_ITEM(4)
+      _USER_ACTION(4)
+    #endif
+    #if HAS_USER_ITEM(5)
+      _USER_ACTION(5)
+    #endif
+    #if HAS_USER_ITEM(6)
+      _USER_ACTION(6)
+    #endif
+    #if HAS_USER_ITEM(7)
+      _USER_ACTION(7)
+    #endif
+    #if HAS_USER_ITEM(8)
+      _USER_ACTION(8)
+    #endif
+    #if HAS_USER_ITEM(9)
+      _USER_ACTION(9)
+    #endif
+    #if HAS_USER_ITEM(10)
+      _USER_ACTION(10)
+    #endif
+    #if HAS_USER_ITEM(11)
+      _USER_ACTION(11)
+    #endif
+    #if HAS_USER_ITEM(12)
+      _USER_ACTION(12)
+    #endif
+    #if HAS_USER_ITEM(13)
+      _USER_ACTION(13)
+    #endif
+    #if HAS_USER_ITEM(14)
+      _USER_ACTION(14)
+    #endif
+    #if HAS_USER_ITEM(15)
+      _USER_ACTION(15)
+    #endif
+    #if HAS_USER_ITEM(16)
+      _USER_ACTION(16)
+    #endif
+    #if HAS_USER_ITEM(17)
+      _USER_ACTION(17)
+    #endif
+    #if HAS_USER_ITEM(18)
+      _USER_ACTION(18)
+    #endif
+    #if HAS_USER_ITEM(19)
+      _USER_ACTION(19)
+    #endif
+    #if HAS_USER_ITEM(20)
+      _USER_ACTION(20)
+    #endif
+
+    case 1: GOTO_PREVIOUS(); break;
+    default: return false;
+  }
+  return true;
+}
+
+#endif // TOUCH_UI_FTDI_EVE && CUSTOM_USER_MENUS && !TOUCH_UI_LULZBOT_BIO && !TOUCH_UI_COCOA_PRESS
diff --git a/Marlin/src/lcd/extui/lib/ftdi_eve_touch_ui/screens/main_menu.cpp b/Marlin/src/lcd/extui/lib/ftdi_eve_touch_ui/screens/main_menu.cpp
index 89b5899e7a5..529daa2f83d 100644
--- a/Marlin/src/lcd/extui/lib/ftdi_eve_touch_ui/screens/main_menu.cpp
+++ b/Marlin/src/lcd/extui/lib/ftdi_eve_touch_ui/screens/main_menu.cpp
@@ -1,3 +1,25 @@
+/**
+ * Marlin 3D Printer Firmware
+ * Copyright (c) 2020 MarlinFirmware [https://github.com/MarlinFirmware/Marlin]
+ *
+ * Based on Sprinter and grbl.
+ * Copyright (c) 2011 Camiel Gubbels / Erik van der Zalm
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program.  If not, see <https://www.gnu.org/licenses/>.
+ *
+ */
+
 /*****************
  * main_menu.cpp *
  *****************/
@@ -42,7 +64,12 @@ void MainMenu::onRedraw(draw_mode_t what) {
     #define GRID_COLS 2
     #define ABOUT_PRINTER_POS     BTN_POS(1,1), BTN_SIZE(2,1)
     #define ADVANCED_SETTINGS_POS BTN_POS(1,2), BTN_SIZE(2,1)
-    #define FILAMENTCHANGE_POS    BTN_POS(1,3), BTN_SIZE(2,1)
+    #if ENABLED(CUSTOM_USER_MENUS)
+      #define FILAMENTCHANGE_POS  BTN_POS(1,3), BTN_SIZE(1,1)
+      #define CUSTOM_USER_MENUS_POS BTN_POS(2,3), BTN_SIZE(1,1)
+    #else
+      #define FILAMENTCHANGE_POS  BTN_POS(1,3), BTN_SIZE(2,1)
+    #endif
     #define TEMPERATURE_POS       BTN_POS(1,4), BTN_SIZE(2,1)
     #define DISABLE_STEPPERS_POS  BTN_POS(1,5), BTN_SIZE(2,1)
     #define MOVE_AXIS_POS         BTN_POS(1,6), BTN_SIZE(1,1)
@@ -52,17 +79,23 @@ void MainMenu::onRedraw(draw_mode_t what) {
     #define BACK_POS              BTN_POS(1,8), BTN_SIZE(2,1)
   #else
     #define GRID_ROWS 5
-    #define GRID_COLS 2
-    #define ADVANCED_SETTINGS_POS BTN_POS(1,1), BTN_SIZE(1,1)
-    #define ABOUT_PRINTER_POS     BTN_POS(2,1), BTN_SIZE(1,1)
-    #define AUTO_HOME_POS         BTN_POS(1,2), BTN_SIZE(1,1)
-    #define CLEAN_NOZZLE_POS      BTN_POS(2,2), BTN_SIZE(1,1)
-    #define MOVE_AXIS_POS         BTN_POS(1,3), BTN_SIZE(1,1)
-    #define DISABLE_STEPPERS_POS  BTN_POS(2,3), BTN_SIZE(1,1)
-    #define TEMPERATURE_POS       BTN_POS(1,4), BTN_SIZE(1,1)
-    #define FILAMENTCHANGE_POS    BTN_POS(2,4), BTN_SIZE(1,1)
-    #define LEVELING_POS          BTN_POS(1,5), BTN_SIZE(1,1)
-    #define BACK_POS              BTN_POS(2,5), BTN_SIZE(1,1)
+    #define GRID_COLS 6
+    #define ADVANCED_SETTINGS_POS BTN_POS(1,1), BTN_SIZE(3,1)
+    #define ABOUT_PRINTER_POS     BTN_POS(4,1), BTN_SIZE(3,1)
+    #define AUTO_HOME_POS         BTN_POS(1,2), BTN_SIZE(3,1)
+    #define CLEAN_NOZZLE_POS      BTN_POS(4,2), BTN_SIZE(3,1)
+    #define MOVE_AXIS_POS         BTN_POS(1,3), BTN_SIZE(3,1)
+    #define DISABLE_STEPPERS_POS  BTN_POS(4,3), BTN_SIZE(3,1)
+    #if ENABLED(CUSTOM_USER_MENUS)
+      #define TEMPERATURE_POS     BTN_POS(1,4), BTN_SIZE(2,1)
+      #define FILAMENTCHANGE_POS  BTN_POS(3,4), BTN_SIZE(2,1)
+      #define CUSTOM_USER_MENUS_POS BTN_POS(5,4), BTN_SIZE(2,1)
+    #else
+      #define TEMPERATURE_POS     BTN_POS(1,4), BTN_SIZE(3,1)
+      #define FILAMENTCHANGE_POS  BTN_POS(4,4), BTN_SIZE(3,1)
+    #endif
+    #define LEVELING_POS          BTN_POS(1,5), BTN_SIZE(3,1)
+    #define BACK_POS              BTN_POS(4,5), BTN_SIZE(3,1)
   #endif
 
   if (what & FOREGROUND) {
@@ -81,6 +114,9 @@ void MainMenu::onRedraw(draw_mode_t what) {
        .enabled(TERN_(HAS_LEVELING, 1))
        .tag( 9).button(LEVELING_POS,        GET_TEXT_F(MSG_LEVELING))
        .tag(10).button(ABOUT_PRINTER_POS,   GET_TEXT_F(MSG_INFO_MENU))
+       #if ENABLED(CUSTOM_USER_MENUS)
+        .tag(11).button(CUSTOM_USER_MENUS_POS, GET_TEXT_F(MSG_USER_MENU))
+       #endif
        .colors(action_btn)
        .tag(1).button(BACK_POS,             GET_TEXT_F(MSG_BACK));
   }
@@ -104,6 +140,10 @@ bool MainMenu::onTouchEnd(uint8_t tag) {
     case 9:  GOTO_SCREEN(LevelingMenu);                               break;
     #endif
     case 10: GOTO_SCREEN(AboutScreen);                                break;
+    #if ENABLED(CUSTOM_USER_MENUS)
+      case 11: GOTO_SCREEN(CustomUserMenus);                          break;
+    #endif
+
     default:
       return false;
   }
diff --git a/Marlin/src/lcd/extui/lib/ftdi_eve_touch_ui/screens/screens.cpp b/Marlin/src/lcd/extui/lib/ftdi_eve_touch_ui/screens/screens.cpp
index ff85689ef2b..5b3f9a201fe 100644
--- a/Marlin/src/lcd/extui/lib/ftdi_eve_touch_ui/screens/screens.cpp
+++ b/Marlin/src/lcd/extui/lib/ftdi_eve_touch_ui/screens/screens.cpp
@@ -1,3 +1,25 @@
+/**
+ * Marlin 3D Printer Firmware
+ * Copyright (c) 2020 MarlinFirmware [https://github.com/MarlinFirmware/Marlin]
+ *
+ * Based on Sprinter and grbl.
+ * Copyright (c) 2011 Camiel Gubbels / Erik van der Zalm
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program.  If not, see <https://www.gnu.org/licenses/>.
+ *
+ */
+
 /***************
  * screens.cpp *
  ***************/
@@ -45,88 +67,91 @@ SCREEN_TABLE {
   DECL_SCREEN(SaveSettingsDialogBox),
   DECL_SCREEN(ConfirmStartPrintDialogBox),
   DECL_SCREEN(ConfirmAbortPrintDialogBox),
-#if ENABLED(CALIBRATION_GCODE)
-  DECL_SCREEN(ConfirmAutoCalibrationDialogBox),
-#endif
+  #if ENABLED(CALIBRATION_GCODE)
+    DECL_SCREEN(ConfirmAutoCalibrationDialogBox),
+  #endif
+  #if ENABLED(CUSTOM_USER_MENUS)
+    DECL_SCREEN(CustomUserMenus),
+  #endif
   DECL_SCREEN(SpinnerDialogBox),
   DECL_SCREEN(AboutScreen),
-#if ENABLED(PRINTCOUNTER)
-  DECL_SCREEN(StatisticsScreen),
-#endif
-#if ENABLED(BABYSTEPPING)
-  DECL_SCREEN(NudgeNozzleScreen),
-#endif
+  #if ENABLED(PRINTCOUNTER)
+    DECL_SCREEN(StatisticsScreen),
+  #endif
+  #if ENABLED(BABYSTEPPING)
+    DECL_SCREEN(NudgeNozzleScreen),
+  #endif
   DECL_SCREEN(MoveAxisScreen),
   DECL_SCREEN(StepsScreen),
-#if HAS_TRINAMIC_CONFIG
-  DECL_SCREEN(StepperCurrentScreen),
-  DECL_SCREEN(StepperBumpSensitivityScreen),
-#endif
-#if HAS_LEVELING
-  DECL_SCREEN(LevelingMenu),
-  #if HAS_BED_PROBE
-    DECL_SCREEN(ZOffsetScreen),
+  #if HAS_TRINAMIC_CONFIG
+    DECL_SCREEN(StepperCurrentScreen),
+    DECL_SCREEN(StepperBumpSensitivityScreen),
   #endif
-  #if HAS_MESH
-    DECL_SCREEN(BedMeshScreen),
+  #if HAS_LEVELING
+    DECL_SCREEN(LevelingMenu),
+    #if HAS_BED_PROBE
+      DECL_SCREEN(ZOffsetScreen),
+    #endif
+    #if HAS_MESH
+      DECL_SCREEN(BedMeshScreen),
+    #endif
+  #endif
+  #if HAS_MULTI_HOTEND
+    DECL_SCREEN(NozzleOffsetScreen),
+  #endif
+  #if ENABLED(BACKLASH_GCODE)
+    DECL_SCREEN(BacklashCompensationScreen),
   #endif
-#endif
-#if HAS_MULTI_HOTEND
-  DECL_SCREEN(NozzleOffsetScreen),
-#endif
-#if ENABLED(BACKLASH_GCODE)
-  DECL_SCREEN(BacklashCompensationScreen),
-#endif
   DECL_SCREEN(FeedratePercentScreen),
   DECL_SCREEN(MaxVelocityScreen),
   DECL_SCREEN(MaxAccelerationScreen),
   DECL_SCREEN(DefaultAccelerationScreen),
-#if HAS_JUNCTION_DEVIATION
-  DECL_SCREEN(JunctionDeviationScreen),
-#else
-  DECL_SCREEN(JerkScreen),
-#endif
-#if ENABLED(CASE_LIGHT_ENABLE)
-  DECL_SCREEN(CaseLightScreen),
-#endif
-#if EITHER(LIN_ADVANCE, FILAMENT_RUNOUT_SENSOR)
-  DECL_SCREEN(FilamentMenu),
-#endif
-#if ENABLED(FILAMENT_RUNOUT_SENSOR)
-  DECL_SCREEN(FilamentRunoutScreen),
-#endif
-#if ENABLED(LIN_ADVANCE)
-  DECL_SCREEN(LinearAdvanceScreen),
-#endif
+  #if HAS_JUNCTION_DEVIATION
+    DECL_SCREEN(JunctionDeviationScreen),
+  #else
+    DECL_SCREEN(JerkScreen),
+  #endif
+  #if ENABLED(CASE_LIGHT_ENABLE)
+    DECL_SCREEN(CaseLightScreen),
+  #endif
+  #if EITHER(LIN_ADVANCE, FILAMENT_RUNOUT_SENSOR)
+    DECL_SCREEN(FilamentMenu),
+  #endif
+  #if ENABLED(FILAMENT_RUNOUT_SENSOR)
+    DECL_SCREEN(FilamentRunoutScreen),
+  #endif
+  #if ENABLED(LIN_ADVANCE)
+    DECL_SCREEN(LinearAdvanceScreen),
+  #endif
   DECL_SCREEN(TemperatureScreen),
   DECL_SCREEN(ChangeFilamentScreen),
   DECL_SCREEN(InterfaceSettingsScreen),
   DECL_SCREEN(InterfaceSoundsScreen),
   DECL_SCREEN(LockScreen),
-#if ENABLED(SDSUPPORT)
-  DECL_SCREEN(FilesScreen),
-#endif
+  #if ENABLED(SDSUPPORT)
+    DECL_SCREEN(FilesScreen),
+  #endif
   DECL_SCREEN(EndstopStatesScreen),
-#if ENABLED(TOUCH_UI_LULZBOT_BIO)
-  DECL_SCREEN(BioPrintingDialogBox),
-  DECL_SCREEN(BioConfirmHomeXYZ),
-  DECL_SCREEN(BioConfirmHomeE),
-#endif
-#if ENABLED(TOUCH_UI_COCOA_PRESS)
-  DECL_SCREEN(PreheatMenu),
-  DECL_SCREEN(PreheatTimerScreen),
-  DECL_SCREEN(UnloadCartridgeScreen),
-  DECL_SCREEN(LoadChocolateScreen),
-  DECL_SCREEN(MoveXYZScreen),
-  DECL_SCREEN(MoveEScreen),
-#endif
-#if ENABLED(TOUCH_UI_DEVELOPER_MENU)
-  DECL_SCREEN(DeveloperMenu),
-  DECL_SCREEN(ConfirmEraseFlashDialogBox),
-  DECL_SCREEN(WidgetsScreen),
-  DECL_SCREEN(TouchRegistersScreen),
-  DECL_SCREEN(StressTestScreen),
-#endif
+  #if ENABLED(TOUCH_UI_LULZBOT_BIO)
+    DECL_SCREEN(BioPrintingDialogBox),
+    DECL_SCREEN(BioConfirmHomeXYZ),
+    DECL_SCREEN(BioConfirmHomeE),
+  #endif
+  #if ENABLED(TOUCH_UI_COCOA_PRESS)
+    DECL_SCREEN(PreheatMenu),
+    DECL_SCREEN(PreheatTimerScreen),
+    DECL_SCREEN(UnloadCartridgeScreen),
+    DECL_SCREEN(LoadChocolateScreen),
+    DECL_SCREEN(MoveXYZScreen),
+    DECL_SCREEN(MoveEScreen),
+  #endif
+  #if ENABLED(TOUCH_UI_DEVELOPER_MENU)
+    DECL_SCREEN(DeveloperMenu),
+    DECL_SCREEN(ConfirmEraseFlashDialogBox),
+    DECL_SCREEN(WidgetsScreen),
+    DECL_SCREEN(TouchRegistersScreen),
+    DECL_SCREEN(StressTestScreen),
+  #endif
   DECL_SCREEN(MediaPlayerScreen),
   DECL_SCREEN(DisplayTuningScreen)
 };
diff --git a/Marlin/src/lcd/extui/lib/ftdi_eve_touch_ui/screens/screens.h b/Marlin/src/lcd/extui/lib/ftdi_eve_touch_ui/screens/screens.h
index 3fa18d9f67c..265d6eb4862 100644
--- a/Marlin/src/lcd/extui/lib/ftdi_eve_touch_ui/screens/screens.h
+++ b/Marlin/src/lcd/extui/lib/ftdi_eve_touch_ui/screens/screens.h
@@ -1,3 +1,25 @@
+/**
+ * Marlin 3D Printer Firmware
+ * Copyright (c) 2020 MarlinFirmware [https://github.com/MarlinFirmware/Marlin]
+ *
+ * Based on Sprinter and grbl.
+ * Copyright (c) 2011 Camiel Gubbels / Erik van der Zalm
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program.  If not, see <https://www.gnu.org/licenses/>.
+ *
+ */
+
 /*************
  * screens.h *
  *************/
@@ -53,59 +75,62 @@ enum {
   MAX_VELOCITY_SCREEN_CACHE,
   MAX_ACCELERATION_SCREEN_CACHE,
   DEFAULT_ACCELERATION_SCREEN_CACHE,
-#if HAS_LEVELING
-  LEVELING_SCREEN_CACHE,
-  #if HAS_BED_PROBE
-    ZOFFSET_SCREEN_CACHE,
+  #if HAS_LEVELING
+    LEVELING_SCREEN_CACHE,
+    #if HAS_BED_PROBE
+      ZOFFSET_SCREEN_CACHE,
+    #endif
+    #if HAS_MESH
+      BED_MESH_SCREEN_CACHE,
+    #endif
   #endif
-  #if HAS_MESH
-    BED_MESH_SCREEN_CACHE,
+  #if ENABLED(BABYSTEPPING)
+    ADJUST_OFFSETS_SCREEN_CACHE,
+  #endif
+  #if HAS_TRINAMIC_CONFIG
+    STEPPER_CURRENT_SCREEN_CACHE,
+    STEPPER_BUMP_SENSITIVITY_SCREEN_CACHE,
+  #endif
+  #if HAS_MULTI_HOTEND
+    NOZZLE_OFFSET_SCREEN_CACHE,
+  #endif
+  #if ENABLED(BACKLASH_GCODE)
+    BACKLASH_COMPENSATION_SCREEN_CACHE,
+  #endif
+  #if HAS_JUNCTION_DEVIATION
+    JUNC_DEV_SCREEN_CACHE,
+  #else
+    JERK_SCREEN_CACHE,
+  #endif
+  #if ENABLED(CASE_LIGHT_ENABLE)
+    CASE_LIGHT_SCREEN_CACHE,
+  #endif
+  #if EITHER(LIN_ADVANCE, FILAMENT_RUNOUT_SENSOR)
+    FILAMENT_MENU_CACHE,
+  #endif
+  #if ENABLED(LIN_ADVANCE)
+    LINEAR_ADVANCE_SCREEN_CACHE,
+  #endif
+  #if ENABLED(FILAMENT_RUNOUT_SENSOR)
+    FILAMENT_RUNOUT_SCREEN_CACHE,
+  #endif
+  #if ENABLED(TOUCH_UI_LULZBOT_BIO)
+    PRINTING_SCREEN_CACHE,
+  #endif
+  #if ENABLED(TOUCH_UI_COCOA_PRESS)
+    PREHEAT_MENU_CACHE,
+    PREHEAT_TIMER_SCREEN_CACHE,
+    UNLOAD_CARTRIDGE_SCREEN_CACHE,
+    LOAD_CHOCOLATE_SCREEN_CACHE,
+    MOVE_XYZ_SCREEN_CACHE,
+    MOVE_E_SCREEN_CACHE,
+  #endif
+  #if ENABLED(SDSUPPORT)
+    FILES_SCREEN_CACHE,
+  #endif
+  #if ENABLED(CUSTOM_USER_MENUS)
+    CUSTOM_USER_MENUS_SCREEN_CACHE,
   #endif
-#endif
-#if ENABLED(BABYSTEPPING)
-  ADJUST_OFFSETS_SCREEN_CACHE,
-#endif
-#if HAS_TRINAMIC_CONFIG
-  STEPPER_CURRENT_SCREEN_CACHE,
-  STEPPER_BUMP_SENSITIVITY_SCREEN_CACHE,
-#endif
-#if HAS_MULTI_HOTEND
-  NOZZLE_OFFSET_SCREEN_CACHE,
-#endif
-#if ENABLED(BACKLASH_GCODE)
-  BACKLASH_COMPENSATION_SCREEN_CACHE,
-#endif
-#if HAS_JUNCTION_DEVIATION
-  JUNC_DEV_SCREEN_CACHE,
-#else
-  JERK_SCREEN_CACHE,
-#endif
-#if ENABLED(CASE_LIGHT_ENABLE)
-  CASE_LIGHT_SCREEN_CACHE,
-#endif
-#if EITHER(LIN_ADVANCE, FILAMENT_RUNOUT_SENSOR)
-  FILAMENT_MENU_CACHE,
-#endif
-#if ENABLED(LIN_ADVANCE)
-  LINEAR_ADVANCE_SCREEN_CACHE,
-#endif
-#if ENABLED(FILAMENT_RUNOUT_SENSOR)
-  FILAMENT_RUNOUT_SCREEN_CACHE,
-#endif
-#if ENABLED(TOUCH_UI_LULZBOT_BIO)
-  PRINTING_SCREEN_CACHE,
-#endif
-#if ENABLED(TOUCH_UI_COCOA_PRESS)
-  PREHEAT_MENU_CACHE,
-  PREHEAT_TIMER_SCREEN_CACHE,
-  UNLOAD_CARTRIDGE_SCREEN_CACHE,
-  LOAD_CHOCOLATE_SCREEN_CACHE,
-  MOVE_XYZ_SCREEN_CACHE,
-  MOVE_E_SCREEN_CACHE,
-#endif
-#if ENABLED(SDSUPPORT)
-  FILES_SCREEN_CACHE,
-#endif
   CHANGE_FILAMENT_SCREEN_CACHE,
   INTERFACE_SETTINGS_SCREEN_CACHE,
   INTERFACE_SOUNDS_SCREEN_CACHE,
@@ -247,6 +272,14 @@ class ConfirmUserRequestAlertBox : public AlertDialogBox {
     static void show(const char*);
 };
 
+#if ENABLED(CUSTOM_USER_MENUS)
+  class CustomUserMenus : public BaseScreen, public CachedScreen<CUSTOM_USER_MENUS_SCREEN_CACHE> {
+    public:
+      static void onRedraw(draw_mode_t);
+      static bool onTouchEnd(uint8_t tag);
+  };
+#endif
+
 class SpinnerDialogBox : public DialogBoxBaseClass, public CachedScreen<SPINNER_CACHE,SPINNER_DL_SIZE> {
   public:
     static void onRedraw(draw_mode_t);
@@ -496,6 +529,7 @@ class StepsScreen : public BaseNumericAdjustmentScreen, public CachedScreen<STEP
 #endif
 
 #if HAS_LEVELING
+
   class LevelingMenu : public BaseScreen, public CachedScreen<LEVELING_SCREEN_CACHE> {
     public:
       static void onRedraw(draw_mode_t);
@@ -511,35 +545,38 @@ class StepsScreen : public BaseNumericAdjustmentScreen, public CachedScreen<STEP
   #endif
 
   #if HAS_MESH
-  class BedMeshScreen : public BaseScreen, public CachedScreen<BED_MESH_SCREEN_CACHE> {
-    private:
-      enum MeshOpts {
-        USE_POINTS    = 0x01,
-        USE_COLORS    = 0x02,
-        USE_TAGS      = 0x04,
-        USE_HIGHLIGHT = 0x08,
-        USE_AUTOSCALE = 0x10
-      };
 
-      static uint8_t pointToTag(uint8_t x, uint8_t y);
-      static bool tagToPoint(uint8_t tag, uint8_t &x, uint8_t &y);
-      static float getHightlightedValue();
-      static void drawHighlightedPointValue();
-      static void drawMesh(int16_t x, int16_t y, int16_t w, int16_t h, ExtUI::bed_mesh_t data, uint8_t opts, float autoscale_max = 0.1);
-      static bool isMeshComplete(ExtUI::bed_mesh_t data);
+    class BedMeshScreen : public BaseScreen, public CachedScreen<BED_MESH_SCREEN_CACHE> {
+      private:
+        enum MeshOpts {
+          USE_POINTS    = 0x01,
+          USE_COLORS    = 0x02,
+          USE_TAGS      = 0x04,
+          USE_HIGHLIGHT = 0x08,
+          USE_AUTOSCALE = 0x10
+        };
 
-    public:
-      static void onMeshUpdate(const int8_t x, const int8_t y, const float val);
-      static void onMeshUpdate(const int8_t x, const int8_t y, const ExtUI::probe_state_t);
-      static void onEntry();
-      static void onRedraw(draw_mode_t);
-      static bool onTouchStart(uint8_t tag);
-      static bool onTouchEnd(uint8_t tag);
+        static uint8_t pointToTag(uint8_t x, uint8_t y);
+        static bool tagToPoint(uint8_t tag, uint8_t &x, uint8_t &y);
+        static float getHightlightedValue();
+        static void drawHighlightedPointValue();
+        static void drawMesh(int16_t x, int16_t y, int16_t w, int16_t h, ExtUI::bed_mesh_t data, uint8_t opts, float autoscale_max = 0.1);
+        static bool isMeshComplete(ExtUI::bed_mesh_t data);
 
-      static void startMeshProbe();
-  };
-  #endif
-#endif
+      public:
+        static void onMeshUpdate(const int8_t x, const int8_t y, const float val);
+        static void onMeshUpdate(const int8_t x, const int8_t y, const ExtUI::probe_state_t);
+        static void onEntry();
+        static void onRedraw(draw_mode_t);
+        static bool onTouchStart(uint8_t tag);
+        static bool onTouchEnd(uint8_t tag);
+
+        static void startMeshProbe();
+    };
+
+  #endif // HAS_MESH
+
+#endif // HAS_LEVELING
 
 #if ENABLED(BABYSTEPPING)
   class NudgeNozzleScreen : public BaseNumericAdjustmentScreen, public CachedScreen<ADJUST_OFFSETS_SCREEN_CACHE> {
@@ -727,6 +764,7 @@ class LockScreen : public BaseScreen, public CachedScreen<LOCK_SCREEN_CACHE> {
 };
 
 #if ENABLED(SDSUPPORT)
+
   class FilesScreen : public BaseScreen, public CachedScreen<FILES_SCREEN_CACHE, FILE_SCREEN_DL_SIZE> {
     private:
       #ifdef TOUCH_UI_PORTRAIT
@@ -761,7 +799,8 @@ class LockScreen : public BaseScreen, public CachedScreen<LOCK_SCREEN_CACHE> {
       static bool onTouchEnd(uint8_t tag);
       static void onIdle();
   };
-#endif
+
+#endif // SDSUPPORT
 
 class EndstopStatesScreen : public BaseScreen, public UncachedScreen {
   public:
@@ -779,6 +818,7 @@ class DisplayTuningScreen : public BaseNumericAdjustmentScreen, public CachedScr
 };
 
 #if ENABLED(TOUCH_UI_DEVELOPER_MENU)
+
   class DeveloperMenu : public BaseScreen, public UncachedScreen {
     public:
       static void onRedraw(draw_mode_t);
@@ -815,7 +855,8 @@ class DisplayTuningScreen : public BaseNumericAdjustmentScreen, public CachedScr
       static bool onTouchEnd(uint8_t tag);
       static void onIdle();
   };
-#endif
+
+#endif // TOUCH_UI_DEVELOPER_MENU
 
 class MediaPlayerScreen : public BaseScreen, public UncachedScreen {
   private:
@@ -840,6 +881,7 @@ class MediaPlayerScreen : public BaseScreen, public UncachedScreen {
 #endif
 
 #if ENABLED(TOUCH_UI_COCOA_PRESS)
+
   class PreheatMenu : public BaseScreen, public CachedScreen<PREHEAT_MENU_CACHE> {
     public:
       static void onRedraw(draw_mode_t);
@@ -888,4 +930,5 @@ class MediaPlayerScreen : public BaseScreen, public UncachedScreen {
       static void onRedraw(draw_mode_t);
       static void onIdle();
   };
-#endif
\ No newline at end of file
+
+#endif // TOUCH_UI_COCOA_PRESS