mirror of
https://github.com/DashyFox/StackSport.git
synced 2025-05-04 07:10:17 +00:00
167 lines
5.2 KiB
C
167 lines
5.2 KiB
C
#include "IR_CMD_Handler.h"
|
|
#include "IR.h"
|
|
#include "SimpleTimer.h"
|
|
#include "ShiftReg.h"
|
|
#include "Print.h"
|
|
#include "Indicator.h"
|
|
|
|
#define IR_Timeout 137
|
|
#define ResetInputProgerss_Timeout 2500
|
|
#define InitialRepeatTime 100 // Начальный интервал времени между вызовами функции при удержании
|
|
#define MinRepeatTime 30 // Минимально допустимый интервал времени между вызовами функции при удержании
|
|
#define HoldTime 500 // Время, необходимое для определения удержания
|
|
#define RepeatDecay 10 // Шаг уменьшения времени между вызовами функции при удержании
|
|
|
|
#define NULL_NumberParam 0xFFFF
|
|
|
|
//extern unsigned char IR_Command;
|
|
//extern unsigned char IR_Address;
|
|
extern unsigned char IRStatus;
|
|
|
|
IRData data;
|
|
IRData old_data;
|
|
|
|
uint32_t IR_Timeout_timer = 0;
|
|
uint8_t dataHandled_flag = 0;
|
|
|
|
uint32_t inputInProgerss_timer = 0;
|
|
uint8_t inputInProgerss = 0;
|
|
uint8_t digitInputInProgerss = 0;
|
|
|
|
uint8_t inputDigit = 0; // left = 0 to right
|
|
|
|
uint16_t inputParam = NULL_NumberParam;
|
|
|
|
uint32_t holdStartTime = 0; // Время начала удержания
|
|
uint32_t lastRepeatTime = 0; // Последнее время повторного вызова функции
|
|
uint32_t currentRepeatTime = InitialRepeatTime; // Текущее значение интервала между вызовами функции
|
|
|
|
void IR_Home_Process();
|
|
|
|
void IR_ParamEnter();
|
|
void IR_CMD_Clear();
|
|
void (*InputHandler)(void) = IR_Home_Process;
|
|
void NullFunc(){};
|
|
void (*onParamEnter)() = NullFunc;
|
|
void (*onHoldRepeat)() = NullFunc; // Указатель на функцию, вызываемую при удержании
|
|
|
|
void paramEnter(void(*onEnter_)()){
|
|
InputHandler = IR_ParamEnter;
|
|
onParamEnter = onEnter_;
|
|
}
|
|
|
|
// Установка функции для вызова при удержании
|
|
void setHoldRepeatHandler(void (*handler)()) {
|
|
onHoldRepeat = handler;
|
|
}
|
|
|
|
void IR_CMD_Handler() {
|
|
|
|
// timeout tick
|
|
if (dataHandled_flag && (millis() - IR_Timeout_timer > IR_Timeout)) {
|
|
dataHandled_flag = 0;
|
|
}
|
|
if (inputInProgerss && (millis() - inputInProgerss_timer > ResetInputProgerss_Timeout)) {
|
|
IR_CMD_Clear();
|
|
|
|
uint8_t blinkPeriod = 25;
|
|
for (int i = 9; i <= 10; ++i) {
|
|
led_blink_num(i, blinkPeriod, 4);
|
|
}
|
|
|
|
}
|
|
|
|
// cmd handler
|
|
if (IR_Available()) {
|
|
data = getIRData();
|
|
|
|
IR_Timeout_timer = millis();
|
|
// works once per button press
|
|
if (memcmp(&data, &old_data, sizeof(IRData)) != 0 || !dataHandled_flag) {
|
|
dataHandled_flag = 1;
|
|
if (IR_Address == 0x01) {
|
|
onHoldRepeat = NullFunc;
|
|
InputHandler();
|
|
inputInProgerss = 1;
|
|
inputInProgerss_timer = millis();
|
|
holdStartTime = millis(); // Запоминаем время начала удержания
|
|
lastRepeatTime = holdStartTime; // Инициализируем таймер повторного вызова
|
|
currentRepeatTime = InitialRepeatTime; // Сбрасываем интервал повторного вызова
|
|
|
|
uint8_t blinkPeriod = 75;
|
|
led_blink_num(19, blinkPeriod, 1);
|
|
led_blink_num(18, blinkPeriod, 1);
|
|
led_blink_num(17, blinkPeriod, 1);
|
|
led_blink_num(2, blinkPeriod, 1);
|
|
led_blink_num(1, blinkPeriod, 1);
|
|
led_blink_num(0, blinkPeriod, 1);
|
|
}
|
|
memcpy(&old_data, &data, sizeof(IRData));
|
|
} else {
|
|
// Проверка на удержание кнопки
|
|
if (millis() - holdStartTime > HoldTime) { // Если кнопка удерживается дольше HoldTime
|
|
if (millis() - lastRepeatTime > currentRepeatTime) { // Если прошло достаточно времени для повторного вызова
|
|
lastRepeatTime = millis(); // Обновляем время последнего вызова
|
|
// uint8_t blinkPeriod = 10;
|
|
led_writeMirror(9, 1);
|
|
|
|
|
|
onHoldRepeat(); // Вызываем функцию при удержании
|
|
|
|
// Уменьшаем интервал до минимального значения
|
|
if (currentRepeatTime > MinRepeatTime) {
|
|
currentRepeatTime -= RepeatDecay;
|
|
if (currentRepeatTime < MinRepeatTime) {
|
|
currentRepeatTime = MinRepeatTime;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
IR_Timeout_timer = millis();
|
|
ClearIRStatus();
|
|
}
|
|
}
|
|
|
|
void IR_CMD_Clear() {
|
|
InputHandler = IR_Home_Process;
|
|
inputDigit = 0;
|
|
inputInProgerss = 0;
|
|
digitInputInProgerss = 0;
|
|
inputParam = NULL_NumberParam;
|
|
// SetShiftReg_inline(0, 0xff, 0);
|
|
}
|
|
|
|
void IR_ParamEnter() {
|
|
// SetShiftReg_inline(0x03, 0, 0);
|
|
if (0 <= data.command && data.command <= 9) {
|
|
if (digitInputInProgerss) {
|
|
inputParam = inputParam * 10; // dec shift << 1
|
|
inputParam += (data.command + 1) % 10;
|
|
// SetShiftReg_inline(0xF0, 0, 0);
|
|
} else {
|
|
inputParam = (data.command + 1) % 10;
|
|
}
|
|
digitInputInProgerss = 1;
|
|
} else {
|
|
digitInputInProgerss = 0;
|
|
switch (data.command) {
|
|
|
|
case IR_ENTER:
|
|
if(inputParam != NULL_NumberParam){
|
|
print("Enter: ");
|
|
printNumber(inputParam);
|
|
// SetShiftReg_inline(0, 0, inputParam);
|
|
onParamEnter();
|
|
}
|
|
inputParam = NULL_NumberParam;
|
|
digitInputInProgerss = 0;
|
|
break;
|
|
|
|
default:
|
|
IR_Home_Process();
|
|
break;
|
|
}
|
|
}
|
|
}
|