stm32 cubeide два инкремента не совместимы.

Кто любит RISC в жизни, заходим, не стесняемся.
Аватара пользователя
AlanDrakes
Прорезались зубы
Сообщения: 236
Зарегистрирован: Пн июл 04, 2016 16:51:22
Откуда: Россия, Омск

Re: stm32 cubeide два инкремента не совместимы.

Сообщение AlanDrakes »

[uquote="ivan dimir",url="/forum/viewtopic.php?p=4163989#p4163989"][А чем писать код?[/uquote]
Не знаю, как кто, но я пишу руками. =]

[uquote="ivan dimir",url="/forum/viewtopic.php?p=4163989#p4163989"]И чем вас смущает эта строка.Нажимаю кнопку выставляется флаг.Когда выставляется флаг в обработчике прерываний по таймеру начинает счёт переменная.[/uquote]
Скорее всего компилятор должен жаловаться на логичнское И, между частью операндов в строке. И что он МОЖЕТ ошибиться, если нет скобок.
Жалоба на неоднозначную трактовку сравнений.

[uquote="ivan dimir",url="/forum/viewtopic.php?p=4163989#p4163989"]Покажите хоть пример.Кусочек кода моего .Так как нужно писать .[/uquote]
Хойку.
Извините, не сдержался.
Реклама
Dimon456
Мудрый кот
Сообщения: 1849
Зарегистрирован: Вс дек 25, 2016 08:34:54

Re: stm32 cubeide два инкремента не совместимы.

Сообщение Dimon456 »

ivan dimir, просто они тебе ни чего другого не могут предложить.
+2 страницы библиотека обработки кнопок
+6 страниц микроменю, это примерный подсчет
и в итоге >16 страниц "индусокода", в котором только автор может разобраться.

Конечно на конечных автоматах это все просто делается, а тут увы, всего 1 страница и абсолютно не читаемый код.
Реклама
ivan dimir
Мучитель микросхем
Сообщения: 440
Зарегистрирован: Вс дек 29, 2019 08:05:21

Re: stm32 cubeide два инкремента не совместимы.

Сообщение ivan dimir »

[uquote="Dimon456",url="/forum/viewtopic.php?p=4164051#p4164051"]ivan dimir, просто они тебе ни чего другого не могут предложить.
+2 страницы библиотека обработки кнопок
+6 страниц микроменю, это примерный подсчет
и в итоге >16 страниц "индусокода", в котором только автор может разобраться.

Конечно на конечных автоматах это все просто делается, а тут увы, всего 1 страница и абсолютно не читаемый код.[/uquote]
Что такое конечный автомат? И как его создать.Обьясните нерусскому электрику.Принцып.Или алгоритм создания этого конечного автомата.Какой ?
Dimon456
Мудрый кот
Сообщения: 1849
Зарегистрирован: Вс дек 25, 2016 08:34:54

Re: stm32 cubeide два инкремента не совместимы.

Сообщение Dimon456 »

Это не ко мне вопрос.
Я не постиг этот >16 страничный высоко интеллектуальный код.
Реклама
Эиком - электронные компоненты и радиодетали
Аватара пользователя
Eddy_Em
Собутыльник Кота
Сообщения: 2516
Зарегистрирован: Пт июл 12, 2019 22:52:01
Контактная информация:

Re: stm32 cubeide два инкремента не совместимы.

Сообщение Eddy_Em »

ivan dimir, а слабо в гугле набить "finite state machine"?
Все очень просто: алгоритм разбивается на этапы, которые можно однозначно охарактеризовать конечным количеством состояний. Все, дальше ты в switch'е проверяешь текущее состояние и выполняешь в зависимости от него какие-то действия.
Например, работа с USB основана на конечном автомате, твои кнопки удобней будет конечным автоматом реализовать и т.д., и т.п.
Я ж тебе давал ссылку на обработку кнопок в конечном автомате:

Код: Выделить всё

switch(e){
                case EVT_NONE: // just pressed
                case EVT_RELEASE:
                    if((k->counter += d) > PRESSTHRESHOLD)
                        k->event = EVT_PRESS;
                break;
                case EVT_PRESS: // hold
                    if((k->counter += d)> HOLDTHRESHOLD)
                        k->event = EVT_HOLD;
                break;
                default:
                break;
            }
(правда, этот пример неудачный. Нельзя так делать. Надо сначала выставить состояние и лишь потом ждать нужное время; а здесь выходит, что событие нажатия система получит лишь через PRESSTHRESHOLD мс, а это около 30 и выше!)

