Светодиод и кнопка

Модератор: boogyman

Светодиод и кнопка

Сообщение:#1  Сообщение winston1777 » 18 май 2014, 13:26

Привет всем ! Помогите новичку в написании программы на C в Codevisionavr. Чтобы когда на кнопку нажимая светодиод загорался, еще раз нажимая он погас ?
Аватара пользователя
winston1777
Новичок
 
Сообщения: 1
Зарегистрирован: 18 май 2014, 13:22

Re: Светодиод и кнопка

Сообщение:#2  Сообщение AntonChip » 19 май 2014, 14:44

Светодиод подключен к PB0, кнопка подключена к PD0
Код: Выделить всё
char temp = 0;

while(1)
{
if(PIND.0 == 0} // Проверяем нажатие кнопки
{
while(PIND.0 == 0){}// Ждем отпускания кнопки
temp++;
delay_ms(100);
}

if(temp)
{
PORTB.0 = 1; // зажигаем светодиод
}

if(temp == 0)
{
PORTB.0 = 0; // гасим светодиод
}

if(temp > 1)
{
temp = 0;
}

}
Аватара пользователя
AntonChip
Администратор
 
Сообщения: 190
Зарегистрирован: 24 дек 2011, 21:11
Откуда: Киров

Re: Светодиод и кнопка

Сообщение:#3  Сообщение AntonChip » 01 июл 2014, 06:38

Специально для Рената пример кода синхронного мигания светодиодов, с использованием прерываний от двух таймеров. Кнопки подключены к PC3 - 0, светодиоды к PD3 - 0

Код: Выделить всё
#include <avr/io.h>
#include <avr/interrupt.h>
#include <util/delay.h>

char s_1 = 0, s_2 = 0, s_3 = 0, s_4 = 0;

volatile char pwm_counter_0, pwm_counter_2;

///////////////////////////////////////////////////////////////////////////
/////////////  Обработчик прерывания по переполнению Т0      //////////////
/////////////  Индикация включенного состоянии светодиодов, мигание  //////
///////////////////////////////////////////////////////////////////////////

ISR (TIMER0_OVF_vect)
{
pwm_counter_0++;

if(pwm_counter_0 > 40)
{
  if(s_1)
  PORTD &= ~(1 << PD0);
  if(s_2)
  PORTD &= ~(1 << PD1);
  if(s_3)
  PORTD &= ~(1 << PD2);
  if(s_4)
  PORTD &= ~(1 << PD3);
  pwm_counter_0 = 0;
}

if(pwm_counter_0 > 20 && s_1)
PORTD |= (1 << PD0);
if(pwm_counter_0 > 20 && s_2)
PORTD |= (1 << PD1);
if(pwm_counter_0 > 20 && s_3)
PORTD |= (1 << PD2);
if(pwm_counter_0 > 20 && s_4)
PORTD |= (1 << PD3);
}

///////////////////////////////////////////////////////////////////////////
/////////////  Обработчик прерывания по переполнению Т2      //////////////
/////////////  Индикация выключенного состоянии светодиодов  //////////////
///////////////////////////////////////////////////////////////////////////

ISR (TIMER2_OVF_vect)
{
pwm_counter_2++;

if(pwm_counter_2 > 40)
{
  if(s_1 == 0)
  PORTD &= ~(1 << PD0);
  if(s_2 == 0)
  PORTD &= ~(1 << PD1);
  if(s_3 == 0)
  PORTD &= ~(1 << PD2);
  if(s_4 == 0)
  PORTD &= ~(1 << PD3);
  pwm_counter_2 = 0;
}

}

///////////////////////////////////////////////////////////////////////////
//////                    Основная программа               ////////////////
///////////////////////////////////////////////////////////////////////////

