Extend M106/M107 for better laser module support (#16082)
Co-authored-by: Scott Lahteine <thinkyhead@users.noreply.github.com>
This commit is contained in:
		| @@ -28,6 +28,10 @@ | ||||
| #include "../../module/motion.h" | ||||
| #include "../../module/temperature.h" | ||||
|  | ||||
| #if ENABLED(LASER_SYNCHRONOUS_M106_M107) | ||||
|   #include "../../module/planner.h" | ||||
| #endif | ||||
|  | ||||
| #if PREHEAT_COUNT | ||||
|   #include "../../lcd/marlinui.h" | ||||
| #endif | ||||
| @@ -82,6 +86,8 @@ void GcodeSuite::M106() { | ||||
|     // Set speed, with constraint | ||||
|     thermalManager.set_fan_speed(pfan, speed); | ||||
|  | ||||
|     TERN_(LASER_SYNCHRONOUS_M106_M107, planner.buffer_sync_block(BLOCK_FLAG_SYNC_FANS)); | ||||
|  | ||||
|     if (TERN0(DUAL_X_CARRIAGE, idex_is_duplicating()))  // pfan == 0 when duplicating | ||||
|       thermalManager.set_fan_speed(1 - pfan, speed); | ||||
|   } | ||||
| @@ -92,12 +98,14 @@ void GcodeSuite::M106() { | ||||
|  */ | ||||
| void GcodeSuite::M107() { | ||||
|   const uint8_t pfan = parser.byteval('P', _ALT_P); | ||||
|   if (pfan < _CNT_P) { | ||||
|     thermalManager.set_fan_speed(pfan, 0); | ||||
|   if (pfan >= _CNT_P) return; | ||||
|  | ||||
|     if (TERN0(DUAL_X_CARRIAGE, idex_is_duplicating()))  // pfan == 0 when duplicating | ||||
|       thermalManager.set_fan_speed(1 - pfan, 0); | ||||
|   } | ||||
|   thermalManager.set_fan_speed(pfan, 0); | ||||
|  | ||||
|   if (TERN0(DUAL_X_CARRIAGE, idex_is_duplicating()))  // pfan == 0 when duplicating | ||||
|     thermalManager.set_fan_speed(1 - pfan, 0); | ||||
|  | ||||
|   TERN_(LASER_SYNCHRONOUS_M106_M107, planner.buffer_sync_block(BLOCK_FLAG_SYNC_FANS)); | ||||
| } | ||||
|  | ||||
| #endif // HAS_FAN | ||||
|   | ||||
| @@ -1217,6 +1217,17 @@ static_assert(Y_MAX_LENGTH >= Y_BED_SIZE, "Movement bounds (Y_MIN_POS, Y_MAX_POS | ||||
|   #error "To use BED_LIMIT_SWITCHING you must disable PIDTEMPBED." | ||||
| #endif | ||||
|  | ||||
| /** | ||||
|  * Synchronous M106/M107 checks | ||||
|  */ | ||||
| #if ENABLED(LASER_SYNCHRONOUS_M106_M107) | ||||
|   #if FAN_KICKSTART_TIME | ||||
|     #error "FAN_KICKSTART_TIME must be 0 with LASER_SYNCHRONOUS_M106_M107 (because the laser will always come on at FULL power)." | ||||
|   #elif FAN_MIN_PWM | ||||
|     #error "FAN_MIN_PWM must be 0 with LASER_SYNCHRONOUS_M106_M107 (otherwise the laser will never turn OFF)." | ||||
|   #endif | ||||
| #endif | ||||
|  | ||||
| /** | ||||
|  * Chamber Heating Options - PID vs Limit Switching | ||||
|  */ | ||||
|   | ||||
| @@ -760,7 +760,7 @@ void MarlinUI::draw_status_screen() { | ||||
|     #endif | ||||
|   #endif // HAS_HEATED_BED | ||||
|  | ||||
|   #if FAN_COUNT > 0 | ||||
|   #if HAS_FAN | ||||
|     uint16_t spd = thermalManager.fan_speed[0]; | ||||
|  | ||||
|     #if ENABLED(ADAPTIVE_FAN_SLOWING) | ||||
| @@ -783,7 +783,7 @@ void MarlinUI::draw_status_screen() { | ||||
|     else | ||||
|       picBits &= ~ICON_FAN; | ||||
|  | ||||
|   #endif // FAN_COUNT > 0 | ||||
|   #endif // HAS_FAN | ||||
|  | ||||
|   // | ||||
|   // Line 9, 10 - icons | ||||
|   | ||||
| @@ -2152,7 +2152,7 @@ void HMI_SelectFile() { | ||||
|  | ||||
|       card.openAndPrintFile(card.filename); | ||||
|  | ||||
|       #if FAN_COUNT > 0 | ||||
|       #if HAS_FAN | ||||
|         // All fans on for Ender 3 v2 ? | ||||
|         // The slicer should manage this for us. | ||||
|         //for (uint8_t i = 0; i < FAN_COUNT; i++) | ||||
|   | ||||
| @@ -22,6 +22,8 @@ | ||||
|  | ||||
| #include "../inc/MarlinConfig.h" | ||||
|  | ||||
| #include "../MarlinCore.h" // for printingIsPaused | ||||
|  | ||||
| #ifdef LED_BACKLIGHT_TIMEOUT | ||||
|   #include "../feature/leds/leds.h" | ||||
| #endif | ||||
| @@ -39,21 +41,21 @@ | ||||
| MarlinUI ui; | ||||
|  | ||||
| #if HAS_DISPLAY | ||||
|   #include "../module/printcounter.h" | ||||
|   #include "../MarlinCore.h" | ||||
|   #include "../gcode/queue.h" | ||||
|   #include "fontutils.h" | ||||
|   #include "../sd/cardreader.h" | ||||
| #endif | ||||
|  | ||||
| #if ENABLED(DWIN_CREALITY_LCD) | ||||
|   #include "../module/printcounter.h" | ||||
|   #include "../MarlinCore.h" | ||||
|   #include "dwin/e3v2/dwin.h" | ||||
| #endif | ||||
|  | ||||
| #if HAS_STATUS_MESSAGE | ||||
|   #define START_OF_UTF8_CHAR(C) (((C) & 0xC0u) != 0x80U) | ||||
| #if ENABLED(LCD_PROGRESS_BAR) && !IS_TFTGLCD_PANEL | ||||
|   #define BASIC_PROGRESS_BAR 1 | ||||
| #endif | ||||
|  | ||||
| #if ANY(HAS_DISPLAY, HAS_STATUS_MESSAGE, BASIC_PROGRESS_BAR) | ||||
|   #include "../module/printcounter.h" | ||||
| #endif | ||||
|  | ||||
| #if LCD_HAS_WAIT_FOR_MOVE | ||||
| @@ -535,7 +537,7 @@ bool MarlinUI::get_blink() { | ||||
|  * This is very display-dependent, so the lcd implementation draws this. | ||||
|  */ | ||||
|  | ||||
| #if ENABLED(LCD_PROGRESS_BAR) && !IS_TFTGLCD_PANEL | ||||
| #if BASIC_PROGRESS_BAR | ||||
|   millis_t MarlinUI::progress_bar_ms; // = 0 | ||||
|   #if PROGRESS_MSG_EXPIRE > 0 | ||||
|     millis_t MarlinUI::expire_status_ms; // = 0 | ||||
| @@ -546,7 +548,7 @@ void MarlinUI::status_screen() { | ||||
|  | ||||
|   TERN_(HAS_LCD_MENU, ENCODER_RATE_MULTIPLY(false)); | ||||
|  | ||||
|   #if ENABLED(LCD_PROGRESS_BAR) && !IS_TFTGLCD_PANEL | ||||
|   #if BASIC_PROGRESS_BAR | ||||
|  | ||||
|     // | ||||
|     // HD44780 implements the following message blinking and | ||||
| @@ -586,7 +588,7 @@ void MarlinUI::status_screen() { | ||||
|  | ||||
|     #endif // PROGRESS_MSG_EXPIRE | ||||
|  | ||||
|   #endif // LCD_PROGRESS_BAR | ||||
|   #endif // BASIC_PROGRESS_BAR | ||||
|  | ||||
|   #if HAS_LCD_MENU | ||||
|     if (use_click()) { | ||||
| @@ -1353,6 +1355,7 @@ void MarlinUI::update() { | ||||
|   /** | ||||
|    * Reset the status message | ||||
|    */ | ||||
|  | ||||
|   void MarlinUI::reset_status(const bool no_welcome) { | ||||
|     #if SERVICE_INTERVAL_1 > 0 | ||||
|       static PGMSTR(service1, "> " SERVICE_NAME_1 "!"); | ||||
| @@ -1438,9 +1441,9 @@ void MarlinUI::update() { | ||||
|  | ||||
|   void MarlinUI::finish_status(const bool persist) { | ||||
|  | ||||
|     #if HAS_SPI_LCD | ||||
|     #if HAS_WIRED_LCD | ||||
|  | ||||
|       #if !(ENABLED(LCD_PROGRESS_BAR) && (PROGRESS_MSG_EXPIRE) > 0) | ||||
|       #if !(BASIC_PROGRESS_BAR && (PROGRESS_MSG_EXPIRE) > 0) | ||||
|         UNUSED(persist); | ||||
|       #endif | ||||
|  | ||||
| @@ -1448,7 +1451,7 @@ void MarlinUI::update() { | ||||
|         const millis_t ms = millis(); | ||||
|       #endif | ||||
|  | ||||
|       #if ENABLED(LCD_PROGRESS_BAR) | ||||
|       #if BASIC_PROGRESS_BAR | ||||
|         progress_bar_ms = ms; | ||||
|         #if PROGRESS_MSG_EXPIRE > 0 | ||||
|           expire_status_ms = persist ? 0 : ms + PROGRESS_MSG_EXPIRE; | ||||
| @@ -1462,7 +1465,7 @@ void MarlinUI::update() { | ||||
|       #if ENABLED(STATUS_MESSAGE_SCROLLING) | ||||
|         status_scroll_offset = 0; | ||||
|       #endif | ||||
|     #else // HAS_SPI_LCD | ||||
|     #else // HAS_WIRED_LCD | ||||
|       UNUSED(persist); | ||||
|     #endif | ||||
|  | ||||
|   | ||||
| @@ -56,6 +56,8 @@ | ||||
|   #include "../module/motion.h" // for active_extruder | ||||
| #endif | ||||
|  | ||||
| #define START_OF_UTF8_CHAR(C) (((C) & 0xC0u) != 0x80U) | ||||
|  | ||||
| #if HAS_WIRED_LCD | ||||
|  | ||||
|   enum LCDViewAction : uint8_t { | ||||
|   | ||||
| @@ -1015,8 +1015,8 @@ void Planner::reverse_pass() { | ||||
|     // Perform the reverse pass | ||||
|     block_t *current = &block_buffer[block_index]; | ||||
|  | ||||
|     // Only consider non sync and page blocks | ||||
|     if (!TEST(current->flag, BLOCK_BIT_SYNC_POSITION) && !IS_PAGE(current)) { | ||||
|     // Only consider non sync-and-page blocks | ||||
|     if (!(current->flag & BLOCK_MASK_SYNC) && !IS_PAGE(current)) { | ||||
|       reverse_pass_kernel(current, next); | ||||
|       next = current; | ||||
|     } | ||||
| @@ -1111,7 +1111,7 @@ void Planner::forward_pass() { | ||||
|     block = &block_buffer[block_index]; | ||||
|  | ||||
|     // Skip SYNC and page blocks | ||||
|     if (!TEST(block->flag, BLOCK_BIT_SYNC_POSITION) && !IS_PAGE(block)) { | ||||
|     if (!(block->flag & BLOCK_MASK_SYNC) && !IS_PAGE(block)) { | ||||
|       // If there's no previous block or the previous block is not | ||||
|       // BUSY (thus, modifiable) run the forward_pass_kernel. Otherwise, | ||||
|       // the previous block became BUSY, so assume the current block's | ||||
| @@ -1147,7 +1147,7 @@ void Planner::recalculate_trapezoids() { | ||||
|     block_t *prev = &block_buffer[prev_index]; | ||||
|  | ||||
|     // If not dealing with a sync block, we are done. The last block is not a SYNC block | ||||
|     if (!TEST(prev->flag, BLOCK_BIT_SYNC_POSITION)) break; | ||||
|     if (!(prev->flag & BLOCK_MASK_SYNC)) break; | ||||
|  | ||||
|     // Examine the previous block. This and all following are SYNC blocks | ||||
|     head_block_index = prev_index; | ||||
| @@ -1161,7 +1161,7 @@ void Planner::recalculate_trapezoids() { | ||||
|     next = &block_buffer[block_index]; | ||||
|  | ||||
|     // Skip sync and page blocks | ||||
|     if (!TEST(next->flag, BLOCK_BIT_SYNC_POSITION) && !IS_PAGE(next)) { | ||||
|     if (!(next->flag & BLOCK_MASK_SYNC) && !IS_PAGE(next)) { | ||||
|       next_entry_speed = SQRT(next->entry_speed_sqr); | ||||
|  | ||||
|       if (block) { | ||||
| @@ -1248,6 +1248,63 @@ void Planner::recalculate() { | ||||
|   recalculate_trapezoids(); | ||||
| } | ||||
|  | ||||
| #if HAS_FAN && DISABLED(LASER_SYNCHRONOUS_M106_M107) | ||||
|   #define HAS_TAIL_FAN_SPEED 1 | ||||
| #endif | ||||
|  | ||||
| /** | ||||
|  * Apply fan speeds | ||||
|  */ | ||||
| #if HAS_FAN | ||||
|  | ||||
|   void Planner::sync_fan_speeds(uint8_t (&fan_speed)[FAN_COUNT]) { | ||||
|  | ||||
|     #if FAN_MIN_PWM != 0 || FAN_MAX_PWM != 255 | ||||
|       #define CALC_FAN_SPEED(f) (fan_speed[f] ? map(fan_speed[f], 1, 255, FAN_MIN_PWM, FAN_MAX_PWM) : FAN_OFF_PWM) | ||||
|     #else | ||||
|       #define CALC_FAN_SPEED(f) (fan_speed[f] ?: FAN_OFF_PWM) | ||||
|     #endif | ||||
|  | ||||
|     #if ENABLED(FAN_SOFT_PWM) | ||||
|       #define _FAN_SET(F) thermalManager.soft_pwm_amount_fan[F] = CALC_FAN_SPEED(F); | ||||
|     #elif ENABLED(FAST_PWM_FAN) | ||||
|       #define _FAN_SET(F) set_pwm_duty(FAN##F##_PIN, CALC_FAN_SPEED(F)); | ||||
|     #else | ||||
|       #define _FAN_SET(F) analogWrite(pin_t(FAN##F##_PIN), CALC_FAN_SPEED(F)); | ||||
|     #endif | ||||
|     #define FAN_SET(F) do{ kickstart_fan(fan_speed, ms, F); _FAN_SET(F); }while(0) | ||||
|  | ||||
|     const millis_t ms = millis(); | ||||
|     TERN_(HAS_FAN0, FAN_SET(0)); | ||||
|     TERN_(HAS_FAN1, FAN_SET(1)); | ||||
|     TERN_(HAS_FAN2, FAN_SET(2)); | ||||
|     TERN_(HAS_FAN3, FAN_SET(3)); | ||||
|     TERN_(HAS_FAN4, FAN_SET(4)); | ||||
|     TERN_(HAS_FAN5, FAN_SET(5)); | ||||
|     TERN_(HAS_FAN6, FAN_SET(6)); | ||||
|     TERN_(HAS_FAN7, FAN_SET(7)); | ||||
|   } | ||||
|  | ||||
|   #if FAN_KICKSTART_TIME | ||||
|  | ||||
|     void Planner::kickstart_fan(uint8_t (&fan_speed)[FAN_COUNT], const millis_t &ms, const uint8_t f) { | ||||
|       static millis_t fan_kick_end[FAN_COUNT] = { 0 }; | ||||
|       if (fan_speed[f]) { | ||||
|         if (fan_kick_end[f] == 0) { | ||||
|           fan_kick_end[f] = ms + FAN_KICKSTART_TIME; | ||||
|           fan_speed[f] = 255; | ||||
|         } | ||||
|         else if (PENDING(ms, fan_kick_end[f])) | ||||
|           fan_speed[f] = 255; | ||||
|       } | ||||
|       else | ||||
|         fan_kick_end[f] = 0; | ||||
|     } | ||||
|  | ||||
|   #endif | ||||
|  | ||||
| #endif // HAS_FAN | ||||
|  | ||||
| /** | ||||
|  * Maintain fans, paste extruder pressure, | ||||
|  */ | ||||
| @@ -1257,7 +1314,7 @@ void Planner::check_axes_activity() { | ||||
|     xyze_bool_t axis_active = { false }; | ||||
|   #endif | ||||
|  | ||||
|   #if HAS_FAN | ||||
|   #if HAS_TAIL_FAN_SPEED | ||||
|     uint8_t tail_fan_speed[FAN_COUNT]; | ||||
|   #endif | ||||
|  | ||||
| @@ -1272,13 +1329,12 @@ void Planner::check_axes_activity() { | ||||
|  | ||||
|   if (has_blocks_queued()) { | ||||
|  | ||||
|     #if HAS_FAN || ENABLED(BARICUDA) | ||||
|     #if EITHER(HAS_TAIL_FAN_SPEED, BARICUDA) | ||||
|       block_t *block = &block_buffer[block_buffer_tail]; | ||||
|     #endif | ||||
|  | ||||
|     #if HAS_FAN | ||||
|       FANS_LOOP(i) | ||||
|         tail_fan_speed[i] = thermalManager.scaledFanSpeed(i, block->fan_speed[i]); | ||||
|     #if HAS_TAIL_FAN_SPEED | ||||
|       FANS_LOOP(i) tail_fan_speed[i] = thermalManager.scaledFanSpeed(i, block->fan_speed[i]); | ||||
|     #endif | ||||
|  | ||||
|     #if ENABLED(BARICUDA) | ||||
| @@ -1300,9 +1356,8 @@ void Planner::check_axes_activity() { | ||||
|  | ||||
|     TERN_(HAS_CUTTER, cutter.refresh()); | ||||
|  | ||||
|     #if HAS_FAN | ||||
|       FANS_LOOP(i) | ||||
|         tail_fan_speed[i] = thermalManager.scaledFanSpeed(i); | ||||
|     #if HAS_TAIL_FAN_SPEED | ||||
|       FANS_LOOP(i) tail_fan_speed[i] = thermalManager.scaledFanSpeed(i); | ||||
|     #endif | ||||
|  | ||||
|     #if ENABLED(BARICUDA) | ||||
| @@ -1321,48 +1376,11 @@ void Planner::check_axes_activity() { | ||||
|  | ||||
|   // | ||||
|   // Update Fan speeds | ||||
|   // Only if synchronous M106/M107 is disabled | ||||
|   // | ||||
|   #if HAS_FAN | ||||
|  | ||||
|     #if FAN_KICKSTART_TIME > 0 | ||||
|       static millis_t fan_kick_end[FAN_COUNT] = { 0 }; | ||||
|       #define KICKSTART_FAN(f)                         \ | ||||
|         if (tail_fan_speed[f]) {                       \ | ||||
|           millis_t ms = millis();                      \ | ||||
|           if (fan_kick_end[f] == 0) {                  \ | ||||
|             fan_kick_end[f] = ms + FAN_KICKSTART_TIME; \ | ||||
|             tail_fan_speed[f] = 255;                   \ | ||||
|           } else if (PENDING(ms, fan_kick_end[f]))     \ | ||||
|             tail_fan_speed[f] = 255;                   \ | ||||
|         } else fan_kick_end[f] = 0 | ||||
|     #else | ||||
|       #define KICKSTART_FAN(f) NOOP | ||||
|     #endif | ||||
|  | ||||
|     #if FAN_MIN_PWM != 0 || FAN_MAX_PWM != 255 | ||||
|       #define CALC_FAN_SPEED(f) (tail_fan_speed[f] ? map(tail_fan_speed[f], 1, 255, FAN_MIN_PWM, FAN_MAX_PWM) : FAN_OFF_PWM) | ||||
|     #else | ||||
|       #define CALC_FAN_SPEED(f) (tail_fan_speed[f] ?: FAN_OFF_PWM) | ||||
|     #endif | ||||
|  | ||||
|     #if ENABLED(FAN_SOFT_PWM) | ||||
|       #define _FAN_SET(F) thermalManager.soft_pwm_amount_fan[F] = CALC_FAN_SPEED(F); | ||||
|     #elif ENABLED(FAST_PWM_FAN) | ||||
|       #define _FAN_SET(F) set_pwm_duty(FAN##F##_PIN, CALC_FAN_SPEED(F)); | ||||
|     #else | ||||
|       #define _FAN_SET(F) analogWrite(pin_t(FAN##F##_PIN), CALC_FAN_SPEED(F)); | ||||
|     #endif | ||||
|     #define FAN_SET(F) do{ KICKSTART_FAN(F); _FAN_SET(F); }while(0) | ||||
|  | ||||
|     TERN_(HAS_FAN0, FAN_SET(0)); | ||||
|     TERN_(HAS_FAN1, FAN_SET(1)); | ||||
|     TERN_(HAS_FAN2, FAN_SET(2)); | ||||
|     TERN_(HAS_FAN3, FAN_SET(3)); | ||||
|     TERN_(HAS_FAN4, FAN_SET(4)); | ||||
|     TERN_(HAS_FAN5, FAN_SET(5)); | ||||
|     TERN_(HAS_FAN6, FAN_SET(6)); | ||||
|     TERN_(HAS_FAN7, FAN_SET(7)); | ||||
|   #endif // HAS_FAN | ||||
|   #if HAS_TAIL_FAN_SPEED | ||||
|     sync_fan_speeds(tail_fan_speed); | ||||
|   #endif | ||||
|  | ||||
|   TERN_(AUTOTEMP, getHighESpeed()); | ||||
|  | ||||
| @@ -2675,9 +2693,14 @@ bool Planner::_populate_block(block_t * const block, bool split_move, | ||||
|  | ||||
| /** | ||||
|  * Planner::buffer_sync_block | ||||
|  * Add a block to the buffer that just updates the position | ||||
|  * Add a block to the buffer that just updates the position, | ||||
|  * or in case of LASER_SYNCHRONOUS_M106_M107 the fan PWM | ||||
|  */ | ||||
| void Planner::buffer_sync_block() { | ||||
| void Planner::buffer_sync_block(TERN_(LASER_SYNCHRONOUS_M106_M107, uint8_t sync_flag)) { | ||||
|   #if DISABLED(LASER_SYNCHRONOUS_M106_M107) | ||||
|     constexpr uint8_t sync_flag = BLOCK_FLAG_SYNC_POSITION; | ||||
|   #endif | ||||
|  | ||||
|   // Wait for the next available block | ||||
|   uint8_t next_buffer_head; | ||||
|   block_t * const block = get_next_free_block(next_buffer_head); | ||||
| @@ -2685,10 +2708,14 @@ void Planner::buffer_sync_block() { | ||||
|   // Clear block | ||||
|   memset(block, 0, sizeof(block_t)); | ||||
|  | ||||
|   block->flag = BLOCK_FLAG_SYNC_POSITION; | ||||
|   block->flag = sync_flag; | ||||
|  | ||||
|   block->position = position; | ||||
|  | ||||
|   #if BOTH(HAS_FAN, LASER_SYNCHRONOUS_M106_M107) | ||||
|     FANS_LOOP(i) block->fan_speed[i] = thermalManager.fan_speed[i]; | ||||
|   #endif | ||||
|  | ||||
|   // If this is the first added movement, reload the delay, otherwise, cancel it. | ||||
|   if (block_buffer_head == block_buffer_tail) { | ||||
|     // If it was the first queued block, restart the 1st block delivery delay, to | ||||
| @@ -2876,7 +2903,7 @@ bool Planner::buffer_line(const float &rx, const float &ry, const float &rz, con | ||||
|  | ||||
|     block->flag = BLOCK_FLAG_IS_PAGE; | ||||
|  | ||||
|     #if FAN_COUNT > 0 | ||||
|     #if HAS_FAN | ||||
|       FANS_LOOP(i) block->fan_speed[i] = thermalManager.fan_speed[i]; | ||||
|     #endif | ||||
|  | ||||
|   | ||||
| @@ -102,6 +102,11 @@ enum BlockFlagBit : char { | ||||
|   #if ENABLED(DIRECT_STEPPING) | ||||
|     , BLOCK_BIT_IS_PAGE | ||||
|   #endif | ||||
|  | ||||
|   // Sync the fan speeds from the block | ||||
|   #if ENABLED(LASER_SYNCHRONOUS_M106_M107) | ||||
|     , BLOCK_BIT_SYNC_FANS | ||||
|   #endif | ||||
| }; | ||||
|  | ||||
| enum BlockFlag : char { | ||||
| @@ -112,8 +117,13 @@ enum BlockFlag : char { | ||||
|   #if ENABLED(DIRECT_STEPPING) | ||||
|     , BLOCK_FLAG_IS_PAGE            = _BV(BLOCK_BIT_IS_PAGE) | ||||
|   #endif | ||||
|   #if ENABLED(LASER_SYNCHRONOUS_M106_M107) | ||||
|     , BLOCK_FLAG_SYNC_FANS          = _BV(BLOCK_BIT_SYNC_FANS) | ||||
|   #endif | ||||
| }; | ||||
|  | ||||
| #define BLOCK_MASK_SYNC ( BLOCK_FLAG_SYNC_POSITION | TERN0(LASER_SYNCHRONOUS_M106_M107, BLOCK_FLAG_SYNC_FANS) ) | ||||
|  | ||||
| #if ENABLED(LASER_POWER_INLINE) | ||||
|  | ||||
|   typedef struct { | ||||
| @@ -499,6 +509,16 @@ class Planner { | ||||
|     // Manage fans, paste pressure, etc. | ||||
|     static void check_axes_activity(); | ||||
|  | ||||
|     // Apply fan speeds | ||||
|     #if HAS_FAN | ||||
|       static void sync_fan_speeds(uint8_t (&fan_speed)[FAN_COUNT]); | ||||
|       #if FAN_KICKSTART_TIME | ||||
|         static void kickstart_fan(uint8_t (&fan_speed)[FAN_COUNT], const millis_t &ms, const uint8_t f); | ||||
|       #else | ||||
|         FORCE_INLINE static void kickstart_fan(uint8_t (&)[FAN_COUNT], const millis_t &, const uint8_t) {} | ||||
|       #endif | ||||
|     #endif | ||||
|  | ||||
|     #if ENABLED(FILAMENT_WIDTH_SENSOR) | ||||
|       void apply_filament_width_sensor(const int8_t encoded_ratio); | ||||
|  | ||||
| @@ -721,9 +741,12 @@ class Planner { | ||||
|  | ||||
|     /** | ||||
|      * Planner::buffer_sync_block | ||||
|      * Add a block to the buffer that just updates the position | ||||
|      * Add a block to the buffer that just updates the position or in | ||||
|      * case of LASER_SYNCHRONOUS_M106_M107 the fan pwm | ||||
|      */ | ||||
|     static void buffer_sync_block(); | ||||
|     static void buffer_sync_block( | ||||
|       TERN_(LASER_SYNCHRONOUS_M106_M107, uint8_t sync_flag=BLOCK_FLAG_SYNC_POSITION) | ||||
|     ); | ||||
|  | ||||
|   #if IS_KINEMATIC | ||||
|     private: | ||||
|   | ||||
| @@ -1988,9 +1988,18 @@ uint32_t Stepper::block_phase_isr() { | ||||
|     // Anything in the buffer? | ||||
|     if ((current_block = planner.get_current_block())) { | ||||
|  | ||||
|       // Sync block? Sync the stepper counts and return | ||||
|       while (TEST(current_block->flag, BLOCK_BIT_SYNC_POSITION)) { | ||||
|         _set_position(current_block->position); | ||||
|       // Sync block? Sync the stepper counts or fan speeds and return | ||||
|       while (current_block->flag & BLOCK_MASK_SYNC) { | ||||
|  | ||||
|         #if ENABLED(LASER_SYNCHRONOUS_M106_M107) | ||||
|           const bool is_sync_fans = TEST(current_block->flag, BLOCK_BIT_SYNC_FANS); | ||||
|           if (is_sync_fans) planner.sync_fan_speeds(current_block->fan_speed); | ||||
|         #else | ||||
|           constexpr bool is_sync_fans = false; | ||||
|         #endif | ||||
|  | ||||
|         if (!is_sync_fans) _set_position(current_block->position); | ||||
|  | ||||
|         discard_current_block(); | ||||
|  | ||||
|         // Try to get a new block | ||||
|   | ||||
| @@ -197,7 +197,7 @@ | ||||
| #endif | ||||
|  | ||||
| #if HAS_SERVOS | ||||
|   #include "./servo.h" | ||||
|   #include "servo.h" | ||||
| #endif | ||||
|  | ||||
| #if ANY(TEMP_SENSOR_0_IS_THERMISTOR, TEMP_SENSOR_1_IS_THERMISTOR, TEMP_SENSOR_2_IS_THERMISTOR, TEMP_SENSOR_3_IS_THERMISTOR, \ | ||||
|   | ||||
| @@ -322,7 +322,8 @@ | ||||
|  | ||||
|   #define TFT_BUFFER_SIZE                  14400 | ||||
|  | ||||
| #elif HAS_SPI_LCD | ||||
| #elif HAS_WIRED_LCD | ||||
|  | ||||
|   #define BEEPER_PIN                        PC5 | ||||
|   #define BTN_ENC                           PE13 | ||||
|   #define LCD_PINS_ENABLE                   PD13 | ||||
| @@ -358,4 +359,5 @@ | ||||
|     #define BOARD_ST7920_DELAY_3    DELAY_NS(600) | ||||
|  | ||||
|   #endif // !MKS_MINI_12864 | ||||
| #endif // HAS_SPI_LCD | ||||
|  | ||||
| #endif // HAS_WIRED_LCD | ||||
|   | ||||
| @@ -327,7 +327,8 @@ | ||||
|   //#define TFT_DRIVER                    ST7796 | ||||
|   #define TFT_BUFFER_SIZE                  14400 | ||||
|  | ||||
| #elif HAS_SPI_LCD | ||||
| #elif HAS_WIRED_LCD | ||||
|  | ||||
|   #define BEEPER_PIN                        PC5 | ||||
|   #define BTN_ENC                           PE13 | ||||
|   #define LCD_PINS_ENABLE                   PD13 | ||||
| @@ -369,4 +370,5 @@ | ||||
|     #endif | ||||
|  | ||||
|   #endif // !MKS_MINI_12864 | ||||
| #endif // HAS_SPI_LCD | ||||
|  | ||||
| #endif // HAS_WIRED_LCD | ||||
|   | ||||
		Reference in New Issue
	
	Block a user