Вроде бы все просто, а не работает..

Mad Fun
Offline
Зарегистрирован: 19.11.2011

Суть задачи в том, что есть 6 кнопок, 6 светодиодов и переменная равная например 50-ти, при нажатии на любую из кнопок переменная уменьшается на единицу, при нажатии одновременно на 2 кнопки - переменная уменьшается на 2 и тд. При значении переменной 50, горят все светодиоды, при значении от 40 до 50-ти  - горт 5 светодиодов, при значении от 30 до 40 - 4 светодиода и тд..

Написал вот такой код:

#define RF 1
#define RC 2
#define RT 3
#define LF 4
#define LC 5
#define LT 6
#define LED1 7
#define LED2 8
#define LED3 9
#define LED4 10
#define LED5 11
#define LED6 12

int health = 50;
int valRF = 0;
int valRC = 0;
int valRT = 0;
int valLF = 0;
int valLC = 0;
int valLT = 0;

void setup()
{
pinMode(RF, INPUT);
pinMode(RC, INPUT);
pinMode(RT, INPUT);
pinMode(LF, INPUT);
pinMode(LC, INPUT);
pinMode(LT, INPUT);
pinMode(LED1, OUTPUT);
pinMode(LED2, OUTPUT);
pinMode(LED3, OUTPUT);
pinMode(LED4, OUTPUT);
pinMode(LED5, OUTPUT);
pinMode(LED6, OUTPUT);
}

void loop()
{
valRF = digitalRead(RF)+1;
valRC = digitalRead(RC)+1;
valRT = digitalRead(RT);
valLF = digitalRead(LF)+1;
valLC = digitalRead(LC)+1;
valLT = digitalRead(LT);
health = health-valRF-valRC-valRT-valLF-valLC-valLT;
if ((health < 50) && (health > 40)) {
digitalWrite(LED6, LOW);
}
else if ((health <= 40) && (health > 30)) {
digitalWrite(LED5, LOW);
}
else if ((health <= 30) && (health > 20)) {
digitalWrite(LED4, LOW);
}
else if ((health <= 20) && (health > 10)) {
digitalWrite(LED3, LOW);
}
else if ((health <= 10) && (health > 0)) {
digitalWrite(LED2, LOW);
}
else if (health <= 0) {
digitalWrite(LED1, LOW);
} else {
digitalWrite(LED1, HIGH);
digitalWrite(LED2, HIGH);
digitalWrite(LED3, HIGH);
digitalWrite(LED4, HIGH);
digitalWrite(LED5, HIGH);
digitalWrite(LED6, HIGH);
}
}

Но что-то не работает он.. Где ошибка?

 

LEVV2006
LEVV2006 аватар
Offline
Зарегистрирован: 15.04.2011

1)Эти строчки мне не понятны. Получается что с каждым проходом цикла у тебя всё равно вычитаются единицы хотя ты кнопок и не нажимал и твоя переменная уходит в мину вообще.

2) У тебя изначально не горят светодиоды

Я всё правильно понимаю 0_0
 

step962
Offline
Зарегистрирован: 23.05.2011

Что значит - не работает?

Не работает так, как вы ожидали?

Не в той очередности загораются светодиоды?

Не загорается ни один из шести светодиодов?

Не горит светодиод POWER?

 

В setup() инициализируйте Serial.

В loop() в каждой из ветвей if() поставьте вывод соответствующего диагностического сообщения, перед первым if() выводите значение health. Может быть, сразу же увидите, в чем там дело.

LEVV2006
LEVV2006 аватар
Offline
Зарегистрирован: 15.04.2011

Полностью согласен с step962 (>Не горит светодиод POWER?< Ржал долго)))))

Надо точнее писать.

Я тут поразмышлял….. Но не пробовал на макете. Компилятор ошибок не выявил

int ledPin[]={
8,9,10,11,12,13};
int btnPin[]={
  2,3,4,5,6,7};

int health = 50;

int knopka[]={
  0,0,0,0,0,0};
void setup()
{

  for(int i=0;i<=5; i++)
    pinMode(btnPin[i], INPUT);
  for(int i=0;i<=5; i++)
    pinMode(ledPin[i], OUTPUT);
  for(int i=0;i<=5; i++)
    digitalWrite(ledPin[i], 1);
}

