Compare commits

...

2 Commits

Author SHA1 Message Date
Clément Grennerat
2c419094ae Setup variable refresh time for different UI components 2025-09-16 23:52:53 +02:00
Clément Grennerat
93a3dd8afd Fixing last UART interface bugs 2025-09-16 23:40:00 +02:00
2 changed files with 102 additions and 33 deletions

View File

@ -3,7 +3,7 @@
#include "LCD_driver.h"
#define COLOR_PRIMARY 0xfdaa
#define COLOR_PRIMARY 0xfd01
#define COLOR_SECONDARY 0x667f
#define COLOR_SUCCESS 0x3766
#define COLOR_ERROR 0xf226
@ -11,11 +11,16 @@
#define COLOR_BG 0x0000
#define COLOR_OFF 0x0000
#define FAULT_CODE_MAX 27
void run_dashboard_loop();
void init();
void update_values_setup();
// refresh_slow = 0 if it should not refresh the low-refresh rate information.
// refresh_mid = 0 if it should not refresh the mid-refresh rate information.
void update_values(uint8_t refresh_slow, uint8_t refresh_mid);
void update_adc();
@ -36,7 +41,7 @@ void draw_power_bars(int16_t duty);
// Displays the huge speed counter with avg and max values.
// Speed from COMM_GET_VALUES_SETUP, scale 1000
void draw_speed(int32_t speed);
void draw_speed(int32_t speed, uint8_t fault_code);
// Displays Current, Duty, Watts
// Current from COMM_GET_VALUES, scale 100

View File

