FastLED 3.9.15
Loading...
Searching...
No Matches

◆ fill_gradient()

template<typename T>
void fl::fill_gradient ( T * targetArray,
u16 startpos,
CHSV startcolor,
u16 endpos,
CHSV endcolor,
TGradientDirectionCode directionCode = SHORTEST_HUES )

Fill a range of LEDs with a smooth HSV gradient between two HSV colors.

This function can write the gradient colors either:

  1. Into an array of CRGBs (e.g., an leds[] array, or a CRGB palette)
  2. Into an array of CHSVs (e.g. a CHSV palette).

In the case of writing into a CRGB array, the gradient is computed in HSV space, and then HSV values are converted to RGB as they're written into the CRGB array.

Parameters
targetArraya pointer to the color array to fill
startposthe starting position in the array
startcolorthe starting color for the gradient
endposthe ending position in the array
endcolorthe end color for the gradient
directionCodethe direction to travel around the color wheel

Definition at line 105 of file fill.h.

107 {
108 // if the points are in the wrong order, straighten them
109 if (endpos < startpos) {
110 u16 t = endpos;
111 CHSV tc = endcolor;
112 endcolor = startcolor;
113 endpos = startpos;
114 startpos = t;
115 startcolor = tc;
116 }
117
118 // If we're fading toward black (val=0) or white (sat=0),
119 // then set the endhue to the starthue.
120 // This lets us ramp smoothly to black or white, regardless
121 // of what 'hue' was set in the endcolor (since it doesn't matter)
122 if (endcolor.value == 0 || endcolor.saturation == 0) {
123 endcolor.hue = startcolor.hue;
124 }
125
126 // Similarly, if we're fading in from black (val=0) or white (sat=0)
127 // then set the starthue to the endhue.
128 // This lets us ramp smoothly up from black or white, regardless
129 // of what 'hue' was set in the startcolor (since it doesn't matter)
130 if (startcolor.value == 0 || startcolor.saturation == 0) {
131 startcolor.hue = endcolor.hue;
132 }
133
134 saccum87 huedistance87;
135 saccum87 satdistance87;
136 saccum87 valdistance87;
137
138 satdistance87 = (endcolor.sat - startcolor.sat) << 7;
139 valdistance87 = (endcolor.val - startcolor.val) << 7;
140
141 fl::u8 huedelta8 = endcolor.hue - startcolor.hue;
142
143 if (directionCode == SHORTEST_HUES) {
144 directionCode = FORWARD_HUES;
145 if (huedelta8 > 127) {
146 directionCode = BACKWARD_HUES;
147 }
148 }
149
150 if (directionCode == LONGEST_HUES) {
151 directionCode = FORWARD_HUES;
152 if (huedelta8 < 128) {
153 directionCode = BACKWARD_HUES;
154 }
155 }
156
157 if (directionCode == FORWARD_HUES) {
158 huedistance87 = huedelta8 << 7;
159 } else /* directionCode == BACKWARD_HUES */
160 {
161 huedistance87 = (fl::u8)(256 - huedelta8) << 7;
162 huedistance87 = -huedistance87;
163 }
164
165 u16 pixeldistance = endpos - startpos;
166 i16 divisor = pixeldistance ? pixeldistance : 1;
167
168#if FASTLED_USE_32_BIT_GRADIENT_FILL
169 // Use higher precision 32 bit math for new micros.
170 i32 huedelta823 = (huedistance87 * 65536) / divisor;
171 i32 satdelta823 = (satdistance87 * 65536) / divisor;
172 i32 valdelta823 = (valdistance87 * 65536) / divisor;
173
174 huedelta823 *= 2;
175 satdelta823 *= 2;
176 valdelta823 *= 2;
177 u32 hue824 = static_cast<u32>(startcolor.hue) << 24;
178 u32 sat824 = static_cast<u32>(startcolor.sat) << 24;
179 u32 val824 = static_cast<u32>(startcolor.val) << 24;
180 for (u16 i = startpos; i <= endpos; ++i) {
181 targetArray[i] = CHSV(hue824 >> 24, sat824 >> 24, val824 >> 24);
182 hue824 += huedelta823;
183 sat824 += satdelta823;
184 val824 += valdelta823;
185 }
186#else
187 // Use 8-bit math for older micros.
188 saccum87 huedelta87 = huedistance87 / divisor;
189 saccum87 satdelta87 = satdistance87 / divisor;
190 saccum87 valdelta87 = valdistance87 / divisor;
191
192 huedelta87 *= 2;
193 satdelta87 *= 2;
194 valdelta87 *= 2;
195
196 accum88 hue88 = startcolor.hue << 8;
197 accum88 sat88 = startcolor.sat << 8;
198 accum88 val88 = startcolor.val << 8;
199 for (u16 i = startpos; i <= endpos; ++i) {
200 targetArray[i] = CHSV(hue88 >> 8, sat88 >> 8, val88 >> 8);
201 hue88 += huedelta87;
202 sat88 += satdelta87;
203 val88 += valdelta87;
204 }
205#endif // defined(FL_IS_AVR)
206}
@ SHORTEST_HUES
Hue goes whichever way is shortest.
@ LONGEST_HUES
Hue goes whichever way is longest.
@ FORWARD_HUES
Hue always goes clockwise around the color wheel.
@ BACKWARD_HUES
Hue always goes counter-clockwise around the color wheel.
static uint32_t t
Definition Luminova.h:55
#define saccum87
ANSI: signed short _Accum.
Definition fill.h:19
fl::hsv8 CHSV
Definition chsv.h:11
u16 accum88
ANSI: unsigned short _Accum. 8 bits int, 8 bits fraction.
Definition s16x16x4.h:182
unsigned char u8
Definition stdint.h:131

Referenced by FL_DISABLE_WARNING().

+ Here is the caller graph for this function: