Відповісти

Введіть повідомлення і натисніть Надіслати
Параметри

Назад

Огляд теми (нові повідомленні вгорі)

akapulko
2023-11-19 17:29:30

Дещо підправив останню ISR, користуйтеся:

volatile uint32_t pulses;

void init_TIMER1(void) {
  TCCR1A = 0;
  TCCR1B = 0x8D;
  TIMSK1 = 0x20; /*Enable ICIE1*/
  OCR1B = 15625; /*1 sec at 16MHz*/
  OCR1A = 46875; /*1+2=3 sec at 16MHz*/
}

void setup() {
  DDRB |= _BV(5); /*Condigure PB5 as outputs*/
  PORTB &= ~_BV(5); /*Initially LOW on PB5*/  
  PORTB |= _BV(0); /*Pull-up PB0*/
  init_TIMER1();
  sei();
}

void loop() {}

ISR(TIMER1_COMPB_vect){
  PORTB |= _BV(5);
}

ISR(TIMER1_COMPA_vect){
  PORTB &= ~_BV(5);
  if (pulses-- == 0) TIMSK1 = 0x20; /*Clear OCIE1B, OCIE1A*/
}

ISR(TIMER1_CAPT_vect){
  if (TIMSK1 == 0x20){
    pulses = TCNT1 = 0;
    TIMSK1 |= 0x06; /*Enable OCIE1B, OCIE1A*/
  }
  pulses += 12;
}
akapulko
2023-11-19 14:45:25

Перекиньте датчик з піна 2 на пін 8:

volatile uint32_t pulses = 0;

void init_TIMER1(void) {
  TCCR1A = 0;
  TCCR1B = 0x8D;
  TIMSK1 = 0x20; /*Enable ICIE1*/
  OCR1B = 15625; /*1 sec at 16MHz*/
  OCR1A = 46875; /*1+2=3 sec at 16MHz*/
  TCNT1 = 0;
}

void setup() {
  DDRB |= _BV(5); /*Condigure PB5 as outputs*/
  PORTB &= ~_BV(5); /*Initially LOW on PB5*/  
  PORTB |= _BV(0); /*Pull-up PB0*/
  init_TIMER1();
  sei();
}

void loop() {}

ISR(TIMER1_COMPB_vect){
  PORTB |= _BV(5);
}

ISR(TIMER1_COMPA_vect){
  PORTB &= ~_BV(5);
  if (pulses-- == 0) TIMSK1 = 0x20; /*Clear OCIE1B, OCIE1A*/
}

ISR(TIMER1_CAPT_vect){
  TCNT1 = 0;
  pulses += 12;
  TIMSK1 |= 0x06; /*Enable OCIE1B, OCIE1A*/
}

Дивовижно, скільком людям може знадобитися той самий шматок коду

Honey
2023-11-19 13:13:26

Заводите змінну "кількість клацань реле". В основному циклі клацаєте реле поки змінна не нульова, кожне клацання віднімає 1 від змінної, роботу зі змінною виконуєте при вимкнених перериваннях. В перериванні по переходу піна 1-0 додаєте до змінної число 12. Або задайте це завдання GPT, або звертайтесь в пошту.

Alexhlor
2023-11-19 11:02:47

Доброго вам дня.
Потрібна допомога у створенні скетчу, в роботі використовуватиму Arduino nano.
Про платформу Arduino маю спільні поняття, тільки-но почав самонавчання, але програму залити вже можу.
Пробував зробити скетч за допомогою GPT бився тиждень виявилося, що його явно перехвалили.
Хоча на мій погляд скетч досить простий задіяний 1 вхід та 1 вихід.
Виглядає завдання так:
У мене є імпульсний витратомір, імпульс подає датчик холу, крок імпульсу 1 імпульс на 100 л.
Сигнал подається на насос дозатором гіпохлориту, однієї дози на 100л для пропорційного розподілу мало. Поміняти лічильник немає можливості як сам датчик холу. у насосі дозаторі такої потрібної функції немає. Я вирішив за допомогою Arduino nano зробити дільник імпульсів.
Завдання для програмування Arduino NANO
Елементи, з якими працюватиме контролер Arduino:
1.) Імпульсний лічильник з датчиком холу (подає сигнал на пін.2)
2.) Електромагнітне реле 5вольт з окремим дротом управління (керується з піна.13)
Алгоритм програми:
1. Імпульсний лічильник з датчиком холу (подає сигнал на пін.2) - імпульсом вважається зміна значення 1-0 якщо геркон зупиняється тільки 0 або 1 це імпульсом не зараховується.
2.після того, як на пин.2 прийшов імпульс включається пин.13 подає імпульс на електромагнітне реле (подається 12 імпульсів, пауза між імпульсами 1секунда, час утримання імпульсу 2 секунди.
3.) якщо пин.13 не відпрацював весь алгоритм, але в пин.2 прийшов новий імпульс то імпульси на виході пин.13 множаться на кількість імпульсів що прийшли на пин.2.
4.) після відпрацювання повного алгоритму на пін.13. програма чекає на новий імпульс на пін.2 і повторює алгоритм.
УВАГА.
Визначення імпульсу змінна 1-0 не випадкова і зумовлена особливостями роботи самого витратоміра, коли рух води через нього закінчиться він може зупинитися як 0 так і 1.
І ні чого страшного якщо він зупиниться в 0, а якщо в 1 то насос дозатор просто буде дубасити поки все не викачає, а буває що і труби рве 12-14 бар на закриту засувку може лупнути.
Заздалегідь дякую.

Підвал форуму