Помогите, пожалуйста ,понять, почему не работает процедура опроса энкодера. Переписал код для JAL с ардуиновского скетча. На ардуине все работает. На JAL и 12f683 яркость светодиода регулируется только в одну сторону. Весь мозг сломал.. Скетч ардуино: Спойлер
Код:
/* ** Энкодер ** Для управлением яркостью LED используется энкодер Sparkfun */
int brightness = 120; // яркость LED, начинаем с половины int fadeAmount = 10; // шаг изменения яркости LED unsigned long currentTime; unsigned long loopTime; const int pin_A = 12; // pin 12 const int pin_B = 11; // pin 11 unsigned char encoder_A; unsigned char encoder_B; unsigned char encoder_A_prev=0;
void setup() { // declare pin 9 to be an output: pinMode(9, OUTPUT); // устанавливаем pin 9 как выход pinMode(pin_A, INPUT); pinMode(pin_B, INPUT); currentTime = millis(); loopTime = currentTime; }
void loop() { currentTime = millis(); if(currentTime >= (loopTime + 5)){ // проверяем каждые 5мс (200 Гц) encoder_A = digitalRead(pin_A); // считываем состояние выхода А энкодера encoder_B = digitalRead(pin_B); // считываем состояние выхода B энкодера if((!encoder_A) && (encoder_A_prev)){ // если состояние изменилось с положительного к нулю if(encoder_B) { // выход В в полож. сост., значит вращение по часовой стрелке // увеличиваем яркость, не более чем до 255 if(brightness + fadeAmount <= 255) brightness += fadeAmount; } else { // выход В в 0 сост., значит вращение против часовой стрелки // уменьшаем яркость, но не ниже 0 if(brightness - fadeAmount >= 0) brightness -= fadeAmount; }
} encoder_A_prev = encoder_A; // сохраняем значение А для следующего цикла
analogWrite(9, brightness); // устанавливаем яркость на 9 ножку
alias enc_a is pin_A4 --энкодер на 2 и 3 ноге pin_A4_direction = input
-- configure PWM pin_ccp1_direction = output include pwm_hardware pwm_max_resolution(1) --включили ШИМ на 5й ноге pwm1_on()
-- timer setup const TIMER0_ISR_RATE = 1000 -- 1 kHz isr rate const DELAY_SLOTS = 1 -- support slots include timer0_isr_interval timer0_isr_init() -- теперь мы можем отслеживать миллисекунды
--setting variables var byte pwm var bit old_a -- pwm = 0 pwm1_set_dutycycle_percent(pwm) --светодиод не светится
forever loop
if check_delay(0) then --если таймер нащелкал 5мсек set_delay(0, 5) --устанавливем новый интервал
if old_a & !enc_a then --если старое значение А высокое а новое низкое,тогда проверяем В if enc_b then if pwm!=254 then pwm = pwm + 1 end if --если В в высоком, то увеличиваем яркость end if if !enc_b then if pwm!=0 then pwm = pwm - 1 end if --если В в низком, то уменьшаем яркость end if pwm1_set_dutycycle_percent(pwm) end if
old_a = enc_a --запомнили значение входа А end if
end loop
Код Ридико видел,но в АВР не силен совершенно, не смогу перевести в JAL, не понимаю, что он там делает, синтаксис совершенно непонятен. Если можно, объясните на пальцах алгоритм. Насколько я понял, в коде Ридико запоминаются предыдущее и предпредыдущее состояния? Собственно, код: Спойлер
Код:
//!************************************************** //! Файл : button_enc.h //! Авторское право (с) : //! Разработка : //! Дата создания : //! Описание //! //!************************************************** #ifndef __button_enc_H__ #define __button_enc_H__
Я бы сделал прерывание (external interrupt) на эту ногу (по ниспадающему или возрастающему фронту, ХЗ какой энкодер), чтобы просто в главной было while(1). Можно ещё код немного оптимизировать. К примеру, вместо ф-ций
Код:
analogWrite(9, brightness);
записывать просто PORTXbits.RXY=1;
с
Код:
encoder_A = digitalRead(pin_A); // считываем состояние выхода А энкодера encoder_B = digitalRead(pin_B); // считываем состояние выхода B энкодера
аналогично. Про асм не говорю, это уже совсем хардкор.
Ну и кварц до 20Мгц внешний этот МК поддерживает.
Ваще я бы немого иначе сделал обработку.
Как-то так.
Состояние энкодера изменилось-->ext_int прерывание-->сбросить флаги-->определить направление-->счётчик крутилки-->крутилку не трогают, навскидку, 20мс?-->изменить яркость.
Открыта удобная площадка с выгодными ценами, поставляющая весь ассортимент продукции, производимой компанией MEAN WELL – от завоевавших популярность и известных на рынке изделий до новинок. MEAN WELL.Market предоставляет гарантийную и сервисную поддержку, удобный подбор продукции, оперативную доставку по России.
На сайте интернет-магазина посетители смогут найти обзоры, интересные статьи о применении, максимальный объем технических сведений.
Тут обнаружилось,что в Джале фигово реализованы прерывания =( всю работу по сохранению регистров и прочий лабутенах предполагается делать программисту в блоках, написанных на асме. Понятно, что первое, что я сделал, когда горшок таки начал варить, это попробовал провернуть тот же алгоритм, используя прерывания,для меня это новая непознанная тема. Как ни плясал,ничего не получается. Отладки как таковой не предусмотрено, прерывания работают(проверял с режимом сна), если есть forever loop с какой-либо полезной нагрузкой, ничего не пашет,значение переменной заполнения ШИМ не изменяется. Код с прерываниями: Спойлер
alias led is pin_A2 pin_A2_direction = output led = off
OPTION_REG_NGPPU = 0 --\ WPU_WPU4 = 1 -- подтяжка WPU_WPU5 = 1 --/ IOC_IOC5 = 1 --разрешаем прерывание OPTION_REG_INTEDG = 0 -- прерывание по переходу в низкий уровень INTCON_GIE = on -- глобальное разрешение прерываний INTCON_GPIF = off -- снимаем флаг прерывания по GPIO --
--setting variables var byte pwm_cnt, pwm = 10 --
procedure interrupt is -- обработчик прерывания по нажатию кнопки pragma interrupt if INTCON_GPIF then -- снимаем флаг прерывания по GPIO INTCON_GPIF = off INTCON_GPIE = off -- запрещаем прерывания по GPIO
if enc_a then if pwm!=254 then pwm = pwm + 1 end if else if pwm!=0 then pwm = pwm - 1 end if end if
INTCON_GPIE = on -- разрешаем прерывания по GPIO end if end procedure
forever loop pwm_cnt = pwm_cnt + 1 --когда дотикает до 255,само станет нулем if pwm_cnt < pwm then led = on else led = off end if end loop
Продукция MOSO предназначена в основном для индустриальных приложений, использует инновационные решения на основе более 200 собственных патентов для силовой электроники и соответствует международным стандартам. LED-драйверы MOSO применяются в системах наружного освещения разных отраслей, включая промышленность, сельское хозяйство, транспорт и железную дорогу. В ряде серий реализована возможность дистанционного контроля и программирования работы по заданному сценарию. Разберем решения MOSO
подробнее>>
Посоветуйте что-нибудь. Лично я склоняюсь к Микропаскалю, потому как есть кое-какой опыт программирования в Делфях. АСМ не осилю, слишком жестко. По Си нужна хорошая обучалка, потому как конструкции этого языка вгоняют меня в ступор.
В защиту С, C++ Учился на фортране, на перфокартах.)))) Спустя много лет, может и не оптимально, но пишу на С микроконтроллеры. И кажется все очень просто.
Есть какое-нибудь толковое руководство для нубаса? По идее, в МК нет ничего сложного в плане программирования по определению, ибо почти все заточено под дерганье ногами. Но синтаксис...синтаксис мне кажется очень специфическим,так скажем.
Спойлер... а в поддержку асма : ИК-приемник RC5/RC6 с энкодером для регулятора громкости + эмулятор PS/2-клавиатуры. Все это влезало в память старого PIC12F629 и нормально работало на 4MHz.
в МК нет ничего сложного в плане программирования по определению, ибо почти все заточено под дерганье ногами. Но синтаксис...синтаксис мне кажется очень специфическим,так скажем.
Вы заблуждаетесь про "дерганье ногами". Это все равно как говорить про любое человеческое умение. Дело не в дерганье. А в РЕЗУЛЬТАТЕ этого дерганья. Можно дергать пинами разъема HDMI и получить на экране тупую заставку, можно вращающуюся фигуру, а можно блокбастер с миллионными просмотрами. И все это можно свести к "дерганью". Си и его синтаксис легко осваивается и ПОНИМАЕТСЯ, если понимаешь АРХИТЕКТУРУ микроконтроллера. Понимаешь почему она именно такая, а не иная. Тогда, кстати и АСМ становится родным. ЗЫ. Чуть выше по теме я привел ответ на Ваш вопрос. Завершенный ответ. Откройте ссылку и получите Си код и его прототип в АСМе. Это даже не потребует знания Си. Конструкции там очень простые. ЗЗЫ. Подключение механического энкодера не требует использования прерываний. Как и подключение кнопки. Это все интерфейсы НЕ РЕАЛЬНОГО ВРЕМЕНИ.
в МК нет ничего сложного в плане программирования по определению, ибо почти все заточено под дерганье ногами. Но синтаксис...синтаксис мне кажется очень специфическим,так скажем.
Вы заблуждаетесь про "дерганье ногами". Это все равно как говорить про любое человеческое умение. Дело не в дерганье. А в РЕЗУЛЬТАТЕ этого дерганья. Можно дергать пинами разъема HDMI и получить на экране тупую заставку, можно вращающуюся фигуру, а можно блокбастер с миллионными просмотрами. И все это можно свести к "дерганью". Си и его синтаксис легко осваивается и ПОНИМАЕТСЯ, если понимаешь АРХИТЕКТУРУ микроконтроллера. Понимаешь почему она именно такая, а не иная. Тогда, кстати и АСМ становится родным. ЗЫ. Чуть выше по теме я привел ответ на Ваш вопрос. Завершенный ответ. Откройте ссылку и получите Си код и его прототип в АСМе. Это даже не потребует знания Си. Конструкции там очень простые. ЗЗЫ. Подключение механического энкодера не требует использования прерываний. Как и подключение кнопки. Это все интерфейсы НЕ РЕАЛЬНОГО ВРЕМЕНИ.
Согласен,с упрощением перебрал. Буду изучать Си, что ж еще поделать. Спасибо, что тратите свое время на разъяснение прописных истин нубасам =)
Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 2
Вы не можете начинать темы Вы не можете отвечать на сообщения Вы не можете редактировать свои сообщения Вы не можете удалять свои сообщения Вы не можете добавлять вложения