int main (void)
{

DDRD = 0xFF; // Выход
PORTD = 0x00;

DDRC = 0x00; // Вход
PORTC = 0xFF;

TCCR0 = (1 << CS02); // clkI/O/256 (From prescaler)
TIMSK |= (1 << TOIE0); // разрешение прерывания от таймера

TCCR2 |= (1 << CS21); // clkI/O/8 (From prescaler)
TIMSK |= (1 << TOIE2); // разрешение прерывания от таймера

sei();

while(1)
{

///////////////////////////////////////////////////////////////////////////
/////////////             Управление кнопкой 1               //////////////
///////////////////////////////////////////////////////////////////////////     
  if((PINC & ( 1 << PC0)) == 0)
   {
    while((PINC & ( 1 << PC0)) == 0){} // Ждем отпускания кнопки
   _delay_ms(10);
    s_1++;
   if(s_1 > 1) s_1 = 0;
   }

///////////////////////////////////////////////////////////////////////////
/////////////             Управление кнопкой 2               //////////////
///////////////////////////////////////////////////////////////////////////     
  if((PINC & ( 1 << PC1)) == 0)
   {
    while((PINC & ( 1 << PC1)) == 0){}
   _delay_ms(10);
    s_2++;
   if(s_2 > 1) s_2 = 0;
   }

///////////////////////////////////////////////////////////////////////////
/////////////             Управление кнопкой 3               //////////////
///////////////////////////////////////////////////////////////////////////     
  if((PINC & ( 1 << PC2)) == 0)
   {
    while((PINC & ( 1 << PC2)) == 0){}
   _delay_ms(10);
    s_3++;
   if(s_3 > 1) s_3 = 0;
   }

///////////////////////////////////////////////////////////////////////////
/////////////             Управление кнопкой 4               //////////////
///////////////////////////////////////////////////////////////////////////     
  if((PINC & ( 1 << PC3)) == 0)
   {
    while((PINC & ( 1 << PC3)) == 0){}
   _delay_ms(10);
    s_4++;
   if(s_4 > 1) s_4 = 0;
   }
 
}
}

Аватара пользователя
AntonChip
Администратор
 
Сообщения: 190
Зарегистрирован: 24 дек 2011, 21:11
Откуда: Киров

Re: Светодиод и кнопка

Сообщение:#4  Сообщение Renat » 02 июл 2014, 06:55

В общем хотел промоделировать твой код на протеусе, и хотел скомпилировать его. Ругается на <avr/io> на interrupt и на ISR (TIMER0_OVF_vect).
Даже не знаю с какой стороны подойти... SOS...SOS....SOS.. :roll:
Аватара пользователя
Renat
Любитель
 
Сообщения: 14
Зарегистрирован: 02 июл 2014, 06:24

Re: Светодиод и кнопка

Сообщение:#5  Сообщение Renat » 02 июл 2014, 08:02

#include <mega16.h>
#include <delay.h>
// Declare your global variables here