void vvod(int bt, int i)
{
  if(digitalRead(bt)==HIGH&&knopka[i]==0)

  {
    delay(50);
    knopka[i]=1;
    health--;

  }
  if(digitalRead(bt)==LOW&&knopka[i]==1)
  {
    knopka[i]=0;
  }
}

void loop()
{
  for(int i=0;i<=5; i++)
    vvod(btnPin[i], i);

  if ((health < 50) && (health > 40)) {
    digitalWrite(ledPin[5], LOW);
  }
  if ((health <= 40) && (health > 30)) {
    digitalWrite(ledPin[4], LOW);
  }
  if ((health <= 30) && (health > 20)) {
    digitalWrite(ledPin[3], LOW);
  }
  if ((health <= 20) && (health > 10)) {
    digitalWrite(ledPin[2], LOW);
  }
  if ((health <= 10) && (health > 0)) {
    digitalWrite(ledPin[1], LOW);
  }
  if (health <= 0) {
    digitalWrite(ledPin[0], LOW); 
  } 

}

 

HOCKU
HOCKU аватар
Offline
Зарегистрирован: 25.04.2011

 А огромное количество условий можно заменить на

digitalWrite(ledPin[ceil(float(health)/10)], 0);
LEVV2006
LEVV2006 аватар
Offline
Зарегистрирован: 15.04.2011

Я не понимаю что делает эта строка

Особенно сeil…
 

Mad Fun
Offline
Зарегистрирован: 19.11.2011

Сразу скажу, что я новичек в программировании микроконтроллеров.. спасибо LEVV2006 за то, что обратил внимание на то, что единицы все равно отнимаются, а на счет светодиодов, то они должны загорется из-за условия:

} else {
digitalWrite(LED1, HIGH);
digitalWrite(LED2, HIGH);
digitalWrite(LED3, HIGH);
digitalWrite(LED4, HIGH);
digitalWrite(LED5, HIGH);
digitalWrite(LED6, HIGH);
}

или лучше записать в функцию setup()?

HOCKU, на сколько я пониял, описанная вами функция заменяет все if?

LEVV2006
LEVV2006 аватар
Offline
Зарегистрирован: 15.04.2011

Я так понял из задания что они горят изначально, а потом выключаются по одному в зависимости от числа health. И больше ничего не происходит. То есть когда число health меньше 0 то гасятся последний светодиод и чтобы начать всё сначала необходимо перезагрузить микроконтроллер. Если так то можно включить их сразу в функции setup() и не париться. Тебе останется только выключать их и всё. 

HOCKU
HOCKU аватар
Offline
Зарегистрирован: 25.04.2011

LEVV2006 пишет:

Я не понимаю что делает эта строка

Особенно сeil…

float(health) приводит health к дробному типу данных. Это необходимо для того, чтобы после деления получилось число с плавающей точкой (дробное). Если этого не сделать, то например 25/10 = 2

ceil округляет число до большнго (ceiling = потолок).  ceil(2)=2; ceil(2.1)=3; ceil(2.7)=3; ceil(3)=3;

Еще кстати есть команда floor, которая округляет до меньшего.

Таким образом в результате операции ceil(float(health)/10), число будет поделено на 10 и округлено до большего.

Mad Fun
Offline
Зарегистрирован: 19.11.2011

LEVV2006, вы абсолютно правы, задача программы именно такая.

HOCKU, спасибо за объяснение.

В итоге получился такой код:

#define RF 1
#define RC 2
#define RT 3
#define LF 4
#define LC 5
#define LT 6
#define LED1 7
#define LED2 8
#define LED3 9
#define LED4 10
#define LED5 11
#define LED6 12

int health = 60;
int valRF = 0;
int valRC = 0;
int valRT = 0;
int valLF = 0;
int valLC = 0;
int valLT = 0;

void setup()
{
pinMode(RF, INPUT);
pinMode(RC, INPUT);
pinMode(RT, INPUT);
pinMode(LF, INPUT);
pinMode(LC, INPUT);
pinMode(LT, INPUT);
pinMode(LED1, OUTPUT);
pinMode(LED2, OUTPUT);
pinMode(LED3, OUTPUT);
pinMode(LED4, OUTPUT);
pinMode(LED5, OUTPUT);
pinMode(LED6, OUTPUT);
digitalWrite(LED1, HIGH);
digitalWrite(LED2, HIGH);
digitalWrite(LED3, HIGH);
digitalWrite(LED4, HIGH);
digitalWrite(LED5, HIGH);
digitalWrite(LED6, HIGH);
}

