mirror of
https://github.com/iNavFlight/inav.git
synced 2025-07-21 07:15:16 +03:00
Merge pull request #1831 from martinbudden/inav_osd_single_element
Draw single OSD element per osdUpdate
This commit is contained in:
commit
f4850845df
5 changed files with 124 additions and 59 deletions
|
@ -59,7 +59,7 @@ static uint8_t screenBuffer[VIDEO_BUFFER_CHARS_PAL+40]; //for faster writes we u
|
|||
static uint8_t shadowBuffer[VIDEO_BUFFER_CHARS_PAL];
|
||||
|
||||
//max chars to update in one idle
|
||||
#define MAX_CHARS2UPDATE 100
|
||||
#define MAX_CHARS2UPDATE 50
|
||||
#ifdef MAX7456_DMA_CHANNEL_TX
|
||||
volatile bool dmaTransactionInProgress = false;
|
||||
#endif
|
||||
|
@ -309,7 +309,7 @@ bool max7456DmaInProgres(void)
|
|||
}
|
||||
#endif
|
||||
|
||||
void max7456DrawScreen(void)
|
||||
void max7456DrawScreenPartial(void)
|
||||
{
|
||||
uint8_t check;
|
||||
static uint16_t pos = 0;
|
||||
|
|
|
@ -145,7 +145,7 @@ enum VIDEO_TYPES { AUTO = 0, PAL, NTSC };
|
|||
extern uint16_t maxScreenSize;
|
||||
|
||||
void max7456Init(uint8_t system);
|
||||
void max7456DrawScreen(void);
|
||||
void max7456DrawScreenPartial(void);
|
||||
void max7456WriteNvm(uint8_t char_address, const uint8_t *font_data);
|
||||
uint8_t max7456GetRowsCount(void);
|
||||
void max7456Write(uint8_t x, uint8_t y, const char *buff);
|
||||
|
|
|
@ -505,7 +505,7 @@ cfTask_t cfTasks[TASK_COUNT] = {
|
|||
[TASK_OSD] = {
|
||||
.taskName = "OSD",
|
||||
.taskFunc = taskUpdateOsd,
|
||||
.desiredPeriod = 1000000 / 60, // 60 Hz
|
||||
.desiredPeriod = TASK_PERIOD_HZ(OSD_TASK_FREQUENCY_HZ),
|
||||
.staticPriority = TASK_PRIORITY_LOW,
|
||||
},
|
||||
#endif
|
||||
|
|
|
@ -100,7 +100,7 @@ typedef struct statistic_s {
|
|||
static statistic_t stats;
|
||||
|
||||
uint16_t refreshTimeout = 0;
|
||||
#define REFRESH_1S 12
|
||||
#define REFRESH_1S OSD_TASK_FREQUENCY_HZ
|
||||
|
||||
static uint8_t armState;
|
||||
|
||||
|
@ -138,16 +138,22 @@ static void osdFormatDistanceStr(char* buff, int32_t dist)
|
|||
|
||||
switch (osdConfig()->units) {
|
||||
case OSD_UNIT_IMPERIAL:
|
||||
if (dist < 0)
|
||||
tfp_sprintf(buff, "-%d%c", dist_abs / 100, SYM_FT);
|
||||
else
|
||||
tfp_sprintf(buff, "%d%c", dist_abs / 100, SYM_FT);
|
||||
if (dist < 0) {
|
||||
tfp_sprintf(buff, "-%d%c ", dist_abs / 100, SYM_FT);
|
||||
} else {
|
||||
tfp_sprintf(buff, "%d%c ", dist_abs / 100, SYM_FT);
|
||||
}
|
||||
break;
|
||||
default: // Metric
|
||||
if (dist < 0)
|
||||
tfp_sprintf(buff, "-%d.%01d%c", dist_abs / 100, (dist_abs % 100) / 10, SYM_M);
|
||||
else
|
||||
tfp_sprintf(buff, "%d.%01d%c", dist_abs / 100, (dist_abs % 100) / 10, SYM_M);
|
||||
if (dist < 0) {
|
||||
tfp_sprintf(buff, "-%d.%01d%c ", dist_abs / 100, (dist_abs % 100) / 10, SYM_M);
|
||||
} else {
|
||||
if (dist < 10000) { // less than 100m
|
||||
tfp_sprintf(buff, "%d.%01d%c ", dist_abs / 100, (dist_abs % 100) / 10, SYM_M);
|
||||
} else {
|
||||
tfp_sprintf(buff, "%d%c ", dist_abs / 100, SYM_M);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -173,17 +179,17 @@ static void osdFormatVelocityStr(char* buff, int32_t vel)
|
|||
{
|
||||
switch (osdConfig()->units) {
|
||||
case OSD_UNIT_IMPERIAL:
|
||||
tfp_sprintf(buff, "%d%c", osdConvertVelocityToUnit(vel), SYM_MPH);
|
||||
tfp_sprintf(buff, "%2d%c", osdConvertVelocityToUnit(vel), SYM_MPH);
|
||||
break;
|
||||
default: // Metric
|
||||
tfp_sprintf(buff, "%d%c", osdConvertVelocityToUnit(vel), SYM_KMH);
|
||||
tfp_sprintf(buff, "%3d%c", osdConvertVelocityToUnit(vel), SYM_KMH);
|
||||
}
|
||||
}
|
||||
|
||||
static void osdDrawSingleElement(uint8_t item)
|
||||
static bool osdDrawSingleElement(uint8_t item)
|
||||
{
|
||||
if (!VISIBLE(osdConfig()->item_pos[item]) || BLINK(osdConfig()->item_pos[item])) {
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
|
||||
uint8_t elemPosX = OSD_X(osdConfig()->item_pos[item]);
|
||||
|
@ -198,7 +204,7 @@ static void osdDrawSingleElement(uint8_t item)
|
|||
osdRssi = 99;
|
||||
|
||||
buff[0] = SYM_RSSI;
|
||||
tfp_sprintf(buff + 1, "%d", osdRssi);
|
||||
tfp_sprintf(buff + 1, "%2d", osdRssi);
|
||||
break;
|
||||
}
|
||||
|
||||
|
@ -207,13 +213,13 @@ static void osdDrawSingleElement(uint8_t item)
|
|||
uint8_t p = calculateBatteryPercentage();
|
||||
p = (100 - p) / 16.6;
|
||||
buff[0] = SYM_BATT_FULL + p;
|
||||
tfp_sprintf(buff + 1, "%d.%1dV", vbat / 10, vbat % 10);
|
||||
tfp_sprintf(buff + 1, "%d.%1dV ", vbat / 10, vbat % 10);
|
||||
break;
|
||||
}
|
||||
|
||||
case OSD_CURRENT_DRAW:
|
||||
buff[0] = SYM_AMP;
|
||||
tfp_sprintf(buff + 1, "%d.%02d", abs(amperage) / 100, abs(amperage) % 100);
|
||||
tfp_sprintf(buff + 1, "%d.%02d ", abs(amperage) / 100, abs(amperage) % 100);
|
||||
break;
|
||||
|
||||
case OSD_MAH_DRAWN:
|
||||
|
@ -225,7 +231,7 @@ static void osdDrawSingleElement(uint8_t item)
|
|||
case OSD_GPS_SATS:
|
||||
buff[0] = 0x1e;
|
||||
buff[1] = 0x1f;
|
||||
tfp_sprintf(buff + 2, "%d", gpsSol.numSat);
|
||||
tfp_sprintf(buff + 2, "%2d", gpsSol.numSat);
|
||||
break;
|
||||
|
||||
case OSD_GPS_SPEED:
|
||||
|
@ -278,7 +284,7 @@ static void osdDrawSingleElement(uint8_t item)
|
|||
if (h < 0) h+=360;
|
||||
|
||||
buff[0] = 0xA9;
|
||||
tfp_sprintf(&buff[1], "%d%c", h , 0xA8 );
|
||||
tfp_sprintf(&buff[1], "%3d%c", h , 0xA8 );
|
||||
break;
|
||||
}
|
||||
#endif // GPS
|
||||
|
@ -313,7 +319,7 @@ static void osdDrawSingleElement(uint8_t item)
|
|||
|
||||
#if 0
|
||||
if (isAirmodeActive())
|
||||
p = "AIR";
|
||||
p = "AIR ";
|
||||
#endif
|
||||
|
||||
if (FLIGHT_MODE(PASSTHRU_MODE))
|
||||
|
@ -333,10 +339,10 @@ static void osdDrawSingleElement(uint8_t item)
|
|||
else if (FLIGHT_MODE(ANGLE_MODE))
|
||||
p = "STAB";
|
||||
else if (FLIGHT_MODE(HORIZON_MODE))
|
||||
p = "HOR";
|
||||
p = "HOR ";
|
||||
|
||||
max7456Write(elemPosX, elemPosY, p);
|
||||
return;
|
||||
return true;
|
||||
}
|
||||
|
||||
case OSD_CRAFT_NAME:
|
||||
|
@ -354,12 +360,12 @@ static void osdDrawSingleElement(uint8_t item)
|
|||
case OSD_THROTTLE_POS:
|
||||
buff[0] = SYM_THR;
|
||||
buff[1] = SYM_THR1;
|
||||
tfp_sprintf(buff + 2, "%d", (constrain(rcData[THROTTLE], PWM_RANGE_MIN, PWM_RANGE_MAX) - PWM_RANGE_MIN) * 100 / (PWM_RANGE_MAX - PWM_RANGE_MIN));
|
||||
tfp_sprintf(buff + 2, "%3d", (constrain(rcData[THROTTLE], PWM_RANGE_MIN, PWM_RANGE_MAX) - PWM_RANGE_MIN) * 100 / (PWM_RANGE_MAX - PWM_RANGE_MIN));
|
||||
break;
|
||||
|
||||
#ifdef VTX
|
||||
case OSD_VTX_CHANNEL:
|
||||
tfp_sprintf(buff, "CH:%d", current_vtx_channel % CHANNELS_PER_BAND + 1);
|
||||
tfp_sprintf(buff, "CH:%2d", current_vtx_channel % CHANNELS_PER_BAND + 1);
|
||||
break;
|
||||
#endif // VTX
|
||||
|
||||
|
@ -400,6 +406,10 @@ static void osdDrawSingleElement(uint8_t item)
|
|||
pitchAngle = (pitchAngle / 8) - 41; // 41 = 4 * 9 + 5
|
||||
|
||||
for (int x = -4; x <= 4; x++) {
|
||||
// clear the y area before writing the new horizon character
|
||||
for (int y = 0; y <= 7; y++) {
|
||||
max7456WriteChar(elemPosX + x, elemPosY + y, 0x20);
|
||||
}
|
||||
int y = (rollAngle * x) / 64;
|
||||
y -= pitchAngle;
|
||||
// y += 41; // == 4 * 9 + 5
|
||||
|
@ -410,7 +420,7 @@ static void osdDrawSingleElement(uint8_t item)
|
|||
|
||||
osdDrawSingleElement(OSD_HORIZON_SIDEBARS);
|
||||
|
||||
return;
|
||||
return true;
|
||||
}
|
||||
|
||||
case OSD_HORIZON_SIDEBARS:
|
||||
|
@ -434,9 +444,10 @@ static void osdDrawSingleElement(uint8_t item)
|
|||
max7456WriteChar(elemPosX - hudwidth + 1, elemPosY, SYM_AH_LEFT);
|
||||
max7456WriteChar(elemPosX + hudwidth - 1, elemPosY, SYM_AH_RIGHT);
|
||||
|
||||
return;
|
||||
return true;
|
||||
}
|
||||
|
||||
#if defined(BARO) || defined(GPS)
|
||||
case OSD_VARIO:
|
||||
{
|
||||
int16_t v = getEstimatedActualVelocity(Z) / 50; //50cm = 1 arrow
|
||||
|
@ -472,7 +483,7 @@ static void osdDrawSingleElement(uint8_t item)
|
|||
max7456WriteChar(elemPosX, elemPosY+2, vchars[2]);
|
||||
max7456WriteChar(elemPosX, elemPosY+3, vchars[3]);
|
||||
max7456WriteChar(elemPosX, elemPosY+4, vchars[4]);
|
||||
return;
|
||||
return true;
|
||||
}
|
||||
|
||||
case OSD_VARIO_NUM:
|
||||
|
@ -482,6 +493,7 @@ static void osdDrawSingleElement(uint8_t item)
|
|||
tfp_sprintf(buff, "%c%d.%01d%c", value < 0 ? '-' : ' ', abs(value / 10), abs((value % 10)), 0x9F);
|
||||
break;
|
||||
}
|
||||
#endif
|
||||
|
||||
case OSD_ROLL_PIDS:
|
||||
{
|
||||
|
@ -508,10 +520,49 @@ static void osdDrawSingleElement(uint8_t item)
|
|||
}
|
||||
|
||||
default:
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
|
||||
max7456Write(elemPosX, elemPosY, buff);
|
||||
return true;
|
||||
}
|
||||
|
||||
static uint8_t osdIncElementIndex(uint8_t elementIndex)
|
||||
{
|
||||
++elementIndex;
|
||||
if (!sensors(SENSOR_ACC)) {
|
||||
if (elementIndex == OSD_CROSSHAIRS) {
|
||||
elementIndex = OSD_ONTIME;
|
||||
}
|
||||
}
|
||||
if (!feature(FEATURE_CURRENT_METER)) {
|
||||
if (elementIndex == OSD_CURRENT_DRAW) {
|
||||
elementIndex = OSD_GPS_SPEED;
|
||||
}
|
||||
|
||||
}
|
||||
if (!sensors(SENSOR_GPS)) {
|
||||
if (elementIndex == OSD_GPS_SPEED) {
|
||||
elementIndex = OSD_ALTITUDE;
|
||||
}
|
||||
if (elementIndex == OSD_GPS_LON) {
|
||||
elementIndex = OSD_VARIO;
|
||||
}
|
||||
}
|
||||
|
||||
if (elementIndex == OSD_ITEM_COUNT) {
|
||||
elementIndex = 0;
|
||||
}
|
||||
return elementIndex;
|
||||
}
|
||||
|
||||
void osdDrawNextElement(void)
|
||||
{
|
||||
static uint8_t elementIndex = 0;
|
||||
while (osdDrawSingleElement(elementIndex) == false) {
|
||||
elementIndex = osdIncElementIndex(elementIndex);
|
||||
}
|
||||
elementIndex = osdIncElementIndex(elementIndex);
|
||||
}
|
||||
|
||||
void osdDrawElements(void)
|
||||
|
@ -577,6 +628,7 @@ void osdDrawElements(void)
|
|||
|
||||
}
|
||||
|
||||
|
||||
void pgResetFn_osdConfig(osdConfig_t *osdConfig)
|
||||
{
|
||||
osdConfig->item_pos[OSD_ALTITUDE] = OSD_POS(1, 0) | VISIBLE_FLAG;
|
||||
|
@ -816,7 +868,7 @@ static void osdArmMotors(void)
|
|||
osdResetStats();
|
||||
}
|
||||
|
||||
static void osdRefresh(timeUs_t currentTimeUs)
|
||||
static void osdRefreshStats(timeUs_t currentTimeUs)
|
||||
{
|
||||
static uint8_t lastSec = 0;
|
||||
uint8_t sec;
|
||||
|
@ -840,27 +892,7 @@ static void osdRefresh(timeUs_t currentTimeUs)
|
|||
lastSec = sec;
|
||||
}
|
||||
|
||||
if (refreshTimeout) {
|
||||
if (checkStickPosition(THR_HI) || checkStickPosition(PIT_HI)) // hide statistics
|
||||
refreshTimeout = 1;
|
||||
refreshTimeout--;
|
||||
if (!refreshTimeout)
|
||||
max7456ClearScreen();
|
||||
return;
|
||||
}
|
||||
|
||||
blinkState = (currentTimeUs / 200000) % 2;
|
||||
|
||||
#ifdef CMS
|
||||
if (!displayIsGrabbed(osdDisplayPort)) {
|
||||
osdUpdateAlarms();
|
||||
osdDrawElements();
|
||||
#ifdef OSD_CALLS_CMS
|
||||
} else {
|
||||
cmsUpdate(currentTimeUs);
|
||||
#endif
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -868,18 +900,49 @@ static void osdRefresh(timeUs_t currentTimeUs)
|
|||
*/
|
||||
void osdUpdate(timeUs_t currentTimeUs)
|
||||
{
|
||||
static uint32_t counter = 0;
|
||||
static uint8_t iterationCounter = 0;
|
||||
|
||||
#ifdef MAX7456_DMA_CHANNEL_TX
|
||||
// don't touch buffers if DMA transaction is in progress
|
||||
if (max7456DmaInProgres())
|
||||
if (max7456DmaInProgres()) {
|
||||
return;
|
||||
}
|
||||
#endif // MAX7456_DMA_CHANNEL_TX
|
||||
|
||||
// redraw values in buffer
|
||||
if (counter++ % 5 == 0)
|
||||
osdRefresh(currentTimeUs);
|
||||
else // rest of time redraw screen 10 chars per idle to don't lock the main idle
|
||||
max7456DrawScreen();
|
||||
// refresh alarms every 20 iterations
|
||||
if (iterationCounter == 0) {
|
||||
if (!displayIsGrabbed(osdDisplayPort)) {
|
||||
osdUpdateAlarms();
|
||||
}
|
||||
}
|
||||
// refresh statistics every 20 iterations
|
||||
if (iterationCounter++ >= 20) {
|
||||
iterationCounter = 0;
|
||||
osdRefreshStats(currentTimeUs);
|
||||
}
|
||||
if (refreshTimeout) {
|
||||
if (checkStickPosition(THR_HI) || checkStickPosition(PIT_HI)) { // hide statistics
|
||||
refreshTimeout = 1;
|
||||
}
|
||||
refreshTimeout--;
|
||||
if (!refreshTimeout) {
|
||||
max7456ClearScreen();
|
||||
}
|
||||
max7456DrawScreenPartial();
|
||||
return;
|
||||
}
|
||||
|
||||
#ifdef CMS
|
||||
if (!displayIsGrabbed(osdDisplayPort)) {
|
||||
osdDrawNextElement();
|
||||
#ifdef OSD_CALLS_CMS
|
||||
} else {
|
||||
cmsUpdate(currentTimeUs);
|
||||
#endif
|
||||
}
|
||||
#endif
|
||||
// draw part of screen 10 chars per idle to don't lock the main idle
|
||||
max7456DrawScreenPartial();
|
||||
|
||||
#ifdef CMS
|
||||
// do not allow ARM if we are in menu
|
||||
|
|
|
@ -20,6 +20,8 @@
|
|||
#include "common/time.h"
|
||||
#include "config/parameter_group.h"
|
||||
|
||||
#define OSD_TASK_FREQUENCY_HZ 100
|
||||
|
||||
#define VISIBLE_FLAG 0x0800
|
||||
#define BLINK_FLAG 0x0400
|
||||
#define VISIBLE(x) (x & VISIBLE_FLAG)
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue