Управление трёхцветным светодиодом по USB
- Войдите на сайт для отправки комментариев
Чт, 02/06/2016 - 20:11
Задумка такая: с клавиатуры вводится 16-ричный код цвета, трёхцветный светодиод отображает этот цвет, но на деле как-то криво всё работает. Например, при вводе "000000" светодиод горит. ЧЯДНТ?
#define R 9
#define G 10
#define B 11
#include <math.h>
String c;
byte r = 0, g = 0, b = 0, i = 0;
void setup() {
pinMode(R, OUTPUT);
pinMode(G, OUTPUT);
pinMode(B, OUTPUT);
Serial.begin(9600);
}
void loop() {
while (Serial.available())
{
char inChar = Serial.read();
if (inChar == '\n')
{
for (i = 0; i <= 1; i++)
{
if (c[i] == 'A')
r += (10 * pow(16, 1 - i));
else if (c[i] == 'B')
r += (11 * pow(16, 1 - i));
else if (c[i] == 'C')
r += (12 * pow(16, 1 - i));
else if (c[i] == 'D')
r += (13 * pow(16, 1 - i));
else if (c[i] == 'E')
r += (14 * pow(16, 1 - i));
else if (c[i] == 'F')
r += (15 * pow(16, 1 - i));
else
r += (c[i] * pow(16, 1 - i));
}
analogWrite(R, r);
for (i = 2; i <= 3; i++)
{
if (c[i] == 'A')
g += (10 * pow(16, 3 - i));
else if (c[i] == 'B')
g += (11 * pow(16, 3 - i));
else if (c[i] == 'C')
g += (12 * pow(16, 3 - i));
else if (c[i] == 'D')
g += (13 * pow(16, 3 - i));
else if (c[i] == 'E')
g += (14 * pow(16, 3 - i));
else if (c[i] == 'F')
g += (15 * pow(16, 3 - i));
else
g += (c[i] * pow(16, 3 - i));
}
analogWrite(G, g);
for (i = 4; i <= 5; i++)
{
if (c[i] == 'A')
b += (10 * pow(16, 5 - i));
else if (c[i] == 'B')
b += (11 * pow(16, 5 - i));
else if (c[i] == 'C')
b += (12 * pow(16, 5 - i));
else if (c[i] == 'D')
b += (13 * pow(16, 5 - i));
else if (c[i] == 'E')
b += (14 * pow(16, 5 - i));
else if (c[i] == 'F')
b += (15 * pow(16, 5 - i));
else
b += (c[i] * pow(16, 5 - i));
}
analogWrite(B, b);
c = "";
}
else
c += inChar;
}
}
Вы как-то слишком уж мудрёно переводите числа. Ещё мудренее не пробовали?
Ошибки очевидны, но Вам лучше найти их самому.
Для этого поставьте перед строками 39, 57 и 75 вывод в сериал соответсвенно r, g и b. Хоть посмотрите что у Вас там получается. Когда посмотрите, думайте, как исправить.
А вообще, это надо делать раз в 20 короче и проще. Вот, смотрите. Все чудеса происхлдят в строках 15-17. Всё остальное - оформительство.
template <typename T> inline Print & operator << (Print &s, T n) { s.print(n); return s; } inline void prompt(void) { Serial << "Enter three bytes hexadecimal number (six characters 0-F with no spaces):\n"; } void setup() { Serial.begin(115200); Serial.setTimeout(0xFFFFFFFF); prompt(); } void loop() { if (! Serial.available()) return; String s = Serial.readStringUntil('\n'); unsigned r, g, b; sscanf(s.c_str(), "%2x%2x%2x", &r, &g, &b); Serial << "s=" << s << "= r=" << r << " g=" << g << " b=" << b << "\n\n"; prompt(); }Здесь нет никакой проверки на правильность введённой информации, а также никакого "паренья" об эффективности. Если уж Вы используете String, то эффективность Вас не волнует, как я понимаю. Если нужна эффективность, то это пшется чуть длинее, но без String и без sscanf.
Спасибо огромное! Как всё оказалось просто)