Бывают автоматы иерархические: когда в каждом состоянии есть какие-то подсостояния.
Linux rules! Windows must die. Здравомыслящий человек добровольно будет пользоваться мастдаем лишь в двух случаях: под дулом автомата или под влиянием анального зонда.
Я на гитхабе, в ЖЖ
Реклама
Dimon456
Мудрый кот
Сообщения: 1849
Зарегистрирован: Вс дек 25, 2016 08:34:54

Re: stm32 cubeide два инкремента не совместимы.

Сообщение Dimon456 »

AlanDrakes писал(а):или хотя бы обрабатывать кнопки в функции
Ни знаю в чем проблема, и не ужели для каких-то кнопок применять конечный автомат?
Спойлер

Код: Выделить всё

#include <stdbool.h>

bool flag_IDR5;
bool flag_IDR4;
bool flag_IDR8;

#define BTN_TIME   50

void ScanButtons(void) {
static uint8_t ButtonFilter[3] = {0};

	flag_IDR5=0; flag_IDR4=0; flag_IDR8=0;
	
 if (GPIOB->IDR & GPIO_IDR_IDR5) {
  // Отпущена, висит в воздухе, подтяжка к VCC
  if (ButtonFilter[0]) { ButtonFilter[0] = 0; }
 } else {
 // Нажата (притянуто к 0)
  if (ButtonFilter[0] == BTN_TIME) {
    ButtonFilter[0] = (BTN_TIME+1);
    flag_IDR5 = 1;
  } else if (ButtonFilter[0] < BTN_TIME) { 
	ButtonFilter[0]++; 
	}
 }
 
 if (GPIOB->IDR & GPIO_IDR_IDR4) {
  if (ButtonFilter[1]) { ButtonFilter[1] = 0; }
 } else {
  if (ButtonFilter[1] == BTN_TIME) {
    ButtonFilter[1] = (BTN_TIME+1);
    flag_IDR4 = 1;
  } else if (ButtonFilter[1] < BTN_TIME) {
	ButtonFilter[1]++;
	}
 } 
 
 if (GPIOB->IDR & GPIO_IDR_IDR8) {
  if (ButtonFilter[2]) { ButtonFilter[2] = 0; }
 } else {
  if (ButtonFilter[2] == BTN_TIME) {
    ButtonFilter[2] = (BTN_TIME+1);
    flag_IDR8 = 1;
  } else if (ButtonFilter[2] < BTN_TIME) { 
	ButtonFilter[2]++; 
	}
 } 
}
а в цикле что-то вроде

Код: Выделить всё

