Помощь - Поиск - Пользователи - Календарь
Полная версия этой страницы: STM32f103 прерывания в режиме энкодера
Форум разработчиков электроники ELECTRONIX.ru > Микроконтроллеры (MCs) > ARM
georgfour
Добрый день!
Хотел спросить у знающих людей, дабы ткнули меня носом, а то я подзапутался - как сделать так, чтобы происходило прерывание при повороте ручки механического энкодера?
Какие конкретно нужно эвенты сконфигурировать и как это будет работать.
Заранее спасибо за помощь!

Я пробовал делать по переполнению, однако ничего не работает:
Я включил общие прерывани и прерывания по таймеру 2:
__enable_irq ();//enable common interrupts
NVIC_EnableIRQ(TIM2_IRQn);//enable TIMER2 interrupt
Потом при инициализации таймера поставил бит :
TIM2->DIER|=TIM_DIER_UIE;
и вот так выглядит обработчик прерываний:
void TIM2_IRQHandler(void)
{
NVIC_DisableIRQ(TIM2_IRQn);
shift_cursor(1);
TIM2->SR &= ~TIM_SR_UIF;
NVIC_EnableIRQ(TIM2_IRQn);
}

И вообщем ничего не работает.
Значения в счетном регистре CNT изменяются как и положено при вращении ручки энкодера.
В чем может быть проблема?
Genadi Zawidowski
Для ручки достаточно и просто прерываний по изменению состояния выводов.
georgfour
Ну так здесь входы сконфигурированы под использование таймером - разве получится назанчить внешние прерывания на эти ноги?
Genadi Zawidowski
Кем-то свыще? Отключите... да, к тому же, возможно что прерывания будут вне зависимости от того, к какому устройству подключено.
Ruslan-maniak
У вас обычный инкрементальный энкодер? Тогда вам нужно просто сконфигурировать таймер в режиме работы с энкодером
Код
    RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE);

    TIM_TimeBaseInitTypeDef timer_base;
    TIM_TimeBaseStructInit(&timer_base);
    timer_base.TIM_Period = encoder->period;
    timer_base.TIM_CounterMode = TIM_CounterMode_Down | TIM_CounterMode_Up;
    TIM_TimeBaseInit(TIM3, &timer_base);
    
    TIM_SetCounter(TIM3, 0);

    TIM_EncoderInterfaceConfig(TIM3, TIM_EncoderMode_TI12, TIM_ICPolarity_BothEdge, TIM_ICPolarity_BothEdge);
    TIM_ITConfig(TIM3, TIM_IT_Update, ENABLE);
    TIM_Cmd(TIM3, ENABLE);


И просто периодически смотреть в счётчике таймера на сколько щелчков мы укрутили., забирать это значение и обнулять счётчик. Вот и всё. По сути прерывания не нужны. Единственное - по переполнению счётчика можно сделать таймер, но обычно это не требуется.
georgfour
Так уже сконфигурировал, и он работает нормально, я просто не хочу делать постоянные опросы в главном цикле или по тикам другого таймера в прерываниях, я хочу чтобы как только ручка повернулась, мы зашли в прерывание и считали значение бита направления DIR - это все что нужно, без каких либо привязок к счетному регистру и его значениям
Ruslan-maniak
а если период сделать равным 1
georgfour
Вы имеете масимально значение регистра ARR?
Пробовал, у меня почему то не работают прерывания по переполнению, инициализацию выше приводил
Шаманъ
Цитата(georgfour @ May 20 2016, 14:10) *
Так уже сконфигурировал, и он работает нормально, я просто не хочу делать постоянные опросы в главном цикле или по тикам другого таймера в прерываниях, я хочу чтобы как только ручка повернулась, мы зашли в прерывание и считали значение бита направления DIR - это все что нужно, без каких либо привязок к счетному регистру и его значениям

Зачем Вам тогда таймер этот нужен? Настраиваете прерывание на один из пинов (куда подключен энкодер), состояние второго пина даст Вам направление и все дела...
Obam
Если в TIMx_CR1 бит UDIS==1, то не будет ни какого UIF в TIMx_SR. Сам сейчас с таймерами "забавляюсь" - чумовые штуки (:
Для просмотра полной версии этой страницы, пожалуйста, пройдите по ссылке.
Invision Power Board © 2001-2025 Invision Power Services, Inc.