Привет, StackOverflow!
В следующем коде у меня есть простой конечный автомат, который изменяет работу некоторого внешнего устройства освещения (как следует из комментариев). Состояние изменяется нажатием кнопки, подключенной к GP1. Схема, подключенная к GP1, является схемой подавления дребезга компаратора, которая сравнивает VDD с 0,6VDD (я также пробовал схему триггера RC/диода/Шмитта), которая затем вызывает сигнал LO. На прицеле мы видим чистую прямоугольную волну при быстром нажатии на кнопку.
Текущее (и нежелательное) поведение PIC10F200 выглядит следующим образом:
- Переключатель нажат (состояние = 0)
- Приращения переменной конечного автомата (состояние = 1)
- Освещение переходит в корпус 1 и включается
- Освещение остается включенным не менее секунды
- Освещение выключается
- Система остается в этом состоянии до тех пор, пока кнопка не будет снова нажата или питание не будет выключено.
Вопрос: почему это так? И как, если возможно, исправить это так, чтобы одно нажатие кнопки равнялось одному приращению состояния, которое PIC затем поддерживает до тех пор, пока как система запитана и кнопка снова не нажимается?
#define SYS_FREQ 8000000L
#define FCY SYS_FREQ/4
#define _XTAL_FREQ 4000000
/******************************************************************************/
/* User Global Variable Declaration */
/******************************************************************************/
/******************************************************************************/
/* Main Program */
/******************************************************************************/
__CONFIG(MCLRE_ON & CP_OFF & OSC_IntRC);
void main(void)
{
TRIS = 0b111110;
unsigned char state = 0;
while(1)
{
switch (state)
{
case 0: // IDLE/OFF
if (GPIObits.GP0) GPIObits.GP0 = 0;
break;
case 1: // ON
if (!GPIObits.GP0) GPIObits.GP0 = 1;
break;
case 2: // BLINK (slow)
GPIObits.GP0 = !GPIObits.GP0;
__delay_ms(100);
break;
case 3: // BLINK (fast)
GPIObits.GP0 = !GPIObits.GP0;
__delay_ms(50);
break;
case 4: // BEAT DETECT
GPIObits.GP0 = GPIObits.GP2;
break;
default:
state = 0;
break;
}
if (!GPIObits.GP1)
{
__delay_ms(250);
state++;
}
}
}
ОБНОВЛЕНИЕ: так как есть небольшая путаница в отношении того, что я пытаюсь сделать с помощью этого кода/системы, давайте предоставим полный контекст. Этот микроконтроллер, PIC10F200, является частью общей конструкции платы для электролюминесцентного (EL) драйвера проводов. Микроконтроллер просто контролирует, включена ли схема драйвера, подключая GP0
к порту EN
микросхемы драйвера. Система имеет четыре режима работы, провод горит постоянно, провод мигает, провод мигает быстрее, и провод мигает при обнаружении низкочастотного биения (другая цепь в системе ). Переход из этих режимов работы управляется кнопочным переключателем (кратковременно включенным), который должен быть установлен на печатной плате. Это требует, чтобы state
в приведенном выше коде оставался стабильным между нажатиями кнопки. В настоящее время он этого не делает и ведет себя так, как описано в исходной части этого поста. Как указано в заголовке вопроса, почему state
в настоящее время не работает стабильно и как мне это сделать?
ОБНОВЛЕНИЕ (08.03.2014): решение
Необходимо установить следующие настройки, предполагая, что GP0 — это выход, GP2 — ваш T0CKI, и у вас есть переключатель, который переводит сигнал в состояние LO при срабатывании.
TRIS = 0b111110;
OPTION = 0b11101111;
Вопрос о том, действительно ли имеют значение биты 0-3 для OPTION, зависит от того, решите ли вы использовать модуль WDT.
Кроме того, реализация обнаружения отпускания кнопки представляет собой простой механизм счетчика, который сбрасывается, когда GP2 становится LO в любой момент во время счета.
if (TMR0 > 0)
{
while (count < 20)
{
if (!GPIObits.GP2) count = 0;
__delay_ms(10);
count++;
}
TMR0 = 0;
state++;
}
state
я пытаюсь просто переключаться между режимами работы устройства, которые помечены в коде. С моим нынешним знанием PIC, как работает XC8 и C, это самый простой способ, который я мог придумать для выполнения этой задачи. Я полностью готов попробовать разные подходы, за исключением любого решения на ассемблере, потому что изменение языка не только не решает проблему, но и усложняет реализацию и поддержку. - person James Lui   schedule 05.03.2014if (!GPIObits.GP1){GPIObits.GP0 = 1; __delay_ms(1000); GPIObits.GP0 = 0;}
- person γηράσκω δ' αεί πο   schedule 05.03.2014