From 91dc74ff16d5edb0d8ab5c809614acad25426553 Mon Sep 17 00:00:00 2001
From: ellensp <ellensp@hotmail.com>
Date: Sat, 4 Jul 2020 09:33:09 +1200
Subject: [PATCH] M150 I to set Neopixel by index (#18490)

---
 Marlin/src/feature/leds/neopixel.cpp   | 26 +++++++++++++++++---------
 Marlin/src/feature/leds/neopixel.h     |  4 ++++
 Marlin/src/gcode/feature/leds/M150.cpp |  9 ++++++++-
 3 files changed, 29 insertions(+), 10 deletions(-)

diff --git a/Marlin/src/feature/leds/neopixel.cpp b/Marlin/src/feature/leds/neopixel.cpp
index 3c2c0b44fc..3d11c5b64e 100644
--- a/Marlin/src/feature/leds/neopixel.cpp
+++ b/Marlin/src/feature/leds/neopixel.cpp
@@ -35,6 +35,7 @@
 #endif
 
 Marlin_NeoPixel neo;
+int8_t Marlin_NeoPixel::neoindex;
 
 Adafruit_NeoPixel Marlin_NeoPixel::adaneo1(NEOPIXEL_PIXELS, NEOPIXEL_PIN, NEOPIXEL_TYPE + NEO_KHZ800)
   #if MULTIPLE_NEOPIXEL_TYPES
@@ -52,14 +53,20 @@ Adafruit_NeoPixel Marlin_NeoPixel::adaneo1(NEOPIXEL_PIXELS, NEOPIXEL_PIN, NEOPIX
 #endif
 
 void Marlin_NeoPixel::set_color(const uint32_t color) {
-  for (uint16_t i = 0; i < pixels(); ++i) {
-    #ifdef NEOPIXEL_BKGD_LED_INDEX
-      if (i == NEOPIXEL_BKGD_LED_INDEX && color != 0x000000) {
-        set_color_background();
-        continue;
-      }
-    #endif
-    set_pixel_color(i, color);
+  if (get_neo_index() < 0) { 
+    set_pixel_color(get_neo_index(), color);
+    set_neo_index(-1);
+  }
+  else { 
+    for (uint16_t i = 0; i < pixels(); ++i) {
+      #ifdef NEOPIXEL_BKGD_LED_INDEX
+        if (i == NEOPIXEL_BKGD_LED_INDEX && color != 0x000000) {
+          set_color_background();
+          continue;
+        }
+      #endif
+      set_pixel_color(i, color);
+    }
   }
   show();
 }
@@ -71,7 +78,8 @@ void Marlin_NeoPixel::set_color_startup(const uint32_t color) {
 }
 
 void Marlin_NeoPixel::init() {
-  set_brightness(NEOPIXEL_BRIGHTNESS); // 0 - 255 range
+  set_neo_index(-1);                   // -1 .. NEOPIXEL_PIXELS-1 range
+  set_brightness(NEOPIXEL_BRIGHTNESS); //  0 .. 255 range
   begin();
   show();  // initialize to all off
 
diff --git a/Marlin/src/feature/leds/neopixel.h b/Marlin/src/feature/leds/neopixel.h
index 1b1b74fdfe..631e4fa004 100644
--- a/Marlin/src/feature/leds/neopixel.h
+++ b/Marlin/src/feature/leds/neopixel.h
@@ -65,6 +65,7 @@ private:
       , adaneo2
     #endif
   ;
+  static int8_t neoindex;
 
 public:
   static void init();
@@ -72,6 +73,9 @@ public:
 
   static void set_color(const uint32_t c);
 
+  FORCE_INLINE static void set_neo_index(const int8_t neoIndex) { neoindex = neoIndex; }
+  FORCE_INLINE static int8_t get_neo_index() { return neoindex; }
+
   #ifdef NEOPIXEL_BKGD_LED_INDEX
     static void set_color_background();
   #endif
diff --git a/Marlin/src/gcode/feature/leds/M150.cpp b/Marlin/src/gcode/feature/leds/M150.cpp
index 656b7e5f90..a2497961ac 100644
--- a/Marlin/src/gcode/feature/leds/M150.cpp
+++ b/Marlin/src/gcode/feature/leds/M150.cpp
@@ -34,6 +34,9 @@
  * Always sets all 3 or 4 components. If a component is left out, set to 0.
  *                                    If brightness is left out, no value changed
  *
+ * With NEOPIXEL_LED:
+ *  I<index>  Set the Neopixel index to affect. Default: All
+ *
  * Examples:
  *
  *   M150 R255       ; Turn LED red
@@ -43,8 +46,12 @@
  *   M150 W          ; Turn LED white using a white LED
  *   M150 P127       ; Set LED 50% brightness
  *   M150 P          ; Set LED full brightness
- */
+ *   M150 I1 R       ; Set NEOPIXEL index 1 to red
+ */  
 void GcodeSuite::M150() {
+  #if ENABLED(NEOPIXEL_LED)
+    neo.set_neo_index(parser.intval('I', -1));
+  #endif
   leds.set_color(MakeLEDColor(
     parser.seen('R') ? (parser.has_value() ? parser.value_byte() : 255) : 0,
     parser.seen('U') ? (parser.has_value() ? parser.value_byte() : 255) : 0,