From 1d79e149cfb3279c9b27fcc2873c3fba8a928841 Mon Sep 17 00:00:00 2001 From: gid9798 <30450294+gid9798@users.noreply.github.com> Date: Fri, 19 May 2023 12:32:35 +0300 Subject: [PATCH 1/6] subrem fix repeat --- .../main/subghz_remote/subghz_remote_app_i.c | 20 ++++++++++++++++--- 1 file changed, 17 insertions(+), 3 deletions(-) diff --git a/applications/main/subghz_remote/subghz_remote_app_i.c b/applications/main/subghz_remote/subghz_remote_app_i.c index 9b0f77d17..171618a5f 100644 --- a/applications/main/subghz_remote/subghz_remote_app_i.c +++ b/applications/main/subghz_remote/subghz_remote_app_i.c @@ -129,23 +129,31 @@ bool subrem_save_protocol_to_file(FlipperFormat* flipper_format, const char* dev Stream* flipper_format_stream = flipper_format_get_raw_stream(flipper_format); bool saved = false; + uint32_t repeat = 200; FuriString* file_dir = furi_string_alloc(); path_extract_dirname(dev_file_name, file_dir); do { - //removing additional fields + // removing additional fields flipper_format_delete_key(flipper_format, "Repeat"); - //flipper_format_delete_key(flipper_format, "Manufacture"); + // flipper_format_delete_key(flipper_format, "Manufacture"); if(!storage_simply_remove(storage, dev_file_name)) { break; } + //ToDo check Write stream_seek(flipper_format_stream, 0, StreamOffsetFromStart); stream_save_to_file(flipper_format_stream, storage, dev_file_name, FSOM_CREATE_ALWAYS); + if(!flipper_format_insert_or_update_uint32(flipper_format, "Repeat", &repeat, 1)) { + FURI_LOG_E(TAG, "Unable Repeat"); + break; + } + saved = true; } while(0); + furi_string_free(file_dir); furi_record_close(RECORD_STORAGE); return saved; @@ -267,7 +275,7 @@ static bool subrem_map_preset_check(SubGhzRemoteApp* app, FlipperFormat* fff_dat bool ret = false; bool sub_preset_loaded = false; SubRemSubFilePreset* sub_preset; - + uint32_t repeat = 200; for(uint8_t i = 0; i < SubRemSubKeyNameMaxCount; i++) { sub_preset = app->subs_preset[i]; sub_preset_loaded = false; @@ -275,6 +283,7 @@ static bool subrem_map_preset_check(SubGhzRemoteApp* app, FlipperFormat* fff_dat // FURI_LOG_I(TAG, "Empty file path"); continue; } + repeat = 200; do { if(!flipper_format_file_open_existing( fff_data_file, furi_string_get_cstr(sub_preset->file_path))) { @@ -361,6 +370,11 @@ static bool subrem_map_preset_check(SubGhzRemoteApp* app, FlipperFormat* fff_dat FURI_LOG_E(TAG, "Protocol does not support transmission"); } + if(!flipper_format_insert_or_update_uint32(fff_data, "Repeat", &repeat, 1)) { + FURI_LOG_E(TAG, "Unable Repeat"); + break; + } + sub_preset_loaded = true; ret |= true; #if FURI_DEBUG From 47f6d787372e577e137f3fd4c645323b436c4b5a Mon Sep 17 00:00:00 2001 From: gid9798 <30450294+gid9798@users.noreply.github.com> Date: Fri, 19 May 2023 23:21:18 +0300 Subject: [PATCH 2/6] Loading States & fix label length --- .../main/subghz_remote/helpers/subrem_types.h | 15 +++++ .../scenes/subrem_scene_openmapfile.c | 2 +- .../subghz_remote/scenes/subrem_scene_start.c | 6 +- .../main/subghz_remote/subghz_remote_app_i.c | 58 ++++++++++++------- .../main/subghz_remote/subghz_remote_app_i.h | 3 +- .../main/subghz_remote/views/remote.c | 2 +- 6 files changed, 60 insertions(+), 26 deletions(-) diff --git a/applications/main/subghz_remote/helpers/subrem_types.h b/applications/main/subghz_remote/helpers/subrem_types.h index 1b99aac6d..13b42897f 100644 --- a/applications/main/subghz_remote/helpers/subrem_types.h +++ b/applications/main/subghz_remote/helpers/subrem_types.h @@ -25,8 +25,23 @@ typedef enum { SubRemViewIDRemote, } SubRemViewID; +typedef enum { + SubRemLoadSubStateNotSet, + SubRemLoadSubStatePreloaded, + SubRemLoadSubStateError, + SubRemLoadSubStateErrorNoFile, + SubRemLoadSubStateErrorFreq, + SubRemLoadSubStateErrorMod, + SubRemLoadSubStateErrorProtocol, + SubRemLoadSubStateOK, +} SubRemLoadSubState; + typedef enum { SubRemLoadMapStateBack = 0, SubRemLoadMapStateError, + SubRemLoadMapStateErrorOpenError, + SubRemLoadMapStateErrorStorage, + SubRemLoadMapStateErrorBrokenFile, + SubRemLoadMapStateNotAllOK, SubRemLoadMapStateOK, } SubRemLoadMapState; \ No newline at end of file diff --git a/applications/main/subghz_remote/scenes/subrem_scene_openmapfile.c b/applications/main/subghz_remote/scenes/subrem_scene_openmapfile.c index 3391845e1..ea5c14a0a 100644 --- a/applications/main/subghz_remote/scenes/subrem_scene_openmapfile.c +++ b/applications/main/subghz_remote/scenes/subrem_scene_openmapfile.c @@ -18,7 +18,7 @@ void subrem_scene_openmapfile_on_enter(void* context) { dialog_message_free(message); #endif } - if(load_state == SubRemLoadMapStateOK) { + if(load_state == SubRemLoadMapStateOK || load_state == SubRemLoadMapStateNotAllOK) { scene_manager_next_scene(app->scene_manager, SubRemSceneRemote); } else { // TODO: Map Preset Reset diff --git a/applications/main/subghz_remote/scenes/subrem_scene_start.c b/applications/main/subghz_remote/scenes/subrem_scene_start.c index 962eda54c..a4bfa5047 100644 --- a/applications/main/subghz_remote/scenes/subrem_scene_start.c +++ b/applications/main/subghz_remote/scenes/subrem_scene_start.c @@ -34,8 +34,10 @@ void subrem_scene_start_on_enter(void* context) { // subrem_scene_start_submenu_callback, // app); - submenu_set_selected_item( - submenu, scene_manager_get_scene_state(app->scene_manager, SubRemSceneStart)); + // TODO: set scene state in subrem alloc + // submenu_set_selected_item( + // submenu, scene_manager_get_scene_state(app->scene_manager, SubRemSceneStart)); + submenu_set_selected_item(submenu, SubmenuIndexSubRemOpenMapFile); view_dispatcher_switch_to_view(app->view_dispatcher, SubRemViewSubmenu); } diff --git a/applications/main/subghz_remote/subghz_remote_app_i.c b/applications/main/subghz_remote/subghz_remote_app_i.c index 171618a5f..349fb87cd 100644 --- a/applications/main/subghz_remote/subghz_remote_app_i.c +++ b/applications/main/subghz_remote/subghz_remote_app_i.c @@ -51,6 +51,7 @@ SubRemSubFilePreset* subrem_sub_file_preset_alloc() { sub_preset->label = furi_string_alloc_set_str("N/A"); sub_preset->type = SubGhzProtocolTypeUnknown; + sub_preset->load_state = SubRemLoadSubStateNotSet; return sub_preset; } @@ -77,6 +78,7 @@ static void subrem_sub_file_preset_reset(SubRemSubFilePreset* sub_preset) { stream_clean(fff_data_stream); sub_preset->type = SubGhzProtocolTypeUnknown; + sub_preset->load_state = SubRemLoadSubStateNotSet; } void subrem_map_preset_reset(SubGhzRemoteApp* app) { @@ -108,6 +110,7 @@ static bool subrem_map_preset_load(SubGhzRemoteApp* app, FlipperFormat* fff_data #endif path_extract_filename(sub_preset->file_path, sub_preset->label, true); } else { + // Preload seccesful FURI_LOG_I( TAG, "%-5s: %s %s", @@ -115,6 +118,7 @@ static bool subrem_map_preset_load(SubGhzRemoteApp* app, FlipperFormat* fff_data furi_string_get_cstr(sub_preset->label), furi_string_get_cstr(sub_preset->file_path)); ret = true; + sub_preset->load_state = SubRemLoadSubStatePreloaded; } flipper_format_rewind(fff_data_file); } @@ -268,21 +272,25 @@ bool subrem_tx_stop_sub(SubGhzRemoteApp* app, bool forced) { return false; } -static bool subrem_map_preset_check(SubGhzRemoteApp* app, FlipperFormat* fff_data_file) { +static SubRemLoadMapState + subrem_map_preset_check(SubGhzRemoteApp* app, FlipperFormat* fff_data_file) { furi_assert(app); FuriString* temp_str = furi_string_alloc(); uint32_t temp_data32; - bool ret = false; - bool sub_preset_loaded = false; + bool all_loaded = true; + SubRemLoadMapState ret = SubRemLoadMapStateErrorBrokenFile; + SubRemLoadSubState sub_preset_loaded; SubRemSubFilePreset* sub_preset; uint32_t repeat = 200; for(uint8_t i = 0; i < SubRemSubKeyNameMaxCount; i++) { sub_preset = app->subs_preset[i]; - sub_preset_loaded = false; if(furi_string_empty(sub_preset->file_path)) { // FURI_LOG_I(TAG, "Empty file path"); continue; } + + sub_preset_loaded = SubRemLoadSubStateErrorNoFile; + repeat = 200; do { if(!flipper_format_file_open_existing( @@ -305,6 +313,7 @@ static bool subrem_map_preset_check(SubGhzRemoteApp* app, FlipperFormat* fff_dat } //Load frequency + sub_preset_loaded = SubRemLoadSubStateErrorFreq; if(!flipper_format_read_uint32(fff_data_file, "Frequency", &temp_data32, 1)) { FURI_LOG_W(TAG, "Cannot read frequency. Set default frequency"); sub_preset->freq_preset.frequency = @@ -317,6 +326,7 @@ static bool subrem_map_preset_check(SubGhzRemoteApp* app, FlipperFormat* fff_dat } //Load preset + sub_preset_loaded = SubRemLoadSubStateErrorMod; if(!flipper_format_read_string(fff_data_file, "Preset", temp_str)) { FURI_LOG_E(TAG, "Missing Preset"); break; @@ -329,6 +339,7 @@ static bool subrem_map_preset_check(SubGhzRemoteApp* app, FlipperFormat* fff_dat } //Load protocol + sub_preset_loaded = SubRemLoadSubStateErrorProtocol; if(!flipper_format_read_string(fff_data_file, "Protocol", temp_str)) { FURI_LOG_E(TAG, "Missing Protocol"); break; @@ -375,8 +386,9 @@ static bool subrem_map_preset_check(SubGhzRemoteApp* app, FlipperFormat* fff_dat break; } - sub_preset_loaded = true; - ret |= true; + sub_preset_loaded = SubRemLoadSubStateOK; + ret = SubRemLoadMapStateNotAllOK; + #if FURI_DEBUG FURI_LOG_I(TAG, "%-16s - protocol Loaded", furi_string_get_cstr(sub_preset->label)); #endif @@ -385,9 +397,15 @@ static bool subrem_map_preset_check(SubGhzRemoteApp* app, FlipperFormat* fff_dat // TODO: // Load file state logic // Label depending on the state + // Move to remote scene - if(!sub_preset_loaded) { + if(sub_preset_loaded != SubRemLoadSubStateOK) { furi_string_set_str(sub_preset->label, "N/A"); + all_loaded = false; + } + + if(ret != SubRemLoadMapStateErrorBrokenFile && all_loaded) { + ret = SubRemLoadMapStateOK; } flipper_format_file_close(fff_data_file); @@ -397,7 +415,7 @@ static bool subrem_map_preset_check(SubGhzRemoteApp* app, FlipperFormat* fff_dat return ret; } -bool subrem_map_file_load(SubGhzRemoteApp* app, const char* file_path) { +SubRemLoadMapState subrem_map_file_load(SubGhzRemoteApp* app, const char* file_path) { furi_assert(app); furi_assert(file_path); #if FURI_DEBUG @@ -405,7 +423,7 @@ bool subrem_map_file_load(SubGhzRemoteApp* app, const char* file_path) { #endif Storage* storage = furi_record_open(RECORD_STORAGE); FlipperFormat* fff_data_file = flipper_format_file_alloc(storage); - bool ret = false; + SubRemLoadMapState ret = SubRemLoadMapStateErrorOpenError; #if FURI_DEBUG FURI_LOG_I(TAG, "Open Map File.."); #endif @@ -413,20 +431,23 @@ bool subrem_map_file_load(SubGhzRemoteApp* app, const char* file_path) { if(!flipper_format_file_open_existing(fff_data_file, file_path)) { FURI_LOG_E(TAG, "Could not open MAP file %s", file_path); + ret = SubRemLoadMapStateErrorOpenError; } else { if(!subrem_map_preset_load(app, fff_data_file)) { FURI_LOG_E(TAG, "Could no Sub file path in MAP file"); // ret = // error for popup - } else if( - (flipper_format_file_close(fff_data_file)) && - (subrem_map_preset_check(app, fff_data_file))) { - FURI_LOG_I(TAG, "Load Map File Seccesful"); - ret = true; + } else if(!flipper_format_file_close(fff_data_file)) { + ret = SubRemLoadMapStateErrorOpenError; + } else { + ret = subrem_map_preset_check(app, fff_data_file); } } - // TODO: Popup for error or return error type - if(!ret) { + if(ret == SubRemLoadMapStateOK) { + FURI_LOG_I(TAG, "Load Map File Seccesful"); + } else if(ret == SubRemLoadMapStateNotAllOK) { + FURI_LOG_I(TAG, "Load Map File Seccesful [Not all files]"); + } else { FURI_LOG_E(TAG, "Broken Map File"); } @@ -434,7 +455,6 @@ bool subrem_map_file_load(SubGhzRemoteApp* app, const char* file_path) { flipper_format_free(fff_data_file); furi_record_close(RECORD_STORAGE); - return ret; } @@ -450,10 +470,8 @@ SubRemLoadMapState subrem_load_from_file(SubGhzRemoteApp* app) { // Input events and views are managed by file_select if(!dialog_file_browser_show(app->dialogs, app->file_path, app->file_path, &browser_options)) { - } else if(subrem_map_file_load(app, furi_string_get_cstr(app->file_path))) { - ret = SubRemLoadMapStateOK; } else { - ret = SubRemLoadMapStateError; + ret = subrem_map_file_load(app, furi_string_get_cstr(app->file_path)); } furi_string_free(file_path); diff --git a/applications/main/subghz_remote/subghz_remote_app_i.h b/applications/main/subghz_remote/subghz_remote_app_i.h index 1cbdbd5cd..40d70411a 100644 --- a/applications/main/subghz_remote/subghz_remote_app_i.h +++ b/applications/main/subghz_remote/subghz_remote_app_i.h @@ -42,6 +42,7 @@ typedef struct { FuriString* protocaol_name; FuriString* label; SubGhzProtocolType type; + SubRemLoadSubState load_state; } SubRemSubFilePreset; SubRemSubFilePreset* subrem_sub_file_preset_alloc(); @@ -70,8 +71,6 @@ typedef struct { bool tx_running; uint8_t chusen_sub; - - // TODO: LoadFileError } SubGhzRemoteApp; SubRemLoadMapState subrem_load_from_file(SubGhzRemoteApp* app); diff --git a/applications/main/subghz_remote/views/remote.c b/applications/main/subghz_remote/views/remote.c index 85c63568e..1f867cd0b 100644 --- a/applications/main/subghz_remote/views/remote.c +++ b/applications/main/subghz_remote/views/remote.c @@ -4,7 +4,7 @@ #include #include -#define SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH 16 +#define SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH 12 struct SubRemViewRemote { View* view; From 561b54ce361c9627cb968f48bf2c3cab5c205b23 Mon Sep 17 00:00:00 2001 From: gid9798 <30450294+gid9798@users.noreply.github.com> Date: Sat, 20 May 2023 09:38:44 +0300 Subject: [PATCH 3/6] SubGHz App: alloc balance --- applications/main/subghz/scenes/subghz_scene_decode_raw.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/applications/main/subghz/scenes/subghz_scene_decode_raw.c b/applications/main/subghz/scenes/subghz_scene_decode_raw.c index e88da3749..102965df5 100644 --- a/applications/main/subghz/scenes/subghz_scene_decode_raw.c +++ b/applications/main/subghz/scenes/subghz_scene_decode_raw.c @@ -179,11 +179,12 @@ void subghz_scene_decode_raw_on_enter(void* context) { furi_string_get_cstr(item_time), subghz_history_get_type_protocol(subghz->history, i)); } - furi_string_free(item_name); - furi_string_free(item_time); subghz_view_receiver_set_idx_menu(subghz->subghz_receiver, subghz->idx_menu_chosen); } + furi_string_free(item_name); + furi_string_free(item_time); + subghz_scene_receiver_update_statusbar(subghz); view_dispatcher_switch_to_view(subghz->view_dispatcher, SubGhzViewIdReceiver); From 47b1cadbb66f00cfdb2f9d7fd63896fa2ca1b20f Mon Sep 17 00:00:00 2001 From: gid9798 <30450294+gid9798@users.noreply.github.com> Date: Sat, 20 May 2023 15:05:26 +0300 Subject: [PATCH 4/6] fix alloc balance --- applications/main/subghz_remote/subghz_remote_app.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/applications/main/subghz_remote/subghz_remote_app.c b/applications/main/subghz_remote/subghz_remote_app.c index 0b3f645ab..b957fb8bc 100644 --- a/applications/main/subghz_remote/subghz_remote_app.c +++ b/applications/main/subghz_remote/subghz_remote_app.c @@ -42,6 +42,7 @@ SubGhzRemoteApp* subghz_remote_app_alloc() { // View Dispatcher app->view_dispatcher = view_dispatcher_alloc(); + app->scene_manager = scene_manager_alloc(&subrem_scene_handlers, app); view_dispatcher_enable_queue(app->view_dispatcher); @@ -127,6 +128,9 @@ void subghz_remote_app_free(SubGhzRemoteApp* app) { view_dispatcher_remove_view(app->view_dispatcher, SubRemViewIDRemote); subrem_view_remote_free(app->subrem_remote_view); + scene_manager_free(app->scene_manager); + view_dispatcher_free(app->view_dispatcher); + subghz_receiver_free(app->receiver); subghz_environment_free(app->environment); subghz_setting_free(app->setting); From e71a66535d3d151af82d02029a8f7bf9396eb2d7 Mon Sep 17 00:00:00 2001 From: gid9798 <30450294+gid9798@users.noreply.github.com> Date: Sun, 21 May 2023 10:29:58 +0300 Subject: [PATCH 5/6] move part of preset --- .../subghz_remote/helpers/subrem_presets.c | 40 ++ .../subghz_remote/helpers/subrem_presets.h | 27 ++ .../scenes/subrem_scene_remote.c | 12 +- .../main/subghz_remote/subghz_remote_app.c | 6 +- .../main/subghz_remote/subghz_remote_app_i.c | 345 ++++++++---------- .../main/subghz_remote/subghz_remote_app_i.h | 28 +- 6 files changed, 237 insertions(+), 221 deletions(-) create mode 100644 applications/main/subghz_remote/helpers/subrem_presets.c create mode 100644 applications/main/subghz_remote/helpers/subrem_presets.h diff --git a/applications/main/subghz_remote/helpers/subrem_presets.c b/applications/main/subghz_remote/helpers/subrem_presets.c new file mode 100644 index 000000000..03e497198 --- /dev/null +++ b/applications/main/subghz_remote/helpers/subrem_presets.c @@ -0,0 +1,40 @@ +#include "subrem_presets.h" + +SubRemSubFilePreset* subrem_sub_file_preset_alloc() { + SubRemSubFilePreset* sub_preset = malloc(sizeof(SubRemSubFilePreset)); + + sub_preset->fff_data = flipper_format_string_alloc(); + sub_preset->file_path = furi_string_alloc(); + sub_preset->protocaol_name = furi_string_alloc(); + sub_preset->label = furi_string_alloc_set_str("N/A"); + + sub_preset->type = SubGhzProtocolTypeUnknown; + sub_preset->load_state = SubRemLoadSubStateNotSet; + + return sub_preset; +} + +void subrem_sub_file_preset_free(SubRemSubFilePreset* sub_preset) { + furi_assert(sub_preset); + + furi_string_free(sub_preset->label); + furi_string_free(sub_preset->protocaol_name); + furi_string_free(sub_preset->file_path); + flipper_format_free(sub_preset->fff_data); + + free(sub_preset); +} + +void subrem_sub_file_preset_reset(SubRemSubFilePreset* sub_preset) { + furi_assert(sub_preset); + + furi_string_set_str(sub_preset->label, "N/A"); + furi_string_reset(sub_preset->protocaol_name); + furi_string_reset(sub_preset->file_path); + + Stream* fff_data_stream = flipper_format_get_raw_stream(sub_preset->fff_data); + stream_clean(fff_data_stream); + + sub_preset->type = SubGhzProtocolTypeUnknown; + sub_preset->load_state = SubRemLoadSubStateNotSet; +} diff --git a/applications/main/subghz_remote/helpers/subrem_presets.h b/applications/main/subghz_remote/helpers/subrem_presets.h new file mode 100644 index 000000000..60eedad57 --- /dev/null +++ b/applications/main/subghz_remote/helpers/subrem_presets.h @@ -0,0 +1,27 @@ +#pragma once + +#include "subrem_types.h" +#include +#include + +typedef struct { + uint32_t frequency; + uint8_t* data; +} FreqPreset; + +// Sub File preset +typedef struct { + FlipperFormat* fff_data; + FreqPreset freq_preset; + FuriString* file_path; + FuriString* protocaol_name; + FuriString* label; + SubGhzProtocolType type; + SubRemLoadSubState load_state; +} SubRemSubFilePreset; + +SubRemSubFilePreset* subrem_sub_file_preset_alloc(); + +void subrem_sub_file_preset_free(SubRemSubFilePreset* sub_preset); + +void subrem_sub_file_preset_reset(SubRemSubFilePreset* sub_preset); diff --git a/applications/main/subghz_remote/scenes/subrem_scene_remote.c b/applications/main/subghz_remote/scenes/subrem_scene_remote.c index c24583233..1b8dbc471 100644 --- a/applications/main/subghz_remote/scenes/subrem_scene_remote.c +++ b/applications/main/subghz_remote/scenes/subrem_scene_remote.c @@ -41,11 +41,11 @@ static bool subrem_scene_remote_update_data_show(void* context) { subrem_view_remote_add_data_to_show( app->subrem_remote_view, - furi_string_get_cstr(app->subs_preset[0]->label), - furi_string_get_cstr(app->subs_preset[1]->label), - furi_string_get_cstr(app->subs_preset[2]->label), - furi_string_get_cstr(app->subs_preset[3]->label), - furi_string_get_cstr(app->subs_preset[4]->label)); + furi_string_get_cstr(app->map_preset->subs_preset[0]->label), + furi_string_get_cstr(app->map_preset->subs_preset[1]->label), + furi_string_get_cstr(app->map_preset->subs_preset[2]->label), + furi_string_get_cstr(app->map_preset->subs_preset[3]->label), + furi_string_get_cstr(app->map_preset->subs_preset[4]->label)); return ret; } @@ -85,7 +85,7 @@ bool subrem_scene_remote_on_event(void* context, SceneManagerEvent event) { subrem_view_remote_set_state(app->subrem_remote_view, SubRemViewRemoteStateLoading); if(subrem_tx_start_sub( app, - app->subs_preset[app->chusen_sub], + app->map_preset->subs_preset[app->chusen_sub], subrem_scene_remote_raw_callback_end_tx)) { subrem_view_remote_set_presed_btn(app->subrem_remote_view, app->chusen_sub); subrem_view_remote_set_state( diff --git a/applications/main/subghz_remote/subghz_remote_app.c b/applications/main/subghz_remote/subghz_remote_app.c index b957fb8bc..4f9138e2a 100644 --- a/applications/main/subghz_remote/subghz_remote_app.c +++ b/applications/main/subghz_remote/subghz_remote_app.c @@ -74,8 +74,9 @@ SubGhzRemoteApp* subghz_remote_app_alloc() { SubRemViewIDRemote, subrem_view_remote_get_view(app->subrem_remote_view)); + app->map_preset = malloc(sizeof(SubRemMapPreset)); for(uint8_t i = 0; i < SubRemSubKeyNameMaxCount; i++) { - app->subs_preset[i] = subrem_sub_file_preset_alloc(); + app->map_preset->subs_preset[i] = subrem_sub_file_preset_alloc(); } app->setting = subghz_setting_alloc(); @@ -136,8 +137,9 @@ void subghz_remote_app_free(SubGhzRemoteApp* app) { subghz_setting_free(app->setting); for(uint8_t i = 0; i < SubRemSubKeyNameMaxCount; i++) { - subrem_sub_file_preset_free(app->subs_preset[i]); + subrem_sub_file_preset_free(app->map_preset->subs_preset[i]); } + free(app->map_preset); // Notifications furi_record_close(RECORD_NOTIFICATION); diff --git a/applications/main/subghz_remote/subghz_remote_app_i.c b/applications/main/subghz_remote/subghz_remote_app_i.c index 349fb87cd..9c35a0e03 100644 --- a/applications/main/subghz_remote/subghz_remote_app_i.c +++ b/applications/main/subghz_remote/subghz_remote_app_i.c @@ -42,50 +42,11 @@ static bool return true; } -SubRemSubFilePreset* subrem_sub_file_preset_alloc() { - SubRemSubFilePreset* sub_preset = malloc(sizeof(SubRemSubFilePreset)); - - sub_preset->fff_data = flipper_format_string_alloc(); - sub_preset->file_path = furi_string_alloc(); - sub_preset->protocaol_name = furi_string_alloc(); - sub_preset->label = furi_string_alloc_set_str("N/A"); - - sub_preset->type = SubGhzProtocolTypeUnknown; - sub_preset->load_state = SubRemLoadSubStateNotSet; - - return sub_preset; -} - -void subrem_sub_file_preset_free(SubRemSubFilePreset* sub_preset) { - furi_assert(sub_preset); - - furi_string_free(sub_preset->label); - furi_string_free(sub_preset->protocaol_name); - furi_string_free(sub_preset->file_path); - flipper_format_free(sub_preset->fff_data); - - free(sub_preset); -} - -static void subrem_sub_file_preset_reset(SubRemSubFilePreset* sub_preset) { - furi_assert(sub_preset); - - furi_string_set_str(sub_preset->label, "N/A"); - furi_string_reset(sub_preset->protocaol_name); - furi_string_reset(sub_preset->file_path); - - Stream* fff_data_stream = flipper_format_get_raw_stream(sub_preset->fff_data); - stream_clean(fff_data_stream); - - sub_preset->type = SubGhzProtocolTypeUnknown; - sub_preset->load_state = SubRemLoadSubStateNotSet; -} - -void subrem_map_preset_reset(SubGhzRemoteApp* app) { - furi_assert(app); +void subrem_map_preset_reset(SubRemMapPreset* map_preset) { + furi_assert(map_preset); for(uint8_t i = 0; i < SubRemSubKeyNameMaxCount; i++) { - subrem_sub_file_preset_reset(app->subs_preset[i]); + subrem_sub_file_preset_reset(map_preset->subs_preset[i]); } } @@ -94,7 +55,7 @@ static bool subrem_map_preset_load(SubGhzRemoteApp* app, FlipperFormat* fff_data bool ret = false; SubRemSubFilePreset* sub_preset; for(uint8_t i = 0; i < SubRemSubKeyNameMaxCount; i++) { - sub_preset = app->subs_preset[i]; + sub_preset = app->map_preset->subs_preset[i]; if(!flipper_format_read_string( fff_data_file, map_file_labels[i][0], sub_preset->file_path)) { #if FURI_DEBUG @@ -125,153 +86,6 @@ static bool subrem_map_preset_load(SubGhzRemoteApp* app, FlipperFormat* fff_data return ret; } -bool subrem_save_protocol_to_file(FlipperFormat* flipper_format, const char* dev_file_name) { - furi_assert(flipper_format); - furi_assert(dev_file_name); - - Storage* storage = furi_record_open(RECORD_STORAGE); - Stream* flipper_format_stream = flipper_format_get_raw_stream(flipper_format); - - bool saved = false; - uint32_t repeat = 200; - FuriString* file_dir = furi_string_alloc(); - - path_extract_dirname(dev_file_name, file_dir); - do { - // removing additional fields - flipper_format_delete_key(flipper_format, "Repeat"); - // flipper_format_delete_key(flipper_format, "Manufacture"); - - if(!storage_simply_remove(storage, dev_file_name)) { - break; - } - - //ToDo check Write - stream_seek(flipper_format_stream, 0, StreamOffsetFromStart); - stream_save_to_file(flipper_format_stream, storage, dev_file_name, FSOM_CREATE_ALWAYS); - - if(!flipper_format_insert_or_update_uint32(flipper_format, "Repeat", &repeat, 1)) { - FURI_LOG_E(TAG, "Unable Repeat"); - break; - } - - saved = true; - } while(0); - - furi_string_free(file_dir); - furi_record_close(RECORD_STORAGE); - return saved; -} - -bool subrem_tx_start_sub( - SubGhzRemoteApp* app, - SubRemSubFilePreset* sub_preset, - SubGhzProtocolEncoderRAWCallbackEnd callback) { - furi_assert(app); - furi_assert(sub_preset); - bool ret = false; - - subrem_tx_stop_sub(app, true); - - if(sub_preset->type == SubGhzProtocolTypeUnknown) { - return false; - } - - FURI_LOG_I(TAG, "Send %s", furi_string_get_cstr(sub_preset->label)); - - subghz_custom_btn_set(SUBGHZ_CUSTOM_BTN_OK); - keeloq_reset_original_btn(); - subghz_custom_btns_reset(); - - do { - flipper_format_rewind(sub_preset->fff_data); // - - app->transmitter = subghz_transmitter_alloc_init( - app->environment, furi_string_get_cstr(sub_preset->protocaol_name)); - - if(app->transmitter) { - if(subghz_transmitter_deserialize(app->transmitter, sub_preset->fff_data) != - SubGhzProtocolStatusOk) { - FURI_LOG_E(TAG, "Deserialize error!"); - break; - } - furi_hal_subghz_reset(); - furi_hal_subghz_idle(); - furi_hal_subghz_load_custom_preset(sub_preset->freq_preset.data); - furi_hal_gpio_init( - furi_hal_subghz.cc1101_g0_pin, GpioModeInput, GpioPullNo, GpioSpeedLow); - - furi_hal_subghz_idle(); - - furi_hal_subghz_set_frequency_and_path(sub_preset->freq_preset.frequency); - furi_hal_gpio_write(furi_hal_subghz.cc1101_g0_pin, false); - furi_hal_gpio_init( - furi_hal_subghz.cc1101_g0_pin, GpioModeOutputPushPull, GpioPullNo, GpioSpeedLow); - - if(!furi_hal_subghz_tx()) { - FURI_LOG_E(TAG, "Sending not allowed"); - break; - } - - if(sub_preset->type == SubGhzProtocolTypeRAW) { - subghz_protocol_raw_file_encoder_worker_set_callback_end( - (SubGhzProtocolEncoderRAW*)subghz_transmitter_get_protocol_instance( - app->transmitter), - callback, - app); - } - - furi_hal_subghz_start_async_tx(subghz_transmitter_yield, app->transmitter); - - ret = true; - } - } while(false); - - app->tx_running = ret; - - return ret; -} - -static void subghz_tx_stop(SubGhzRemoteApp* app) { - furi_assert(app); - - //Stop TX - furi_hal_subghz_stop_async_tx(); - - subghz_transmitter_stop(app->transmitter); - subghz_transmitter_free(app->transmitter); - furi_hal_subghz_idle(); -} - -bool subrem_tx_stop_sub(SubGhzRemoteApp* app, bool forced) { - furi_assert(app); - SubRemSubFilePreset* sub_preset = app->subs_preset[app->chusen_sub]; - - if(forced || (sub_preset->type != SubGhzProtocolTypeRAW)) { - // SubRemSubKeyTypeRawKey)) { - if(app->tx_running) { - subghz_tx_stop(app); - - if(sub_preset->type == SubGhzProtocolTypeDynamic) { - subrem_save_protocol_to_file( - sub_preset->fff_data, furi_string_get_cstr(sub_preset->file_path)); - - keeloq_reset_mfname(); - keeloq_reset_kl_type(); - keeloq_reset_original_btn(); - subghz_custom_btns_reset(); - star_line_reset_mfname(); - star_line_reset_kl_type(); - } - - app->tx_running = false; - return true; - } - } - - return false; -} - static SubRemLoadMapState subrem_map_preset_check(SubGhzRemoteApp* app, FlipperFormat* fff_data_file) { furi_assert(app); @@ -283,7 +97,7 @@ static SubRemLoadMapState SubRemSubFilePreset* sub_preset; uint32_t repeat = 200; for(uint8_t i = 0; i < SubRemSubKeyNameMaxCount; i++) { - sub_preset = app->subs_preset[i]; + sub_preset = app->map_preset->subs_preset[i]; if(furi_string_empty(sub_preset->file_path)) { // FURI_LOG_I(TAG, "Empty file path"); continue; @@ -427,7 +241,7 @@ SubRemLoadMapState subrem_map_file_load(SubGhzRemoteApp* app, const char* file_p #if FURI_DEBUG FURI_LOG_I(TAG, "Open Map File.."); #endif - subrem_map_preset_reset(app); + subrem_map_preset_reset(app->map_preset); if(!flipper_format_file_open_existing(fff_data_file, file_path)) { FURI_LOG_E(TAG, "Could not open MAP file %s", file_path); @@ -458,6 +272,153 @@ SubRemLoadMapState subrem_map_file_load(SubGhzRemoteApp* app, const char* file_p return ret; } +bool subrem_save_protocol_to_file(FlipperFormat* flipper_format, const char* dev_file_name) { + furi_assert(flipper_format); + furi_assert(dev_file_name); + + Storage* storage = furi_record_open(RECORD_STORAGE); + Stream* flipper_format_stream = flipper_format_get_raw_stream(flipper_format); + + bool saved = false; + uint32_t repeat = 200; + FuriString* file_dir = furi_string_alloc(); + + path_extract_dirname(dev_file_name, file_dir); + do { + // removing additional fields + flipper_format_delete_key(flipper_format, "Repeat"); + // flipper_format_delete_key(flipper_format, "Manufacture"); + + if(!storage_simply_remove(storage, dev_file_name)) { + break; + } + + //ToDo check Write + stream_seek(flipper_format_stream, 0, StreamOffsetFromStart); + stream_save_to_file(flipper_format_stream, storage, dev_file_name, FSOM_CREATE_ALWAYS); + + if(!flipper_format_insert_or_update_uint32(flipper_format, "Repeat", &repeat, 1)) { + FURI_LOG_E(TAG, "Unable Repeat"); + break; + } + + saved = true; + } while(0); + + furi_string_free(file_dir); + furi_record_close(RECORD_STORAGE); + return saved; +} + +bool subrem_tx_start_sub( + SubGhzRemoteApp* app, + SubRemSubFilePreset* sub_preset, + SubGhzProtocolEncoderRAWCallbackEnd callback) { + furi_assert(app); + furi_assert(sub_preset); + bool ret = false; + + subrem_tx_stop_sub(app, true); + + if(sub_preset->type == SubGhzProtocolTypeUnknown) { + return false; + } + + FURI_LOG_I(TAG, "Send %s", furi_string_get_cstr(sub_preset->label)); + + subghz_custom_btn_set(SUBGHZ_CUSTOM_BTN_OK); + keeloq_reset_original_btn(); + subghz_custom_btns_reset(); + + do { + flipper_format_rewind(sub_preset->fff_data); // + + app->transmitter = subghz_transmitter_alloc_init( + app->environment, furi_string_get_cstr(sub_preset->protocaol_name)); + + if(app->transmitter) { + if(subghz_transmitter_deserialize(app->transmitter, sub_preset->fff_data) != + SubGhzProtocolStatusOk) { + FURI_LOG_E(TAG, "Deserialize error!"); + break; + } + furi_hal_subghz_reset(); + furi_hal_subghz_idle(); + furi_hal_subghz_load_custom_preset(sub_preset->freq_preset.data); + furi_hal_gpio_init( + furi_hal_subghz.cc1101_g0_pin, GpioModeInput, GpioPullNo, GpioSpeedLow); + + furi_hal_subghz_idle(); + + furi_hal_subghz_set_frequency_and_path(sub_preset->freq_preset.frequency); + furi_hal_gpio_write(furi_hal_subghz.cc1101_g0_pin, false); + furi_hal_gpio_init( + furi_hal_subghz.cc1101_g0_pin, GpioModeOutputPushPull, GpioPullNo, GpioSpeedLow); + + if(!furi_hal_subghz_tx()) { + FURI_LOG_E(TAG, "Sending not allowed"); + break; + } + + if(sub_preset->type == SubGhzProtocolTypeRAW) { + subghz_protocol_raw_file_encoder_worker_set_callback_end( + (SubGhzProtocolEncoderRAW*)subghz_transmitter_get_protocol_instance( + app->transmitter), + callback, + app); + } + + furi_hal_subghz_start_async_tx(subghz_transmitter_yield, app->transmitter); + + ret = true; + } + } while(false); + + app->tx_running = ret; + + return ret; +} + +static void subghz_tx_stop(SubGhzRemoteApp* app) { + furi_assert(app); + + //Stop TX + furi_hal_subghz_stop_async_tx(); + + subghz_transmitter_stop(app->transmitter); + subghz_transmitter_free(app->transmitter); + furi_hal_subghz_idle(); +} + +bool subrem_tx_stop_sub(SubGhzRemoteApp* app, bool forced) { + furi_assert(app); + SubRemSubFilePreset* sub_preset = app->map_preset->subs_preset[app->chusen_sub]; + + if(forced || (sub_preset->type != SubGhzProtocolTypeRAW)) { + // SubRemSubKeyTypeRawKey)) { + if(app->tx_running) { + subghz_tx_stop(app); + + if(sub_preset->type == SubGhzProtocolTypeDynamic) { + subrem_save_protocol_to_file( + sub_preset->fff_data, furi_string_get_cstr(sub_preset->file_path)); + + keeloq_reset_mfname(); + keeloq_reset_kl_type(); + keeloq_reset_original_btn(); + subghz_custom_btns_reset(); + star_line_reset_mfname(); + star_line_reset_kl_type(); + } + + app->tx_running = false; + return true; + } + } + + return false; +} + SubRemLoadMapState subrem_load_from_file(SubGhzRemoteApp* app) { furi_assert(app); diff --git a/applications/main/subghz_remote/subghz_remote_app_i.h b/applications/main/subghz_remote/subghz_remote_app_i.h index 40d70411a..5d34968cd 100644 --- a/applications/main/subghz_remote/subghz_remote_app_i.h +++ b/applications/main/subghz_remote/subghz_remote_app_i.h @@ -1,6 +1,8 @@ #pragma once #include "helpers/subrem_types.h" +#include "helpers/subrem_presets.h" + #include #include "views/remote.h" @@ -30,25 +32,8 @@ #define SUBREM_MAX_LEN_NAME 64 typedef struct { - uint32_t frequency; - uint8_t* data; -} FreqPreset; - -// Sub File preset -typedef struct { - FlipperFormat* fff_data; - FreqPreset freq_preset; - FuriString* file_path; - FuriString* protocaol_name; - FuriString* label; - SubGhzProtocolType type; - SubRemLoadSubState load_state; -} SubRemSubFilePreset; - -SubRemSubFilePreset* subrem_sub_file_preset_alloc(); - -void subrem_sub_file_preset_free(SubRemSubFilePreset* sub_preset); - + SubRemSubFilePreset* subs_preset[SubRemSubKeyNameMaxCount]; +} SubRemMapPreset; typedef struct { Gui* gui; ViewDispatcher* view_dispatcher; @@ -56,12 +41,13 @@ typedef struct { NotificationApp* notifications; DialogsApp* dialogs; Submenu* submenu; + FuriString* file_path; - char file_name_tmp[SUBREM_MAX_LEN_NAME]; + // char file_name_tmp[SUBREM_MAX_LEN_NAME]; SubRemViewRemote* subrem_remote_view; - SubRemSubFilePreset* subs_preset[SubRemSubKeyNameMaxCount]; + SubRemMapPreset* map_preset; SubGhzSetting* setting; SubGhzEnvironment* environment; From 58b21f2a49aa5608c297be0ab0c1dd4bfdd858ac Mon Sep 17 00:00:00 2001 From: gid9798 <30450294+gid9798@users.noreply.github.com> Date: Sun, 21 May 2023 23:34:42 +0300 Subject: [PATCH 6/6] Using TxRx from subghz --- .../subghz_remote/helpers/subrem_presets.c | 139 +++++++ .../subghz_remote/helpers/subrem_presets.h | 13 +- .../main/subghz_remote/helpers/subrem_types.h | 2 +- .../scenes/subrem_scene_openmapfile.c | 3 +- .../scenes/subrem_scene_remote.c | 51 +-- .../main/subghz_remote/subghz_remote_app.c | 22 +- .../main/subghz_remote/subghz_remote_app_i.c | 346 ++++++------------ .../main/subghz_remote/subghz_remote_app_i.h | 19 +- .../main/subghz_remote/views/remote.c | 36 +- .../main/subghz_remote/views/remote.h | 12 +- 10 files changed, 310 insertions(+), 333 deletions(-) diff --git a/applications/main/subghz_remote/helpers/subrem_presets.c b/applications/main/subghz_remote/helpers/subrem_presets.c index 03e497198..9601aae6c 100644 --- a/applications/main/subghz_remote/helpers/subrem_presets.c +++ b/applications/main/subghz_remote/helpers/subrem_presets.c @@ -1,5 +1,7 @@ #include "subrem_presets.h" +#define TAG "SubRemPresets" + SubRemSubFilePreset* subrem_sub_file_preset_alloc() { SubRemSubFilePreset* sub_preset = malloc(sizeof(SubRemSubFilePreset)); @@ -8,6 +10,8 @@ SubRemSubFilePreset* subrem_sub_file_preset_alloc() { sub_preset->protocaol_name = furi_string_alloc(); sub_preset->label = furi_string_alloc_set_str("N/A"); + sub_preset->freq_preset.name = furi_string_alloc(); + sub_preset->type = SubGhzProtocolTypeUnknown; sub_preset->load_state = SubRemLoadSubStateNotSet; @@ -22,6 +26,8 @@ void subrem_sub_file_preset_free(SubRemSubFilePreset* sub_preset) { furi_string_free(sub_preset->file_path); flipper_format_free(sub_preset->fff_data); + furi_string_free(sub_preset->freq_preset.name); + free(sub_preset); } @@ -38,3 +44,136 @@ void subrem_sub_file_preset_reset(SubRemSubFilePreset* sub_preset) { sub_preset->type = SubGhzProtocolTypeUnknown; sub_preset->load_state = SubRemLoadSubStateNotSet; } + +SubRemLoadSubState subrem_sub_preset_load( + SubRemSubFilePreset* sub_preset, + SubGhzTxRx* txrx, + FlipperFormat* fff_data_file) { + furi_assert(sub_preset); + furi_assert(txrx); + furi_assert(fff_data_file); + + Stream* fff_data_stream = flipper_format_get_raw_stream(sub_preset->fff_data); + + SubRemLoadSubState ret; + FuriString* temp_str = furi_string_alloc(); + uint32_t temp_data32; + uint32_t repeat = 200; + + ret = SubRemLoadSubStateError; + + do { + stream_clean(fff_data_stream); + if(!flipper_format_read_header(fff_data_file, temp_str, &temp_data32)) { + FURI_LOG_E(TAG, "Missing or incorrect header"); + break; + } + + if(((!strcmp(furi_string_get_cstr(temp_str), SUBGHZ_KEY_FILE_TYPE)) || + (!strcmp(furi_string_get_cstr(temp_str), SUBGHZ_RAW_FILE_TYPE))) && + temp_data32 == SUBGHZ_KEY_FILE_VERSION) { + } else { + FURI_LOG_E(TAG, "Type or version mismatch"); + break; + } + + SubGhzSetting* setting = subghz_txrx_get_setting(txrx); // txrx->setting; + + //Load frequency or using default from settings + ret = SubRemLoadSubStateErrorFreq; + if(!flipper_format_read_uint32(fff_data_file, "Frequency", &temp_data32, 1)) { + FURI_LOG_W(TAG, "Cannot read frequency. Set default frequency"); + sub_preset->freq_preset.frequency = subghz_setting_get_default_frequency(setting); + } else if(!furi_hal_subghz_is_tx_allowed(temp_data32)) { + FURI_LOG_E(TAG, "This frequency can only be used for RX"); + break; + } + sub_preset->freq_preset.frequency = temp_data32; + + //Load preset + ret = SubRemLoadSubStateErrorMod; + if(!flipper_format_read_string(fff_data_file, "Preset", temp_str)) { + FURI_LOG_E(TAG, "Missing Preset"); + break; + } + + furi_string_set_str( + temp_str, subghz_txrx_get_preset_name(txrx, furi_string_get_cstr(temp_str))); + if(!strcmp(furi_string_get_cstr(temp_str), "")) { + break; + } + + if(!strcmp(furi_string_get_cstr(temp_str), "CUSTOM")) { + FURI_LOG_E(TAG, "CUSTOM preset is not supported"); + break; + // TODO Custom preset loading logic if need + // sub_preset->freq_preset.preset_index = + // subghz_setting_get_inx_preset_by_name(setting, furi_string_get_cstr(temp_str)); + } + + furi_string_set(sub_preset->freq_preset.name, temp_str); + + // Load protocol + ret = SubRemLoadSubStateErrorProtocol; + if(!flipper_format_read_string(fff_data_file, "Protocol", temp_str)) { + FURI_LOG_E(TAG, "Missing Protocol"); + break; + } + + FlipperFormat* fff_data = sub_preset->fff_data; + if(!strcmp(furi_string_get_cstr(temp_str), "RAW")) { + //if RAW + subghz_protocol_raw_gen_fff_data( + fff_data, furi_string_get_cstr(sub_preset->file_path)); + } else { + stream_copy_full( + flipper_format_get_raw_stream(fff_data_file), + flipper_format_get_raw_stream(fff_data)); + } + + if(subghz_txrx_load_decoder_by_name_protocol(txrx, furi_string_get_cstr(temp_str))) { + SubGhzProtocolStatus status = + subghz_protocol_decoder_base_deserialize(subghz_txrx_get_decoder(txrx), fff_data); + if(status != SubGhzProtocolStatusOk) { + break; + } + } else { + FURI_LOG_E(TAG, "Protocol not found"); + break; + } + + const SubGhzProtocol* protocol = subghz_txrx_get_decoder(txrx)->protocol; + + if(protocol->flag & SubGhzProtocolFlag_Send) { + if((protocol->type == SubGhzProtocolTypeStatic) || + (protocol->type == SubGhzProtocolTypeDynamic) || + // TODO: BINRAW It probably works, but checks are needed. + // (protocol->type == SubGhzProtocolTypeBinRAW) || + (protocol->type == SubGhzProtocolTypeRAW)) { + sub_preset->type = protocol->type; + } else { + FURI_LOG_E(TAG, "Unsuported Protocol"); + break; + } + + furi_string_set(sub_preset->protocaol_name, temp_str); + } else { + FURI_LOG_E(TAG, "Protocol does not support transmission"); + break; + } + + if(!flipper_format_insert_or_update_uint32(fff_data, "Repeat", &repeat, 1)) { + FURI_LOG_E(TAG, "Unable Repeat"); + break; + } + + ret = SubRemLoadSubStateOK; + +#if FURI_DEBUG + FURI_LOG_I(TAG, "%-16s - protocol Loaded", furi_string_get_cstr(sub_preset->label)); +#endif + } while(false); + + furi_string_free(temp_str); + return ret; +} diff --git a/applications/main/subghz_remote/helpers/subrem_presets.h b/applications/main/subghz_remote/helpers/subrem_presets.h index 60eedad57..fd4a2d780 100644 --- a/applications/main/subghz_remote/helpers/subrem_presets.h +++ b/applications/main/subghz_remote/helpers/subrem_presets.h @@ -3,10 +3,12 @@ #include "subrem_types.h" #include #include +#include "../../subghz/helpers/subghz_txrx.h" typedef struct { + FuriString* name; uint32_t frequency; - uint8_t* data; + // size_t preset_index; // Need for custom preset } FreqPreset; // Sub File preset @@ -20,8 +22,17 @@ typedef struct { SubRemLoadSubState load_state; } SubRemSubFilePreset; +typedef struct { + SubRemSubFilePreset* subs_preset[SubRemSubKeyNameMaxCount]; +} SubRemMapPreset; + SubRemSubFilePreset* subrem_sub_file_preset_alloc(); void subrem_sub_file_preset_free(SubRemSubFilePreset* sub_preset); void subrem_sub_file_preset_reset(SubRemSubFilePreset* sub_preset); + +SubRemLoadSubState subrem_sub_preset_load( + SubRemSubFilePreset* sub_preset, + SubGhzTxRx* txrx, + FlipperFormat* fff_data_file); diff --git a/applications/main/subghz_remote/helpers/subrem_types.h b/applications/main/subghz_remote/helpers/subrem_types.h index 13b42897f..def807898 100644 --- a/applications/main/subghz_remote/helpers/subrem_types.h +++ b/applications/main/subghz_remote/helpers/subrem_types.h @@ -26,7 +26,7 @@ typedef enum { } SubRemViewID; typedef enum { - SubRemLoadSubStateNotSet, + SubRemLoadSubStateNotSet = 0, SubRemLoadSubStatePreloaded, SubRemLoadSubStateError, SubRemLoadSubStateErrorNoFile, diff --git a/applications/main/subghz_remote/scenes/subrem_scene_openmapfile.c b/applications/main/subghz_remote/scenes/subrem_scene_openmapfile.c index ea5c14a0a..796699c83 100644 --- a/applications/main/subghz_remote/scenes/subrem_scene_openmapfile.c +++ b/applications/main/subghz_remote/scenes/subrem_scene_openmapfile.c @@ -4,7 +4,8 @@ void subrem_scene_openmapfile_on_enter(void* context) { SubGhzRemoteApp* app = context; SubRemLoadMapState load_state = subrem_load_from_file(app); - if(load_state == SubRemLoadMapStateError) { + if(load_state != SubRemLoadMapStateOK && load_state != SubRemLoadMapStateNotAllOK && + load_state != SubRemLoadMapStateBack) { #ifdef SUBREM_LIGHT dialog_message_show_storage_error(app->dialogs, "Can't load\nMap file"); #else diff --git a/applications/main/subghz_remote/scenes/subrem_scene_remote.c b/applications/main/subghz_remote/scenes/subrem_scene_remote.c index 1b8dbc471..eaa1c41d9 100644 --- a/applications/main/subghz_remote/scenes/subrem_scene_remote.c +++ b/applications/main/subghz_remote/scenes/subrem_scene_remote.c @@ -37,17 +37,16 @@ static uint8_t subrem_scene_remote_event_to_index(SubRemCustomEvent event_id) { static bool subrem_scene_remote_update_data_show(void* context) { SubGhzRemoteApp* app = context; - bool ret = false; - subrem_view_remote_add_data_to_show( - app->subrem_remote_view, - furi_string_get_cstr(app->map_preset->subs_preset[0]->label), - furi_string_get_cstr(app->map_preset->subs_preset[1]->label), - furi_string_get_cstr(app->map_preset->subs_preset[2]->label), - furi_string_get_cstr(app->map_preset->subs_preset[3]->label), - furi_string_get_cstr(app->map_preset->subs_preset[4]->label)); + const char* labels[SubRemSubKeyNameMaxCount]; - return ret; + for(uint8_t i = 0; i < SubRemSubKeyNameMaxCount; i++) { + labels[i] = furi_string_get_cstr(app->map_preset->subs_preset[i]->label); + } + + subrem_view_remote_add_data_to_show(app->subrem_remote_view, labels); + + return true; } void subrem_scene_remote_on_enter(void* context) { @@ -81,32 +80,37 @@ bool subrem_scene_remote_on_event(void* context, SceneManagerEvent event) { event.event == SubRemCustomEventViewRemoteStartOK) { // Start sending sub subrem_tx_stop_sub(app, true); - app->chusen_sub = subrem_scene_remote_event_to_index(event.event); - subrem_view_remote_set_state(app->subrem_remote_view, SubRemViewRemoteStateLoading); - if(subrem_tx_start_sub( - app, - app->map_preset->subs_preset[app->chusen_sub], - subrem_scene_remote_raw_callback_end_tx)) { - subrem_view_remote_set_presed_btn(app->subrem_remote_view, app->chusen_sub); + + uint8_t chusen_sub = subrem_scene_remote_event_to_index(event.event); + app->chusen_sub = chusen_sub; + + subrem_view_remote_set_state( + app->subrem_remote_view, SubRemViewRemoteStateLoading, chusen_sub); + + if(subrem_tx_start_sub(app, app->map_preset->subs_preset[chusen_sub])) { + if(app->map_preset->subs_preset[chusen_sub]->type == SubGhzProtocolTypeRAW) { + subghz_txrx_set_raw_file_encoder_worker_callback_end( + app->txrx, subrem_scene_remote_raw_callback_end_tx, app); + } subrem_view_remote_set_state( - app->subrem_remote_view, SubRemViewRemoteStateSending); + app->subrem_remote_view, SubRemViewRemoteStateSending, chusen_sub); notification_message(app->notifications, &sequence_blink_start_magenta); } else { - subrem_view_remote_set_state(app->subrem_remote_view, SubRemViewRemoteStateIdle); + subrem_view_remote_set_state( + app->subrem_remote_view, SubRemViewRemoteStateIdle, 0); notification_message(app->notifications, &sequence_blink_stop); } return true; } else if(event.event == SubRemCustomEventViewRemoteForcedStop) { subrem_tx_stop_sub(app, true); - subrem_view_remote_set_presed_btn(app->subrem_remote_view, 0); - subrem_view_remote_set_state(app->subrem_remote_view, SubRemViewRemoteStateIdle); + subrem_view_remote_set_state(app->subrem_remote_view, SubRemViewRemoteStateIdle, 0); notification_message(app->notifications, &sequence_blink_stop); return true; } else if(event.event == SubRemCustomEventViewRemoteStop) { if(subrem_tx_stop_sub(app, false)) { - subrem_view_remote_set_presed_btn(app->subrem_remote_view, 0); - subrem_view_remote_set_state(app->subrem_remote_view, SubRemViewRemoteStateIdle); + subrem_view_remote_set_state( + app->subrem_remote_view, SubRemViewRemoteStateIdle, 0); notification_message(app->notifications, &sequence_blink_stop); } @@ -123,8 +127,7 @@ void subrem_scene_remote_on_exit(void* context) { subrem_tx_stop_sub(app, true); - subrem_view_remote_set_presed_btn(app->subrem_remote_view, 0); - subrem_view_remote_set_state(app->subrem_remote_view, SubRemViewRemoteStateIdle); + subrem_view_remote_set_state(app->subrem_remote_view, SubRemViewRemoteStateIdle, 0); notification_message(app->notifications, &sequence_blink_stop); } diff --git a/applications/main/subghz_remote/subghz_remote_app.c b/applications/main/subghz_remote/subghz_remote_app.c index 4f9138e2a..7383757d2 100644 --- a/applications/main/subghz_remote/subghz_remote_app.c +++ b/applications/main/subghz_remote/subghz_remote_app.c @@ -79,23 +79,9 @@ SubGhzRemoteApp* subghz_remote_app_alloc() { app->map_preset->subs_preset[i] = subrem_sub_file_preset_alloc(); } - app->setting = subghz_setting_alloc(); - subghz_setting_load(app->setting, EXT_PATH("subghz/assets/setting_user")); + app->txrx = subghz_txrx_alloc(); - app->environment = subghz_environment_alloc(); - - subghz_environment_load_keystore(app->environment, EXT_PATH("subghz/assets/keeloq_mfcodes")); - subghz_environment_load_keystore( - app->environment, EXT_PATH("subghz/assets/keeloq_mfcodes_user")); - subghz_environment_set_came_atomo_rainbow_table_file_name( - app->environment, EXT_PATH("subghz/assets/came_atomo")); - subghz_environment_set_alutech_at_4n_rainbow_table_file_name( - app->environment, EXT_PATH("subghz/assets/alutech_at_4n")); - subghz_environment_set_nice_flor_s_rainbow_table_file_name( - app->environment, EXT_PATH("subghz/assets/nice_flor_s")); - subghz_environment_set_protocol_registry(app->environment, (void*)&subghz_protocol_registry); - - app->receiver = subghz_receiver_alloc_init(app->environment); + subghz_txrx_set_need_save_callback(app->txrx, subrem_save_active_sub, app); app->tx_running = false; @@ -132,9 +118,7 @@ void subghz_remote_app_free(SubGhzRemoteApp* app) { scene_manager_free(app->scene_manager); view_dispatcher_free(app->view_dispatcher); - subghz_receiver_free(app->receiver); - subghz_environment_free(app->environment); - subghz_setting_free(app->setting); + subghz_txrx_free(app->txrx); for(uint8_t i = 0; i < SubRemSubKeyNameMaxCount; i++) { subrem_sub_file_preset_free(app->map_preset->subs_preset[i]); diff --git a/applications/main/subghz_remote/subghz_remote_app_i.c b/applications/main/subghz_remote/subghz_remote_app_i.c index 9c35a0e03..fb34b59f7 100644 --- a/applications/main/subghz_remote/subghz_remote_app_i.c +++ b/applications/main/subghz_remote/subghz_remote_app_i.c @@ -4,6 +4,8 @@ #include +#include "../subghz/helpers/subghz_txrx_i.h" + // #include // #include @@ -11,6 +13,12 @@ #define TAG "SubGhzRemote" +// XXX Using TxRx +// [x] use TxRx preset subrem_sub_preset_load & subrem_tx_start_sub +// [x] subrem_sub_preset_load & drop subrem_set_preset_data +// [x] subrem_tx_start_sub +// [x] subrem_tx_stop_sub + static const char* map_file_labels[SubRemSubKeyNameMaxCount][2] = { [SubRemSubKeyNameUp] = {"UP", "ULABEL"}, [SubRemSubKeyNameDown] = {"DOWN", "DLABEL"}, @@ -19,30 +27,7 @@ static const char* map_file_labels[SubRemSubKeyNameMaxCount][2] = { [SubRemSubKeyNameOk] = {"OK", "OKLABEL"}, }; -static bool - subrem_set_preset_data(SubGhzSetting* setting, FreqPreset* freq_preset, const char* preset) { - const char* preset_name = ""; - if(!strcmp(preset, "FuriHalSubGhzPresetOok270Async")) { - preset_name = "AM270"; - } else if(!strcmp(preset, "FuriHalSubGhzPresetOok650Async")) { - preset_name = "AM650"; - } else if(!strcmp(preset, "FuriHalSubGhzPreset2FSKDev238Async")) { - preset_name = "FM238"; - } else if(!strcmp(preset, "FuriHalSubGhzPreset2FSKDev476Async")) { - preset_name = "FM476"; - } else if(!strcmp(preset, "FuriHalSubGhzPresetCustom")) { - // preset_name = "CUSTOM"; - return false; - } else { - FURI_LOG_E(TAG, "Unknown preset"); - return false; - } - size_t preset_index = subghz_setting_get_inx_preset_by_name(setting, preset_name); - freq_preset->data = subghz_setting_get_preset_data(setting, preset_index); - return true; -} - -void subrem_map_preset_reset(SubRemMapPreset* map_preset) { +static void subrem_map_preset_reset(SubRemMapPreset* map_preset) { furi_assert(map_preset); for(uint8_t i = 0; i < SubRemSubKeyNameMaxCount; i++) { @@ -50,12 +35,61 @@ void subrem_map_preset_reset(SubRemMapPreset* map_preset) { } } -static bool subrem_map_preset_load(SubGhzRemoteApp* app, FlipperFormat* fff_data_file) { - furi_assert(app); +static SubRemLoadMapState subrem_map_preset_check( + SubRemMapPreset* map_preset, + SubGhzTxRx* txrx, + FlipperFormat* fff_data_file) { + furi_assert(map_preset); + furi_assert(txrx); + + bool all_loaded = true; + SubRemLoadMapState ret = SubRemLoadMapStateErrorBrokenFile; + + SubRemLoadSubState sub_preset_loaded; + SubRemSubFilePreset* sub_preset; + + for(uint8_t i = 0; i < SubRemSubKeyNameMaxCount; i++) { + sub_preset = map_preset->subs_preset[i]; + + sub_preset_loaded = SubRemLoadSubStateErrorNoFile; + + if(furi_string_empty(sub_preset->file_path)) { + // FURI_LOG_I(TAG, "Empty file path"); + } else if(!flipper_format_file_open_existing( + fff_data_file, furi_string_get_cstr(sub_preset->file_path))) { + FURI_LOG_W(TAG, "Error open file %s", furi_string_get_cstr(sub_preset->file_path)); + } else { + sub_preset_loaded = subrem_sub_preset_load(sub_preset, txrx, fff_data_file); + } + + // TODO: + // Load file state logic + // Label depending on the state + // Move to remote scene + + if(sub_preset_loaded != SubRemLoadSubStateOK) { + furi_string_set_str(sub_preset->label, "N/A"); + all_loaded = false; + } else { + ret = SubRemLoadMapStateNotAllOK; + } + + if(ret != SubRemLoadMapStateErrorBrokenFile && all_loaded) { + ret = SubRemLoadMapStateOK; + } + + flipper_format_file_close(fff_data_file); + } + + return ret; +} + +static bool subrem_map_preset_load(SubRemMapPreset* map_preset, FlipperFormat* fff_data_file) { + furi_assert(map_preset); bool ret = false; SubRemSubFilePreset* sub_preset; for(uint8_t i = 0; i < SubRemSubKeyNameMaxCount; i++) { - sub_preset = app->map_preset->subs_preset[i]; + sub_preset = map_preset->subs_preset[i]; if(!flipper_format_read_string( fff_data_file, map_file_labels[i][0], sub_preset->file_path)) { #if FURI_DEBUG @@ -69,8 +103,13 @@ static bool subrem_map_preset_load(SubGhzRemoteApp* app, FlipperFormat* fff_data #if FURI_DEBUG FURI_LOG_W(TAG, "No Label for %s", map_file_labels[i][0]); #endif + // TODO move to remote scene path_extract_filename(sub_preset->file_path, sub_preset->label, true); + ret = true; } else { + ret = true; + } + if(ret) { // Preload seccesful FURI_LOG_I( TAG, @@ -78,157 +117,14 @@ static bool subrem_map_preset_load(SubGhzRemoteApp* app, FlipperFormat* fff_data map_file_labels[i][0], furi_string_get_cstr(sub_preset->label), furi_string_get_cstr(sub_preset->file_path)); - ret = true; sub_preset->load_state = SubRemLoadSubStatePreloaded; } + flipper_format_rewind(fff_data_file); } return ret; } -static SubRemLoadMapState - subrem_map_preset_check(SubGhzRemoteApp* app, FlipperFormat* fff_data_file) { - furi_assert(app); - FuriString* temp_str = furi_string_alloc(); - uint32_t temp_data32; - bool all_loaded = true; - SubRemLoadMapState ret = SubRemLoadMapStateErrorBrokenFile; - SubRemLoadSubState sub_preset_loaded; - SubRemSubFilePreset* sub_preset; - uint32_t repeat = 200; - for(uint8_t i = 0; i < SubRemSubKeyNameMaxCount; i++) { - sub_preset = app->map_preset->subs_preset[i]; - if(furi_string_empty(sub_preset->file_path)) { - // FURI_LOG_I(TAG, "Empty file path"); - continue; - } - - sub_preset_loaded = SubRemLoadSubStateErrorNoFile; - - repeat = 200; - do { - if(!flipper_format_file_open_existing( - fff_data_file, furi_string_get_cstr(sub_preset->file_path))) { - FURI_LOG_W(TAG, "Error open file %s", furi_string_get_cstr(sub_preset->file_path)); - break; - } - - if(!flipper_format_read_header(fff_data_file, temp_str, &temp_data32)) { - FURI_LOG_E(TAG, "Missing or incorrect header"); - break; - } - - if(((!strcmp(furi_string_get_cstr(temp_str), SUBGHZ_KEY_FILE_TYPE)) || - (!strcmp(furi_string_get_cstr(temp_str), SUBGHZ_RAW_FILE_TYPE))) && - temp_data32 == SUBGHZ_KEY_FILE_VERSION) { - } else { - FURI_LOG_E(TAG, "Type or version mismatch"); - break; - } - - //Load frequency - sub_preset_loaded = SubRemLoadSubStateErrorFreq; - if(!flipper_format_read_uint32(fff_data_file, "Frequency", &temp_data32, 1)) { - FURI_LOG_W(TAG, "Cannot read frequency. Set default frequency"); - sub_preset->freq_preset.frequency = - subghz_setting_get_default_frequency(app->setting); - } else if(!furi_hal_subghz_is_tx_allowed(temp_data32)) { - FURI_LOG_E(TAG, "This frequency can only be used for RX"); - break; - } else { - sub_preset->freq_preset.frequency = temp_data32; - } - - //Load preset - sub_preset_loaded = SubRemLoadSubStateErrorMod; - if(!flipper_format_read_string(fff_data_file, "Preset", temp_str)) { - FURI_LOG_E(TAG, "Missing Preset"); - break; - } - - if(!subrem_set_preset_data( - app->setting, &sub_preset->freq_preset, furi_string_get_cstr(temp_str))) { - FURI_LOG_E(TAG, "Cannot load preset."); - break; - } - - //Load protocol - sub_preset_loaded = SubRemLoadSubStateErrorProtocol; - if(!flipper_format_read_string(fff_data_file, "Protocol", temp_str)) { - FURI_LOG_E(TAG, "Missing Protocol"); - break; - } - - FlipperFormat* fff_data = sub_preset->fff_data; - if(!strcmp(furi_string_get_cstr(temp_str), "RAW")) { - //if RAW - subghz_protocol_raw_gen_fff_data( - fff_data, furi_string_get_cstr(sub_preset->file_path)); - } else { - stream_copy_full( - flipper_format_get_raw_stream(fff_data_file), - flipper_format_get_raw_stream(fff_data)); - } - - const SubGhzProtocolRegistry* protocol_registry_items = - subghz_environment_get_protocol_registry(app->environment); - - const SubGhzProtocol* protocol = subghz_protocol_registry_get_by_name( - protocol_registry_items, furi_string_get_cstr(temp_str)); - - if(!protocol) { - FURI_LOG_E(TAG, "Protocol not found"); - break; - } else if(protocol->flag & SubGhzProtocolFlag_Send) { - if((protocol->type == SubGhzProtocolTypeStatic) || - (protocol->type == SubGhzProtocolTypeDynamic) || - // (protocol->type == SubGhzProtocolTypeBinRAW) || // TODO: BINRAW - (protocol->type == SubGhzProtocolTypeRAW)) { - sub_preset->type = protocol->type; - } else { - FURI_LOG_E(TAG, "Unsuported Protocol"); - break; - } - - furi_string_set(sub_preset->protocaol_name, temp_str); - } else { - FURI_LOG_E(TAG, "Protocol does not support transmission"); - } - - if(!flipper_format_insert_or_update_uint32(fff_data, "Repeat", &repeat, 1)) { - FURI_LOG_E(TAG, "Unable Repeat"); - break; - } - - sub_preset_loaded = SubRemLoadSubStateOK; - ret = SubRemLoadMapStateNotAllOK; - -#if FURI_DEBUG - FURI_LOG_I(TAG, "%-16s - protocol Loaded", furi_string_get_cstr(sub_preset->label)); -#endif - } while(false); - - // TODO: - // Load file state logic - // Label depending on the state - // Move to remote scene - - if(sub_preset_loaded != SubRemLoadSubStateOK) { - furi_string_set_str(sub_preset->label, "N/A"); - all_loaded = false; - } - - if(ret != SubRemLoadMapStateErrorBrokenFile && all_loaded) { - ret = SubRemLoadMapStateOK; - } - - flipper_format_file_close(fff_data_file); - } - furi_string_free(temp_str); - - return ret; -} - SubRemLoadMapState subrem_map_file_load(SubGhzRemoteApp* app, const char* file_path) { furi_assert(app); furi_assert(file_path); @@ -247,13 +143,13 @@ SubRemLoadMapState subrem_map_file_load(SubGhzRemoteApp* app, const char* file_p FURI_LOG_E(TAG, "Could not open MAP file %s", file_path); ret = SubRemLoadMapStateErrorOpenError; } else { - if(!subrem_map_preset_load(app, fff_data_file)) { + if(!subrem_map_preset_load(app->map_preset, fff_data_file)) { FURI_LOG_E(TAG, "Could no Sub file path in MAP file"); // ret = // error for popup } else if(!flipper_format_file_close(fff_data_file)) { ret = SubRemLoadMapStateErrorOpenError; } else { - ret = subrem_map_preset_check(app, fff_data_file); + ret = subrem_map_preset_check(app->map_preset, app->txrx, fff_data_file); } } @@ -272,9 +168,9 @@ SubRemLoadMapState subrem_map_file_load(SubGhzRemoteApp* app, const char* file_p return ret; } -bool subrem_save_protocol_to_file(FlipperFormat* flipper_format, const char* dev_file_name) { +bool subrem_save_protocol_to_file(FlipperFormat* flipper_format, const char* sub_file_name) { furi_assert(flipper_format); - furi_assert(dev_file_name); + furi_assert(sub_file_name); Storage* storage = furi_record_open(RECORD_STORAGE); Stream* flipper_format_stream = flipper_format_get_raw_stream(flipper_format); @@ -283,19 +179,19 @@ bool subrem_save_protocol_to_file(FlipperFormat* flipper_format, const char* dev uint32_t repeat = 200; FuriString* file_dir = furi_string_alloc(); - path_extract_dirname(dev_file_name, file_dir); + path_extract_dirname(sub_file_name, file_dir); do { // removing additional fields flipper_format_delete_key(flipper_format, "Repeat"); // flipper_format_delete_key(flipper_format, "Manufacture"); - if(!storage_simply_remove(storage, dev_file_name)) { + if(!storage_simply_remove(storage, sub_file_name)) { break; } //ToDo check Write stream_seek(flipper_format_stream, 0, StreamOffsetFromStart); - stream_save_to_file(flipper_format_stream, storage, dev_file_name, FSOM_CREATE_ALWAYS); + stream_save_to_file(flipper_format_stream, storage, sub_file_name, FSOM_CREATE_ALWAYS); if(!flipper_format_insert_or_update_uint32(flipper_format, "Repeat", &repeat, 1)) { FURI_LOG_E(TAG, "Unable Repeat"); @@ -310,10 +206,16 @@ bool subrem_save_protocol_to_file(FlipperFormat* flipper_format, const char* dev return saved; } -bool subrem_tx_start_sub( - SubGhzRemoteApp* app, - SubRemSubFilePreset* sub_preset, - SubGhzProtocolEncoderRAWCallbackEnd callback) { +void subrem_save_active_sub(void* context) { + furi_assert(context); + SubGhzRemoteApp* app = context; + + SubRemSubFilePreset* sub_preset = app->map_preset->subs_preset[app->chusen_sub]; + subrem_save_protocol_to_file( + sub_preset->fff_data, furi_string_get_cstr(sub_preset->file_path)); +} + +bool subrem_tx_start_sub(SubGhzRemoteApp* app, SubRemSubFilePreset* sub_preset) { furi_assert(app); furi_assert(sub_preset); bool ret = false; @@ -321,88 +223,44 @@ bool subrem_tx_start_sub( subrem_tx_stop_sub(app, true); if(sub_preset->type == SubGhzProtocolTypeUnknown) { - return false; - } + ret = false; + } else { + FURI_LOG_I(TAG, "Send %s", furi_string_get_cstr(sub_preset->label)); - FURI_LOG_I(TAG, "Send %s", furi_string_get_cstr(sub_preset->label)); + subghz_txrx_load_decoder_by_name_protocol( + app->txrx, furi_string_get_cstr(sub_preset->protocaol_name)); - subghz_custom_btn_set(SUBGHZ_CUSTOM_BTN_OK); - keeloq_reset_original_btn(); - subghz_custom_btns_reset(); + subghz_txrx_set_preset( + app->txrx, + furi_string_get_cstr(sub_preset->freq_preset.name), + sub_preset->freq_preset.frequency, + NULL, + 0); - do { - flipper_format_rewind(sub_preset->fff_data); // - - app->transmitter = subghz_transmitter_alloc_init( - app->environment, furi_string_get_cstr(sub_preset->protocaol_name)); - - if(app->transmitter) { - if(subghz_transmitter_deserialize(app->transmitter, sub_preset->fff_data) != - SubGhzProtocolStatusOk) { - FURI_LOG_E(TAG, "Deserialize error!"); - break; - } - furi_hal_subghz_reset(); - furi_hal_subghz_idle(); - furi_hal_subghz_load_custom_preset(sub_preset->freq_preset.data); - furi_hal_gpio_init( - furi_hal_subghz.cc1101_g0_pin, GpioModeInput, GpioPullNo, GpioSpeedLow); - - furi_hal_subghz_idle(); - - furi_hal_subghz_set_frequency_and_path(sub_preset->freq_preset.frequency); - furi_hal_gpio_write(furi_hal_subghz.cc1101_g0_pin, false); - furi_hal_gpio_init( - furi_hal_subghz.cc1101_g0_pin, GpioModeOutputPushPull, GpioPullNo, GpioSpeedLow); - - if(!furi_hal_subghz_tx()) { - FURI_LOG_E(TAG, "Sending not allowed"); - break; - } - - if(sub_preset->type == SubGhzProtocolTypeRAW) { - subghz_protocol_raw_file_encoder_worker_set_callback_end( - (SubGhzProtocolEncoderRAW*)subghz_transmitter_get_protocol_instance( - app->transmitter), - callback, - app); - } - - furi_hal_subghz_start_async_tx(subghz_transmitter_yield, app->transmitter); + subghz_custom_btn_set(SUBGHZ_CUSTOM_BTN_OK); + keeloq_reset_original_btn(); + subghz_custom_btns_reset(); + if(subghz_txrx_tx_start(app->txrx, sub_preset->fff_data) == SubGhzTxRxStartTxStateOk) { ret = true; } - } while(false); + } app->tx_running = ret; return ret; } -static void subghz_tx_stop(SubGhzRemoteApp* app) { - furi_assert(app); - - //Stop TX - furi_hal_subghz_stop_async_tx(); - - subghz_transmitter_stop(app->transmitter); - subghz_transmitter_free(app->transmitter); - furi_hal_subghz_idle(); -} - bool subrem_tx_stop_sub(SubGhzRemoteApp* app, bool forced) { furi_assert(app); SubRemSubFilePreset* sub_preset = app->map_preset->subs_preset[app->chusen_sub]; if(forced || (sub_preset->type != SubGhzProtocolTypeRAW)) { - // SubRemSubKeyTypeRawKey)) { + // XXX drop app->tx_running if(app->tx_running) { - subghz_tx_stop(app); + subghz_txrx_stop(app->txrx); if(sub_preset->type == SubGhzProtocolTypeDynamic) { - subrem_save_protocol_to_file( - sub_preset->fff_data, furi_string_get_cstr(sub_preset->file_path)); - keeloq_reset_mfname(); keeloq_reset_kl_type(); keeloq_reset_original_btn(); diff --git a/applications/main/subghz_remote/subghz_remote_app_i.h b/applications/main/subghz_remote/subghz_remote_app_i.h index 5d34968cd..50e2bae9f 100644 --- a/applications/main/subghz_remote/subghz_remote_app_i.h +++ b/applications/main/subghz_remote/subghz_remote_app_i.h @@ -3,6 +3,8 @@ #include "helpers/subrem_types.h" #include "helpers/subrem_presets.h" +#include "../subghz/helpers/subghz_txrx.h" + #include #include "views/remote.h" @@ -31,9 +33,6 @@ #define SUBREM_APP_FOLDER EXT_PATH("subghz_remote") #define SUBREM_MAX_LEN_NAME 64 -typedef struct { - SubRemSubFilePreset* subs_preset[SubRemSubKeyNameMaxCount]; -} SubRemMapPreset; typedef struct { Gui* gui; ViewDispatcher* view_dispatcher; @@ -49,10 +48,7 @@ typedef struct { SubRemMapPreset* map_preset; - SubGhzSetting* setting; - SubGhzEnvironment* environment; - SubGhzReceiver* receiver; - SubGhzTransmitter* transmitter; + SubGhzTxRx* txrx; bool tx_running; @@ -61,9 +57,8 @@ typedef struct { SubRemLoadMapState subrem_load_from_file(SubGhzRemoteApp* app); -bool subrem_tx_start_sub( - SubGhzRemoteApp* app, - SubRemSubFilePreset* sub_preset, - SubGhzProtocolEncoderRAWCallbackEnd callback); +bool subrem_tx_start_sub(SubGhzRemoteApp* app, SubRemSubFilePreset* sub_preset); -bool subrem_tx_stop_sub(SubGhzRemoteApp* app, bool forced); \ No newline at end of file +bool subrem_tx_stop_sub(SubGhzRemoteApp* app, bool forced); + +void subrem_save_active_sub(void* context); \ No newline at end of file diff --git a/applications/main/subghz_remote/views/remote.c b/applications/main/subghz_remote/views/remote.c index 1f867cd0b..e062f11b1 100644 --- a/applications/main/subghz_remote/views/remote.c +++ b/applications/main/subghz_remote/views/remote.c @@ -41,24 +41,18 @@ void subrem_view_remote_set_callback( subrem_view_remote->context = context; } -void subrem_view_remote_add_data_to_show( - SubRemViewRemote* subrem_view_remote, - const char* up_label, - const char* down_label, - const char* left_label, - const char* right_label, - const char* ok_label) { +void subrem_view_remote_add_data_to_show(SubRemViewRemote* subrem_view_remote, const char** labels) { furi_assert(subrem_view_remote); with_view_model( subrem_view_remote->view, SubRemViewRemoteModel * model, { - strncpy(model->up_label, up_label, SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH); - strncpy(model->down_label, down_label, SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH); - strncpy(model->left_label, left_label, SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH); - strncpy(model->right_label, right_label, SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH); - strncpy(model->ok_label, ok_label, SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH); + strncpy(model->up_label, labels[0], SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH); + strncpy(model->down_label, labels[1], SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH); + strncpy(model->left_label, labels[2], SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH); + strncpy(model->right_label, labels[3], SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH); + strncpy(model->ok_label, labels[4], SUBREM_VIEW_REMOTE_MAX_LABEL_LENGTH); // furi_string_set(model->up_label, up_label); // furi_string_set(model->down_label, down_label); @@ -69,23 +63,21 @@ void subrem_view_remote_add_data_to_show( true); } -void subrem_view_remote_set_presed_btn(SubRemViewRemote* subrem_view_remote, uint8_t presed_btn) { +void subrem_view_remote_set_state( + SubRemViewRemote* subrem_view_remote, + SubRemViewRemoteState state, + uint8_t presed_btn) { furi_assert(subrem_view_remote); with_view_model( subrem_view_remote->view, SubRemViewRemoteModel * model, - { model->pressed_btn = presed_btn; }, + { + model->state = state; + model->pressed_btn = presed_btn; + }, true); } -void subrem_view_remote_set_state( - SubRemViewRemote* subrem_view_remote, - SubRemViewRemoteState state) { - furi_assert(subrem_view_remote); - with_view_model( - subrem_view_remote->view, SubRemViewRemoteModel * model, { model->state = state; }, true); -} - void subrem_view_remote_draw(Canvas* canvas, SubRemViewRemoteModel* model) { canvas_clear(canvas); canvas_set_color(canvas, ColorBlack); diff --git a/applications/main/subghz_remote/views/remote.h b/applications/main/subghz_remote/views/remote.h index 76121cf8a..ea274fca4 100644 --- a/applications/main/subghz_remote/views/remote.h +++ b/applications/main/subghz_remote/views/remote.h @@ -24,15 +24,9 @@ void subrem_view_remote_free(SubRemViewRemote* subrem_view_remote); View* subrem_view_remote_get_view(SubRemViewRemote* subrem_view_remote); -void subrem_view_remote_add_data_to_show( - SubRemViewRemote* subrem_view_remote, - const char* up_label, - const char* down_label, - const char* left_label, - const char* right_label, - const char* ok_label); +void subrem_view_remote_add_data_to_show(SubRemViewRemote* subrem_view_remote, const char** labels); -void subrem_view_remote_set_presed_btn(SubRemViewRemote* subrem_view_remote, uint8_t presed_btn); void subrem_view_remote_set_state( SubRemViewRemote* subrem_view_remote, - SubRemViewRemoteState state); \ No newline at end of file + SubRemViewRemoteState state, + uint8_t presed_btn); \ No newline at end of file