Browse Source

Followup for I2C_POSITION_ENCODERS

Scott Lahteine 7 years ago
parent
commit
fc140c4962
7 changed files with 352 additions and 321 deletions
  1. 1
    1
      .travis.yml
  2. 1
    0
      Marlin/Configuration_adv.h
  3. 224
    196
      Marlin/I2CPositionEncoder.cpp
  4. 119
    116
      Marlin/I2CPositionEncoder.h
  5. 2
    2
      Marlin/Marlin_main.cpp
  6. 1
    3
      Marlin/SanityCheck.h
  7. 4
    3
      Marlin/ubl_G29.cpp

+ 1
- 1
.travis.yml View File

@@ -93,7 +93,7 @@ script:
93 93
   #
94 94
   - restore_configs
95 95
   - opt_enable AUTO_BED_LEVELING_UBL UBL_G26_MESH_EDITING ENABLE_LEVELING_FADE_HEIGHT FIX_MOUNTED_PROBE EEPROM_SETTINGS G3D_PANEL
96
-  - opt_enable_adv CUSTOM_USER_MENUS
96
+  - opt_enable_adv CUSTOM_USER_MENUS I2C_POSITION_ENCODERS BABYSTEPPING
97 97
   - build_marlin
98 98
   #
99 99
   # Test a Sled Z Probe

+ 1
- 0
Marlin/Configuration_adv.h View File

@@ -1271,6 +1271,7 @@
1271 1271
 //===========================================================================
1272 1272
 //====================== I2C Position Encoder Settings ======================
1273 1273
 //===========================================================================
