Например TDA7294

Форум РадиоКот • Просмотр темы - Считаем импульсы, вращаем моторчик)
Форум РадиоКот
Здесь можно немножко помяукать :)





Текущее время: Вт апр 23, 2024 18:34:47

Часовой пояс: UTC + 3 часа


ПРЯМО СЕЙЧАС:



Начать новую тему Ответить на тему  [ Сообщений: 2 ] 
Автор Сообщение
Не в сети
 Заголовок сообщения: Считаем импульсы, вращаем моторчик)
СообщениеДобавлено: Пн фев 20, 2017 21:17:01 
Родился

Зарегистрирован: Ср ноя 16, 2016 07:04:33
Сообщений: 9
Откуда: Одесса
Рейтинг сообщения: 0
Здраствуйте, уважаемые форумчане!
Написал программку, все работает, но немного не так как надо :(
Суть: считаем импульсы на входе, в зависимости от их кол-ва приводим в действие исполнительный механизм (моторчик и концевик, сигнализирующий о необходимости выключения моторчика). Новые импульсы могут прийти во время работы мотора, потому создал переменную для хранения кол-ва циклов включения мех-ма "ball". На случай поломки концевика(INT1), каждый цикл включения мотора ограничен по времени (TIMER2_OVF_vect). Входящие импульсы принимаем на INT0, в случае окончания пакета импульсов не будет в течении пол секунды, считаем (TIMER1_OVF_vect). Все работает, НО при опыте, вместо 10 необходимых срабатываний концевичка, хватает 8..9 иногда 10 для завершения работы, т.е. Должны выдать 10 мячиков, выдаем 8. Я только учусь, поэтому буду благодарен каждому тычку носом в проблемные места :)
Код:
#define F_CPU 1000000
#include <avr/io.h>
#include <util/delay.h>
#include <avr/interrupt.h>


volatile uint8_t timer0_counter = 0;   //счетчик таймера макс длинны импульса
volatile uint8_t imp = 0;   //подсчет импульсов
volatile uint8_t ball = 0;   //подсчет, необходимого к выдачи, количества мячиков


ISR(INT0_vect){//принимаем импульсы с купброприемника
   GICR &= ~(1 << INT0);   //выключаем прерывания от купюроприемника
   _delay_ms(20);
   if(!(PIND & (1 << 2))){
      GICR |= (1 << INT0);
      return;
   }
   TCNT0 = 0;            //
   timer0_counter = 0;      //настраиваем таймер длинны импульса
   TIMSK |= (1 << TOIE0);   //и включаем прерываниуе по переполнению таймера0
   imp++;         //считаем импульс
   GICR |= (1 << INT0);   //включаем прерывания от купюроприемника
   
}
ISR(TIMER0_OVF_vect){            //таймер длинны импульса
   timer0_counter++;               //по истечению мы понимаем, что пакет импульсов от купюроприемника
   if(timer0_counter > 3){         //принят, и назначаем количество выдаваемых мячиков, увеличивая значение
      TIMSK &= ~(1 << TOIE0);         // буферной переменной ball
      if(imp > 4 && imp < 6){
         ball++;
         imp = 0;
         return;
      }
      else if(imp > 9 && imp < 11){
         ball += 2;
         imp = 0;
         return;
      }
      else if (imp >19 && imp < 21){
         ball += 4;
         imp = 0;
         return;
      }
      else if (imp > 49 && imp < 51){
         ball += 10;
         imp = 0;
         return;
      }
   }
}

volatile uint8_t flag = 0;   //флаг отключения мотора, по признаку срабатывания концевика INT1 либо исхода макс времени работы мотора
volatile int timer2_counter = 0;//счетчик длительности работы мотора

ISR(INT1_vect){         //концевик выключения мотора
   GICR &= ~(1 << INT1);
   flag = 1;
   _delay_ms(300);
}

ISR(TIMER2_OVF_vect){   //таймер выключения мотора ~5 секунд
   timer2_counter++;
   if(timer2_counter > 15){
      flag = 2;
      TIMSK &= ~(1 << TOIE2);
   }
   
}




int main(void)
{
   MCUCR = (1 << ISC01)|(1 << ISC00)|(1 << ISC11);
   GICR = (1 << INT0);
   TCCR0 = (1 << CS02)|(1 << CS00);
   TCCR2 = (1 << CS22)|(1 << CS21)|(1 << CS20);
   TIMSK = 0;
   DDRD = 1;
   PORTD = 0;
   sei();
   while(1)
   {
      if(ball > 0 && !(PIND &(1<<0))){      //включаем мотор
         PORTD |= (1 << 0);
         GICR |= (1 << INT1);//включаем прерывание от концевика
         timer2_counter = 0;
         TCNT2 = 0;
         TIMSK |= (1 << TOIE2);// настраиваем и включаем таймер длительности работы мотора
         flag = 0;
      }
      if(flag != 0 && (PIND &(1<<0))){      //выключаем мотор
         PORTD &= ~(1 << 0);
         GICR &= ~(1 << INT1);//выкл прерывание от концевика
         TIMSK &= ~(1 << TOIE2);//выкл таймер длительности работы мотора
         ball--;
         //flag = 0;
      }
      
   }
}


И схемка [img][url=http://img.radiokot.ru/files/119676/medium/17bk7b5cc1.jpg][/img]


Вернуться наверх
 
Не в сети
 Заголовок сообщения: Re: Считаем импульсы, вращаем моторчик)
СообщениеДобавлено: Ср фев 22, 2017 14:01:49 
Встал на лапы
Аватар пользователя

Карма: 1
Рейтинг сообщений: 19
Зарегистрирован: Пн ноя 02, 2009 05:27:41
Сообщений: 119
Откуда: С-Пб
Рейтинг сообщения: 0
Я бы для начала избавился от задержек в прерываниях, как-то это не по-кошачьи.
Затем, нарисовал бы алгоритм работы сего аппарата и уже после разделил на блоки и написал код.
А тут как-то видать все решалось по ходу пьесы. И уже к тому, что написано приклеивался новый код.
Видать сначала был написан код учитывающий работу концевых датчиков, а потом приклеился таймаут, если
концевик сломался.. и поехали ошибки.


Вернуться наверх
 
Показать сообщения за:  Сортировать по:  Вернуться наверх
Начать новую тему Ответить на тему  [ Сообщений: 2 ] 

Часовой пояс: UTC + 3 часа


Кто сейчас на форуме

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


Вы не можете начинать темы
Вы не можете отвечать на сообщения
Вы не можете редактировать свои сообщения
Вы не можете удалять свои сообщения
Вы не можете добавлять вложения

Найти:
Перейти:  


Powered by phpBB © 2000, 2002, 2005, 2007 phpBB Group
Русская поддержка phpBB
Extended by Karma MOD © 2007—2012 m157y
Extended by Topic Tags MOD © 2012 m157y