Merge pull request #6480 from pulquero/osd_frame_errors_3_5

Added frame quality to OSD.
This commit is contained in:
Michael Keller 2018-11-01 22:24:20 +13:00 committed by GitHub
commit ace5017cc8
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
8 changed files with 113 additions and 22 deletions

View File

@ -997,6 +997,9 @@ const clivalue_t valueTable[] = {
{ "osd_vbat_pos", VAR_UINT16 | MASTER_VALUE, .config.minmax = { 0, OSD_POSCFG_MAX }, PG_OSD_CONFIG, offsetof(osdConfig_t, item_pos[OSD_MAIN_BATT_VOLTAGE]) },
{ "osd_rssi_pos", VAR_UINT16 | MASTER_VALUE, .config.minmax = { 0, OSD_POSCFG_MAX }, PG_OSD_CONFIG, offsetof(osdConfig_t, item_pos[OSD_RSSI_VALUE]) },
#ifdef USE_RX_LINK_QUALITY_INFO
{ "osd_link_quality_pos", VAR_UINT16 | MASTER_VALUE, .config.minmax = { 0, OSD_POSCFG_MAX }, PG_OSD_CONFIG, offsetof(osdConfig_t, item_pos[OSD_LINK_QUALITY]) },
#endif
{ "osd_tim_1_pos", VAR_UINT16 | MASTER_VALUE, .config.minmax = { 0, OSD_POSCFG_MAX }, PG_OSD_CONFIG, offsetof(osdConfig_t, item_pos[OSD_ITEM_TIMER_1]) },
{ "osd_tim_2_pos", VAR_UINT16 | MASTER_VALUE, .config.minmax = { 0, OSD_POSCFG_MAX }, PG_OSD_CONFIG, offsetof(osdConfig_t, item_pos[OSD_ITEM_TIMER_2]) },
{ "osd_remaining_time_estimate_pos", VAR_UINT16 | MASTER_VALUE, .config.minmax = { 0, OSD_POSCFG_MAX }, PG_OSD_CONFIG, offsetof(osdConfig_t, item_pos[OSD_REMAINING_TIME_ESTIMATE]) },
@ -1067,6 +1070,7 @@ const clivalue_t valueTable[] = {
{ "osd_stat_max_g_force", VAR_UINT32 | MASTER_VALUE | MODE_BITSET, .config.bitpos = OSD_STAT_MAX_G_FORCE, PG_OSD_CONFIG, offsetof(osdConfig_t, enabled_stats)},
{ "osd_stat_max_esc_temp", VAR_UINT32 | MASTER_VALUE | MODE_BITSET, .config.bitpos = OSD_STAT_MAX_ESC_TEMP, PG_OSD_CONFIG, offsetof(osdConfig_t, enabled_stats)},
{ "osd_stat_max_esc_rpm", VAR_UINT32 | MASTER_VALUE | MODE_BITSET, .config.bitpos = OSD_STAT_MAX_ESC_RPM, PG_OSD_CONFIG, offsetof(osdConfig_t, enabled_stats)},
{ "osd_stat_min_link_quality", VAR_UINT32 | MASTER_VALUE | MODE_BITSET, .config.bitpos = OSD_STAT_MIN_LINK_QUALITY,PG_OSD_CONFIG, offsetof(osdConfig_t, enabled_stats)},
#endif

View File

@ -133,12 +133,13 @@ typedef struct statistic_s {
int16_t max_speed;
int16_t min_voltage; // /10
int16_t max_current; // /10
int16_t min_rssi;
uint8_t min_rssi;
int32_t max_altitude;
int16_t max_distance;
float max_g_force;
int16_t max_esc_temp;
int32_t max_esc_rpm;
uint8_t min_link_quality;
} statistic_t;
static statistic_t stats;
@ -216,6 +217,9 @@ static const uint8_t osdElementDisplayOrder[] = {
#ifdef USE_ADC_INTERNAL
OSD_CORE_TEMPERATURE,
#endif
#ifdef USE_RX_LINK_QUALITY_INFO
OSD_LINK_QUALITY,
#endif
};
PG_REGISTER_WITH_RESET_FN(osdConfig_t, osdConfig, PG_OSD_CONFIG, 3);
@ -502,13 +506,28 @@ static bool osdDrawSingleElement(uint8_t item)
case OSD_RSSI_VALUE:
{
uint16_t osdRssi = getRssi() * 100 / 1024; // change range
if (osdRssi >= 100)
if (osdRssi >= 100) {
osdRssi = 99;
}
tfp_sprintf(buff, "%c%2d", SYM_RSSI, osdRssi);
break;
}
#ifdef USE_RX_LINK_QUALITY_INFO
case OSD_LINK_QUALITY:
{
// change range to 0-9 (two sig. fig. adds little extra value, also reduces screen estate)
uint8_t osdLinkQuality = rxGetLinkQuality() * 10 / LINK_QUALITY_MAX_VALUE;
if (osdLinkQuality >= 10) {
osdLinkQuality = 9;
}
tfp_sprintf(buff, "%1d", osdLinkQuality);
break;
}
#endif
case OSD_MAIN_BATT_VOLTAGE:
buff[0] = osdGetBatterySymbol(osdGetBatteryAverageCellVoltage());
tfp_sprintf(buff + 1, "%2d.%1d%c", getBatteryVoltage() / 10, getBatteryVoltage() % 10, SYM_VOLT);
@ -1345,13 +1364,14 @@ static void osdResetStats(void)
stats.max_current = 0;
stats.max_speed = 0;
stats.min_voltage = 500;
stats.min_rssi = 99;
stats.min_rssi = 99; // percent
stats.max_altitude = 0;
stats.max_distance = 0;
stats.armed_time = 0;
stats.max_g_force = 0;
stats.max_esc_temp = 0;
stats.max_esc_rpm = 0;
stats.min_link_quality = 99; // percent
}
static void osdUpdateStats(void)
@ -1395,6 +1415,13 @@ static void osdUpdateStats(void)
stats.max_g_force = osdGForce;
}
#ifdef USE_RX_LINK_QUALITY_INFO
value = rxGetLinkQualityPercent();
if (stats.min_link_quality > value) {
stats.min_link_quality = value;
}
#endif
#ifdef USE_GPS
if (STATE(GPS_FIX) && STATE(GPS_FIX_HOME)) {
value = GPS_distanceToHome;
@ -1591,6 +1618,13 @@ static void osdShowStats(uint16_t endBatteryVoltage)
}
#endif
#ifdef USE_RX_LINK_QUALITY_INFO
if (osdStatGetState(OSD_STAT_MIN_LINK_QUALITY)) {
itoa(stats.min_link_quality, buff, 10);
strcat(buff, "%");
osdDisplayStatisticLabel(top++, "MIN LINK", buff);
}
#endif
}
static void osdShowArmed(void)

