| 187 | } |
| 188 | |
| 189 | void FlowFieldFloat::drawAALine(float x0, float y0, float x1, float y1, |
| 190 | float t, float colorShift) { |
| 191 | int w = (int)getWidth(); |
| 192 | int h = (int)getHeight(); |
| 193 | float dx = x1 - x0; |
| 194 | float dy = y1 - y0; |
| 195 | int steps = fl::max(1, (int)(fl::max(fabsf(dx), fabsf(dy)) * 3.0f)); |
| 196 | float invSteps = 1.0f / (float)steps; |
| 197 | |
| 198 | for (int i = 0; i <= steps; i++) { |
| 199 | float u = i * invSteps; |
| 200 | float px = x0 + dx * u; |
| 201 | float py = y0 + dy * u; |
| 202 | CRGB c = rainbow(t, colorShift, u); |
| 203 | |
| 204 | int ix = (int)floorf(px); |
| 205 | int iy = (int)floorf(py); |
| 206 | float fx = px - ix; |
| 207 | float fy = py - iy; |
| 208 | |
| 209 | float weights[4] = { |
| 210 | (1.0f - fx) * (1.0f - fy), |
| 211 | fx * (1.0f - fy), |
| 212 | (1.0f - fx) * fy, |
| 213 | fx * fy, |
| 214 | }; |
| 215 | int offX[4] = {0, 1, 0, 1}; |
| 216 | int offY[4] = {0, 0, 1, 1}; |
| 217 | |
| 218 | for (int j = 0; j < 4; j++) { |
| 219 | int cx = ix + offX[j]; |
| 220 | int cy = iy + offY[j]; |
| 221 | if (cx < 0 || cx >= w || cy < 0 || cy >= h) |
| 222 | continue; |
| 223 | float wt = weights[j]; |
| 224 | if (wt <= 0.0f) |
| 225 | continue; |
| 226 | int gi = idx(cy, cx); |
| 227 | float inv = 1.0f - wt; |
| 228 | mR[gi] = mR[gi] * inv + c.r * wt; |
| 229 | mG[gi] = mG[gi] * inv + c.g * wt; |
| 230 | mB[gi] = mB[gi] * inv + c.b * wt; |
| 231 | } |
| 232 | } |
| 233 | } |
| 234 | |
| 235 | void FlowFieldFloat::emitLissajousLine(float t) { |
| 236 | int w = (int)getWidth(); |