/* Эффект часов для gyver лампы Цвет часовой и минутной стрелки регулируются скоростью и масштабом вызов : ClockRoutine(WIDTH,HEIGHT,true); цвет меток циферблата - радужный, цвет метки возле минутной стрелки стремится к цвету минутной стрелки фон черный. Ширина, высота, требуется ли очистить экран; вызов : ClockRoutine(WIDTH,HEIGHT,false); цвет всех елементов - белый фон предыдущий. Примеры вызова с наложением case EFF_COLOR: colorRoutine(); ClockRoutine(WIDTH,HEIGHT,false); break; без наложения case EFF_новое: ClockRoutine(WIDTH,HEIGHT,true); break; для цилиндрических ламп наверно лучще будет case EFF_новое: ClockRoutine(10,16,true); break; */ void ClockRoutine(uint8_t cl_w, uint8_t cl_h, bool fon_clear) { float r_clock; int c_x1; int c_y1; int c_x2; int c_y2; float dx=(cl_w % 2 ==1) ? 0.49 : 0; float dy=(cl_h % 2 ==1) ? 0.49 : 0; int c_cx=(WIDTH-cl_w)/2; int c_cy=(HEIGHT-cl_h)/2; CHSV color = CHSV(0,(modes[currentMode].Speed>150)?0:255,(modes[currentMode].Speed<150)?0:255); int bridges=(thisTime < NIGHT_HOURS_START && thisTime > NIGHT_HOURS_STOP)?255:64; //Очистка if (fon_clear) FastLED.clear(); //Циферблат // метки 1,2,4,5, 7,8, 10,11 (цвет метка сопровождает цвет минутной стрелки for (int i=0; i<12; i++) { r_clock=PI*i/6; c_x1=sin(r_clock)*(cl_w/2+dx-0.1)+cl_w/2+dx+c_cx; c_y1=cos(r_clock)*(cl_h/2+dy-0.1)+cl_h/2+dy+c_cy; if (fon_clear) color=CHSV(i*21-map(thisTime%60,0,59,0,255)+map(modes[currentMode].Scale,1,100,0,255),255,bridges/4); drawPixelXY(c_x1, c_y1, color); } // метки 3, 9, if (cl_h % 2 ==0) { if (fon_clear) color= CHSV(192-map(thisTime%60,0,59,0,255)+map(modes[currentMode].Scale,1,100,0,255),255,bridges/2); DrawLine(c_cx, cl_h/2-1+c_cy, c_cx, cl_h/2+c_cy, color); if (fon_clear) color= CHSV(64-map(thisTime%60,0,59,0,255)+map(modes[currentMode].Scale,1,100,0,255),255,bridges/2); DrawLine(c_cx+cl_w-1,cl_h/2-1+c_cy,c_cx+cl_w-1,cl_h/2+c_cy, color); } // метки 12, 6, if (cl_w % 2 ==0) { if (fon_clear) color= CHSV(128-map(thisTime%60,0,59,0,255)+map(modes[currentMode].Scale,1,100,0,255),255,bridges/2); DrawLine(cl_w/2-1+c_cx, c_cy, cl_w/2+c_cx, c_cy, color); if (fon_clear) color= CHSV(-map(thisTime%60,0,59,0,255)+map(modes[currentMode].Scale,1,100,0,255),255,bridges/2) ; DrawLine(cl_w/2-1+c_cx, cl_h-1+c_cy, cl_w/2+c_cx, cl_h-1+c_cy,color); } // Минутная стрелка r_clock=PI*(thisTime % 60)/30; c_x1=sin(r_clock)+cl_w/2+dx+c_cx; c_y1=cos(r_clock)+cl_h/2+dy+c_cy; c_x2=sin(r_clock)*(cl_w/2.5)+cl_w/2+dx+c_cx; c_y2=cos(r_clock)*(cl_h/2.5)+cl_h/2+dy+c_cy; if (fon_clear) color=CHSV(map(modes[currentMode].Scale,1,100,0,255),255,bridges); DrawLine(c_x1,c_y1,c_x2,c_y2,color); // Часовая стрелка r_clock=PI*(thisTime % 720)/360; c_x1=sin(r_clock)+cl_w/2+dx+c_cx; c_y1=cos(r_clock)+cl_h/2+dy+c_cy; c_x2=sin(r_clock)*(cl_w/3)+cl_w/2+dx+c_cx; c_y2=cos(r_clock)*(cl_h/3)+cl_h/2+dy+c_cy; if (fon_clear) color=CHSV(modes[currentMode].Speed*2.55,255,bridges) ; DrawLine(c_x1,c_y1,c_x2,c_y2,color); } //Дополнитеьная функция построения линий void DrawLine(int x1, int y1, int x2, int y2, CHSV color) { int tmp; int x,y; int dx, dy; int err; int ystep; uint8_t swapxy = 0; if ( x1 > x2 ) dx = x1-x2; else dx = x2-x1; if ( y1 > y2 ) dy = y1-y2; else dy = y2-y1; if ( dy > dx ) { swapxy = 1; tmp = dx; dx =dy; dy = tmp; tmp = x1; x1 =y1; y1 = tmp; tmp = x2; x2 =y2; y2 = tmp; } if ( x1 > x2 ) { tmp = x1; x1 =x2; x2 = tmp; tmp = y1; y1 =y2; y2 = tmp; } err = dx >> 1; if ( y2 > y1 ) ystep = 1; else ystep = -1; y = y1; for( x = x1; x <= x2; x++ ) { if ( swapxy == 0 ) drawPixelXY(x, y, color); else drawPixelXY(y, x, color); err -= (uint8_t)dy; if ( err < 0 ) { y += ystep; err += dx; } } }