void loop()
{
valRF = digitalRead(RF);
valRC = digitalRead(RC);
valRT = digitalRead(RT);
valLF = digitalRead(LF);
valLC = digitalRead(LC);
valLT = digitalRead(LT);
health = health-valRF-valRC-valRT-valLF-valLC-valLT;
digitalWrite(LED[ceil(float(health)/10)+1], LOW);
}

В строчке "digitalWrite(LED[ceil(float(health)/10)+1], LOW)" +1 добавлено для того, чтобы начальном значении переменной health = 60, все светодиоды горели.

Mad Fun
Offline
Зарегистрирован: 19.11.2011

Хм, программа жалуется на строчку

digitalWrite(LED[ceil(float(health)/10)+1], LOW);

 

 

step962
Offline
Зарегистрирован: 23.05.2011

Опять-таки - как жалуется? Что пишет?

Что-то мне подсказывает, что жалуется не программа (судя по исходному коду - ей просто нечем), а компилятор.

Укажите, какое именно сообщение выдается.

Пока нет более подробной информации, рискну предположить, что проблема в обратном преобразовании вещественного типа к целому, который необходим для индексации массива.

Попробуйте переписать строчку в виде

digitalWrite(LED[int(ceil(float(health)/10))+1], LOW);

или

digitalWrite(LED[(int)ceil(float(health)/10)+1], LOW);

Надеюсь, что поможет.

LEVV2006
LEVV2006 аватар
Offline
Зарегистрирован: 15.04.2011

Проблема в том что LED это должен быть массив (из моего переделанного кода(ledPin) который я писал выше) а у вас это просто число которое даже не объявлено. 

HOCKU спасибо. Надо будет не забыть)))))
 

step962
Offline
Зарегистрирован: 23.05.2011

Присмотрелся повнимательнее.

А где у вас объявление массива LED?

Если хотите работать "одной строчкой", то после блока #define поставьте объявление массива:

int LED[7]={0,LED1,LED2,LED3,LED4,LED5,LED6};

Mad Fun
Offline
Зарегистрирован: 19.11.2011

 Спасибо всем за коментарии, вот что получилось:

#define RF 1
#define RC 2
#define RT 3
#define LF 4
#define LC 5
#define LT 6
#define LED1 7
#define LED2 8
#define LED3 9
#define LED4 10
#define LED5 11
#define LED6 12

int LED[7]={0,LED1,LED2,LED3,LED4,LED5,LED6};

int health = 60;
int valRF = 0;
int valRC = 0;
int valRT = 0;
int valLF = 0;
int valLC = 0;
int valLT = 0;

void setup()
{
pinMode(RF, INPUT);
pinMode(RC, INPUT);
pinMode(RT, INPUT);
pinMode(LF, INPUT);
pinMode(LC, INPUT);
pinMode(LT, INPUT);
pinMode(LED1, OUTPUT);
pinMode(LED2, OUTPUT);
pinMode(LED3, OUTPUT);
pinMode(LED4, OUTPUT);
pinMode(LED5, OUTPUT);
pinMode(LED6, OUTPUT);
digitalWrite(LED1, HIGH);
digitalWrite(LED2, HIGH);
digitalWrite(LED3, HIGH);
digitalWrite(LED4, HIGH);
digitalWrite(LED5, HIGH);
digitalWrite(LED6, HIGH);
}

void loop()
{
valRF = digitalRead(RF);
valRC = digitalRead(RC);
valRT = digitalRead(RT);
valLF = digitalRead(LF);
valLC = digitalRead(LC);
valLT = digitalRead(LT);
health = health-valRF-valRC-valRT-valLF-valLC-valLT;
digitalWrite(LED[int(ceil(float(health/10)+1))], LOW);
}

Вроде скомпилировалось, позже отпишусь как работает..

Mad Fun
Offline
Зарегистрирован: 19.11.2011

Наконец-то все работает, как я и хотел изначально. Вот итоговый код:

