diff --git a/Marlin/src/inc/Conditionals_LCD.h b/Marlin/src/inc/Conditionals_LCD.h index 2d088ed30bcb..0e1e65c87f17 100644 --- a/Marlin/src/inc/Conditionals_LCD.h +++ b/Marlin/src/inc/Conditionals_LCD.h @@ -288,7 +288,11 @@ #endif #ifndef STD_ENCODER_PULSES_PER_STEP - #define STD_ENCODER_PULSES_PER_STEP 5 + #if ENABLED(TOUCH_BUTTONS) + #define STD_ENCODER_PULSES_PER_STEP 1 + #else + #define STD_ENCODER_PULSES_PER_STEP 5 + #endif #endif #ifndef STD_ENCODER_STEPS_PER_MENU_ITEM #define STD_ENCODER_STEPS_PER_MENU_ITEM 1 diff --git a/Marlin/src/lcd/HD44780/ultralcd_HD44780.cpp b/Marlin/src/lcd/HD44780/ultralcd_HD44780.cpp index a8cf421dcb8d..b7ebc111a5e6 100644 --- a/Marlin/src/lcd/HD44780/ultralcd_HD44780.cpp +++ b/Marlin/src/lcd/HD44780/ultralcd_HD44780.cpp @@ -371,8 +371,8 @@ bool MarlinUI::detected() { #if HAS_SLOW_BUTTONS uint8_t MarlinUI::read_slow_buttons() { #if ENABLED(LCD_I2C_TYPE_MCP23017) - // Reading these buttons this is likely to be too slow to call inside interrupt context - // so they are called during normal lcd_update + // Reading these buttons is too slow for interrupt context + // so they are read during LCD update in the main loop. uint8_t slow_bits = lcd.readButtons() #if !BUTTON_EXISTS(ENC) << B_I2C_BTN_OFFSET @@ -381,7 +381,7 @@ bool MarlinUI::detected() { #if ENABLED(LCD_I2C_VIKI) if ((slow_bits & (B_MI | B_RI)) && PENDING(millis(), next_button_update_ms)) // LCD clicked slow_bits &= ~(B_MI | B_RI); // Disable LCD clicked buttons if screen is updated - #endif // LCD_I2C_VIKI + #endif return slow_bits; #endif // LCD_I2C_TYPE_MCP23017 } diff --git a/Marlin/src/lcd/dogm/u8g_dev_tft_320x240_upscale_from_128x64.cpp b/Marlin/src/lcd/dogm/u8g_dev_tft_320x240_upscale_from_128x64.cpp index 8451a10e0ef7..0081b077390f 100644 --- a/Marlin/src/lcd/dogm/u8g_dev_tft_320x240_upscale_from_128x64.cpp +++ b/Marlin/src/lcd/dogm/u8g_dev_tft_320x240_upscale_from_128x64.cpp @@ -267,51 +267,102 @@ static const uint8_t ili9341_init_sequence[] = { // 0x9341 - ILI9341 B01111111,B11111111,B11111111,B11111110, }; - static const uint8_t buttonA[] = { - B01111111,B11111111,B11111111,B11111110, - B10000000,B00000000,B00000000,B00000001, - B10000000,B00000000,B00000000,B00000001, - B10000000,B00000000,B00000000,B00000001, - B10000000,B00000000,B00000000,B00000001, - B10000000,B01000000,B00000000,B00000001, - B10000000,B11100000,B00000000,B00000001, - B10000001,B11110000,B00000000,B00000001, - B10000011,B11111000,B00000000,B00000001, - B10000111,B11111100,B00111111,B11100001, - B10000000,B11100000,B00111111,B11100001, - B10000000,B11100000,B00000000,B00000001, - B10000000,B11100000,B00000000,B00000001, - B10000000,B11100000,B00000000,B00000001, - B10000000,B11100000,B00000000,B00000001, - B10000000,B00000000,B00000000,B00000001, - B10000000,B00000000,B00000000,B00000001, - B10000000,B00000000,B00000000,B00000001, - B10000000,B00000000,B00000000,B00000001, - B01111111,B11111111,B11111111,B11111110, - }; + #if ENABLED(REVERSE_MENU_DIRECTION) + + static const uint8_t buttonA[] = { + B01111111,B11111111,B11111111,B11111110, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B11100000,B00000000,B00000001, + B10000000,B11100000,B00000000,B00000001, + B10000000,B11100000,B00000000,B00000001, + B10000000,B11100000,B00000000,B00000001, + B10000000,B11100000,B00111111,B11100001, + B10000111,B11111100,B00111111,B11100001, + B10000011,B11111000,B00000000,B00000001, + B10000001,B11110000,B00000000,B00000001, + B10000000,B11100000,B00000000,B00000001, + B10000000,B01000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B01111111,B11111111,B11111111,B11111110, + }; + static const uint8_t buttonB[] = { + B01111111,B11111111,B11111111,B11111110, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B01100000,B00000010,B00000001, + B10000000,B01100000,B00000111,B00000001, + B10000000,B01100000,B00001111,B10000001, + B10000000,B01100000,B00011111,B11000001, + B10000111,B11111110,B00111111,B11100001, + B10000111,B11111110,B00000111,B00000001, + B10000000,B01100000,B00000111,B00000001, + B10000000,B01100000,B00000111,B00000001, + B10000000,B01100000,B00000111,B00000001, + B10000000,B01100000,B00000111,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B01111111,B11111111,B11111111,B11111110, + }; - static const uint8_t buttonB[] = { - B01111111,B11111111,B11111111,B11111110, - B10000000,B00000000,B00000000,B00000001, - B10000000,B00000000,B00000000,B00000001, - B10000000,B00000000,B00000000,B00000001, - B10000000,B00000000,B00000000,B00000001, - B10000000,B01100000,B00000111,B00000001, - B10000000,B01100000,B00000111,B00000001, - B10000000,B01100000,B00000111,B00000001, - B10000000,B01100000,B00000111,B00000001, - B10000111,B11111110,B00000111,B00000001, - B10000111,B11111110,B00111111,B11100001, - B10000000,B01100000,B00011111,B11000001, - B10000000,B01100000,B00001111,B10000001, - B10000000,B01100000,B00000111,B00000001, - B10000000,B01100000,B00000010,B00000001, - B10000000,B00000000,B00000000,B00000001, - B10000000,B00000000,B00000000,B00000001, - B10000000,B00000000,B00000000,B00000001, - B10000000,B00000000,B00000000,B00000001, - B01111111,B11111111,B11111111,B11111110, - }; + #else + + static const uint8_t buttonA[] = { + B01111111,B11111111,B11111111,B11111110, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B01000000,B00000000,B00000001, + B10000000,B11100000,B00000000,B00000001, + B10000001,B11110000,B00000000,B00000001, + B10000011,B11111000,B00000000,B00000001, + B10000111,B11111100,B00111111,B11100001, + B10000000,B11100000,B00111111,B11100001, + B10000000,B11100000,B00000000,B00000001, + B10000000,B11100000,B00000000,B00000001, + B10000000,B11100000,B00000000,B00000001, + B10000000,B11100000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B01111111,B11111111,B11111111,B11111110, + }; + + static const uint8_t buttonB[] = { + B01111111,B11111111,B11111111,B11111110, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B01100000,B00000111,B00000001, + B10000000,B01100000,B00000111,B00000001, + B10000000,B01100000,B00000111,B00000001, + B10000000,B01100000,B00000111,B00000001, + B10000111,B11111110,B00000111,B00000001, + B10000111,B11111110,B00111111,B11100001, + B10000000,B01100000,B00011111,B11000001, + B10000000,B01100000,B00001111,B10000001, + B10000000,B01100000,B00000111,B00000001, + B10000000,B01100000,B00000010,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B10000000,B00000000,B00000000,B00000001, + B01111111,B11111111,B11111111,B11111110, + }; + + #endif static const uint8_t buttonC[] = { B01111111,B11111111,B11111111,B11111110, @@ -369,11 +420,8 @@ static const uint8_t ili9341_init_sequence[] = { // 0x9341 - ILI9341 // Used to fill RGB565 (16bits) background inline void memset2(const void *ptr, uint16_t fill, size_t cnt) { - uint16_t* wptr = (uint16_t*) ptr; - for (size_t i = 0; i < cnt; i += 2) { - *wptr = fill; - wptr++; - } + uint16_t* wptr = (uint16_t*)ptr; + for (size_t i = 0; i < cnt; i += 2) { *wptr = fill; wptr++; } } static bool preinit = true; diff --git a/Marlin/src/lcd/ultralcd.cpp b/Marlin/src/lcd/ultralcd.cpp index 5228292b7020..ba2de995e428 100644 --- a/Marlin/src/lcd/ultralcd.cpp +++ b/Marlin/src/lcd/ultralcd.cpp @@ -116,8 +116,6 @@ #endif #if ENABLED(TOUCH_BUTTONS) #include "../feature/touch/xpt2046.h" - volatile uint8_t MarlinUI::touch_buttons; - uint8_t MarlinUI::read_touch_buttons() { return touch.read_buttons(); } #endif #endif @@ -135,7 +133,7 @@ uint8_t MarlinUI::lcd_status_update_delay = 1; // First update one loop delayed millis_t MarlinUI::next_filament_display; // = 0 #endif -millis_t next_button_update_ms; +millis_t MarlinUI::next_button_update_ms; // = 0 #if HAS_GRAPHICAL_LCD bool MarlinUI::drawing_screen, MarlinUI::first_page; // = false @@ -345,9 +343,6 @@ void MarlinUI::init() { #if HAS_SLOW_BUTTONS slow_buttons = 0; #endif - #if ENABLED(TOUCH_BUTTONS) - touch_buttons = 0; - #endif #endif update_buttons(); @@ -746,16 +741,19 @@ void MarlinUI::update() { static millis_t next_lcd_update_ms; millis_t ms = millis(); + #if HAS_LCD_MENU && LCD_TIMEOUT_TO_STATUS + static millis_t return_to_status_ms = 0; + #define RESET_STATUS_TIMEOUT() (return_to_status_ms = ms + LCD_TIMEOUT_TO_STATUS) + #else + #define RESET_STATUS_TIMEOUT() NOOP + #endif + #ifdef LED_BACKLIGHT_TIMEOUT leds.update_timeout(powersupply_on); #endif #if HAS_LCD_MENU - #if LCD_TIMEOUT_TO_STATUS - static millis_t return_to_status_ms = 0; - #endif - // Handle any queued Move Axis motion manage_manual_move(); @@ -764,54 +762,67 @@ void MarlinUI::update() { update_buttons(); // If the action button is pressed... - static bool wait_for_unclick; // = 0 - auto generate_click = [&]() { - if (!wait_for_unclick) { // If not waiting for a debounce release: - wait_for_unclick = true; // - Set debounce flag to ignore continous clicks - lcd_clicked = !wait_for_user && !no_reentry; // - Keep the click if not waiting for a user-click - wait_for_user = false; // - Any click clears wait for user - quick_feedback(); // - Always make a click sound - } - }; + static bool wait_for_unclick; // = false #if ENABLED(TOUCH_BUTTONS) - if (touch_buttons) { - if (buttons & EN_C) - generate_click(); - else if (buttons & (EN_A | EN_B)) { // Ignore the encoder if clicked, to prevent "slippage" - const millis_t ms = millis(); - if (ELAPSED(ms, next_button_update_ms)) { - next_button_update_ms = ms + 50; - encoderDiff = (ENCODER_STEPS_PER_MENU_ITEM) * (ENCODER_PULSES_PER_STEP); - if (buttons & EN_A) encoderDiff *= -1; - if (!wait_for_unclick) { - next_button_update_ms += 250; + + #define TOUCH_MENU_MASK 0x80 + + static bool arrow_pressed; // = false + + // Handle touch events which are slow to read + if (ELAPSED(ms, next_button_update_ms)) { + uint8_t touch_buttons = touch.read_buttons(); + if (touch_buttons) { + RESET_STATUS_TIMEOUT(); + if (touch_buttons & TOUCH_MENU_MASK) { // Processing Menu Area touch? + if (!wait_for_unclick) { // If not waiting for a debounce release: + wait_for_unclick = true; // - Set debounce flag to ignore continous clicks + wait_for_user = false; // - Any click clears wait for user + // TODO for next PR. + //uint8_t tpos = touch_buttons & ~(TOUCH_MENU_MASK); // Safe 7bit touched screen coordinate + next_button_update_ms = ms + 500; // Defer next check for 1/2 second + #if HAS_LCD_MENU + refresh(); + #endif + } + touch_buttons = 0; // Swallow the touch + } + buttons |= (touch_buttons & (EN_C | EN_D)); // Pass on Click and Back buttons + if (touch_buttons & (EN_A | EN_B)) { // A and/or B button? + encoderDiff = (ENCODER_STEPS_PER_MENU_ITEM) * (ENCODER_PULSES_PER_STEP) * encoderDirection; + if (touch_buttons & EN_A) encoderDiff *= -1; + next_button_update_ms = ms + 50; // Assume the repeat delay + if (!wait_for_unclick && !arrow_pressed) { // On click prepare for repeat + next_button_update_ms += 250; // Longer delay on first press + arrow_pressed = true; // Mark arrow as pressed #if HAS_BUZZER buzz(LCD_FEEDBACK_FREQUENCY_DURATION_MS, LCD_FEEDBACK_FREQUENCY_HZ); #endif - wait_for_unclick = true; // - Set debounce flag to ignore continous clicks } } } + if (!(touch_buttons & (EN_A | EN_B))) arrow_pressed = false; } - else + #endif // TOUCH_BUTTONS - { - // - // Integrated LCD click handling via button_pressed() - // - if (!external_control && button_pressed()) - generate_click(); - else - wait_for_unclick = false; - } - #if HAS_DIGITAL_BUTTONS && (BUTTON_EXISTS(BACK) || ENABLED(TOUCH_BUTTONS)) - if (LCD_BACK_CLICKED()) { - quick_feedback(); - goto_previous_screen(); + // Integrated LCD click handling via button_pressed + if (!external_control && button_pressed()) { + if (!wait_for_unclick) { // If not waiting for a debounce release: + wait_for_unclick = true; // - Set debounce flag to ignore continous clicks + lcd_clicked = !wait_for_user && !no_reentry; // - Keep the click if not waiting for a user-click + wait_for_user = false; // - Any click clears wait for user + quick_feedback(); // - Always make a click sound } - #endif + } + else + wait_for_unclick = false; + + if (LCD_BACK_CLICKED()) { + quick_feedback(); + goto_previous_screen(); + } #endif // HAS_LCD_MENU @@ -885,23 +896,8 @@ void MarlinUI::update() { slow_buttons = read_slow_buttons(); // Buttons that take too long to read in interrupt context #endif - #if ENABLED(TOUCH_BUTTONS) - touch_buttons = read_touch_buttons(); - if (touch_buttons) { - #if HAS_LCD_MENU && LCD_TIMEOUT_TO_STATUS - return_to_status_ms = ms + LCD_TIMEOUT_TO_STATUS; - #endif - } - #endif - #if ENABLED(REPRAPWORLD_KEYPAD) - - if (handle_keypad()) { - #if HAS_LCD_MENU && LCD_TIMEOUT_TO_STATUS - return_to_status_ms = ms + LCD_TIMEOUT_TO_STATUS; - #endif - } - + if (handle_keypad()) RESET_STATUS_TIMEOUT(); #endif const float abs_diff = ABS(encoderDiff); @@ -947,9 +943,7 @@ void MarlinUI::update() { encoderDiff = 0; } - #if HAS_LCD_MENU && LCD_TIMEOUT_TO_STATUS - return_to_status_ms = ms + LCD_TIMEOUT_TO_STATUS; - #endif + RESET_STATUS_TIMEOUT(); refresh(LCDVIEW_REDRAW_NOW); @@ -982,9 +976,7 @@ void MarlinUI::update() { lcd_status_update_delay = 12; } refresh(LCDVIEW_REDRAW_NOW); - #if LCD_TIMEOUT_TO_STATUS - return_to_status_ms = ms + LCD_TIMEOUT_TO_STATUS; - #endif + RESET_STATUS_TIMEOUT(); } #endif @@ -1058,7 +1050,7 @@ void MarlinUI::update() { #if HAS_LCD_MENU && LCD_TIMEOUT_TO_STATUS // Return to Status Screen after a timeout if (on_status_screen() || defer_return_to_status) - return_to_status_ms = ms + LCD_TIMEOUT_TO_STATUS; + RESET_STATUS_TIMEOUT(); else if (ELAPSED(ms, return_to_status_ms)) return_to_status(); #endif @@ -1241,12 +1233,12 @@ void MarlinUI::update() { #if HAS_SLOW_BUTTONS | slow_buttons #endif - #if ENABLED(TOUCH_BUTTONS) - | touch_buttons - #endif ; + #elif HAS_ADC_BUTTONS + buttons = 0; + #endif #if HAS_ADC_BUTTONS diff --git a/Marlin/src/lcd/ultralcd.h b/Marlin/src/lcd/ultralcd.h index 26e9261bd528..973fbc451e92 100644 --- a/Marlin/src/lcd/ultralcd.h +++ b/Marlin/src/lcd/ultralcd.h @@ -306,6 +306,8 @@ class MarlinUI { #if HAS_SPI_LCD + static millis_t next_button_update_ms; + static bool detected(); static LCDViewAction lcdDrawUpdate; @@ -531,10 +533,6 @@ class MarlinUI { static volatile uint8_t slow_buttons; static uint8_t read_slow_buttons(); #endif - #if ENABLED(TOUCH_BUTTONS) - static volatile uint8_t touch_buttons; - static uint8_t read_touch_buttons(); - #endif static void update_buttons(); static inline bool button_pressed() { return BUTTON_CLICK(); }