@ -8,22 +8,18 @@
#include "usart.h"
#include "crc.h"
#include "float16.h"
#include "math.h"
#include <stdio.h>
uint8_t initialized = 0;
void run_dashboard_loop() {
LCD_Init();
LCD_Fill_Screen(COLOR_OFF, 1);
LCD_Fill_Screen(COLOR_BG, 0);
HAL_Delay(1000);
while (1) {
update_values_setup();
update_adc();
HAL_Delay(100);
}
}
const char *fault_code_strings[] = { "none", "over voltage", "under voltage",
"driver fault", "abs over current", "over tmp FET", "over tmp motor",
"gate drv over v", "gate drv under v", "MCU under voltage",
"boot watchdog rst", "encoder SPI error", "encoder scos min",
"encoder scos max", "flash corruption", "high ofst cur s1",
"high ofst cur s2", "high ofst cur s3", "unbalanced curs", "brake fault",
"resolver LOT", "resolver DOS", "resolver LOS", "app flash corupt",
"mot flash corupt", "encoder no magnet", "encoder str magnet",
"phase filter fault" };
void run_dashboard_loop_test() {
LCD_Init();
@ -34,12 +30,13 @@ void run_dashboard_loop_test() {
while (1) {
draw_battery(654, i * 100 / 4, 1321, 343);
draw_speed(i * 1000 / 4);
draw_speed(i * 1000 / 4, i % 30);
int16_t duty = 1000 - (int16_t) i * 1000 / 200;
draw_power_bars(duty);
draw_power(100 * i / 20 * (duty < 0 ? -1 : 1), duty, 60 * 10);
draw_adc(i % 34, (400 - i + 16) % 34, i % 34 >= 2.5, (400 - i + 16) % 34 >= 2.5);
draw_adc(i % 34, (400 - i + 16) % 34, i % 34 >= 2.5,
(400 - i + 16) % 34 >= 2.5);
draw_temps((4 * i) % 900, ((10 * i) + 450) % 900);
@ -53,7 +50,33 @@ void run_dashboard_loop_test() {
}
void update_values_setup() {
uint8_t initialized = 0;
void run_dashboard_loop() {
LCD_Init();
LCD_Fill_Screen(COLOR_OFF, 1);
LCD_Fill_Screen(COLOR_BG, 0);
HAL_Delay(1000);
uint8_t i = 0;
while (1) {
uint8_t refresh_slow = (i % 10) == 0;
uint8_t refresh_mid = (i % 3) == 0;
update_values(refresh_slow, refresh_mid);
update_adc();
HAL_Delay(50);
i++;
if (i == 120) {
i = 0;
}
}
}
// refresh_slow = 0 if it should not refresh the low-refresh rate information.
// refresh_mid = 0 if it should not refresh the mid-refresh rate information.
void update_values(uint8_t refresh_slow, uint8_t refresh_mid) {
// UART send 0201 2F D58D 03
uint8_t packet[1];
packet[0] = 0x2F;// COMM_GET_VALUES_SETUP
@ -103,14 +126,25 @@ void update_values_setup() {
if (!initialized) {
draw_init();
initialized = 1;
refresh_slow = 1;
refresh_mid = 1;
}
//speed = (int32_t) (((float) speed) / 1.609344);
//float wheel_diameter = 0.246; // in meter
//speed = ((float) rpm) * 3.14159265359 * wheel_diameter * 60 / 1000;
draw_power_bars(duty_cycle);
if (refresh_mid) {
draw_speed((int32_t) (((float) speed) * 3.6), fault_code);
draw_power(current_in_tot, duty_cycle, input_voltage_filtered);
}
if (refresh_slow) {
draw_battery(input_voltage_filtered, battery_level, distance_abs,
distance_life);
draw_power_bars(duty_cycle);
draw_speed(speed * 10);
draw_power(current_in_tot, duty_cycle, input_voltage_filtered);
draw_temps(temp_fet, temp_motor);
}
}
void update_adc() {
// Replies to 0x24 0x65 for command id: 0, 1, 18, 19, 1B, 1D, C9, CA
// 0 1 24 25 27 29 201 202
@ -381,7 +415,8 @@ uint32_t max_speed = 0;
uint32_t last_avg_speed = 30;
uint32_t avg_speed_tot = 0;// You need to ride super fast for a super long time for it to overflow ;)
uint32_t avg_speed_count = 0;
void draw_speed(int32_t speedd) {
uint8_t last_fault_code = 0;
void draw_speed(int32_t speedd, uint8_t fault_code) {
uint32_t speed = speedd < 0 ? -speedd / 1000 : speedd / 1000;
if (speed >= 100) {
@ -415,9 +450,31 @@ void draw_speed(int32_t speedd) {
COLOR_FG, COLOR_BG, 1, -5);
}
uint16_t erase_width = 90;// width to erase from center
if (last_fault_code != fault_code) {
last_fault_code = fault_code;
if (fault_code == 0) {
update_stats = 1;
erase_width = 100;
} else {
update_stats = 0;
char fault_text[50];// Increased size to accommodate longer strings
if (fault_code <= FAULT_CODE_MAX) {
sprintf(fault_text, "%u %s", fault_code,
fault_code_strings[fault_code]);
} else {
sprintf(fault_text, "%u unknown fault", fault_code);
}
LCD_Draw_Rectangle(LCD_WIDTH / 2 - erase_width, 140, 2 * erase_width, 25,
COLOR_BG);
GFX_DrawText(LCD_WIDTH / 2, 159, fault_text, &monomaniacone14pt,
COLOR_ERROR, COLOR_BG, 1, -3);
}
}
if (update_stats) {
char stats_text[20];
uint16_t erase_width = 90;// width to erase from center
sprintf(stats_text, "avg: %lu max: %lu", avg_speed, max_speed);
LCD_Draw_Rectangle(LCD_WIDTH / 2 - erase_width, 140, 2 * erase_width, 25,
COLOR_BG);
@ -434,10 +491,13 @@ int32_t last_power = 1000;
// Duty from COMM_GET_VALUES, scale 1000
// Input voltage from COMM_GET_VALUES, scale 10
void draw_power(int32_t current_i, int16_t duty_i, int16_t voltage_i) {
if (duty_i < 0 && current_i > 0) {
current_i = -current_i;
}
int16_t current = current_i / 100;
uint16_t duty = duty_i < 0 ? -duty_i / 10 : duty_i / 10;
int32_t power = ((int32_t) voltage_i) * ((int32_t) current_i) / 10000 * 10;
if (power >= 1000) {
power = power / 100 * 100;
} else if (power <= -1000) {
@ -493,7 +553,11 @@ uint8_t last_adc1_en = 0;
uint8_t last_adc2_en = 0;
// Displays the two ADC voltages
//2 voltages from reFloat - COMM_CUSTOM_APP_DATA, scale 10, adcx_en are booleans.
void draw_adc(int32_t adc1_scaled, int32_t adc2_scaled, uint8_t adc1_en, uint8_t adc2_en) {
void draw_adc(
int32_t adc1_scaled,
int32_t adc2_scaled,
uint8_t adc1_en,
uint8_t adc2_en) {
uint16_t adc1 = adc1_scaled < 0 ? -adc1_scaled : adc1_scaled;
uint16_t adc2 = adc2_scaled < 0 ? -adc2_scaled : adc2_scaled;
if (adc1 > 33) {