ScanButtons();

    switch (nastroyki.menu_btn) {
      case 0:
        break;
      case 1:
        if (flag_IDR4) {
            if (danie.a < 4095) danie.a++;
          }
       
        if (flag_IDR8) {
            if (danie.a) danie.a--;
        }
        break;
первые можно в макрос обернуть типа такого

Код: Выделить всё

#define BTN_TIME(port,pin,b_time,flag) do{ flag=0; if(port&(pin)) { if(b_time)b_time=0; } else { if(b_time == BTN_LOCK_TIME) { b_time = (BTN_LOCK_TIME+1);  flag=1; } else if(b_time<BTN_LOCK_TIME) b_time++; } }while(0)

void ScanButtons(void) {
static uint8_t ButtonFilter[3] = {0};
	
	BTN_TIME(GPIOB->IDR, GPIO_IDR_IDR5, ButtonFilter[0], flag_IDR5);
	BTN_TIME(GPIOB->IDR, GPIO_IDR_IDR4, ButtonFilter[1], flag_IDR4);
	BTN_TIME(GPIOB->IDR, GPIO_IDR_IDR8, ButtonFilter[2], flag_IDR8);
	
}
Реклама
ivan dimir
Мучитель микросхем
Сообщения: 440
Зарегистрирован: Вс дек 29, 2019 08:05:21

Re: stm32 cubeide два инкремента не совместимы.

Сообщение ivan dimir »

[uquote="Dimon456",url="/forum/viewtopic.php?p=4164174#p4164174"]
AlanDrakes писал(а):или хотя бы обрабатывать кнопки в функции
Ни знаю в чем проблема, и не ужели для каких-то кнопок применять конечный автомат?
Спойлер

Код: Выделить всё

#include <stdbool.h>

bool flag_IDR5;
bool flag_IDR4;
bool flag_IDR8;

#define BTN_TIME   50

void ScanButtons(void) {
static uint8_t ButtonFilter[3] = {0};

	flag_IDR5=0; flag_IDR4=0; flag_IDR8=0;
	
 if (GPIOB->IDR & GPIO_IDR_IDR5) {
  // Отпущена, висит в воздухе, подтяжка к VCC
  if (ButtonFilter[0]) { ButtonFilter[0] = 0; }
 } else {
 // Нажата (притянуто к 0)
  if (ButtonFilter[0] == BTN_TIME) {
    ButtonFilter[0] = (BTN_TIME+1);
    flag_IDR5 = 1;
  } else if (ButtonFilter[0] < BTN_TIME) { 
	ButtonFilter[0]++; 
	}
 }
 
 if (GPIOB->IDR & GPIO_IDR_IDR4) {
  if (ButtonFilter[1]) { ButtonFilter[1] = 0; }
 } else {
  if (ButtonFilter[1] == BTN_TIME) {
    ButtonFilter[1] = (BTN_TIME+1);
    flag_IDR4 = 1;
  } else if (ButtonFilter[1] < BTN_TIME) {
	ButtonFilter[1]++;
	}
 } 
 
 if (GPIOB->IDR & GPIO_IDR_IDR8) {
  if (ButtonFilter[2]) { ButtonFilter[2] = 0; }
 } else {
  if (ButtonFilter[2] == BTN_TIME) {
    ButtonFilter[2] = (BTN_TIME+1);
    flag_IDR8 = 1;
  } else if (ButtonFilter[2] < BTN_TIME) { 
	ButtonFilter[2]++; 
	}
 } 
}
а в цикле что-то вроде

Код: Выделить всё

ScanButtons();

    switch (nastroyki.menu_btn) {
      case 0:
        break;
      case 1:
        if (flag_IDR4) {
            if (danie.a < 4095) danie.a++;
          }
       
        if (flag_IDR8) {
            if (danie.a) danie.a--;
        }
        break;
первые можно в макрос обернуть типа такого

Код: Выделить всё

#define BTN_TIME(port,pin,b_time,flag) do{ flag=0; if(port&(pin)) { if(b_time)b_time=0; } else { if(b_time == BTN_LOCK_TIME) { b_time = (BTN_LOCK_TIME+1);  flag=1; } else if(b_time<BTN_LOCK_TIME) b_time++; } }while(0)

void ScanButtons(void) {
static uint8_t ButtonFilter[3] = {0};
	
	BTN_TIME(GPIOB->IDR, GPIO_IDR_IDR5, ButtonFilter[0], flag_IDR5);
	BTN_TIME(GPIOB->IDR, GPIO_IDR_IDR4, ButtonFilter[1], flag_IDR4);
	BTN_TIME(GPIOB->IDR, GPIO_IDR_IDR8, ButtonFilter[2], flag_IDR8);
	
}
[/uquote]
Код увеличится.И нет простоты кода.Для меня это сильно заумно.Слишком много событий.И операции.
Dimon456
Мудрый кот
Сообщения: 1849
Зарегистрирован: Вс дек 25, 2016 08:34:54

Re: stm32 cubeide два инкремента не совместимы.

Сообщение Dimon456 »

В конечных автоматах точно будет сильно заумно, слишком много событий и операции.
Самое главное, событий, а операций там столько же будет.

Один вопрос: за чем две совершенно одинаковых переменные?

Код: Выделить всё

nastroyki.menu_btn
nastroyki.menu_lcd
если их объединить, то код примет вид
Спойлер

Код: Выделить всё

  while (1) { 
  
	ScanButtons();
	
    if (flag_IDR5) {
      if(++nastroyki.menu_btn > 4) nastroyki.menu_btn = 0;
    }
    switch (nastroyki.menu_btn) {
      case 0:
        LCD_SetPos(0, 0);
        LCD_String("Bobr_stm32");	  
        break;
      case 1:
		if(flag_IDR4) if(danie.a < 4095) danie.a++;      
		if(flag_IDR8) if(danie.a) danie.a--;

        sprintf(nastroyki.buf, "a=%2d ", danie.a);
        LCD_SetPos(0, 0);
        LCD_String(nastroyki.buf);		
        break;
      case 2:
		if(flag_IDR4) if(danie.b < 4095) danie.b++;
		if(flag_IDR8) if(danie.b) danie.b--;
        
        sprintf(nastroyki.buf2, "b=%2d ", danie.b);
        LCD_SetPos(0, 0);
        LCD_String(nastroyki.buf2);		
        break;
      case 3:
		if(flag_IDR4) if(danie.c < 4095) danie.c++;
		if(flag_IDR8) if(danie.c) danie.c--;
        
        sprintf(nastroyki.buf4, "c=%2d ", danie.c);
        LCD_SetPos(0, 0);
        LCD_String(nastroyki.buf4);		
        break;
      case 4:
		if(flag_IDR4) if(danie.d < 1023) danie.d++;
		if(flag_IDR8) if(danie.d) danie.d--;

        sprintf(nastroyki.buf6, "d=%2d ", danie.d);
        LCD_SetPos(0, 0);
        LCD_String(nastroyki.buf6);		
        break;
      default:   break;
    }
	
  }
ScanButtons() можно объявить как inline функцию.
Аватара пользователя
Eddy_Em
Собутыльник Кота
Сообщения: 2516
Зарегистрирован: Пт июл 12, 2019 22:52:01
Контактная информация:

Re: stm32 cubeide два инкремента не совместимы.

Сообщение Eddy_Em »

Ну так сравни объем одного и того же кода без КА и с ними!
Я уж молчу о простоте сопровождения кода. С КА воткнуть новое состояние намного проще, чем без оного!
Linux rules! Windows must die. Здравомыслящий человек добровольно будет пользоваться мастдаем лишь в двух случаях: под дулом автомата или под влиянием анального зонда.
Я на гитхабе, в ЖЖ
ivan dimir
Мучитель микросхем
Сообщения: 440
Зарегистрирован: Вс дек 29, 2019 08:05:21

Re: stm32 cubeide два инкремента не совместимы.

Сообщение ivan dimir »

[uquote="Dimon456",url="/forum/viewtopic.php?p=4164331#p4164331"]В конечных автоматах точно будет сильно заумно, слишком много событий и операции.
Самое главное, событий, а операций там столько же будет.

Один вопрос: за чем две совершенно одинаковых переменные?

Код: Выделить всё

nastroyki.menu_btn
nastroyki.menu_lcd
если их объединить, то код примет вид
Спойлер

Код: Выделить всё

  while (1) { 
  
	ScanButtons();
	
    if (flag_IDR5) {
      if(++nastroyki.menu_btn > 4) nastroyki.menu_btn = 0;
    }
    switch (nastroyki.menu_btn) {
      case 0:
        LCD_SetPos(0, 0);
        LCD_String("Bobr_stm32");	  
        break;
      case 1:
		if(flag_IDR4) if(danie.a < 4095) danie.a++;      
		if(flag_IDR8) if(danie.a) danie.a--;

        sprintf(nastroyki.buf, "a=%2d ", danie.a);
        LCD_SetPos(0, 0);
        LCD_String(nastroyki.buf);		
        break;
      case 2:
		if(flag_IDR4) if(danie.b < 4095) danie.b++;
		if(flag_IDR8) if(danie.b) danie.b--;
        
        sprintf(nastroyki.buf2, "b=%2d ", danie.b);
        LCD_SetPos(0, 0);
        LCD_String(nastroyki.buf2);		
        break;
      case 3:
		if(flag_IDR4) if(danie.c < 4095) danie.c++;
		if(flag_IDR8) if(danie.c) danie.c--;
        
        sprintf(nastroyki.buf4, "c=%2d ", danie.c);
        LCD_SetPos(0, 0);
        LCD_String(nastroyki.buf4);		
        break;
      case 4:
		if(flag_IDR4) if(danie.d < 1023) danie.d++;
		if(flag_IDR8) if(danie.d) danie.d--;

        sprintf(nastroyki.buf6, "d=%2d ", danie.d);
        LCD_SetPos(0, 0);
        LCD_String(nastroyki.buf6);		
        break;
      default:   break;
    }
	
  }
ScanButtons() можно объявить как inline функцию.
[/uquote]
Может можно.Но по памяти в avr .Не совсем работает.С глюком.Но вижу что эклипсе др среда.Ей пофиг атомарные операции.Нужно попробывать ваш вариант.Спасибо.Я кстати подумал об этом.И у меня один маленький вопрос.В каких случаях нужно применять указатели ?

Добавлено after 9 minutes 12 seconds:
Хотя по мне две переменные. Бараны на лево.Козлы на право.Вот принцып.Код увеличился.Ну и структуры тоже код увеличили.Когда слишком много переменных .То структуры в помощь.
tonyk
Это не хвост, это антенна
Сообщения: 1309
Зарегистрирован: Вт ноя 19, 2019 06:10:18

Re: stm32 cubeide два инкремента не совместимы.

Сообщение tonyk »

Конечные автоматы очень удобны, быстры при разборе сложных условий, а ещё их очень просто и удобно рисовать. Заметьте, сначала рисуем автомат, а потом его кодируем. Учитесь рисовать и работать с КА, ибо это очень эффективный способ создания ПО! Заумь начинается, когда у вас при анализе получается 100500 if-then-else, а в самой глубине goto.
Аватара пользователя
AlanDrakes
Прорезались зубы
Сообщения: 236
Зарегистрирован: Пн июл 04, 2016 16:51:22
Откуда: Россия, Омск

Re: stm32 cubeide два инкремента не совместимы.

Сообщение AlanDrakes »

[uquote="Dimon456",url="/forum/viewtopic.php?p=4164174#p4164174"]
AlanDrakes писал(а):или хотя бы обрабатывать кнопки в функции
Не знаю в чем проблема, и неужели для каких-то кнопок применять конечный автомат?
Спойлер<...>
первые можно в макрос обернуть типа такого

Код: Выделить всё

#define BTN_TIME(port,pin,b_time,flag) do{ flag=0; if(port&(pin)) { if(b_time)b_time=0; } else { if(b_time == BTN_LOCK_TIME) { b_time = (BTN_LOCK_TIME+1);  flag=1; } else if(b_time<BTN_LOCK_TIME) b_time++; } }while(0)

void ScanButtons(void) {
static uint8_t ButtonFilter[3] = {0};
	
	BTN_TIME(GPIOB->IDR, GPIO_IDR_IDR5, ButtonFilter[0], flag_IDR5);
	BTN_TIME(GPIOB->IDR, GPIO_IDR_IDR4, ButtonFilter[1], flag_IDR4);
	BTN_TIME(GPIOB->IDR, GPIO_IDR_IDR8, ButtonFilter[2], flag_IDR8);
	
}
[/uquote]

Макрос интересный, согласен. Хотя писать такие не люблю - компилятор любит их разворачивать в inline-функции, а мне привычнее немного иначе оформить код - обработка ввода, фильтры, вызов события.
Когда-то писал функции обработки меню для графического экрана, с курсором (не указателем мыши, а виртуальным, прыгающим по кнопкам) и в какой-то момент понял, что дошёл до копии классического же меню. А потом понадобилось сделать "активную" кнопку, которая ловит хуки событий. Вот там всё стало странным, но решилось небольшой модификацией примитивов обработчиков. Ладно, это другая тема уже.
Dimon456
Мудрый кот
Сообщения: 1849
Зарегистрирован: Вс дек 25, 2016 08:34:54

Re: stm32 cubeide два инкремента не совместимы.

Сообщение Dimon456 »

Eddy_Em писал(а):Ну так сравни объем одного и того же кода без КА и с ними!
я тебе даю свой рабочий проект, а ты из него делаешь КА, вот тогда и поговорим о размере кода.
Eddy_Em писал(а):С КА воткнуть новое состояние намного проще, чем без оного!

Код: Выделить всё

while (1) {
 
   ScanButtons();
   
   новое_состояние();
tonyk писал(а):Заметьте, сначала рисуем автомат, а потом его кодируем.
под каждую задачу вы будете рисовать свой автомат, а потом его кодировать.
Универсального ни чего нет, как с теми же микроменю.
tonyk писал(а):Учитесь рисовать и работать с КА, ибо это очень эффективный способ создания ПО!

Код: Выделить всё

   КА++
   switch (KA){
      case 0 : опрос_кнопок(); break;
      case 1 : действие(); break;
	  case 2 : вывод_лсд(); break;
	  
      default : КА=-1
	}

Код: Выделить всё

	while(1){	
	опрос_кнопок();
	действие();
	вывод_лсд();	
	}
Пока что не вижу ни какой эффективности
tonyk писал(а):когда у вас при анализе получается 100500 if-then-else, а в самой глубине goto.
пример в студию, с КА и без КА.
ivan dimir
Мучитель микросхем
Сообщения: 440
Зарегистрирован: Вс дек 29, 2019 08:05:21

Re: stm32 cubeide два инкремента не совместимы.

Сообщение ivan dimir »

[uquote="Dimon456",url="/forum/viewtopic.php?p=4164331#p4164331"]В конечных автоматах точно будет сильно заумно, слишком много событий и операции.
Самое главное, событий, а операций там столько же будет.

Один вопрос: за чем две совершенно одинаковых переменные?

Код: Выделить всё

nastroyki.menu_btn
nastroyki.menu_lcd
если их объединить, то код примет вид
Спойлер

Код: Выделить всё

  while (1) { 
  
	ScanButtons();
	
    if (flag_IDR5) {
      if(++nastroyki.menu_btn > 4) nastroyki.menu_btn = 0;
    }
    switch (nastroyki.menu_btn) {
      case 0:
        LCD_SetPos(0, 0);
        LCD_String("Bobr_stm32");	  
        break;
      case 1:
		if(flag_IDR4) if(danie.a < 4095) danie.a++;      
		if(flag_IDR8) if(danie.a) danie.a--;

        sprintf(nastroyki.buf, "a=%2d ", danie.a);
        LCD_SetPos(0, 0);
        LCD_String(nastroyki.buf);		
        break;
      case 2:
		if(flag_IDR4) if(danie.b < 4095) danie.b++;
		if(flag_IDR8) if(danie.b) danie.b--;
        
        sprintf(nastroyki.buf2, "b=%2d ", danie.b);
        LCD_SetPos(0, 0);
        LCD_String(nastroyki.buf2);		
        break;
      case 3:
		if(flag_IDR4) if(danie.c < 4095) danie.c++;
		if(flag_IDR8) if(danie.c) danie.c--;
        
        sprintf(nastroyki.buf4, "c=%2d ", danie.c);
        LCD_SetPos(0, 0);
        LCD_String(nastroyki.buf4);		
        break;
      case 4:
		if(flag_IDR4) if(danie.d < 1023) danie.d++;
		if(flag_IDR8) if(danie.d) danie.d--;

        sprintf(nastroyki.buf6, "d=%2d ", danie.d);
        LCD_SetPos(0, 0);
        LCD_String(nastroyki.buf6);		
        break;
      default:   break;
    }
	
  }
ScanButtons() можно объявить как inline функцию.
[/uquote]
Меня заинтересовал ваш код у вас флаги в качестве кнопок?И меня заинтерисовала функция ScanButtons()? Что это ? И с чем его едят.Код ваш похож на мой единственное что переход на ноль при ++ и переход с нуля на 1023 при --.И замедление показаний.Ну а так ваш код лучше.Правда я использовал число 4095 дискретность ацп.1023 у avr.Да и ещё при переключении меню сначала нажимаем кнопку я выставляю флаг потом при ожатии флаг сбрасываю и срабатывает меню.

Добавлено after 2 minutes 23 seconds:
[uquote="AlanDrakes",url="/forum/viewtopic.php?p=4164036#p4164036"][uquote="ivan dimir",url="/forum/viewtopic.php?p=4163989#p4163989"][А чем писать код?[/uquote]
Не знаю, как кто, но я пишу руками. =]

[uquote="ivan dimir",url="/forum/viewtopic.php?p=4163989#p4163989"]И чем вас смущает эта строка.Нажимаю кнопку выставляется флаг.Когда выставляется флаг в обработчике прерываний по таймеру начинает счёт переменная.[/uquote]
Скорее всего компилятор должен жаловаться на логичнское И, между частью операндов в строке. И что он МОЖЕТ ошибиться, если нет скобок.
Жалоба на неоднозначную трактовку сравнений.

[uquote="ivan dimir",url="/forum/viewtopic.php?p=4163989#p4163989"]Покажите хоть пример.Кусочек кода моего .Так как нужно писать .[/uquote]
Хойку.
Извините, не сдержался.[/uquote]
Да код написан не правильно.Но работает.Исправлю.Спасибо за замечания.
Dimon456
Мудрый кот
Сообщения: 1849
Зарегистрирован: Вс дек 25, 2016 08:34:54

Re: stm32 cubeide два инкремента не совместимы.

Сообщение Dimon456 »

ivan dimir, код не мой, код опубликовал AlanDrakes в этой теме 2 сообщение, я просто взял и использовал.
ivan dimir писал(а):И меня заинтерисовала функция ScanButtons()?
AlanDrakes писал(а):или хотя бы обрабатывать кнопки в функции
что и требовалось.
ivan dimir писал(а):что переход на ноль при ++ и переход с нуля на 1023 при --
здесь мне не понятно было, а переспрашивать не стал, в качестве демонстрации.
ivan dimir писал(а):И замедление показаний.
опять не понятно, что значит замедление?

Код: Выделить всё

#define BTN_TIME   50
число 50 взято с потолка, в зависимости от тактовой частоты чипа это число будет меняться, это число больше определяет сколько надо времени держать нажатой кнопку до ее срабатывания, до установки флага.
Попробуйте поиграться от 5-250.
tonyk
Это не хвост, это антенна
Сообщения: 1309
Зарегистрирован: Вт ноя 19, 2019 06:10:18

Re: stm32 cubeide два инкремента не совместимы.

Сообщение tonyk »

Dimon456 написал:

Код: Выделить всё

  КА++
   switch (KA){
      case 0 : опрос_кнопок(); break;
      case 1 : действие(); break;
     case 2 : вывод_лсд(); break;
    
      default : КА=-1
   }
Вот сразу видно человека, который не понимает, что такое конечный автомат. Даже книжки не читал.
Dimon456
Мудрый кот
Сообщения: 1849
Зарегистрирован: Вс дек 25, 2016 08:34:54

Re: stm32 cubeide два инкремента не совместимы.

Сообщение Dimon456 »

tonyk, я поторопился, надо было так

Код: Выделить всё

   KA = 0;
   while (1) {
     switch (KA) {
       case 0: инит_всего();   KA = 1; break;
       case 1: опрос_кнопок(); KA = 2; break;
       case 2: действие();     KA = 3; break;
       case 3: вывод_лсд();    KA = 1; break;
       default: в пиииии.....();
     }
   }
Аватара пользователя
Eddy_Em
Собутыльник Кота
Сообщения: 2516
Зарегистрирован: Пт июл 12, 2019 22:52:01
Контактная информация:

Re: stm32 cubeide два инкремента не совместимы.

Сообщение Eddy_Em »

Dimon456, все равно неправильно. У тебя - не конечный автомат, а тупой последовательный код, написанный через жопу!
Linux rules! Windows must die. Здравомыслящий человек добровольно будет пользоваться мастдаем лишь в двух случаях: под дулом автомата или под влиянием анального зонда.
Я на гитхабе, в ЖЖ
Dimon456
Мудрый кот
Сообщения: 1849
Зарегистрирован: Вс дек 25, 2016 08:34:54

Re: stm32 cubeide два инкремента не совместимы.

Сообщение Dimon456 »

Eddy_Em, мне что, твои куски коды сюда начать выкладывать?
В любой момент времени мы можем прерваться и прочитать состояние KA и узнать в каком состоянии находится последовательный код.
В своем проекте я хотел использовать совт_таймер, как бы не из ваших КА
Спойлер

Код: Выделить всё

//==================
#ifndef SOFT_TIMERS_H

#define SOFT_TIMERS_H

#include "soft_timers.h"

#include "main.h"
#define SwTimerCount  8	//Количество программных таймеров

/*Режимы работы таймеров*/
typedef enum
	{
		SWTIMER_MODE_EMPTY,
		SWTIMER_MODE_WAIT_ON,
		SWTIMER_MODE_WAIT_OFF,
		SWTIMER_MODE_CYCLE,
		SWTIMER_MODE_SINGLE
} SwTimerMode;


/*Стурктура программного таймера*/
typedef struct
    {
		unsigned LocalCount:32;	//Переменная для отсчета таймера
    	unsigned Count:24;		//Переменная для хранения задержки
    	unsigned Mode:3;		//Режим работы
    	unsigned On:1;			//Разрешиющий бит
    	unsigned Reset:1;		//Сброс счета таймера без его выключения
    	unsigned Off:1;			//Останавливающий бит
    	unsigned Out:1;			//Выход таймера
    	unsigned Status:1;		//Состояние таймера
}SW_TIMER;

#if (SwTimerCount>0)
volatile SW_TIMER TIM[SwTimerCount]; //Объявление софтовых таймеров
#endif


void SwTimerWork(volatile SW_TIMER* TIM, unsigned char Count);	//Сама функция для обработки таймеров
void OnSwTimer(volatile SW_TIMER* TIM, SwTimerMode Mode, unsigned int SwCount);	//Подготовливает выбранный из массива таймер
unsigned char GetStatusSwTimer(volatile SW_TIMER* TIM);	//Считывание статуса таймера

#endif
Спойлер

Код: Выделить всё


//==================
//--------------------- Пример использования -----------------------------
// set_soft_timer (ST_LED_2_BLINK, 50, 50); // Установка таймера.
// if (handle_soft_timer (ST_LED_2_BLINK))  // Проверка таймера.
//==================

//==================
#include "soft_timers.h"
//==================

//Подпрограмма программных таймеров
void SwTimerWork(volatile SW_TIMER* TIM, unsigned char Count){
	unsigned short i=0;
		for (i=0; i<Count; i++){
			if (TIM->Mode==SWTIMER_MODE_EMPTY){
				TIM++;
				continue;
			}

			if (TIM->Mode==SWTIMER_MODE_WAIT_ON){ //Если таймер на задержку включения
				if (TIM->On){
					if (TIM->LocalCount>0) TIM->LocalCount--;
						else {
							TIM->Out=1;
							TIM->Status=1;
						}
				}
				else {
					TIM->Out=0;
					TIM->LocalCount=TIM->Count-1;
				}
			}
			if (TIM->Mode==SWTIMER_MODE_WAIT_OFF){ //Если таймер на задержку выключения
				if (TIM->On){
					TIM->Out=1;
					TIM->Status=1;
					TIM->LocalCount=TIM->Count-1;
				}
				else {
					if (TIM->LocalCount>0) TIM->LocalCount--;
						else TIM->Out=0;
				}
			}
			if (TIM->Mode==SWTIMER_MODE_CYCLE){
				if (TIM->Off){
					if (TIM->On){
						TIM->Off=0;
						if (TIM->LocalCount>0) TIM->LocalCount--;
					}
				}
				else{
					if (TIM->LocalCount>0) {
						TIM->LocalCount--;
						TIM->Out=0;
					}
					else {
						TIM->Out=1;
						TIM->Status=1;
						TIM->LocalCount=TIM->Count-1;
					}
				}
				if (TIM->Reset){
					TIM->LocalCount=TIM->Count-1;
					TIM->Out=0;
					TIM->Status=0;
				}
			}
			if (TIM->Mode==SWTIMER_MODE_SINGLE){
				if (TIM->Off){
					if (TIM->On){
						TIM->Off=0;
						if (TIM->LocalCount>0) TIM->LocalCount--;
					}
				}
				else{
					if (TIM->LocalCount>0) {
						TIM->LocalCount--;
						TIM->Out=0;
					}
					else {
						TIM->Out=1;
						TIM->Status=1;
						TIM->LocalCount=TIM->Count-1;
						TIM->Off=1;
						TIM->On=0;
					}
				}
				if (TIM->Reset){
					TIM->LocalCount=TIM->Count-1;
					TIM->Out=0;
					TIM->Status=0;
				}
			}

			TIM++;
		}
}

void OnSwTimer(volatile  SW_TIMER* TIM, SwTimerMode Mode, unsigned int SwCount){
		TIM->Mode=Mode;
		if (SwCount){
			TIM->Count=SwCount;
			TIM->LocalCount=SwCount-1;
		}
		if (TIM->Mode==SWTIMER_MODE_CYCLE || TIM->Mode==SWTIMER_MODE_SINGLE){
			TIM->Off=1;
		}
}


unsigned char GetStatusSwTimer(volatile SW_TIMER* TIM){
	unsigned char status=0;
	if (TIM->Mode==SWTIMER_MODE_EMPTY) return -1;
	if (TIM->Status){
		TIM->Status=0;
		status=1;
	}
	else {
		status=0;
	}
	return status;
}
но из-за того что мне стало жалко лишние 300-400 байт флеша, обошелся такой конструкцией
Спойлер

Код: Выделить всё

volatile uint32_t currentMillis = 0;

void SysTick_Handler(void)
{ static uint8_t count=0;
	currentMillis++;
}


uint32_t millis (void)
{
	return currentMillis;
}

Код: Выделить всё

	if((millis() - previousMillis) > 500){
		previousMillis = millis();
		blink = !blink;
	}

	LCDI2C_setCursor (10,0);
	if (blink) LCDI2C_write(0x22); else LCDI2C_write(0x20);

	LCDI2C_setCursor (11, 0);
	sprintf (string_out,"%02dV",(uint8_t)table_u);
	LCDI2C_write_String (string_out);

	LCDI2C_setCursor (15,0);
	if (blink) LCDI2C_write(0x22); else LCDI2C_write(0x20);
Так что, будешь дербанить мой код?
Аватара пользователя
Eddy_Em
Собутыльник Кота
Сообщения: 2516
Зарегистрирован: Пт июл 12, 2019 22:52:01
Контактная информация:

Re: stm32 cubeide два инкремента не совместимы.

Сообщение Eddy_Em »

Dimon456, вот, ты как раз сделал то, о чем я ТСу уже давно пытаюсь вталдычить: SysTick нужно использовать для отсчета условного внутреннего времени. И в конечных автоматах для выставления длинных задержек именно его и использовать, а не как абдуринщики вызывать delay_ms(500)!
Скажем, надо тебе сделать переинициализацию дисплея в процессе работы. А там бывают приличные паузы. Ты процесс разбиваешь на несколько кусков. Как только нужна пауза, у тебя состояние, скажем, WAIT_FOR_SOMETH. В нем тупо проверяешь: если миллисекунды натикали достаточно, то переходишь в следующее состояние, если нет - остаешься в этом.

В общем, не понял ты вообще никак, что такое конечные автоматы и в чем их прелесть. А твой код "софтового таймера" - ад какой-то.
Linux rules! Windows must die. Здравомыслящий человек добровольно будет пользоваться мастдаем лишь в двух случаях: под дулом автомата или под влиянием анального зонда.
Я на гитхабе, в ЖЖ
Ответить

Вернуться в «ARM»