Помогите с таймером
|
|
Катран | Дата: Воскресенье, 30.05.2010, 09:33 | Сообщение # 46 |
GOD
Группа: Администраторы
Сообщений: 1221
Репутация: 7801
Статус: Offline
| Можно уточнение? О каком таймере идет речь? а то в этой теме уже 3 таймера обсуждают. И нужен именно таймер или обычный светофор?
|
|
| |
black7 | Дата: Понедельник, 31.05.2010, 00:20 | Сообщение # 47 |
Новенький
Группа: Радиолюбитель
Сообщений: 7
Репутация: 0
Статус: Offline
| Здравствуйте Катран, можете тыкнуть носом что мя не так…. Задача та же самая… присобачит к таймеру еще 1 функцию, во время обратного отщета таймера .(при условии что сначала выбреем алгоритм ,потом задаем время таймера ,потом жмем старт ) Имеется 4 кнопки , от нажатой кнопки должен выполнятся 1 из 4 алгоритмов… Вот 1 из алгоритм : if (num==16) //если 16 сек. "выключаем" ПОРТ C.0 PORTC.0=0; if (num==22) // если num = 22 сек. зануляем num и включаем ПОРТ C.0 { num=0; PORTC.0=1; } Тут цикл 22 сек, 16 сек на PORTC.0=1, потом оставшиеся 6 сек до конца цикла PORTC.0=0 Это при условии что таймер настроен на прерывания 1 секунды, а в обработчике прерывания инкрементирую переменные : num++; sec++; Применил для этого оператор switch(x){ case 0: { какой-то код 0 } } как я понелв моем случии работать это будет так: сравнивается значение переменной X с case, то есть если Х=0, тогда будет выполняться код который записан в case 0.и так далия… Но у меня не зависимо от условия всегда выполняется case 0…. Почему так..? --------------------------------------------- Code interrupt [TIM1_OVF] void timer1_ovf_isr(void) { TCNT1H=0; TCNT1L=0; num++; sec++; } while (1) { switch(x) { case 0: { if (num==22) PORTC.0=0; if (num==22) { num=0; PORTC.0=1; } break; // выходим из оператора switch }
case 1: { if (num==16) //если 16 сек. "выключаем" ПОРТ C.0 PORTC.0=0; if (num==22) // если num = 22 сек. зануляем num и включаем ПОРТ C.0 { num=0; PORTC.0=1; } break; }
case 2: { if (num==10) PORTC.0=0; if (num==22) { num=0; PORTC.0=1; } break; }
case 3: { if (num==6) PORTC.0=0; if (num==22) { num=0; PORTC.0=1; } break; } if ((PINC.1==0)&&(PINC.2==1)&&(PINC.3==1)&&(PINC.4==1)) x=0; if ((PINC.1==1)&&(PINC.2==0)&&(PINC.3==1)&&(PINC.4==1)) x=1; if ((PINC.1==1)&&(PINC.2==1)&&(PINC.3==0)&&(PINC.4==1)) x=2; if ((PINC.1==1)&&(PINC.2==1)&&(PINC.3==1)&&(PINC.4==0)) x=3; }; код *.с
Сообщение отредактировал black7 - Понедельник, 31.05.2010, 00:46 |
|
| |
Катран | Дата: Вторник, 01.06.2010, 08:38 | Сообщение # 48 |
GOD
Группа: Администраторы
Сообщений: 1221
Репутация: 7801
Статус: Offline
| Как так можно писать, если скобки в один ряд?! Пока отредактировал в удобный вид - позже пересмотрю и напишу в чем причина. Code interrupt [TIM1_OVF] void timer1_ovf_isr(void) { TCNT1H=0; TCNT1L=0; num++; sec++; } while (1) { switch(x) { case 0: { if (num==22) PORTC.0=0; if (num==22) { num=0; PORTC.0=1; } break; // выходим из оператора switch } case 1: { if (num==16) //если 16 сек. "выключаем" ПОРТ C.0 PORTC.0=0; if (num==22) // если num = 22 сек. зануляем num и включаем ПОРТ C.0 { num=0; PORTC.0=1; } break; } case 2: { if (num==10) PORTC.0=0; if (num==22) { num=0; PORTC.0=1; } break; } case 3: { if (num==6) PORTC.0=0; if (num==22) { num=0; PORTC.0=1; } break; } if ((PINC.1==0)&&(PINC.2==1)&&(PINC.3==1)&&(PINC.4==1)) x=0; if ((PINC.1==1)&&(PINC.2==0)&&(PINC.3==1)&&(PINC.4==1)) x=1; if ((PINC.1==1)&&(PINC.2==1)&&(PINC.3==0)&&(PINC.4==1)) x=2; if ((PINC.1==1)&&(PINC.2==1)&&(PINC.3==1)&&(PINC.4==0)) x=3; };
|
|
| |
Катран | Дата: Вторник, 01.06.2010, 20:20 | Сообщение # 49 |
GOD
Группа: Администраторы
Сообщений: 1221
Репутация: 7801
Статус: Offline
| Обьясняю почему так происходит. Дело в том, что ты в начале задал переменную unsigned int num,sec,x Сразу вопрос не по теме: зачем использовать переменную типа int, занимающая 2 байта при реальном использовании менее байта и, что особенно важно, использовании 8 разрядного микроконтроллера; этим ты заставляешь его выполнять лишние машинные циклы, что в твоем случае не смертельно, но в особо критичных приложениях будет получаться нехорошо, поэтому лучше задать тип переменной unsigned char Ты задал переменную x и она по умолчанию стала 0. А тебе нужно задать ее отличную от того значения, которые используются в функции case, а также по окончанию каждого ветвления case, перед командой break задавать x, что бы он не входил туда снова, если не требует того подогрев пищи, создать флаг, который будет запрещать модификацию x, пока не закончится время.
|
|
| |
black7 | Дата: Суббота, 05.06.2010, 00:30 | Сообщение # 50 |
Новенький
Группа: Радиолюбитель
Сообщений: 7
Репутация: 0
Статус: Offline
| Спасибо Катран, попробую переделать Пока сделал бонально: Code if (PINC.4==0) // если нажата первая кнопка { delay_ms(250); // задержка 1/4 сек. (для удобства) выбора if (num <16)SIGNAL = ON; if( num >=16)SIGNAL = OFF; if (num==22){num=0; SIGNAL = OFF; } Вот вопрос по вашему таймеру можете обеснить для чего это и как работает не могу понять…? Code void time(void) // Подготовка регистров для заполнения данными { //============================================================================= help = minuts; // Разложение значения МИНут по разрядам cd : __ while (help > 9) { help -= 10; c++; }; d = help; //=============================================================================
lcd_putchar(c+0x30); }; И для чего в обработчике прерываний это Добавлено (05.06.2010, 00:30) --------------------------------------------- Катран ,большее при большее спасибо за помощь ,терпения и вашу конструкцию таймера),собрал макет работает)))
Сообщение отредактировал black7 - Вторник, 01.06.2010, 23:09 |
|
| |
Катран | Дата: Суббота, 05.06.2010, 09:53 | Сообщение # 51 |
GOD
Группа: Администраторы
Сообщений: 1221
Репутация: 7801
Статус: Offline
| По своему таймеру на атмеге нужно разбираться, а то я уже забыл что там было.
|
|
| |
romakolo | Дата: Четверг, 10.06.2010, 16:35 | Сообщение # 52 |
Решил остаться
Группа: Радиолюбитель
Сообщений: 22
Репутация: 0
Статус: Offline
| Привет Катран! Вы мне обещали переделать прошивку: а по стопу сделаю так, что б когда нажимаешь, то ишел сброс в то значение, которое установил(я 2 прошивки сделаю). Сделаю, когда немного освобожусь, а то полный завал, практически не выкисаю з-за компа, много работы. Мне еще подождать? И про внутренний генератор интересно,может так сделать,и со звуком,как я описал?Програмировать я не умею и очень Вас прошу помочь в написании прошивки.
|
|
| |
StreamX | Дата: Пятница, 23.07.2010, 22:31 | Сообщение # 53 |
Решил остаться
Группа: Радиолюбитель
Сообщений: 26
Репутация: 0
Статус: Offline
| Немного доработал прошивку. Добавил на PC1: При нажатии "Пуск" - единица. При окончании счёта - ноль. Так удобнее. PC1 - управляет включением нагрузки, строго по установленному времени. PC0 - включает звуковой сигнал при окончании. P.S. Замечания по схеме: VR1 - 10 - 20 kOm (это по даташиту) Если индикатор с подсветкой, то подсветку цепляем через сопротивление 30Ом, тогда общий потребляемый ток 40мА. Питание везде +5V.
Сообщение отредактировал StreamX - Суббота, 24.07.2010, 02:20 |
|
| |
Катран | Дата: Суббота, 24.07.2010, 06:53 | Сообщение # 54 |
GOD
Группа: Администраторы
Сообщений: 1221
Репутация: 7801
Статус: Offline
| Добавлю пршивку и схему к статье.
|
|
| |
romakolo | Дата: Воскресенье, 25.07.2010, 21:48 | Сообщение # 55 |
Решил остаться
Группа: Радиолюбитель
Сообщений: 22
Репутация: 0
Статус: Offline
| Я извиняюсь но мне кажется ,что Вы сейчас пишете про не ту схему.Здесь на жк индикаторе,а Вы мне переделывали схему и прошивку на светодиодных семисегментных индикаторах. Остановились на том,что нада, когда жмеш кнопку пуск-стоп, то; остановка счета,отключение реле и сброс показаний индикатора в то значение с какого начался счет. Например: Выставляем показания 05мин-00сек,жмем ПУСК-СТОП ,включается реле и убывают значения показания индикатора.Доходит до 00-00,Выключается реле,и на индикаторе включается опять 05мин00сек и так многократно.Если во время счета нажать кнопку ПУСК-СТОП то отключение реле,и сброс индикатора в то значение с которого начался счет в 05мин00сек А сейчас просто остановка счета,отключение реле и при повторном нажатии продолжение счета и включение реле. А кнопка сброс;сброс на самое начало;01-00,так и остается. Я там в самом начале просил про звуковой сигнал,Вы говорили,что нет уже выводов. А можно ли сделать внутренний генератор,а на вывода где сейчас кварц посадить пищалку и запрограмировать так как я писал раньше? За 10сек до окончания счета,при изменении показаний последних секунд, коротко пикает пищалка.Пищалку можно которая пищит от постоянного тока. По истечении времени отключается реле, а пищалка включается непрерывно на 3сек. Когда пищалка отключится,показания на индикаторе возвращаются в ранее выставленное значение.И ожидает следующего нажатия кнопки ПУСК-СТОП.Так много раз. При нажатии кнопки ПУСК-СТОП во время счета времени, происходит остановка счета,отключение реле, а пищалка на 3сек запищит.После пищалки на индикаторе снова выставленное ранее время.
|
|
| |
Катран | Дата: Среда, 28.07.2010, 20:59 | Сообщение # 56 |
GOD
Группа: Администраторы
Сообщений: 1221
Репутация: 7801
Статус: Offline
| Хорошо, я уберу внешний генератор и добавлю звуковой сигнал. На выходных займусь.
|
|
| |
Катран | Дата: Среда, 18.08.2010, 20:07 | Сообщение # 57 |
GOD
Группа: Администраторы
Сообщений: 1221
Репутация: 7801
Статус: Offline
| Да, хорошо, сейчас займусь! Если не хватит времени то к выходным попробую закончить.
|
|
| |
Катран | Дата: Среда, 18.08.2010, 21:32 | Сообщение # 58 |
GOD
Группа: Администраторы
Сообщений: 1221
Репутация: 7801
Статус: Offline
| Вроде написал. Что изменил: - на выводе RA6 выходит сигнал на пьезоизлучатель(напрямую не включать, только через транзистор) - кварцевый резонатор подключать не нужно - время должно сбрасываться на начальное при окончании отсчета - время должно сбрасываться на начальное при сбросе проверить нужно всё, я мог где то ошибиться, так как не имею макетки и делал всё по памяти.
|
|
| |
StreamX | Дата: Среда, 18.08.2010, 21:49 | Сообщение # 59 |
Решил остаться
Группа: Радиолюбитель
Сообщений: 26
Репутация: 0
Статус: Offline
| Quote (Катран) на выводе RA6 выходит сигнал на пьезоизлучатель(напрямую не включать, только через транзистор) Я конечно не вижу схему, но почему нельзя напрямую? Пьезоизлучатель, всегда подключается напрямую. А вот через транзистор - не правильно.... Пьезоизлучатель можно взять со встроенным генератором. Тогда просто подключается напрямую к МК. Потребление меньше 7мА. http://www.jlworld.com/products/spdpn/HPM14AX/$FILE/HPM14AX.pdf Без генератора, и того меньше. И можно мелодию написать. Выход МК расчитан на 40 мА.
Сообщение отредактировал StreamX - Среда, 18.08.2010, 21:53 |
|
| |
Катран | Дата: Среда, 18.08.2010, 22:29 | Сообщение # 60 |
GOD
Группа: Администраторы
Сообщений: 1221
Репутация: 7801
Статус: Offline
| Я на работе сегодня имел дело с пьезоизлучателем того же jlworld, в котором написано потребление до 80мА. Завтра модель уточню. Напрямую(через конденсатор) подключал обычные "пьезики", еще на древний F84
|
|
| |