View File

@ -99,6 +99,7 @@ typedef enum {
OSD_G_FORCE,
OSD_LOG_STATUS,
OSD_FLIP_ARROW,
OSD_LINK_QUALITY,
OSD_ITEM_COUNT // MUST BE LAST
} osd_items_e;
@ -129,6 +130,7 @@ typedef enum {
OSD_STAT_MAX_G_FORCE,
OSD_STAT_MAX_ESC_TEMP,
OSD_STAT_MAX_ESC_RPM,
OSD_STAT_MIN_LINK_QUALITY,
OSD_STAT_COUNT // MUST BE LAST
} osd_stats_e;

View File

@ -72,6 +72,9 @@ const char rcChannelLetters[] = "AERT12345678abcdefgh";
static uint16_t rssi = 0; // range: [0;1023]
static timeUs_t lastMspRssiUpdateUs = 0;
#ifdef USE_RX_LINK_QUALITY_INFO
static uint8_t linkQuality = 0;
#endif
#define MSP_RSSI_TIMEOUT_US 1500000 // 1.5 sec
@ -344,6 +347,34 @@ void resumeRxPwmPpmSignal(void)
#endif
}
#ifdef USE_RX_LINK_QUALITY_INFO
#define LINK_QUALITY_SAMPLE_COUNT 16
static uint8_t updateLinkQualitySamples(uint8_t value)
{
static uint8_t samples[LINK_QUALITY_SAMPLE_COUNT];
static uint8_t sampleIndex = 0;
static unsigned sum = 0;
sum += value - samples[sampleIndex];
samples[sampleIndex] = value;
sampleIndex = (sampleIndex + 1) % LINK_QUALITY_SAMPLE_COUNT;
return sum / LINK_QUALITY_SAMPLE_COUNT;
}
#endif
static void setLinkQuality(bool validFrame)
{
#ifdef USE_RX_LINK_QUALITY_INFO
// calculate new sample mean
linkQuality = updateLinkQualitySamples(validFrame ? LINK_QUALITY_MAX_VALUE : 0);
#endif
if (rssiSource == RSSI_SOURCE_FRAME_ERRORS) {
setRssi(validFrame ? RSSI_MAX_VALUE : 0, RSSI_SOURCE_FRAME_ERRORS);
}
}
bool rxUpdateCheck(timeUs_t currentTimeUs, timeDelta_t currentDeltaTime)
{
UNUSED(currentDeltaTime);
@ -378,13 +409,7 @@ bool rxUpdateCheck(timeUs_t currentTimeUs, timeDelta_t currentDeltaTime)
needRxSignalBefore = currentTimeUs + needRxSignalMaxDelayUs;
}
if (frameStatus & (RX_FRAME_FAILSAFE | RX_FRAME_DROPPED)) {
// No (0%) signal
setRssi(0, RSSI_SOURCE_FRAME_ERRORS);
} else {
// Valid (100%) signal
setRssi(RSSI_MAX_VALUE, RSSI_SOURCE_FRAME_ERRORS);
}
setLinkQuality(signalReceived);
}
if (frameStatus & RX_FRAME_PROCESSING_REQUIRED) {
@ -594,24 +619,26 @@ void setRssiDirect(uint16_t newRssi, rssiSource_e source)
#define RSSI_SAMPLE_COUNT 16
static uint16_t updateRssiSamples(uint16_t value)
{
static uint16_t samples[RSSI_SAMPLE_COUNT];
static uint8_t sampleIndex = 0;
static unsigned sum = 0;
sum += value - samples[sampleIndex];
samples[sampleIndex] = value;
sampleIndex = (sampleIndex + 1) % RSSI_SAMPLE_COUNT;
return sum / RSSI_SAMPLE_COUNT;
}
void setRssi(uint16_t rssiValue, rssiSource_e source)
{
if (source != rssiSource) {
return;
}
static uint16_t rssiSamples[RSSI_SAMPLE_COUNT];
static uint8_t rssiSampleIndex = 0;
static unsigned sum = 0;
sum = sum + rssiValue;
sum = sum - rssiSamples[rssiSampleIndex];
rssiSamples[rssiSampleIndex] = rssiValue;
rssiSampleIndex = (rssiSampleIndex + 1) % RSSI_SAMPLE_COUNT;
int16_t rssiMean = sum / RSSI_SAMPLE_COUNT;
rssi = rssiMean;
// calculate new sample mean
rssi = updateRssiSamples(rssiValue);
}
void setRssiMsp(uint8_t newMspRssi)
@ -693,6 +720,18 @@ uint8_t getRssiPercent(void)
return scaleRange(getRssi(), 0, RSSI_MAX_VALUE, 0, 100);
}
#ifdef USE_RX_LINK_QUALITY_INFO
uint8_t rxGetLinkQuality(void)
{
return linkQuality;
}
uint8_t rxGetLinkQualityPercent(void)
{
return scaleRange(rxGetLinkQuality(), 0, LINK_QUALITY_MAX_VALUE, 0, 100);
}
#endif
uint16_t rxGetRefreshRate(void)
{
return rxRuntimeConfig.rxRefreshRate;

View File

@ -168,6 +168,11 @@ uint16_t getRssi(void);
uint8_t getRssiPercent(void);
bool isRssiConfigured(void);
#define LINK_QUALITY_MAX_VALUE 255
uint8_t rxGetLinkQuality(void);
uint8_t rxGetLinkQualityPercent(void);
void resetAllRxChannelRangeConfigurations(rxChannelRangeConfig_t *rxChannelRangeConfig);
void suspendRxPwmPpmSignal(void);

View File

@ -124,6 +124,10 @@
#undef USE_MSP_OVER_TELEMETRY
#endif
#if !defined(USE_OSD)
#undef USE_RX_LINK_QUALITY_INFO
#endif
/* If either VTX_CONTROL or VTX_COMMON is undefined then remove common code and device drivers */
#if !defined(USE_VTX_COMMON) || !defined(USE_VTX_CONTROL)
#undef USE_VTX_COMMON

View File

@ -229,4 +229,5 @@
#define USE_HOTT_TEXTMODE
#define USE_LED_STRIP
#define USE_VARIO
#define USE_RX_LINK_QUALITY_INFO
#endif

View File

@ -1051,6 +1051,8 @@ extern "C" {
uint8_t getRssiPercent(void) { return scaleRange(rssi, 0, RSSI_MAX_VALUE, 0, 100); }
uint8_t rxGetLinkQuality(void) { return LINK_QUALITY_MAX_VALUE; }
uint16_t getCoreTemperatureCelsius(void) { return simulationCoreTemperature; }
bool isFlipOverAfterCrashMode(void) {