1274
+
1274 1275
 /**
1275 1276
  *  I2C position encoders for closed loop control.
1276 1277
  *  Developed by Chris Barr at Aus3D.

+ 224
- 196
Marlin/I2CPositionEncoder.cpp View File

@@ -40,13 +40,14 @@
40 40
 
41 41
   #include <Wire.h>
42 42
 
43
-  void I2CPositionEncoder::init(uint8_t address, AxisEnum axis) {
43
+
44
+  void I2CPositionEncoder::init(const uint8_t address, const AxisEnum axis) {
44 45
     encoderAxis = axis;
45 46
     i2cAddress = address;
46 47
 
47 48
     initialised++;
48 49
 
49
-    SERIAL_ECHOPAIR("Seetting up encoder on ", axis_codes[encoderAxis]);
50
+    SERIAL_ECHOPAIR("Setting up encoder on ", axis_codes[encoderAxis]);
50 51
     SERIAL_ECHOLNPAIR(" axis, addr = ", address);
51 52
 
52 53
     position = get_position();
@@ -98,13 +99,13 @@
98 99
 
99 100
           //the encoder likely lost its place when the error occured, so we'll reset and use the printer's
100 101
           //idea of where it the axis is to re-initialise
101
-          double position = stepper.get_axis_position_mm(encoderAxis);
102
-          long positionInTicks = position * get_ticks_unit();
102
+          float position = stepper.get_axis_position_mm(encoderAxis);
103
+          int32_t positionInTicks = position * get_ticks_unit();
103 104
 
104 105
           //shift position from previous to current position
105 106
           zeroOffset -= (positionInTicks - get_position());
106 107
 
107
-          #if defined(I2CPE_DEBUG)
108
+          #ifdef I2CPE_DEBUG
108 109
             SERIAL_ECHOPGM("Current position is ");
109 110
             SERIAL_ECHOLN(position);
110 111
 
@@ -126,23 +127,23 @@
126 127
     }
127 128
 
128 129
     lastPosition = position;
129
-    millis_t positionTime = millis();
130
+    const millis_t positionTime = millis();
130 131
 
131 132
     //only do error correction if setup and enabled
132 133
     if (ec && ecMethod != I2CPE_ECM_NONE) {
133 134
 
134
-      #if defined(I2CPE_EC_THRESH_PROPORTIONAL)
135
-        millis_t deltaTime = positionTime - lastPositionTime;
136
-        unsigned long distance = abs(position - lastPosition);
137
-        unsigned long speed = distance / deltaTime;
138
-        float threshold = constrain(speed / 50, 1, 50) * ecThreshold;
135
+      #ifdef I2CPE_EC_THRESH_PROPORTIONAL
136
+        const millis_t deltaTime = positionTime - lastPositionTime;
137
+        const uint32_t distance = abs(position - lastPosition),
138
+                       speed = distance / deltaTime;
139
+        const float threshold = constrain((speed / 50), 1, 50) * ecThreshold;
139 140
       #else
140
-        float threshold = get_error_correct_threshold();
141
+        const float threshold = get_error_correct_threshold();
141 142
       #endif
142 143
 
143 144
       //check error
144 145
       #if ENABLED(I2CPE_ERR_ROLLING_AVERAGE)
145
-        double sum = 0, diffSum = 0;
146
+        float sum = 0, diffSum = 0;
146 147
 
147 148
         errIdx = (errIdx >= I2CPE_ERR_ARRAY_SIZE - 1) ? 0 : errIdx + 1;
148 149
         err[errIdx] = get_axis_error_steps(false);
@@ -152,16 +153,16 @@
152 153
           if (i) diffSum += abs(err[i-1] - err[i]);
153 154
         }
154 155
 
155
-        long error = (long)(sum/(I2CPE_ERR_ARRAY_SIZE + 1)); //calculate average for error
156
+        const int32_t error = int32_t(sum / (I2CPE_ERR_ARRAY_SIZE + 1)); //calculate average for error
156 157
 
157 158
       #else
158
-        long error = get_axis_error_steps(false);
159
+        const int32_t error = get_axis_error_steps(false);
159 160
       #endif
160 161
 
161
-      //SERIAL_ECHOPGM("Axis err*r steps: ");
162
+      //SERIAL_ECHOPGM("Axis error steps: ");
162 163
       //SERIAL_ECHOLN(error);
163 164
 
164
-      #if defined(I2CPE_ERR_THRESH_ABORT)
165
+      #ifdef I2CPE_ERR_THRESH_ABORT
165 166
         if (labs(error) > I2CPE_ERR_THRESH_ABORT * planner.axis_steps_per_mm[encoderAxis]) {
166 167
           //kill("Significant Error");
167 168
           SERIAL_ECHOPGM("Axis error greater than set threshold, aborting!");
@@ -215,7 +216,7 @@
215 216
       homed++;
216 217
       trusted++;
217 218
 
218
-      #if defined(I2CPE_DEBUG)
219
+      #ifdef I2CPE_DEBUG
219 220
         SERIAL_ECHO(axis_codes[encoderAxis]);
220 221
         SERIAL_ECHOPAIR(" axis encoder homed, offset of ", zeroOffset);
221 222
         SERIAL_ECHOLNPGM(" ticks.");
@@ -223,36 +224,27 @@
223 224
     }
224 225
   }
225 226
 
226
-  bool I2CPositionEncoder::passes_test(bool report) {
227
-    if (H == I2CPE_MAG_SIG_GOOD) {
228
-      if (report) {
229
-        SERIAL_ECHO(axis_codes[encoderAxis]);
230
-        SERIAL_ECHOLNPGM(" axis encoder passes test; field strength good.");
231
-      }
232
-      return true;
233
-    } else if (H == I2CPE_MAG_SIG_MID) {
234
-      if (report) {
235
-        SERIAL_ECHOPAIR("Warning, ", axis_codes[encoderAxis]);
236
-        SERIAL_ECHOLNPGM(" axis encoder passes test; field strength fair.");
237
-      }
238
-      return true;
239
-    } else if (H == I2CPE_MAG_SIG_BAD) {
240
-      if (report) {
241
-        SERIAL_ECHOPAIR("Warning, ", axis_codes[encoderAxis]);
242
-        SERIAL_ECHOLNPGM(" axis magnetic strip not detected!");
243
-      }
244
-      return false;
245
-    }
246
-
227
+  bool I2CPositionEncoder::passes_test(const bool report) {
247 228
     if (report) {
248
-      SERIAL_ECHOPAIR("Warning, ", axis_codes[encoderAxis]);
249
-      SERIAL_ECHOLNPGM(" axis encoder not detected!");
229
+      if (H != I2CPE_MAG_SIG_GOOD) SERIAL_ECHOPGM("Warning. ");
230
+      SERIAL_ECHO(axis_codes[encoderAxis]);
231
+      SERIAL_ECHOPGM(" axis ");
232
+      serialprintPGM(H == I2CPE_MAG_SIG_BAD ? PSTR("magnetic strip ") : PSTR("encoder "));
233
+      switch (H) {
234
+        case I2CPE_MAG_SIG_GOOD:
235
+        case I2CPE_MAG_SIG_MID:
236
+          SERIAL_ECHOLNPGM("passes test; field strength ");
237
+          serialprintPGM(H == I2CPE_MAG_SIG_GOOD ? PSTR("good.\n") : PSTR("fair.\n"));
238
+          break;
239
+        default:
240
+          SERIAL_ECHOLNPGM("not detected!");
241
+      }
250 242
     }
251
-    return false;
243
+    return (H == I2CPE_MAG_SIG_GOOD || H == I2CPE_MAG_SIG_MID);
252 244
   }
253 245
 
254
-  double I2CPositionEncoder::get_axis_error_mm(bool report) {
255
-    double target, actual, error;
246
+  float I2CPositionEncoder::get_axis_error_mm(const bool report) {
247
+    float target, actual, error;
256 248
 
257 249
     target = stepper.get_axis_position_mm(encoderAxis);
258 250
     actual = mm_from_count(position);
@@ -270,7 +262,7 @@
270 262
     return error;
271 263
   }
272 264
 
273
-  long I2CPositionEncoder::get_axis_error_steps(bool report) {
265
+  int32_t I2CPositionEncoder::get_axis_error_steps(const bool report) {
274 266
     if (!active) {
275 267
       if (report) {
276 268
         SERIAL_ECHO(axis_codes[encoderAxis]);
@@ -280,8 +272,8 @@
280 272
     }
281 273
 
282 274
     float stepperTicksPerUnit;
283
-    long encoderTicks = position, encoderCountInStepperTicksScaled;
284
-    //long stepperTicks = stepper.position(encoderAxis);
275
+    int32_t encoderTicks = position, encoderCountInStepperTicksScaled;
276
+    //int32_t stepperTicks = stepper.position(encoderAxis);
285 277
 
286 278
     // With a rotary encoder we're concerned with ticks/rev; whereas with a linear we're concerned with ticks/mm
287 279
     stepperTicksPerUnit = (type == I2CPE_ENC_TYPE_ROTARY) ? stepperTicks : planner.axis_steps_per_mm[encoderAxis];
@@ -289,8 +281,8 @@
289 281
     //convert both 'ticks' into same units / base
290 282
     encoderCountInStepperTicksScaled = LROUND((stepperTicksPerUnit * encoderTicks) / encoderTicksPerUnit);
291 283
 
292
-    long target = stepper.position(encoderAxis),
293
-         error = (encoderCountInStepperTicksScaled - target);
284
+    int32_t target = stepper.position(encoderAxis),
285
+            error = (encoderCountInStepperTicksScaled - target);
294 286
 
295 287
     //suppress discontinuities (might be caused by bad I2C readings...?)
296 288
     bool suppressOutput = (labs(error - errorPrev) > 100);
@@ -309,7 +301,7 @@
309 301
     return (suppressOutput ? 0 : error);
310 302
   }
311 303
 
312
-  long I2CPositionEncoder::get_raw_count() {
304
+  int32_t I2CPositionEncoder::get_raw_count() {
313 305
     uint8_t index = 0;
314 306
     i2cLong encoderCount;
315 307
 
@@ -340,14 +332,11 @@
340 332
     //only works on XYZ cartesian machines for the time being
341 333
     if (!(encoderAxis == X_AXIS || encoderAxis == Y_AXIS || encoderAxis == Z_AXIS)) return false;
342 334
 
343
-    int feedrate;
344
-    float startPosition, endPosition;
345
-    float startCoord[NUM_AXIS] = {0}, endCoord[NUM_AXIS] = {0};
346
-
347
-    startPosition = soft_endstop_min[encoderAxis] + 10;
348
-    endPosition = soft_endstop_max[encoderAxis] - 10;
335
+    float startCoord[NUM_AXIS] = { 0 }, endCoord[NUM_AXIS] = { 0 };
349 336
 
350
-    feedrate = (int)MMM_TO_MMS((encoderAxis == Z_AXIS) ? HOMING_FEEDRATE_Z : HOMING_FEEDRATE_XY);
337
+    const float startPosition = soft_endstop_min[encoderAxis] + 10,
338
+                endPosition = soft_endstop_max[encoderAxis] - 10,
339
+                feedrate = FLOOR(MMM_TO_MMS((encoderAxis == Z_AXIS) ? HOMING_FEEDRATE_Z : HOMING_FEEDRATE_XY));
351 340
 
352 341
     ec = false;
353 342
 
@@ -367,7 +356,7 @@
367 356
 
368 357
     // if the module isn't currently trusted, wait until it is (or until it should be if things are working)
369 358
     if (!trusted) {
370
-      long startWaitingTime = millis();
359
+      int32_t startWaitingTime = millis();
371 360
       while (!trusted && millis() - startWaitingTime < I2CPE_TIME_TRUSTED)
372 361
         safe_delay(500);
373 362
     }
@@ -381,7 +370,7 @@
381 370
     return trusted;
382 371
   }
383 372
 
384
-  void I2CPositionEncoder::calibrate_steps_mm(int iter) {
373
+  void I2CPositionEncoder::calibrate_steps_mm(const uint8_t iter) {
385 374
     if (type != I2CPE_ENC_TYPE_LINEAR) {
386 375
       SERIAL_ECHOLNPGM("Steps per mm calibration is only available using linear encoders.");
387 376
       return;
@@ -392,14 +381,14 @@
392 381
       return;
393 382
     }
394 383
 
395
-    float oldStepsMm, newStepsMm,
384
+    float old_steps_mm, new_steps_mm,
396 385
           startDistance, endDistance,
397 386
           travelDistance, travelledDistance, total = 0,
398
-          startCoord[NUM_AXIS] = {0}, endCoord[NUM_AXIS] = {0};
387
+          startCoord[NUM_AXIS] = { 0 }, endCoord[NUM_AXIS] = { 0 };
399 388
 
400
-    double feedrate;
389
+    float feedrate;
401 390
 
402
-    long startCount, stopCount;
391
+    int32_t startCount, stopCount;
403 392
 
404 393
     feedrate = MMM_TO_MMS((encoderAxis == Z_AXIS) ? HOMING_FEEDRATE_Z : HOMING_FEEDRATE_XY);
405 394
 
@@ -447,17 +436,17 @@
447 436
       SERIAL_ECHOLNPGM("mm.");
448 437
 
449 438
       //Calculate new axis steps per unit
450
-      oldStepsMm = planner.axis_steps_per_mm[encoderAxis];
451
-      newStepsMm = (oldStepsMm * travelDistance) / travelledDistance;
439
+      old_steps_mm = planner.axis_steps_per_mm[encoderAxis];
440
+      new_steps_mm = (old_steps_mm * travelDistance) / travelledDistance;
452 441
 
453
-      SERIAL_ECHOLNPAIR("Old steps per mm: ", oldStepsMm);
454
-      SERIAL_ECHOLNPAIR("New steps per mm: ", newStepsMm);
442
+      SERIAL_ECHOLNPAIR("Old steps per mm: ", old_steps_mm);
443
+      SERIAL_ECHOLNPAIR("New steps per mm: ", new_steps_mm);
455 444
 
456 445
       //Save new value
457
-      planner.axis_steps_per_mm[encoderAxis] = newStepsMm;
446
+      planner.axis_steps_per_mm[encoderAxis] = new_steps_mm;
458 447
 
459 448
       if (iter > 1) {
460
-        total += newStepsMm;
449
+        total += new_steps_mm;
461 450
 
462 451
         // swap start and end points so next loop runs from current position
463 452
         float tempCoord = startCoord[encoderAxis];
@@ -486,6 +475,12 @@
486 475
     #endif
487 476
   }
488 477
 
478
+
479
+  bool I2CPositionEncodersMgr::I2CPE_anyaxis;
480
+  uint8_t I2CPositionEncodersMgr::I2CPE_addr,
481
+          I2CPositionEncodersMgr::I2CPE_idx;
482
+  I2CPositionEncoder I2CPositionEncodersMgr::encoders[I2CPE_ENCODER_CNT];
483
+
489 484
   void I2CPositionEncodersMgr::init() {
490 485
     Wire.begin();
491 486
 
@@ -494,28 +489,28 @@
494 489
 
495 490
       encoders[i].init(I2CPE_ENC_1_ADDR, I2CPE_ENC_1_AXIS);
496 491
 
497
-      #if defined(I2CPE_ENC_1_TYPE)
492
+      #ifdef I2CPE_ENC_1_TYPE
498 493
         encoders[i].set_type(I2CPE_ENC_1_TYPE);
499 494
       #endif
500
-      #if defined(I2CPE_ENC_1_TICKS_UNIT)
495
+      #ifdef I2CPE_ENC_1_TICKS_UNIT
501 496
         encoders[i].set_ticks_unit(I2CPE_ENC_1_TICKS_UNIT);
502 497
       #endif
503
-      #if defined(I2CPE_ENC_1_TICKS_REV)
498
+      #ifdef I2CPE_ENC_1_TICKS_REV
504 499
         encoders[i].set_stepper_ticks(I2CPE_ENC_1_TICKS_REV);
505 500
       #endif
506
-      #if defined(I2CPE_ENC_1_INVERT)
501
+      #ifdef I2CPE_ENC_1_INVERT
507 502
         encoders[i].set_inverted(I2CPE_ENC_1_INVERT);
508 503
       #endif
509
-      #if defined(I2CPE_ENC_1_EC_METHOD)
504
+      #ifdef I2CPE_ENC_1_EC_METHOD
510 505
         encoders[i].set_ec_method(I2CPE_ENC_1_EC_METHOD);
511 506
       #endif
512
-      #if defined(I2CPE_ENC_1_EC_THRESH)
507
+      #ifdef I2CPE_ENC_1_EC_THRESH
513 508
         encoders[i].set_ec_threshold(I2CPE_ENC_1_EC_THRESH);
514 509
       #endif
515 510
 
516 511
       encoders[i].set_active(encoders[i].passes_test(true));
517 512
 
518
-      #if (I2CPE_ENC_1_AXIS == E_AXIS)
513
+      #if I2CPE_ENC_1_AXIS == E_AXIS
519 514
         encoders[i].set_homed();
520 515
       #endif
521 516
     #endif
@@ -525,28 +520,28 @@
525 520
 
526 521
       encoders[i].init(I2CPE_ENC_2_ADDR, I2CPE_ENC_2_AXIS);
527 522
 
528
-      #if defined(I2CPE_ENC_2_TYPE)
523
+      #ifdef I2CPE_ENC_2_TYPE
529 524
         encoders[i].set_type(I2CPE_ENC_2_TYPE);
530 525
       #endif
531
-      #if defined(I2CPE_ENC_2_TICKS_UNIT)
526
+      #ifdef I2CPE_ENC_2_TICKS_UNIT
532 527
         encoders[i].set_ticks_unit(I2CPE_ENC_2_TICKS_UNIT);
533 528
       #endif
534
-      #if defined(I2CPE_ENC_2_TICKS_REV)
529
+      #ifdef I2CPE_ENC_2_TICKS_REV
535 530
         encoders[i].set_stepper_ticks(I2CPE_ENC_2_TICKS_REV);
536 531
       #endif
537
-      #if defined(I2CPE_ENC_2_INVERT)
532
+      #ifdef I2CPE_ENC_2_INVERT
538 533
         encoders[i].set_inverted(I2CPE_ENC_2_INVERT);
539 534
       #endif
540
-      #if defined(I2CPE_ENC_2_EC_METHOD)
535
+      #ifdef I2CPE_ENC_2_EC_METHOD
541 536
         encoders[i].set_ec_method(I2CPE_ENC_2_EC_METHOD);
542 537
       #endif
543
-      #if defined(I2CPE_ENC_2_EC_THRESH)
538
+      #ifdef I2CPE_ENC_2_EC_THRESH
544 539
         encoders[i].set_ec_threshold(I2CPE_ENC_2_EC_THRESH);
545 540
       #endif
546 541
 
547 542
       encoders[i].set_active(encoders[i].passes_test(true));
548 543
 
549
-      #if (I2CPE_ENC_2_AXIS == E_AXIS)
544
+      #if I2CPE_ENC_2_AXIS == E_AXIS
550 545
         encoders[i].set_homed();
551 546
       #endif
552 547
     #endif
@@ -556,28 +551,28 @@
556 551
 
557 552
       encoders[i].init(I2CPE_ENC_3_ADDR, I2CPE_ENC_3_AXIS);
558 553
 
559
-      #if defined(I2CPE_ENC_3_TYPE)
554
+      #ifdef I2CPE_ENC_3_TYPE
560 555
         encoders[i].set_type(I2CPE_ENC_3_TYPE);
561 556
       #endif
562
-      #if defined(I2CPE_ENC_3_TICKS_UNIT)
557
+      #ifdef I2CPE_ENC_3_TICKS_UNIT
563 558
         encoders[i].set_ticks_unit(I2CPE_ENC_3_TICKS_UNIT);
564 559
       #endif
565
-      #if defined(I2CPE_ENC_3_TICKS_REV)
560
+      #ifdef I2CPE_ENC_3_TICKS_REV
566 561
         encoders[i].set_stepper_ticks(I2CPE_ENC_3_TICKS_REV);
567 562
       #endif
568
-      #if defined(I2CPE_ENC_3_INVERT)
563
+      #ifdef I2CPE_ENC_3_INVERT
569 564
         encoders[i].set_inverted(I2CPE_ENC_3_INVERT);
570 565
       #endif
571
-      #if defined(I2CPE_ENC_3_EC_METHOD)
566
+      #ifdef I2CPE_ENC_3_EC_METHOD
572 567
         encoders[i].set_ec_method(I2CPE_ENC_3_EC_METHOD);
573 568
       #endif
574
-      #if defined(I2CPE_ENC_3_EC_THRESH)
569
+      #ifdef I2CPE_ENC_3_EC_THRESH
575 570
         encoders[i].set_ec_threshold(I2CPE_ENC_3_EC_THRESH);
576 571
       #endif
577 572
 
578 573
     encoders[i].set_active(encoders[i].passes_test(true));
579 574
 
580
-      #if (I2CPE_ENC_3_AXIS == E_AXIS)
575
+      #if I2CPE_ENC_3_AXIS == E_AXIS
581 576
         encoders[i].set_homed();
582 577
       #endif
583 578
     #endif
@@ -587,28 +582,28 @@
587 582
 
588 583
       encoders[i].init(I2CPE_ENC_4_ADDR, I2CPE_ENC_4_AXIS);
589 584
 
590
-      #if defined(I2CPE_ENC_4_TYPE)
585
+      #ifdef I2CPE_ENC_4_TYPE
591 586
         encoders[i].set_type(I2CPE_ENC_4_TYPE);
592 587
       #endif
593
-      #if defined(I2CPE_ENC_4_TICKS_UNIT)
588
+      #ifdef I2CPE_ENC_4_TICKS_UNIT
594 589
         encoders[i].set_ticks_unit(I2CPE_ENC_4_TICKS_UNIT);
595 590
       #endif
596
-      #if defined(I2CPE_ENC_4_TICKS_REV)
591
+      #ifdef I2CPE_ENC_4_TICKS_REV
597 592
         encoders[i].set_stepper_ticks(I2CPE_ENC_4_TICKS_REV);
598 593
       #endif
599
-      #if defined(I2CPE_ENC_4_INVERT)
594
+      #ifdef I2CPE_ENC_4_INVERT
600 595
         encoders[i].set_inverted(I2CPE_ENC_4_INVERT);
601 596
       #endif
602
-      #if defined(I2CPE_ENC_4_EC_METHOD)
597
+      #ifdef I2CPE_ENC_4_EC_METHOD
603 598
         encoders[i].set_ec_method(I2CPE_ENC_4_EC_METHOD);
604 599
       #endif
605
-      #if defined(I2CPE_ENC_4_EC_THRESH)
600
+      #ifdef I2CPE_ENC_4_EC_THRESH
606 601
         encoders[i].set_ec_threshold(I2CPE_ENC_4_EC_THRESH);
607 602
       #endif
608 603
 
609 604
       encoders[i].set_active(encoders[i].passes_test(true));
610 605
 
611
-      #if (I2CPE_ENC_4_AXIS == E_AXIS)
606
+      #if I2CPE_ENC_4_AXIS == E_AXIS
612 607
         encoders[i].set_homed();
613 608
       #endif
614 609
     #endif
@@ -618,56 +613,57 @@
618 613
 
619 614
       encoders[i].init(I2CPE_ENC_5_ADDR, I2CPE_ENC_5_AXIS);
620 615
 
621
-      #if defined(I2CPE_ENC_5_TYPE)
616
+      #ifdef I2CPE_ENC_5_TYPE
622 617
         encoders[i].set_type(I2CPE_ENC_5_TYPE);
623 618
       #endif
624
-      #if defined(I2CPE_ENC_5_TICKS_UNIT)
619
+      #ifdef I2CPE_ENC_5_TICKS_UNIT
625 620
         encoders[i].set_ticks_unit(I2CPE_ENC_5_TICKS_UNIT);
626 621
       #endif
627
-      #if defined(I2CPE_ENC_5_TICKS_REV)
622
+      #ifdef I2CPE_ENC_5_TICKS_REV
628 623
         encoders[i].set_stepper_ticks(I2CPE_ENC_5_TICKS_REV);
629 624
       #endif
630
-      #if defined(I2CPE_ENC_5_INVERT)
625
+      #ifdef I2CPE_ENC_5_INVERT
631 626
         encoders[i].set_inverted(I2CPE_ENC_5_INVERT);
632 627
       #endif
633
-      #if defined(I2CPE_ENC_5_EC_METHOD)
628
+      #ifdef I2CPE_ENC_5_EC_METHOD
634 629
         encoders[i].set_ec_method(I2CPE_ENC_5_EC_METHOD);
635 630
       #endif
636
-      #if defined(I2CPE_ENC_5_EC_THRESH)
631
+      #ifdef I2CPE_ENC_5_EC_THRESH
637 632
         encoders[i].set_ec_threshold(I2CPE_ENC_5_EC_THRESH);
638 633
       #endif
639 634
 
640 635
       encoders[i].set_active(encoders[i].passes_test(true));
641 636
 
642
-      #if (I2CPE_ENC_5_AXIS == E_AXIS)
637
+      #if I2CPE_ENC_5_AXIS == E_AXIS
643 638
         encoders[i].set_homed();
644 639
       #endif
645 640
     #endif
646
-
647 641
   }
648 642
 
649
-  void I2CPositionEncodersMgr::report_position(uint8_t idx, bool units, bool noOffset) {
650
-    CHECK_IDX
643
+  void I2CPositionEncodersMgr::report_position(const int8_t idx, const bool units, const bool noOffset) {
644
+    CHECK_IDX();
651 645
 
652
-    if (units) {
646
+    if (units)
653 647
       SERIAL_ECHOLN(noOffset ? encoders[idx].mm_from_count(encoders[idx].get_raw_count()) : encoders[idx].get_position_mm());
654
-    } else {
648
+    else {
655 649
       if (noOffset) {
656
-        long raw_count = encoders[idx].get_raw_count();
650
+        const int32_t raw_count = encoders[idx].get_raw_count();
657 651
         SERIAL_ECHO(axis_codes[encoders[idx].get_axis()]);
658
-        SERIAL_ECHOPGM(" ");
652
+        SERIAL_CHAR(' ');
659 653
 
660 654
         for (uint8_t j = 31; j > 0; j--)
661 655
           SERIAL_ECHO((bool)(0x00000001 & (raw_count >> j)));
662 656
 
663
-        SERIAL_ECHO((bool)(0x00000001 & (raw_count)));
664
-        SERIAL_ECHOLNPAIR(" ", raw_count);
665
-      } else
657
+        SERIAL_ECHO((bool)(0x00000001 & raw_count));
658
+        SERIAL_CHAR(' ');
659
+        SERIAL_ECHOLN(raw_count);
660
+      }
661
+      else
666 662
         SERIAL_ECHOLN(encoders[idx].get_position());
667 663
     }
668 664
   }
669 665
 
670
-  void I2CPositionEncodersMgr::change_module_address(uint8_t oldaddr, uint8_t newaddr) {
666
+  void I2CPositionEncodersMgr::change_module_address(const uint8_t oldaddr, const uint8_t newaddr) {
671 667
     // First check 'new' address is not in use
672 668
     Wire.beginTransmission(newaddr);
673 669
     if (!Wire.endTransmission()) {
@@ -709,7 +705,7 @@
709 705
 
710 706
     // Now, if this module is configured, find which encoder instance it's supposed to correspond to
711 707
     // and enable it (it will likely have failed initialisation on power-up, before the address change).
712
-    int8_t idx = idx_from_addr(newaddr);
708
+    const int8_t idx = idx_from_addr(newaddr);
713 709
     if (idx >= 0 && !encoders[idx].get_active()) {
714 710
       SERIAL_ECHO(axis_codes[encoders[idx].get_axis()]);
715 711
       SERIAL_ECHOLNPGM(" axis encoder was not detected on printer startup. Trying again.");
@@ -717,7 +713,7 @@
717 713
     }
718 714
   }
719 715
 
720
-  void I2CPositionEncodersMgr::report_module_firmware(uint8_t address) {
716
+  void I2CPositionEncodersMgr::report_module_firmware(const uint8_t address) {
721 717
     // First check there is a module
722 718
     Wire.beginTransmission(address);
723 719
     if (Wire.endTransmission()) {
@@ -727,7 +723,7 @@
727 723
     }
728 724
 
729 725
     SERIAL_ECHOPAIR("Requesting version info from module at address ", address);
730
-    SERIAL_ECHOPGM(":\n");
726
+    SERIAL_ECHOLNPGM(":");
731 727
 
732 728
     Wire.beginTransmission(address);
733 729
     Wire.write(I2CPE_SET_REPORT_MODE);
@@ -743,7 +739,7 @@
743 739
     }
744 740
 
745 741
     // Set module back to normal (distance) mode
746
-    Wire.beginTransmission((int)address);
742
+    Wire.beginTransmission(address);
747 743
     Wire.write(I2CPE_SET_REPORT_MODE);
748 744
     Wire.write(I2CPE_REPORT_DISTANCE);
749 745
     Wire.endTransmission();
@@ -753,43 +749,43 @@
753 749
     I2CPE_addr = 0;
754 750
 
755 751
     if (parser.seen('A')) {
752
+
756 753
       if (!parser.has_value()) {
757 754
         SERIAL_PROTOCOLLNPGM("?A seen, but no address specified! [30-200]");
758 755
         return I2CPE_PARSE_ERR;
759 756
       };
760 757
 
761 758
       I2CPE_addr = parser.value_byte();
762
-
763 759
       if (!WITHIN(I2CPE_addr, 30, 200)) { // reserve the first 30 and last 55
764 760
         SERIAL_PROTOCOLLNPGM("?Address out of range. [30-200]");
765 761
         return I2CPE_PARSE_ERR;
766 762
       }
767 763
 
768 764
       I2CPE_idx = idx_from_addr(I2CPE_addr);
769
-
770
-      if (!WITHIN(I2CPE_idx, 0, I2CPE_ENCODER_CNT - 1)) {
765
+      if (I2CPE_idx >= I2CPE_ENCODER_CNT) {
771 766
         SERIAL_PROTOCOLLNPGM("?No device with this address!");
772 767
         return I2CPE_PARSE_ERR;
773 768
       }
774
-    } else if (parser.seenval('I')) {
769
+    }
770
+    else if (parser.seenval('I')) {
771
+
775 772
       if (!parser.has_value()) {
776 773
         SERIAL_PROTOCOLLNPAIR("?I seen, but no index specified! [0-", I2CPE_ENCODER_CNT - 1);
777
-        SERIAL_ECHOLNPGM("]");
774
+        SERIAL_PROTOCOLLNPGM("]");
778 775
         return I2CPE_PARSE_ERR;
779 776
       };
780 777
 
781 778
       I2CPE_idx = parser.value_byte();
782
-
783
-      if (!WITHIN(I2CPE_idx, 0, I2CPE_ENCODER_CNT - 1)) {
779
+      if (I2CPE_idx >= I2CPE_ENCODER_CNT) {
784 780
         SERIAL_PROTOCOLLNPAIR("?Index out of range. [0-", I2CPE_ENCODER_CNT - 1);
785 781
         SERIAL_ECHOLNPGM("]");
786 782
         return I2CPE_PARSE_ERR;
787 783
       }
788 784
 
789 785
       I2CPE_addr = encoders[I2CPE_idx].get_address();
790
-    } else {
791
-      I2CPE_idx = -1;
792 786
     }
787
+    else
788
+      I2CPE_idx = 0xFF;
793 789
 
794 790
     I2CPE_anyaxis = parser.seen_axis();
795 791
 
@@ -814,15 +810,18 @@
814 810
   void I2CPositionEncodersMgr::M860() {
815 811
     if (parse()) return;
816 812
 
817
-    bool hasU = parser.seen('U'), hasO = parser.seen('O');
813
+    const bool hasU = parser.seen('U'), hasO = parser.seen('O');
818 814
 
819
-    if (I2CPE_idx < 0) {
820
-      int8_t idx;
815
+    if (I2CPE_idx == 0xFF) {
821 816
       LOOP_XYZE(i) {
822
-        if ((!I2CPE_anyaxis || parser.seen(axis_codes[i])) && ((idx = idx_from_axis(AxisEnum(i))) >= 0))
823
-          report_position((uint8_t)idx, hasU, hasO);
817
+        if (!I2CPE_anyaxis || parser.seen(axis_codes[i])) {
818
+          const uint8_t idx = idx_from_axis(AxisEnum(i));
819
+          if ((int8_t)idx >= 0) report_position(idx, hasU, hasO);
820
+        }
824 821
       }
825
-    } else report_position((uint8_t)I2CPE_idx, hasU, hasO);
822
+    }
823
+    else
824
+      report_position(I2CPE_idx, hasU, hasO);
826 825
   }
827 826
 
828 827
   /**
@@ -841,13 +840,16 @@
841 840
   void I2CPositionEncodersMgr::M861() {
842 841
     if (parse()) return;
843 842
 
844
-    if (I2CPE_idx < 0) {
845
-      int8_t idx;
843
+    if (I2CPE_idx == 0xFF) {
846 844
       LOOP_XYZE(i) {
847
-        if ((!I2CPE_anyaxis || parser.seen(axis_codes[i])) && ((idx = idx_from_axis(AxisEnum(i))) >= 0))
848
-          report_status((uint8_t)idx);
845
+        if (!I2CPE_anyaxis || parser.seen(axis_codes[i])) {
846
+          const uint8_t idx = idx_from_axis(AxisEnum(i));
847
+          if ((int8_t)idx >= 0) report_status(idx);
848
+        }
849 849
       }
850
-    } else report_status((uint8_t)I2CPE_idx);
850
+    }
851
+    else
852
+      report_status(I2CPE_idx);
851 853
   }
852 854
 
853 855
   /**
@@ -867,13 +869,16 @@
867 869
   void I2CPositionEncodersMgr::M862() {
868 870
     if (parse()) return;
869 871
 
870
-    if (I2CPE_idx < 0) {
871
-      int8_t idx;
872
+    if (I2CPE_idx == 0xFF) {
872 873
       LOOP_XYZE(i) {
873
-        if ((!I2CPE_anyaxis || parser.seen(axis_codes[i])) && ((idx = idx_from_axis(AxisEnum(i))) >= 0))
874
-          test_axis((uint8_t)idx);
874
+        if (!I2CPE_anyaxis || parser.seen(axis_codes[i])) {
875
+          const uint8_t idx = idx_from_axis(AxisEnum(i));
876
+          if ((int8_t)idx >= 0) test_axis(idx);
877
+        }
875 878
       }
876
-    } else test_axis((uint8_t)I2CPE_idx);
879
+    }
880
+    else
881
+      test_axis(I2CPE_idx);
877 882
   }
878 883
 
879 884
   /**
@@ -894,15 +899,18 @@
894 899
   void I2CPositionEncodersMgr::M863() {
895 900
     if (parse()) return;
896 901
 
897
-    int iterations = parser.seenval('P') ? constrain(parser.value_byte(), 1, 10) : 1;
902
+    const uint8_t iterations = constrain(parser.byteval('P', 1), 1, 10);
898 903
 
899
-    if (I2CPE_idx < 0) {
900
-      int8_t idx;
904
+    if (I2CPE_idx == 0xFF) {
901 905
       LOOP_XYZE(i) {
902
-        if ((!I2CPE_anyaxis || parser.seen(axis_codes[i])) && ((idx = idx_from_axis(AxisEnum(i))) >= 0))
903
-          calibrate_steps_mm((uint8_t)idx, iterations);
906
+        if (!I2CPE_anyaxis || parser.seen(axis_codes[i])) {
907
+          const uint8_t idx = idx_from_axis(AxisEnum(i));
908
+          if ((int8_t)idx >= 0) calibrate_steps_mm(idx, iterations);
909
+        }
904 910
       }
905
-    } else calibrate_steps_mm((uint8_t)I2CPE_idx, iterations);
911
+    }
912
+    else
913
+      calibrate_steps_mm(I2CPE_idx, iterations);
906 914
   }
907 915
 
908 916
   /**
@@ -910,9 +918,9 @@
910 918
    *
911 919
    *   A<addr>  Module current/old I2C address.  If not present,
912 920
    *            assumes default address (030).  [30, 200].
913
-   *   N<addr>  Module new I2C address. [30, 200].
921
+   *   S<addr>  Module new I2C address. [30, 200].
914 922
    *
915
-   *   If N not specified:
923
+   *   If S is not specified:
916 924
    *    X       Use I2CPE_PRESET_ADDR_X (030).
917 925
    *    Y       Use I2CPE_PRESET_ADDR_Y (031).
918 926
    *    Z       Use I2CPE_PRESET_ADDR_Z (032).
@@ -925,23 +933,24 @@
925 933
 
926 934
     if (!I2CPE_addr) I2CPE_addr = I2CPE_PRESET_ADDR_X;
927 935
 
928
-    if (parser.seen('N')) {
936
+    if (parser.seen('S')) {
929 937
       if (!parser.has_value()) {
930
-        SERIAL_PROTOCOLLNPGM("?N seen, but no address specified! [30-200]");
938
+        SERIAL_PROTOCOLLNPGM("?S seen, but no address specified! [30-200]");
931 939
         return;
932 940
       };
933 941
 
934 942
       newAddress = parser.value_byte();
935
-
936 943
       if (!WITHIN(newAddress, 30, 200)) {
937 944
         SERIAL_PROTOCOLLNPGM("?New address out of range. [30-200]");
938 945
         return;
939 946
       }
940
-    } else if (!I2CPE_anyaxis) {
941
-      SERIAL_PROTOCOLLNPGM("?You must specify N or [XYZE].");
947
+    }
948
+    else if (!I2CPE_anyaxis) {
949
+      SERIAL_PROTOCOLLNPGM("?You must specify S or [XYZE].");
942 950
       return;
943
-    } else {
944
-      if (parser.seen('X')) newAddress = I2CPE_PRESET_ADDR_X;
951
+    }
952
+    else {
953
+           if (parser.seen('X')) newAddress = I2CPE_PRESET_ADDR_X;
945 954
       else if (parser.seen('Y')) newAddress = I2CPE_PRESET_ADDR_Y;
946 955
       else if (parser.seen('Z')) newAddress = I2CPE_PRESET_ADDR_Z;
947 956
       else if (parser.seen('E')) newAddress = I2CPE_PRESET_ADDR_E;
@@ -970,12 +979,15 @@
970 979
     if (parse()) return;
971 980
 
972 981
     if (!I2CPE_addr) {
973
-      int8_t idx;
974 982
       LOOP_XYZE(i) {
975
-        if ((!I2CPE_anyaxis || parser.seen(axis_codes[i])) && ((idx = idx_from_axis(AxisEnum(i))) >= 0))
976
-          report_module_firmware(encoders[idx].get_address());
983
+        if (!I2CPE_anyaxis || parser.seen(axis_codes[i])) {
984
+          const uint8_t idx = idx_from_axis(AxisEnum(i));
985
+          if ((int8_t)idx >= 0) report_module_firmware(encoders[idx].get_address());
986
+        }
977 987
       }
978
-    } else report_module_firmware(I2CPE_addr);
988
+    }
989
+    else
990
+      report_module_firmware(I2CPE_addr);
979 991
   }
980 992
 
981 993
   /**
@@ -995,20 +1007,25 @@
995 1007
   void I2CPositionEncodersMgr::M866() {
996 1008
     if (parse()) return;
997 1009
 
998
-    bool hasR = parser.seen('R');
1010
+    const bool hasR = parser.seen('R');
999 1011
 
1000
-    if (I2CPE_idx < 0) {
1001
-      int8_t idx;
1012
+    if (I2CPE_idx == 0xFF) {
1002 1013
       LOOP_XYZE(i) {
1003
-        if ((!I2CPE_anyaxis || parser.seen(axis_codes[i])) && ((idx = idx_from_axis(AxisEnum(i))) >= 0)) {
1004
-          if (hasR) reset_error_count((uint8_t)idx, AxisEnum(i));
1005
-          else report_error_count((uint8_t)idx, AxisEnum(i));
1014
+        if (!I2CPE_anyaxis || parser.seen(axis_codes[i])) {
1015
+          const uint8_t idx = idx_from_axis(AxisEnum(i));
1016
+          if ((int8_t)idx >= 0) {
1017
+            if (hasR)
1018
+              reset_error_count(idx, AxisEnum(i));
1019
+            else
1020
+              report_error_count(idx, AxisEnum(i));
1021
+          }
1006 1022
         }
1007 1023
       }
1008
-    } else {
1009
-      if (hasR) reset_error_count((uint8_t)I2CPE_idx, encoders[I2CPE_idx].get_axis());
1010
-      else report_error_count((uint8_t)I2CPE_idx, encoders[I2CPE_idx].get_axis());
1011 1024
     }
1025
+    else if (hasR)
1026
+      reset_error_count(I2CPE_idx, encoders[I2CPE_idx].get_axis());
1027
+    else
1028
+      report_error_count(I2CPE_idx, encoders[I2CPE_idx].get_axis());
1012 1029
   }
1013 1030
 
1014 1031
   /**
@@ -1028,19 +1045,22 @@
1028 1045
   void I2CPositionEncodersMgr::M867() {
1029 1046
     if (parse()) return;
1030 1047
 
1031
-    int8_t onoff = parser.seenval('S') ? parser.value_int() : -1;
1048
+    const int8_t onoff = parser.seenval('S') ? parser.value_int() : -1;
1032 1049
 
1033
-    if (I2CPE_idx < 0) {
1034
-      int8_t idx;
1050
+    if (I2CPE_idx == 0xFF) {
1035 1051
       LOOP_XYZE(i) {
1036
-        if ((!I2CPE_anyaxis || parser.seen(axis_codes[i])) && ((idx = idx_from_axis(AxisEnum(i))) >= 0)) {
1037
-          if (onoff == -1) enable_ec((uint8_t)idx, !encoders[idx].get_ec_enabled(), AxisEnum(i));
1038
-          else enable_ec((uint8_t)idx, (bool)onoff, AxisEnum(i));
1052
+        if (!I2CPE_anyaxis || parser.seen(axis_codes[i])) {
1053
+          const uint8_t idx = idx_from_axis(AxisEnum(i));
1054
+          if ((int8_t)idx >= 0) {
1055
+            const bool ena = onoff == -1 ? !encoders[I2CPE_idx].get_ec_enabled() : !!onoff;
1056
+            enable_ec(idx, ena, AxisEnum(i));
1057
+          }
1039 1058
         }
1040 1059
       }
1041
-    } else {
1042
-      if (onoff == -1) enable_ec((uint8_t)I2CPE_idx, !encoders[I2CPE_idx].get_ec_enabled(), encoders[I2CPE_idx].get_axis());
1043
-      else enable_ec((uint8_t)I2CPE_idx, (bool)onoff, encoders[I2CPE_idx].get_axis());
1060
+    }
1061
+    else {
1062
+      const bool ena = onoff == -1 ? !encoders[I2CPE_idx].get_ec_enabled() : !!onoff;
1063
+      enable_ec(I2CPE_idx, ena, encoders[I2CPE_idx].get_axis());
1044 1064
     }
1045 1065
   }
1046 1066
 
@@ -1061,20 +1081,25 @@
1061 1081
   void I2CPositionEncodersMgr::M868() {
1062 1082
     if (parse()) return;
1063 1083
 
1064
-    float newThreshold = parser.seenval('T') ? parser.value_float() : -9999;
1084
+    const float newThreshold = parser.seenval('T') ? parser.value_float() : -9999;
1065 1085
 
1066
-    if (I2CPE_idx < 0) {
1067
-      int8_t idx;
1086
+    if (I2CPE_idx == 0xFF) {
1068 1087
       LOOP_XYZE(i) {
1069
-        if ((!I2CPE_anyaxis || parser.seen(axis_codes[i])) && ((idx = idx_from_axis(AxisEnum(i))) >= 0)) {
1070
-          if (newThreshold != -9999) set_ec_threshold((uint8_t)idx, newThreshold, encoders[idx].get_axis());
1071
-          else get_ec_threshold((uint8_t)idx, encoders[idx].get_axis());
1088
+        if (!I2CPE_anyaxis || parser.seen(axis_codes[i])) {
1089
+          const uint8_t idx = idx_from_axis(AxisEnum(i));
1090
+          if ((int8_t)idx >= 0) {
1091
+            if (newThreshold != -9999)
1092
+              set_ec_threshold(idx, newThreshold, encoders[idx].get_axis());
1093
+            else
1094
+              get_ec_threshold(idx, encoders[idx].get_axis());
1095
+          }
1072 1096
         }
1073 1097
       }
1074
-    } else {
1075
-      if (newThreshold != -9999) set_ec_threshold((uint8_t)I2CPE_idx, newThreshold, encoders[I2CPE_idx].get_axis());
1076
-      else get_ec_threshold((uint8_t)I2CPE_idx, encoders[I2CPE_idx].get_axis());
1077 1098
     }
1099
+    else if (newThreshold != -9999)
1100
+      set_ec_threshold(I2CPE_idx, newThreshold, encoders[I2CPE_idx].get_axis());
1101
+    else
1102
+      get_ec_threshold(I2CPE_idx, encoders[I2CPE_idx].get_axis());
1078 1103
   }
1079 1104
 
1080 1105
   /**
@@ -1092,13 +1117,16 @@
1092 1117
   void I2CPositionEncodersMgr::M869() {
1093 1118
     if (parse()) return;
1094 1119
 
1095
-    if (I2CPE_idx < 0) {
1096
-      int8_t idx;
1120
+    if (I2CPE_idx == 0xFF) {
1097 1121
       LOOP_XYZE(i) {
1098
-        if ((!I2CPE_anyaxis || parser.seen(axis_codes[i])) && ((idx = idx_from_axis(AxisEnum(i))) >= 0))
1099
-          report_error((uint8_t)idx);
1122
+        if (!I2CPE_anyaxis || parser.seen(axis_codes[i])) {
1123
+          const uint8_t idx = idx_from_axis(AxisEnum(i));
1124
+          if ((int8_t)idx >= 0) report_error(idx);
1125
+        }
1100 1126
       }
1101
-    } else report_error((uint8_t)I2CPE_idx);
1127
+    }
1128
+    else
1129
+      report_error(I2CPE_idx);
1102 1130
   }
1103 1131
 
1104
-#endif
1132
+#endif // I2C_POSITION_ENCODERS

+ 119
- 116
Marlin/I2CPositionEncoder.h View File

@@ -95,195 +95,202 @@
95 95
   #define I2CPE_PARSE_OK                0
96 96
 
97 97
   #define LOOP_PE(VAR) LOOP_L_N(VAR, I2CPE_ENCODER_CNT)
98
-  #define CHECK_IDX if (!WITHIN(idx, 0, I2CPE_ENCODER_CNT - 1)) return;
98
+  #define CHECK_IDX() do{ if (!WITHIN(idx, 0, I2CPE_ENCODER_CNT - 1)) return; }while(0)
99 99
 
100 100
   extern const char axis_codes[XYZE];
101 101
 
102 102
   typedef union {
103
-    volatile long   val = 0;
104
-    uint8_t         bval[4];
103
+    volatile int32_t val = 0;
104
+    uint8_t          bval[4];
105 105
   } i2cLong;
106 106
 
107 107
   class I2CPositionEncoder {
108 108
   private:
109
-    AxisEnum        encoderAxis             = I2CPE_DEF_AXIS;
109
+    AxisEnum  encoderAxis         = I2CPE_DEF_AXIS;
110 110
 
111
-    uint8_t         i2cAddress              = I2CPE_DEF_ADDR,
112
-                    ecMethod                = I2CPE_DEF_EC_METHOD,
113
-                    type                    = I2CPE_DEF_TYPE,
114
-                    H                       = I2CPE_MAG_SIG_NF;    // Magnetic field strength
111
+    uint8_t   i2cAddress          = I2CPE_DEF_ADDR,
112
+              ecMethod            = I2CPE_DEF_EC_METHOD,
113
+              type                = I2CPE_DEF_TYPE,
114
+              H                   = I2CPE_MAG_SIG_NF;    // Magnetic field strength
115 115
 
116
-    int             encoderTicksPerUnit     = I2CPE_DEF_ENC_TICKS_UNIT,
117
-                    stepperTicks            = I2CPE_DEF_TICKS_REV;
116
+    int       encoderTicksPerUnit = I2CPE_DEF_ENC_TICKS_UNIT,
117
+              stepperTicks        = I2CPE_DEF_TICKS_REV,
118
+              errorCount          = 0,
119
+              errorPrev           = 0;
118 120
 
119
-    float           ecThreshold             = I2CPE_DEF_EC_THRESH;
121
+    float     ecThreshold         = I2CPE_DEF_EC_THRESH;
120 122
 
121
-    bool            homed                   = false,
122
-                    trusted                 = false,
123
-                    initialised             = false,
124
-                    active                  = false,
125
-                    invert                  = false,
126
-                    ec                      = true;
123
+    bool      homed               = false,
124
+              trusted             = false,
125
+              initialised         = false,
126
+              active              = false,
127
+              invert              = false,
128
+              ec                  = true;
127 129
 
128
-    int             errorCount              = 0,
129
-                    errorPrev               = 0;
130
+    float     axisOffset          = 0;
130 131
 
131
-    float           axisOffset              = 0;
132
+    int32_t   axisOffsetTicks     = 0,
133
+              zeroOffset          = 0,
134
+              lastPosition        = 0,
135
+              position;
132 136
 
133
-    long            axisOffsetTicks         = 0,
134
-                    zeroOffset              = 0,
135
-                    lastPosition            = 0,
136
-                    position;
137
-
138
-    unsigned long   lastPositionTime        = 0,
139
-                    nextErrorCountTime      = 0,
140
-                    lastErrorTime;
137
+    millis_t  lastPositionTime    = 0,
138
+              nextErrorCountTime  = 0,
139
+              lastErrorTime;
141 140
 
142 141
     //double        positionMm; //calculate
143 142
 
144 143
     #if ENABLED(I2CPE_ERR_ROLLING_AVERAGE)
145
-      uint8_t       errIdx = 0;
146
-      int           err[I2CPE_ERR_ARRAY_SIZE] = {0};
144
+      uint8_t errIdx = 0;
145
+      int     err[I2CPE_ERR_ARRAY_SIZE] = { 0 };
147 146
     #endif
148 147
 
148
+    //float        positionMm; //calculate
149
+
149 150
   public:
150
-    void init(uint8_t address, AxisEnum axis);
151
+    void init(const uint8_t address, const AxisEnum axis);
151 152
     void reset();
152 153
 
153 154
     void update();
154 155
 
155 156
     void set_homed();
156 157
 
157
-    long get_raw_count();
158
+    int32_t get_raw_count();
158 159
 
159
-    FORCE_INLINE double mm_from_count(long count) {
160
-      if (type == I2CPE_ENC_TYPE_LINEAR) return count / encoderTicksPerUnit;
161
-      else if (type == I2CPE_ENC_TYPE_ROTARY)
162
-        return (count * stepperTicks) / (encoderTicksPerUnit * planner.axis_steps_per_mm[encoderAxis]);
163
-      return -1;
160
+    FORCE_INLINE float mm_from_count(const int32_t count) {
161
+      switch (type) {
162
+        default: return -1;
163
+        case I2CPE_ENC_TYPE_LINEAR:
164
+          return count / encoderTicksPerUnit;
165
+        case I2CPE_ENC_TYPE_ROTARY:
166
+          return (count * stepperTicks) / (encoderTicksPerUnit * planner.axis_steps_per_mm[encoderAxis]);
167
+      }
164 168
     }
165 169
 
166
-    FORCE_INLINE double get_position_mm() { return mm_from_count(get_position()); }
167
-    FORCE_INLINE long get_position() { return get_raw_count() - zeroOffset - axisOffsetTicks; }
170
+    FORCE_INLINE float get_position_mm() { return mm_from_count(get_position()); }
171
+    FORCE_INLINE int32_t get_position() { return get_raw_count() - zeroOffset - axisOffsetTicks; }
168 172
 
169
-    long get_axis_error_steps(bool report);
170
-    double get_axis_error_mm(bool report);
173
+    int32_t get_axis_error_steps(const bool report);
174
+    float get_axis_error_mm(const bool report);
171 175
 
172
-    void calibrate_steps_mm(int iter);
176
+    void calibrate_steps_mm(const uint8_t iter);
173 177
 
174
-    bool passes_test(bool report);
178
+    bool passes_test(const bool report);
175 179
 
176 180
     bool test_axis(void);
177 181
 
178 182
     FORCE_INLINE int get_error_count(void) { return errorCount; }
179
-    FORCE_INLINE void set_error_count(int newCount) { errorCount = newCount; }
183
+    FORCE_INLINE void set_error_count(const int newCount) { errorCount = newCount; }
180 184
 
181 185
     FORCE_INLINE uint8_t get_address() { return i2cAddress; }
182
-    FORCE_INLINE void set_address(uint8_t addr) { i2cAddress = addr; }
186
+    FORCE_INLINE void set_address(const uint8_t addr) { i2cAddress = addr; }
183 187
 
184 188
     FORCE_INLINE bool get_active(void) { return active; }
185
-    FORCE_INLINE void set_active(bool a) { active = a; }
189
+    FORCE_INLINE void set_active(const bool a) { active = a; }
186 190
 
187
-    FORCE_INLINE void set_inverted(bool i) { invert = i; }
191
+    FORCE_INLINE void set_inverted(const bool i) { invert = i; }
188 192
 
189 193
     FORCE_INLINE AxisEnum get_axis() { return encoderAxis; }
190 194
 
191 195
     FORCE_INLINE bool get_ec_enabled() { return ec; }
192
-    FORCE_INLINE void set_ec_enabled(bool enabled) { ec = enabled; }
196
+    FORCE_INLINE void set_ec_enabled(const bool enabled) { ec = enabled; }
193 197
 
194 198
     FORCE_INLINE uint8_t get_ec_method() { return ecMethod; }
195
-    FORCE_INLINE void set_ec_method(byte method) { ecMethod = method; }
199
+    FORCE_INLINE void set_ec_method(const byte method) { ecMethod = method; }
196 200
 
197 201
     FORCE_INLINE float get_ec_threshold() { return ecThreshold; }
198
-    FORCE_INLINE void set_ec_threshold(float newThreshold) { ecThreshold = newThreshold; }
202
+    FORCE_INLINE void set_ec_threshold(const float newThreshold) { ecThreshold = newThreshold; }
199 203
 
200 204
     FORCE_INLINE int get_encoder_ticks_mm() {
201
-      if (type == I2CPE_ENC_TYPE_LINEAR) return encoderTicksPerUnit;
202
-      else if (type == I2CPE_ENC_TYPE_ROTARY)
203
-        return (int)((encoderTicksPerUnit / stepperTicks) * planner.axis_steps_per_mm[encoderAxis]);
204
-      return 0;
205
+      switch (type) {
206
+        default: return 0;
207
+        case I2CPE_ENC_TYPE_LINEAR:
208
+          return encoderTicksPerUnit;
209
+        case I2CPE_ENC_TYPE_ROTARY:
210
+          return (int)((encoderTicksPerUnit / stepperTicks) * planner.axis_steps_per_mm[encoderAxis]);
211
+      }
205 212
     }
206 213
 
207 214
     FORCE_INLINE int get_ticks_unit() { return encoderTicksPerUnit; }
208
-    FORCE_INLINE void set_ticks_unit(int ticks) { encoderTicksPerUnit = ticks; }
215
+    FORCE_INLINE void set_ticks_unit(const int ticks) { encoderTicksPerUnit = ticks; }
209 216
 
210 217
     FORCE_INLINE uint8_t get_type() { return type; }
211
-    FORCE_INLINE void set_type(byte newType) { type = newType; }
218
+    FORCE_INLINE void set_type(const byte newType) { type = newType; }
212 219
 
213 220
     FORCE_INLINE int get_stepper_ticks() { return stepperTicks; }
214
-    FORCE_INLINE void set_stepper_ticks(int ticks) { stepperTicks = ticks; }
221
+    FORCE_INLINE void set_stepper_ticks(const int ticks) { stepperTicks = ticks; }
215 222
 
216 223
     FORCE_INLINE float get_axis_offset() { return axisOffset; }
217
-    FORCE_INLINE void set_axis_offset(float newOffset) {
224
+    FORCE_INLINE void set_axis_offset(const float newOffset) {
218 225
       axisOffset = newOffset;
219
-      axisOffsetTicks = (long)(axisOffset * get_encoder_ticks_mm());
226
+      axisOffsetTicks = int32_t(axisOffset * get_encoder_ticks_mm());
220 227
     }
221 228
 
222
-    FORCE_INLINE void set_current_position(float newPositionMm) {
229
+    FORCE_INLINE void set_current_position(const float newPositionMm) {
223 230
       set_axis_offset(get_position_mm() - newPositionMm + axisOffset);
224 231
     }
225 232
   };
226 233
 
227 234
   class I2CPositionEncodersMgr {
228 235
   private:
229
-    bool I2CPE_anyaxis;
230
-    uint8_t I2CPE_addr;
231
-    int8_t I2CPE_idx;
236
+    static bool I2CPE_anyaxis;
237
+    static uint8_t I2CPE_addr, I2CPE_idx;
232 238
 
233 239
   public:
234
-    void init(void);
240
+
241
+    static void init(void);
235 242
 
236 243
     // consider only updating one endoder per call / tick if encoders become too time intensive
237
-    void update(void) { LOOP_PE(i) encoders[i].update(); }
244
+    static void update(void) { LOOP_PE(i) encoders[i].update(); }
238 245
 
239
-    void homed(AxisEnum axis) {
246
+    static void homed(const AxisEnum axis) {
240 247
       LOOP_PE(i)
241 248
         if (encoders[i].get_axis() == axis) encoders[i].set_homed();
242 249
     }
243 250
 
244
-    void report_position(uint8_t idx, bool units, bool noOffset);
251
+    static void report_position(const int8_t idx, const bool units, const bool noOffset);
245 252
 
246
-    void report_status(uint8_t idx) {
247
-      CHECK_IDX
253
+    static void report_status(const int8_t idx) {
254
+      CHECK_IDX();
248 255
       SERIAL_ECHOPAIR("Encoder ",idx);
249 256
       SERIAL_ECHOPGM(": ");
250 257
       encoders[idx].get_raw_count();
251 258
       encoders[idx].passes_test(true);
252 259
     }
253 260
 
254
-    void report_error(uint8_t idx) {
255
-      CHECK_IDX
261
+    static void report_error(const int8_t idx) {
262
+      CHECK_IDX();
256 263
       encoders[idx].get_axis_error_steps(true);
257 264
     }
258 265
 
259
-    void test_axis(uint8_t idx) {
260
-      CHECK_IDX
266
+    static void test_axis(const int8_t idx) {
267
+      CHECK_IDX();
261 268
       encoders[idx].test_axis();
262 269
     }
263 270
 
264
-    void calibrate_steps_mm(uint8_t idx, int iterations) {
265
-      CHECK_IDX
271
+    static void calibrate_steps_mm(const int8_t idx, const int iterations) {
272
+      CHECK_IDX();
266 273
       encoders[idx].calibrate_steps_mm(iterations);
267 274
     }
268 275
 
269
-    void change_module_address(uint8_t oldaddr, uint8_t newaddr);
270
-    void report_module_firmware(uint8_t address);
276
+    static void change_module_address(const uint8_t oldaddr, const uint8_t newaddr);
277
+    static void report_module_firmware(const uint8_t address);
271 278
 
272
-    void report_error_count(uint8_t idx, AxisEnum axis) {
273
-      CHECK_IDX
279
+    static void report_error_count(const int8_t idx, const AxisEnum axis) {
280
+      CHECK_IDX();
274 281
       SERIAL_ECHOPAIR("Error count on ", axis_codes[axis]);
275 282
       SERIAL_ECHOLNPAIR(" axis is ", encoders[idx].get_error_count());
276 283
     }
277 284
 
278
-    void reset_error_count(uint8_t idx, AxisEnum axis) {
279
-      CHECK_IDX
285
+    static void reset_error_count(const int8_t idx, const AxisEnum axis) {
286
+      CHECK_IDX();
280 287
       encoders[idx].set_error_count(0);
281 288
       SERIAL_ECHOPAIR("Error count on ", axis_codes[axis]);
282 289
       SERIAL_ECHOLNPGM(" axis has been reset.");
283 290
     }
284 291
 
285
-    void enable_ec(uint8_t idx, bool enabled, AxisEnum axis) {
286
-      CHECK_IDX
292
+    static void enable_ec(const int8_t idx, const bool enabled, const AxisEnum axis) {
293
+      CHECK_IDX();
287 294
       encoders[idx].set_ec_enabled(enabled);
288 295
       SERIAL_ECHOPAIR("Error correction on ", axis_codes[axis]);
289 296
       SERIAL_ECHOPGM(" axis is ");
@@ -291,66 +298,62 @@
291 298
       SERIAL_ECHOLNPGM("abled.");
292 299
     }
293 300
 
294
-    void set_ec_threshold(uint8_t idx, float newThreshold, AxisEnum axis) {
295
-      CHECK_IDX
301
+    static void set_ec_threshold(const int8_t idx, const float newThreshold, const AxisEnum axis) {
302
+      CHECK_IDX();
296 303
       encoders[idx].set_ec_threshold(newThreshold);
297 304
       SERIAL_ECHOPAIR("Error correct threshold for ", axis_codes[axis]);
298 305
       SERIAL_ECHOPAIR_F(" axis set to ", newThreshold);
299 306
       SERIAL_ECHOLNPGM("mm.");
300 307
     }
301 308
 
302
-    void get_ec_threshold(uint8_t idx, AxisEnum axis) {
303
-      CHECK_IDX
304
-      float threshold = encoders[idx].get_ec_threshold();
309
+    static void get_ec_threshold(const int8_t idx, const AxisEnum axis) {
310
+      CHECK_IDX();
311
+      const float threshold = encoders[idx].get_ec_threshold();
305 312
       SERIAL_ECHOPAIR("Error correct threshold for ", axis_codes[axis]);
306 313
       SERIAL_ECHOPAIR_F(" axis is ", threshold);
307 314
       SERIAL_ECHOLNPGM("mm.");
308 315
     }
309 316
 
310
-    int8_t idx_from_axis(AxisEnum axis) {
317
+    static int8_t idx_from_axis(const AxisEnum axis) {
311 318
       LOOP_PE(i)
312 319
         if (encoders[i].get_axis() == axis) return i;
313
-
314 320
       return -1;
315 321
     }
316 322
 
317
-    int8_t idx_from_addr(uint8_t addr) {
323
+    static int8_t idx_from_addr(const uint8_t addr) {
318 324
       LOOP_PE(i)
319 325
         if (encoders[i].get_address() == addr) return i;
320
-
321 326
       return -1;
322 327
     }
323 328
 
324
-    int8_t parse();
329
+    static int8_t parse();
325 330
 
326
-    void M860();
327
-    void M861();
328
-    void M862();
329
-    void M863();
330
-    void M864();
331
-    void M865();
332
-    void M866();
333
-    void M867();
334
-    void M868();
335
-    void M869();
331
+    static void M860();
332
+    static void M861();
333
+    static void M862();
334
+    static void M863();
335
+    static void M864();
336
+    static void M865();
337
+    static void M866();
338
+    static void M867();
339
+    static void M868();
340
+    static void M869();
336 341
 
337
-    I2CPositionEncoder encoders[I2CPE_ENCODER_CNT];
342
+    static I2CPositionEncoder encoders[I2CPE_ENCODER_CNT];
338 343
   };
339 344
 
340 345
   extern I2CPositionEncodersMgr I2CPEM;
341 346
 
342
-  FORCE_INLINE void gcode_M860() { I2CPEM.M860(); }
343
-  FORCE_INLINE void gcode_M861() { I2CPEM.M861(); }
344
-  FORCE_INLINE void gcode_M862() { I2CPEM.M862(); }
345
-  FORCE_INLINE void gcode_M863() { I2CPEM.M863(); }
346
-  FORCE_INLINE void gcode_M864() { I2CPEM.M864(); }
347
-  FORCE_INLINE void gcode_M865() { I2CPEM.M865(); }
348
-  FORCE_INLINE void gcode_M866() { I2CPEM.M866(); }
349
-  FORCE_INLINE void gcode_M867() { I2CPEM.M867(); }
350
-  FORCE_INLINE void gcode_M868() { I2CPEM.M868(); }
351
-  FORCE_INLINE void gcode_M869() { I2CPEM.M869(); }
347
+  FORCE_INLINE static void gcode_M860() { I2CPEM.M860(); }
348
+  FORCE_INLINE static void gcode_M861() { I2CPEM.M861(); }
349
+  FORCE_INLINE static void gcode_M862() { I2CPEM.M862(); }
350
+  FORCE_INLINE static void gcode_M863() { I2CPEM.M863(); }
351
+  FORCE_INLINE static void gcode_M864() { I2CPEM.M864(); }
352
+  FORCE_INLINE static void gcode_M865() { I2CPEM.M865(); }
353
+  FORCE_INLINE static void gcode_M866() { I2CPEM.M866(); }
354
+  FORCE_INLINE static void gcode_M867() { I2CPEM.M867(); }
355
+  FORCE_INLINE static void gcode_M868() { I2CPEM.M868(); }
356
+  FORCE_INLINE static void gcode_M869() { I2CPEM.M869(); }
352 357
 
353 358
 #endif //I2C_POSITION_ENCODERS
354 359
 #endif //I2CPOSENC_H
355
-
356
-

+ 2
- 2
Marlin/Marlin_main.cpp View File

@@ -5141,7 +5141,7 @@ void home_all_axes() { gcode_G28(true); }
5141 5141
      *   T   Don't calibrate tower angle corrections
5142 5142
      *
5143 5143
      *   Cn.nn Calibration precision; when omitted calibrates to maximum precision
5144
-     *   
5144
+     *
5145 5145
      *   Fn  Force to run at least n iterations and takes the best result
5146 5146
      *
5147 5147
      *   Vn  Verbose level:
@@ -5687,7 +5687,7 @@ inline void gcode_G92() {
5687 5687
             update_software_endstops((AxisEnum)i);
5688 5688
 
5689 5689
             #if ENABLED(I2C_POSITION_ENCODERS)
5690
-              I2CPEM.encoders[I2CPEM.idx_from_axis((AxisEnum) i)].set_axis_offset(position_shift[i]);
5690
+              I2CPEM.encoders[I2CPEM.idx_from_axis((AxisEnum)i)].set_axis_offset(position_shift[i]);
5691 5691
             #endif
5692 5692
 
5693 5693
           #endif

+ 1
- 3
Marlin/SanityCheck.h View File

@@ -276,9 +276,7 @@
276 276
 #if ENABLED(I2C_POSITION_ENCODERS)
277 277
   #if DISABLED(BABYSTEPPING)
278 278
     #error "I2C_POSITION_ENCODERS requires BABYSTEPPING."
279
-  #endif
280
-
281
-  #if I2CPE_ENCODER_CNT > 5 || I2CPE_ENCODER_CNT < 1
279
+  #elif !WITHIN(I2CPE_ENCODER_CNT, 1, 5)
282 280
     #error "I2CPE_ENCODER_CNT must be between 1 and 5."
283 281
   #endif
284 282
 #endif

+ 4
- 3
Marlin/ubl_G29.cpp View File

@@ -328,7 +328,8 @@
328 328
       g29_repetition_cnt = parser.has_value() ? parser.value_int() : 1;
329 329
       if (g29_repetition_cnt >= GRID_MAX_POINTS) {
330 330
         set_all_mesh_points_to_value(NAN);
331
-      } else {
331
+      }
332
+      else {
332 333
         while (g29_repetition_cnt--) {
333 334
           if (cnt > 20) { cnt = 0; idle(); }
334 335
           const mesh_index_pair location = find_closest_mesh_point_of_type(REAL, g29_x_pos, g29_y_pos, USE_NOZZLE_AS_REFERENCE, NULL, false);
@@ -1454,7 +1455,7 @@
1454 1455
     void unified_bed_leveling::fine_tune_mesh(const float &lx, const float &ly, const bool do_ubl_mesh_map) {
1455 1456
       if (!parser.seen('R'))    // fine_tune_mesh() is special. If no repetition count flag is specified
1456 1457
         g29_repetition_cnt = 1;   // do exactly one mesh location. Otherwise use what the parser decided.
1457
-      
1458
+
1458 1459
       #if ENABLED(UBL_MESH_EDIT_MOVES_Z)
1459 1460
         const bool is_offset = parser.seen('H');
1460 1461
         const float h_offset = is_offset ? parser.value_linear_units() : Z_CLEARANCE_BETWEEN_PROBES;
@@ -1463,7 +1464,7 @@
1463 1464
           return;
1464 1465
         }
1465 1466
       #endif
1466
-      
1467
+
1467 1468
       mesh_index_pair location;
1468 1469
 
1469 1470
       if (!position_is_reachable_xy(lx, ly)) {

Loading…
Cancel
Save