#define RF 1
#define RC 2
#define RT 3
#define LF 4
#define LC 5
#define LT 6
#define LED1 7
#define LED2 8
#define LED3 9
#define LED4 10
#define LED5 11
#define LED6 12

int LED[7]={0,LED1,LED2,LED3,LED4,LED5,LED6};

int health = 60;
int valRF = 0;
int valRC = 0;
int valRT = 0;
int valLF = 0;
int valLC = 0;
int valLT = 0;
int a = 0;
int k = 0;
int b1 = 0;
int b2 = 0;
int b3 = 0;
int b4 = 0;
int b5 = 0;
int b6 = 0;

void setup()
{
pinMode(RF, INPUT);
pinMode(RC, INPUT);
pinMode(RT, INPUT);
pinMode(LF, INPUT);
pinMode(LC, INPUT);
pinMode(LT, INPUT);
pinMode(LED1, OUTPUT);
pinMode(LED2, OUTPUT);
pinMode(LED3, OUTPUT);
pinMode(LED4, OUTPUT);
pinMode(LED5, OUTPUT);
pinMode(LED6, OUTPUT);
digitalWrite(LED1, HIGH);
digitalWrite(LED2, HIGH);
digitalWrite(LED3, HIGH);
digitalWrite(LED4, HIGH);
digitalWrite(LED5, HIGH);
digitalWrite(LED6, HIGH);
}

void loop()
{
valRF = digitalRead(RF);
if (valRF == HIGH) {
if (b1 == 0) {
k = k+1;

}
b1 = 1;
} else {
b1 = 0;
}
valRC = digitalRead(RC);
if (valRC == HIGH) {
if (b2 == 0) {
k = k+1;

}
b2 = 1;
} else {
b2 = 0;
}
valRT = digitalRead(RT);
if (valRT == HIGH) {
if (b3 == 0) {
k = k+1;

}
b3 = 1;
} else {
b3 = 0;
}
valLF = digitalRead(LF);
if (valLF == HIGH) {
if (b4 == 0) {
k = k+1;

}
b4 = 1;
} else {
b4 = 0;
}
valLC = digitalRead(LC);
if (valLC == HIGH) {
if (b5 == 0) {
k = k+1;

}
b5 = 1;
} else {
b5 = 0;
}
valLT = digitalRead(LT);
if (valLT == HIGH) {
if (b6 == 0) {
k = k+1;

}
b6 = 1;
} else {
b6 = 0;
}
health = health - k;
k = 0;
a = ceil(float(health/10)+1);
digitalWrite(LED[a], LOW);
}

Хочу отметить момент, который вызвал у меня затруднение, я не знал о необходимости использования pull-down резисторов на входах для получения нуля, т.к. предполагал что там изначально ноль..

Вот фото 

http://saveimg.ru/show-image.php?id=bf46d614f33e988791fe9e3fa4974d94

На подключенной плате располагается стабилизатор питания и 4 резистора 4,7 КОм.

 

step962
Offline
Зарегистрирован: 23.05.2011

Mad Fun пишет:

Наконец-то все работает, как я и хотел изначально. Вот итоговый код:

[...]

void setup()

{
pinMode(RF, INPUT);
pinMode(RC, INPUT);
pinMode(RT, INPUT);
pinMode(LF, INPUT);
pinMode(LC, INPUT);
pinMode(LT, INPUT);
pinMode(LED1, OUTPUT);
pinMode(LED2, OUTPUT);
pinMode(LED3, OUTPUT);
pinMode(LED4, OUTPUT);
pinMode(LED5, OUTPUT);
pinMode(LED6, OUTPUT);
digitalWrite(LED1, HIGH);
digitalWrite(LED2, HIGH);
digitalWrite(LED3, HIGH);
digitalWrite(LED4, HIGH);
digitalWrite(LED5, HIGH);
digitalWrite(LED6, HIGH);

}

Нк и на кой вы массив вводили???

Срочно переделайте выделение на

for(i=1;i<7;i++) {
  pinMode(LED[i], OUTPUT);
  digitalWrite(LED[i], HIGH); 
}

 

Mad Fun
Offline
Зарегистрирован: 19.11.2011

 Спасибо за замечание)) Я только начинаю программировать и поэтому оптимизация у меня еще хромает..