diff --git a/sa_core.c b/sa_core.c index aa59331..0a86247 100644 --- a/sa_core.c +++ b/sa_core.c @@ -295,8 +295,11 @@ void set_output_path(freq_t f, float level) // if (signal_path != PATH_LEAKAGE) a -= ATTENUATION_RESERVE; if (a > 0) { - a = 0; if (!level_error) { level_error = true; redraw_request |= REDRAW_CAL_STATUS; draw_all(true);} + a += 0.49; + a = (float)((int)(a*2))/2.0; + setting.level -= a; + a = 0; // } else if (setting.modulation == MO_AM && a < -10) { // Insufficient headroom for modulation // if (!level_error) { level_error = true; redraw_request |= REDRAW_CAL_STATUS; draw_all(true); } } else { @@ -5148,6 +5151,17 @@ static volatile int dummy; RSSI = temp_t[i]; #else +#ifdef TINYSA4 + if (MODE_OUTPUT(setting.mode)) { + if (level_error) { + drawMessageBox("WARNING", "Output level reduced", 2000); + level_error = false; + ui_mode_menu(); // Refresh menu + } + } +#endif + + if (MODE_INPUT(setting.mode)) { for (int t=0; t menu_back }; #endif @@ -4365,9 +4371,10 @@ static const menuitem_t menu_traces[] = { MT_ADV_CALLBACK,3, MT_CUSTOM_LABEL, menu_traces_acb}, // Calc { MT_ADV_CALLBACK,4, "NORMALIZE", menu_traces_acb}, { MT_ADV_CALLBACK,5, MT_CUSTOM_LABEL, menu_traces_acb}, // Trace Math - { MT_SUBMENU, 0, "COPY\n"S_RARROW"TRACE", menu_store_trace}, + { MT_SUBMENU, 0, "TRACE\n"S_RARROW"TRACE", menu_store_trace}, #ifdef TINYSA4 - { MT_ADV_CALLBACK,6, "WRITE\n"S_RARROW"SD", menu_traces_acb}, + { MT_ADV_CALLBACK,6, "TRACE\n"S_RARROW"SD", menu_traces_acb}, + { MT_CALLBACK, FMT_CSV_FILE, "SD"S_RARROW"\nTRACE", menu_sdcard_browse_cb }, #endif { MT_NONE, 0, NULL, menu_back} // next-> menu_back }; @@ -6841,6 +6848,17 @@ static void sa_save_file(uint8_t format) { res = f_write(fs_file, (char *)spi_buffer, buf - (char *)spi_buffer, &size); } break; + case FMT_TBL_FILE: + for (i = 0; i < LIMITS_MAX && res == FR_OK; i++) { + if (setting.limits[current_trace][i].enabled) { + char *buf = (char *)spi_buffer; + buf += plot_printf(buf, 100, "%U, ", setting.limits[current_trace][i].frequency); + buf += plot_printf(buf, 100, "%f ", setting.limits[current_trace][i].level); + buf += plot_printf(buf, 100, "\r\n"); + res = f_write(fs_file, (char *)spi_buffer, buf - (char *)spi_buffer, &size); + } + } + break; #ifdef __SD_CARD_DUMP_FIRMWARE__ /* * Dump firmware to SD card as bin file image diff --git a/vna_browser.c b/vna_browser.c index 2183f2d..39d8d30 100644 --- a/vna_browser.c +++ b/vna_browser.c @@ -113,6 +113,82 @@ repeat: ili9341_set_foreground(LCD_FG_COLOR); ili9341_set_background(LCD_BG_COLOR); switch (keypad_mode) { + case FMT_TBL_FILE: + { + const int buffer_size = 256; + const int line_size = 128; + char *buf_8 = (char *)spi_buffer; // must be greater then buffer_size + line_size + char *line = buf_8 + buffer_size; + uint16_t j = 0, i, count = 0; + while (f_read(fs_file, buf_8, buffer_size, &size) == FR_OK && size > 0) { + for (i = 0; i < size; i++) { + uint8_t c = buf_8[i]; + if (c == '\r') { // New line (Enter) + line[j] = 0; j = 0; + char *args[16]; + int nargs = parse_line(line, args, 16); // Parse line to 16 args + if (nargs < 2 || args[0][0] == '#' || args[0][0] == '!') continue; // No data or comment or settings + if (count >= LIMITS_MAX) {error = "Format err"; goto finish2;} + setting.limits[current_trace][count].frequency = my_atoui(args[0]);// Get frequency + setting.limits[current_trace][count].level = my_atof(args[1]); // Get frequency + setting.limits[current_trace][count].enabled = true; // Get frequency + count++; + } + else if (c < 0x20) continue; // Others (skip) + else if (j < line_size) line[j++] = (char)c; // Store + } + } +finish2: + for (; count < LIMITS_MAX; i++) { + setting.limits[current_trace][count].frequency = 0; + setting.limits[current_trace][count].level = 0; + setting.limits[current_trace][count].enabled = false; + count++; + } + break; + } + case FMT_CSV_FILE: + { + const int buffer_size = 256; + const int line_size = 128; + char *buf_8 = (char *)spi_buffer; // must be greater then buffer_size + line_size + char *line = buf_8 + buffer_size; + uint16_t j = 0, i, count = 0; + freq_t start = 0, stop = 0, f; + while (f_read(fs_file, buf_8, buffer_size, &size) == FR_OK && size > 0) { + for (i = 0; i < size; i++) { + uint8_t c = buf_8[i]; + if (c == '\r') { // New line (Enter) + line[j] = 0; j = 0; + char *args[16]; + int nargs = parse_line(line, args, 16); // Parse line to 16 args + if (nargs < 2 || args[0][0] == '#' || args[0][0] == '!') continue; // No data or comment or settings + f = my_atoui(args[0]); // Get frequency + if (count >= POINTS_COUNT || f > maxFreq) {error = "Format err"; goto finish;} + if (count == 0) { + start = f; // For index 0 set as start + setting.stored[current_trace] = true; + TRACE_ENABLE(1<