void main(void)
{
// Port A initialization
PORTA=0x00;
DDRA=0x00;


// Port B initialization
PORTB=0x00;
DDRB=0x00;

// Port C initialization

PORTC=0b11111111;
DDRC=0b11111111;

// Port D initialization
PORTD=0b11111111;
DDRD=0b11111111;

while (1)
{
if (PINA.0==0)
{
PORTC.0=1;
delay_ms(500);
PORTC.0=0;
delay_ms(810000);
PORTC.0=1;
delay_ms(500);
PORTC.0=0;
delay_ms(60000);
}
else if(PINA.1==0)
{
PORTC.1=1;
delay_ms(500);
PORTC.1=0;
delay_ms(810000);
PORTC.1=1;
delay_ms(500);
PORTC.1=0;
delay_ms(60000);
}
else if(PINA.2==0)
{
PORTC.2=1;
delay_ms(500);
PORTC.2=0;
delay_ms(810000);
PORTC.2=1;
delay_ms(500);
PORTC.2=0;
delay_ms(60000);
}
if (PINA.3==0)
{
PORTC.3=1;
delay_ms(500);
PORTC.3=0;
delay_ms(228000);
PORTC.3=1;
delay_ms(500);
PORTC.3=0;
delay_ms(60000);
}
if (PINA.4==0)
{
PORTC.4=1;
delay_ms(500);
PORTC.4=0;
delay_ms(111000);
PORTC.4=1;
delay_ms(500);
PORTC.4=0;
delay_ms(60000);
}
if (PINA.5==0)
{
PORTC.5=1;
delay_ms(500);
PORTC.5=0;
delay_ms(111000);
PORTC.5=1;
delay_ms(500);
PORTC.5=0;
delay_ms(60000);
}
if (PINA.6==0)
{
PORTC.6=1;
delay_ms(500);
PORTC.6=0;
delay_ms(111000);
PORTC.6=1;
delay_ms(500);
PORTC.6=0;
delay_ms(60000);
}
if (PINA.7==0)
{
PORTC.7=1;
delay_ms(500);
PORTC.7=0;
delay_ms(111000);
PORTC.7=1;
delay_ms(500);
PORTC.7=0;
delay_ms(60000);
}



}
}
Вот такой код был у меня, и именно такой нужен. Только чтоб все работало одновременно. А где и как настраивать время с таймером и прерываниями, я не понимаю((((
Аватара пользователя
Renat
Любитель
 
Сообщения: 14
Зарегистрирован: 02 июл 2014, 06:24

Re: Светодиод и кнопка

Сообщение:#6  Сообщение AntonChip » 02 июл 2014, 10:42

А задержки разные между переключениями светодиодов разные, это так и должно быть?
Аватара пользователя
AntonChip
Администратор
 
Сообщения: 190
Зарегистрирован: 24 дек 2011, 21:11
Откуда: Киров

Re: Светодиод и кнопка

Сообщение:#7  Сообщение Renat » 03 июл 2014, 09:35

Да, на самом деле мне нужен сигнал 0.5 сек. для включения выпрямителей, после включения через определенное время их нужно снова выключить(снова сигнал 0.5 сек.). Для простоты, чтоб наглядно увидеть я поставил светодиоды.
Аватара пользователя
Renat
Любитель
 
Сообщения: 14
Зарегистрирован: 02 июл 2014, 06:24

Re: Светодиод и кнопка

Сообщение:#8  Сообщение AntonChip » 03 июл 2014, 16:20

При нажатии и удержании на кнопку должно быть постоянное переключение выхода или одноразовое? Просто не вникну в суть задачи
Аватара пользователя
AntonChip
Администратор
 
Сообщения: 190
Зарегистрирован: 24 дек 2011, 21:11
Откуда: Киров

Re: Светодиод и кнопка

Сообщение:#9  Сообщение Renat » 04 июл 2014, 07:08

Вот смотри, пришел сигнал с датчика. Когда приходит сигнал с датчика, у меня порт, где стоят кнопки, заземляется через оптрон. То есть кнопка постоянно нажата. В это время начинается цикл. 0.5 секунд сигнал 5 вольт на порте где светодиоды, и снова ноль в течении некоторого времени. Потом снова 0.5 секунд сигнал и в течении минуты снова ноль. Время, как на выходе появилось 5 вольт, исчезло, снова появилось через некоторое время и исчезло примерно равно времени нажатого состояния кнопки. Постоянного переключения быть не должно. Если даже по каким то причинам сигнал исчез с датчика на секунду и снова появился цикл должен работать не обращая на это внимания пока не законцится
Аватара пользователя
Renat
Любитель
 
Сообщения: 14
Зарегистрирован: 02 июл 2014, 06:24

Re: Светодиод и кнопка

Сообщение:#10  Сообщение Renat » 08 июл 2014, 07:54

есть мысли?
Аватара пользователя
Renat
Любитель
 
Сообщения: 14
Зарегистрирован: 02 июл 2014, 06:24

Re: Светодиод и кнопка

Сообщение:#11  Сообщение Renat » 09 июл 2014, 06:35

Антооооон))) Такое возможно вообще? чтоб микроконтроллер выполнял несколько задач одновременно? Я читал про прерывания, и так и не понял, то ли процессор останавливается и выполняет команду, то ли в фоновом режиме выполняет разные команды. И если в моем случае применить прерывания на все 8 кнопок, и если придет сигнал со всех кнопок одновременно, микроконтроллер сможет обработать все команды?
Аватара пользователя
Renat
Любитель
 
Сообщения: 14
Зарегистрирован: 02 июл 2014, 06:24

Re: Светодиод и кнопка

Сообщение:#12  Сообщение Renat » 09 июл 2014, 06:37

http://www.ap-impulse.ru/podklyuchaem-k ... r-shag-12/ вот здесь есть что то подобное, но я не могу написать программу от и до чтоб она скомпилировалась без ошибок((
Аватара пользователя
Renat
Любитель
 
Сообщения: 14
Зарегистрирован: 02 июл 2014, 06:24

Re: Светодиод и кнопка

Сообщение:#13  Сообщение Renat » 09 июл 2014, 06:38

здесь есть кто?((
Аватара пользователя
Renat
Любитель
 
Сообщения: 14
Зарегистрирован: 02 июл 2014, 06:24

Re: Светодиод и кнопка

Сообщение:#14  Сообщение Renat » 11 июл 2014, 05:07

я забыт? или это с прерываниями нельзя сделать? Скажите что нибудь, или я реализую это на 8 МК((
Аватара пользователя
Renat
Любитель
 
Сообщения: 14
Зарегистрирован: 02 июл 2014, 06:24

Re: Светодиод и кнопка

Сообщение:#15  Сообщение AntonChip » 13 июл 2014, 11:09

Все 8 кнопок можно опрашивать по прерыванию таймера, например сделать чтобы прерывание было каждые 10мс, а в самом цикле прерывания смотреть какой сигнал будет с кнопок, лог. 0 или лог. 1. Останется свободных еще 2 таймера, а их использовать для синхронного включения выключения нагрузки.
Аватара пользователя
AntonChip
Администратор
 
Сообщения: 190
Зарегистрирован: 24 дек 2011, 21:11
Откуда: Киров

Re: Светодиод и кнопка

Сообщение:#16  Сообщение Renat » 14 июл 2014, 09:34

Антон, посоветуй литературу, для дебилов)) и может это сделаем как занятие? я думаю что кому то в будущем пригодятся такие знания...
Аватара пользователя
Renat
Любитель
 
Сообщения: 14
Зарегистрирован: 02 июл 2014, 06:24

Re: Светодиод и кнопка

Сообщение:#17  Сообщение Renat » 18 июл 2014, 08:01

Я нашел код программы для 5 кнопок на атмега8
#include <inttypes.h>
#include <avr/io.h>
#include <avr/interrupt.h>
#include <avr/signal.h>

//////////////////////////////////////////////////////////////////
// Раздел функций
//////////////////////////////////////////////////////////////////

// Функция задержки. Минимальная задержка с кварцем 8MHz, равна около 1 ms

void delay_ms2(unsigned short ms)
{
unsigned short i, j, k;

for (i=0; i<ms; i++) /* цикл формирования временной задержки */
for(j=0; j<185;j++) /* вложенный цикл формирования временной задержки */
k++; /* произвольное действие */
}



// signal handler для внешнего прерывания int0

SIGNAL(SIG_INTERRUPT0)
{

PORTD &= ~_BV(PD1);// Сбросить бит PD1 в "0" = 0V, светодиод выключен , pin=0V
delay_ms2(1000); // Ждем 1 сек.
PORTD |= _BV(PD1); // Установить бит PD1 в "1" = 5V, светодиод включен, pin=1V


}

//////////////////////////////////////////////////////////////////



int main(void) // ОСНОВНАЯ ПРОГРАММА
{


DDRD |= 1<<1; // вывод 1 порта D работает на вывод
PORTD |= _BV(PD1); // инициализировать начальное состояние, установить бит PD1 в "1"

DDRD &= ~(0<<2); // вывод 2 порта D работает на ввод
PORTD |= _BV(PD2); // активизировать подтягивающий резистор

GIMSK = 1<<INT0; // разрешить внешнее прерывание Int0
MCUCR = 1<<ISC01; // сигнал низкого уровня на Int0 вызовет внешнее прерывание

sei(); // разрешить прерывания

for (;;) { } // бесконечный цикл

}
и нифига не понятно что и как делается((
Аватара пользователя
Renat
Любитель
 
Сообщения: 14
Зарегистрирован: 02 июл 2014, 06:24

Re: Светодиод и кнопка

Сообщение:#18  Сообщение Renat » 18 июл 2014, 08:05

Допустим как мне в этом примере сделать так чтоб при нажатии кнопки на выходе появился сигнал на 0.5 сек. и появился через 14 минут снова на 0.5 сек?
Аватара пользователя
Renat
Любитель
 
Сообщения: 14
Зарегистрирован: 02 июл 2014, 06:24

Re: Светодиод и кнопка

Сообщение:#19  Сообщение Renat » 18 июл 2014, 08:09

где обозначения пинов под кнопки? где обозначение пинов под светодиоды?
Аватара пользователя
Renat
Любитель
 
Сообщения: 14
Зарегистрирован: 02 июл 2014, 06:24

Re: Светодиод и кнопка

Сообщение:#20  Сообщение Renat » 18 июл 2014, 08:11

где настраивается прерывание от кнопки?
Аватара пользователя
Renat
Любитель
 
Сообщения: 14
Зарегистрирован: 02 июл 2014, 06:24

След.

Вернуться в Микроконтроллеры AVR

Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 1

Rambler's Top100