Проблема с прерываниями яркость или на одном уровне или медленно плавно самопроизвольно меняется
- Войдите на сайт для отправки комментариев
Ср, 29/10/2014 - 11:02
//Прерыания по спаду и наростанию работают нормально. #include <avr/io.h> #include <avr/interrupt.h> #define SIMISTOR_OFF_TIME 65500 // т.е. отключение при значении стчетчика 65535 #define SIMISTOR_PIN 10 // выход для симистора #define LED_PIN 13 volatile int i=0;//перменнная мигания светодиодом volatile int period=3; //период установится после прерывания volatile unsigned int Delay_On=55700;//начало отсчета задержки на выключение max= 65400 c с учетом времени на отключение min=45535 volatile boolean Front;//какой у нас фронт положительный или отрицательный полупериод volatile boolean schet;//меняет свое состояние с каждым положительным полупериодом //int analogPin = 3; // номер порта к которому подключен потенциометр //int val = 0; // переменная для хранения считываемого значения ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// //----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// void setup() { cli(); // disable global interrupts TCCR1A=0; TCCR1B = (0<<CS12)|(1<<CS11)|(0<<CS10); // настраиваем делитель на 8 таймера 1 //1600000/8=2000000;1/2000000=0.0000005c * 65535=0,0327675сек переполнение //0.01сек длительность полупериода(при 50гц).(65535*0,01)/0.0327675=20000 отсчетов таймер сделает за 0,01 сек //значит эти 20000 мы будем отсчитывать между 45535 и 65535 pinMode(SIMISTOR_PIN, OUTPUT); pinMode(LED_PIN, OUTPUT); TCNT1 = Delay_On; // выставляем начальное значение в счетном регистре TCNT1//задержка на включение sei(); // выставляем бит общего разрешения прерываний attachInterrupt(0, FrontUp, RISING); //разрешаем прерывание по изменению уровня с низкого на высокий } ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// //------------------------------------------------------------------ Функция обработки прерывания на подъем -------------------------------------------------------------------------- ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// void FrontUp() { schet=!schet; i++; if(i>100) { digitalWrite(LED_PIN, HIGH); } Front=1; detachInterrupt(0); //отключаем внешние прерывания period=1; //положительный полупериод TIMSK1 |= (1<<TOIE1); // разрешаем прерывание по переполнению таймера 1 } ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// //------------------------------------------------------------------ Функция обработки прерывания на спад ---------------------------------------------------------------------------- ////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// void FrontDown() { i++; if(i>200) { digitalWrite(LED_PIN, LOW); i=0; } Front=0; detachInterrupt(0); //отключаем прерывания period=1; //отрицатеьный полупериод TIMSK1 |= (1<<TOIE1); // разрешаем прерывание по переполнению таймера 1 } ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// //-//-----------------------------------------------------------------функция обработки прерывания по переполнению таймера 1----------------------------------------------------------- ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// ISR( TIMER1_OVF_vect )//сработало прерывание по переполнению таймера TCNT1 = Delay_On; { if(period==1) { digitalWrite(SIMISTOR_PIN, HIGH); TCNT1 = SIMISTOR_OFF_TIME ; // выставляем время на отключение симстора period=0; } else { digitalWrite(SIMISTOR_PIN, LOW); TIMSK1 &= ~(1<<TOIE1); // запрещаем прерывание по переполнению таймера 1 TCNT1 = Delay_On; // выставляем начальное значение TCNT1//задержка на включение if (Front)attachInterrupt(0, FrontDown, FALLING) ;//настраиваем прерывание по спаду else attachInterrupt(0, FrontUp, RISING); //прерывание по изменению уровня с низкого на высокий } } ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// /////----------------------------------------------------------------- оснавная программа-------------------------------------------------------------------------------------------- ///////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// void loop() { if(schet)Delay_On=45600+10; if(Delay_On>65535)Delay_On=0; // val = analogRead(analogPin); // считываем значение //0-0,01сек = 0-20000 отсчетов таймера начиная с 45535 до 65535 //interval = 5000; // Delay_On=;//расчет задержки }