diff options
author | William Wilgus <wilgus.william@gmail.com> | 2021-10-22 22:17:36 -0400 |
---|---|---|
committer | William Wilgus <wilgus.william@gmail.com> | 2021-10-29 03:07:42 -0400 |
commit | dc24a18cef83d88f4e6ab657ca0adfccf1051474 (patch) | |
tree | 3e07fe2e5fa1a75eb549bd770270d2985c8a640f /apps | |
parent | 8ee24d8cb47939ff04fa42b1ae9719ebeba64d29 (diff) | |
download | rockbox-dc24a18cef83d88f4e6ab657ca0adfccf1051474.tar.gz rockbox-dc24a18cef83d88f4e6ab657ca0adfccf1051474.zip |
PLUGINBROWSER make resumable
make the plugin browser remember the last item between invocations
this has bugged me for the longest time dealing with the plugin_menu
Fix a very old bug fix for reloading lang strings in the lang menu
FS#8117, sending multiple ENTER_MENU_ITEM callbacks from different
areas of the code makes it hard to keep track of where your callback
is originating
Change-Id: Ib0a61558c11ee4c772134378a7020ac0e10fc4ee
Diffstat (limited to 'apps')
-rw-r--r-- | apps/menu.c | 27 | ||||
-rw-r--r-- | apps/menus/plugin_menu.c | 30 | ||||
-rw-r--r-- | apps/root_menu.c | 66 | ||||
-rw-r--r-- | apps/tree.c | 14 |
4 files changed, 106 insertions, 31 deletions
diff --git a/apps/menu.c b/apps/menu.c index 830bc67a11..802a16bbb8 100644 --- a/apps/menu.c +++ b/apps/menu.c | |||
@@ -187,17 +187,18 @@ static enum themable_icons menu_get_icon(int selected_item, void * data) | |||
187 | return menu_icon; | 187 | return menu_icon; |
188 | } | 188 | } |
189 | 189 | ||
190 | static void init_menu_lists(const struct menu_item_ex *menu, | 190 | static int init_menu_lists(const struct menu_item_ex *menu, |
191 | struct gui_synclist *lists, int selected, bool callback, | 191 | struct gui_synclist *lists, int selected, bool callback, |
192 | struct viewport parent[NB_SCREENS]) | 192 | struct viewport parent[NB_SCREENS]) |
193 | { | 193 | { |
194 | if (!menu || !lists) | 194 | if (!menu || !lists) |
195 | { | 195 | { |
196 | panicf("init_menu_lists, NULL pointer"); | 196 | panicf("init_menu_lists, NULL pointer"); |
197 | return; | 197 | return 0; |
198 | } | 198 | } |
199 | 199 | ||
200 | int i; | 200 | int i; |
201 | int start_action = ACTION_ENTER_MENUITEM; | ||
201 | int count = MIN(MENU_GET_COUNT(menu->flags), MAX_MENU_SUBITEMS); | 202 | int count = MIN(MENU_GET_COUNT(menu->flags), MAX_MENU_SUBITEMS); |
202 | int type = (menu->flags&MENU_TYPE_MASK); | 203 | int type = (menu->flags&MENU_TYPE_MASK); |
203 | menu_callback_type menu_callback = NULL; | 204 | menu_callback_type menu_callback = NULL; |
@@ -264,7 +265,9 @@ static void init_menu_lists(const struct menu_item_ex *menu, | |||
264 | 265 | ||
265 | get_menu_callback(menu,&menu_callback); | 266 | get_menu_callback(menu,&menu_callback); |
266 | if (callback && menu_callback) | 267 | if (callback && menu_callback) |
267 | menu_callback(ACTION_ENTER_MENUITEM, menu, lists); | 268 | start_action = menu_callback(start_action, menu, lists); |
269 | |||
270 | return start_action; | ||
268 | } | 271 | } |
269 | 272 | ||
270 | static int talk_menu_item(int selected_item, void *data) | 273 | static int talk_menu_item(int selected_item, void *data) |
@@ -381,6 +384,7 @@ int do_menu(const struct menu_item_ex *start_menu, int *start_selected, | |||
381 | int selected = start_selected? *start_selected : 0; | 384 | int selected = start_selected? *start_selected : 0; |
382 | int ret = 0; | 385 | int ret = 0; |
383 | int action; | 386 | int action; |
387 | int start_action; | ||
384 | struct gui_synclist lists; | 388 | struct gui_synclist lists; |
385 | const struct menu_item_ex *temp = NULL; | 389 | const struct menu_item_ex *temp = NULL; |
386 | const struct menu_item_ex *menu = start_menu; | 390 | const struct menu_item_ex *menu = start_menu; |
@@ -407,8 +411,10 @@ int do_menu(const struct menu_item_ex *start_menu, int *start_selected, | |||
407 | menu_callback_type menu_callback = NULL; | 411 | menu_callback_type menu_callback = NULL; |
408 | 412 | ||
409 | /* if hide_theme is true, assume parent has been fixed before passed into | 413 | /* if hide_theme is true, assume parent has been fixed before passed into |
410 | * this function, e.g. with viewport_set_defaults(parent, screen) */ | 414 | * this function, e.g. with viewport_set_defaults(parent, screen) |
411 | init_menu_lists(menu, &lists, selected, true, parent); | 415 | * start_action allows an action to be processed |
416 | * by menu logic by bypassing get_action on the initial run */ | ||
417 | start_action = init_menu_lists(menu, &lists, selected, true, parent); | ||
412 | vps = *(lists.parent); | 418 | vps = *(lists.parent); |
413 | in_stringlist = ((menu->flags&MENU_TYPE_MASK) == MT_RETURN_ID); | 419 | in_stringlist = ((menu->flags&MENU_TYPE_MASK) == MT_RETURN_ID); |
414 | /* load the callback, and only reload it if menu changes */ | 420 | /* load the callback, and only reload it if menu changes */ |
@@ -421,7 +427,13 @@ int do_menu(const struct menu_item_ex *start_menu, int *start_selected, | |||
421 | { | 427 | { |
422 | keyclick_set_callback(gui_synclist_keyclick_callback, &lists); | 428 | keyclick_set_callback(gui_synclist_keyclick_callback, &lists); |
423 | 429 | ||
424 | action = get_action(CONTEXT_MAINMENU|ALLOW_SOFTLOCK, | 430 | if (UNLIKELY(start_action != ACTION_ENTER_MENUITEM)) |
431 | { | ||
432 | action = start_action; | ||
433 | start_action = ACTION_ENTER_MENUITEM; | ||
434 | } | ||
435 | else | ||
436 | action = get_action(CONTEXT_MAINMENU|ALLOW_SOFTLOCK, | ||
425 | list_do_action_timeout(&lists, HZ)); | 437 | list_do_action_timeout(&lists, HZ)); |
426 | /* HZ so the status bar redraws corectly */ | 438 | /* HZ so the status bar redraws corectly */ |
427 | 439 | ||
@@ -639,7 +651,8 @@ int do_menu(const struct menu_item_ex *start_menu, int *start_selected, | |||
639 | if (!(menu->flags&MENU_EXITAFTERTHISMENU) || | 651 | if (!(menu->flags&MENU_EXITAFTERTHISMENU) || |
640 | (temp->flags&MENU_EXITAFTERTHISMENU)) | 652 | (temp->flags&MENU_EXITAFTERTHISMENU)) |
641 | { | 653 | { |
642 | init_menu_lists(menu, &lists, selected, true, vps); | 654 | /* Reload menu but don't run the calback again FS#8117 */ |
655 | init_menu_lists(menu, &lists, selected, false, vps); | ||
643 | } | 656 | } |
644 | if (temp->flags&MENU_FUNC_CHECK_RETVAL) | 657 | if (temp->flags&MENU_FUNC_CHECK_RETVAL) |
645 | { | 658 | { |
diff --git a/apps/menus/plugin_menu.c b/apps/menus/plugin_menu.c index 055cfce140..7f29e61af4 100644 --- a/apps/menus/plugin_menu.c +++ b/apps/menus/plugin_menu.c | |||
@@ -24,11 +24,12 @@ | |||
24 | #include "config.h" | 24 | #include "config.h" |
25 | #include "lang.h" | 25 | #include "lang.h" |
26 | #include "menu.h" | 26 | #include "menu.h" |
27 | #include "action.h" | ||
27 | #include "settings.h" | 28 | #include "settings.h" |
28 | #include "rbpaths.h" | 29 | #include "rbpaths.h" |
29 | #include "root_menu.h" | 30 | #include "root_menu.h" |
30 | #include "tree.h" | 31 | #include "tree.h" |
31 | 32 | static int reenter = 0; | |
32 | 33 | ||
33 | enum { | 34 | enum { |
34 | GAMES, | 35 | GAMES, |
@@ -53,13 +54,36 @@ static int plugins_menu(void* param) | |||
53 | 54 | ||
54 | browse_context_init(&browse, SHOW_PLUGINS, 0, str(items[item].id), | 55 | browse_context_init(&browse, SHOW_PLUGINS, 0, str(items[item].id), |
55 | Icon_Plugin, items[item].path, NULL); | 56 | Icon_Plugin, items[item].path, NULL); |
56 | 57 | ||
57 | ret = rockbox_browse(&browse); | 58 | ret = rockbox_browse(&browse); |
59 | |||
58 | if (ret == GO_TO_PREVIOUS) | 60 | if (ret == GO_TO_PREVIOUS) |
59 | return 0; | 61 | return 0; |
62 | if (ret == GO_TO_PLUGIN) | ||
63 | reenter = 1; | ||
60 | return ret; | 64 | return ret; |
61 | } | 65 | } |
62 | 66 | ||
67 | static int menu_callback(int action, | ||
68 | const struct menu_item_ex *this_item, | ||
69 | struct gui_synclist *this_list) | ||
70 | { | ||
71 | (void)this_item; | ||
72 | static int selected = 0; | ||
73 | |||
74 | if (action == ACTION_ENTER_MENUITEM) | ||
75 | { | ||
76 | this_list->selected_item = selected; | ||
77 | if (reenter-- > 0) | ||
78 | action = ACTION_STD_OK; | ||
79 | } | ||
80 | else if (action == ACTION_STD_OK) | ||
81 | { | ||
82 | selected = gui_synclist_get_sel_pos(this_list); | ||
83 | } | ||
84 | return action; | ||
85 | } | ||
86 | |||
63 | #define ITEM_FLAG (MENU_FUNC_USEPARAM|MENU_FUNC_CHECK_RETVAL) | 87 | #define ITEM_FLAG (MENU_FUNC_USEPARAM|MENU_FUNC_CHECK_RETVAL) |
64 | 88 | ||
65 | MENUITEM_FUNCTION(games_item, ITEM_FLAG, ID2P(LANG_PLUGIN_GAMES), | 89 | MENUITEM_FUNCTION(games_item, ITEM_FLAG, ID2P(LANG_PLUGIN_GAMES), |
@@ -69,6 +93,6 @@ MENUITEM_FUNCTION(apps_item, ITEM_FLAG, ID2P(LANG_PLUGIN_APPS), | |||
69 | MENUITEM_FUNCTION(demos_item, ITEM_FLAG, ID2P(LANG_PLUGIN_DEMOS), | 93 | MENUITEM_FUNCTION(demos_item, ITEM_FLAG, ID2P(LANG_PLUGIN_DEMOS), |
70 | plugins_menu, (void*)DEMOS, NULL, Icon_Folder); | 94 | plugins_menu, (void*)DEMOS, NULL, Icon_Folder); |
71 | 95 | ||
72 | MAKE_MENU(plugin_menu, ID2P(LANG_PLUGINS), NULL, | 96 | MAKE_MENU(plugin_menu, ID2P(LANG_PLUGINS), &menu_callback, |
73 | Icon_Plugin, | 97 | Icon_Plugin, |
74 | &games_item, &apps_item, &demos_item); | 98 | &games_item, &apps_item, &demos_item); |
diff --git a/apps/root_menu.c b/apps/root_menu.c index 15d03a7cda..ed6bdfdcca 100644 --- a/apps/root_menu.c +++ b/apps/root_menu.c | |||
@@ -634,6 +634,7 @@ static int item_callback(int action, | |||
634 | } | 634 | } |
635 | return action; | 635 | return action; |
636 | } | 636 | } |
637 | |||
637 | static int get_selection(int last_screen) | 638 | static int get_selection(int last_screen) |
638 | { | 639 | { |
639 | int i; | 640 | int i; |
@@ -683,6 +684,7 @@ static inline int load_screen(int screen) | |||
683 | last_screen = old_previous; | 684 | last_screen = old_previous; |
684 | return ret_val; | 685 | return ret_val; |
685 | } | 686 | } |
687 | |||
686 | static int load_context_screen(int selection) | 688 | static int load_context_screen(int selection) |
687 | { | 689 | { |
688 | const struct menu_item_ex *context_menu = NULL; | 690 | const struct menu_item_ex *context_menu = NULL; |
@@ -709,13 +711,12 @@ static int load_plugin_screen(char *key) | |||
709 | { | 711 | { |
710 | int ret_val; | 712 | int ret_val; |
711 | int old_previous = last_screen; | 713 | int old_previous = last_screen; |
714 | int old_global = global_status.last_screen; | ||
712 | last_screen = next_screen; | 715 | last_screen = next_screen; |
713 | global_status.last_screen = (char)next_screen; | 716 | global_status.last_screen = (char)next_screen; |
714 | status_save(); | 717 | status_save(); |
715 | 718 | ||
716 | |||
717 | int opret = open_plugin_get_entry(key, &open_plugin_entry); | 719 | int opret = open_plugin_get_entry(key, &open_plugin_entry); |
718 | bool flush = (opret == OPEN_PLUGIN_NEEDS_FLUSHED); | ||
719 | char *path = open_plugin_entry.path; | 720 | char *path = open_plugin_entry.path; |
720 | char *param = open_plugin_entry.param; | 721 | char *param = open_plugin_entry.param; |
721 | if (param[0] == '\0') | 722 | if (param[0] == '\0') |
@@ -723,6 +724,9 @@ static int load_plugin_screen(char *key) | |||
723 | 724 | ||
724 | switch (plugin_load(path, param)) | 725 | switch (plugin_load(path, param)) |
725 | { | 726 | { |
727 | case PLUGIN_USB_CONNECTED: | ||
728 | ret_val = GO_TO_ROOT; | ||
729 | break; | ||
726 | case PLUGIN_GOTO_WPS: | 730 | case PLUGIN_GOTO_WPS: |
727 | ret_val = GO_TO_WPS; | 731 | ret_val = GO_TO_WPS; |
728 | break; | 732 | break; |
@@ -730,18 +734,30 @@ static int load_plugin_screen(char *key) | |||
730 | ret_val = GO_TO_PLUGIN; | 734 | ret_val = GO_TO_PLUGIN; |
731 | break; | 735 | break; |
732 | case PLUGIN_OK: | 736 | case PLUGIN_OK: |
733 | ret_val = audio_status() ? GO_TO_PREVIOUS : GO_TO_ROOT; | 737 | /* Prevents infinite loop with WPS & Plugins*/ |
734 | break; | 738 | if (old_global == GO_TO_WPS && !audio_status()) |
739 | { | ||
740 | ret_val = GO_TO_ROOT; | ||
741 | break; | ||
742 | } | ||
743 | /*fallthrough*/ | ||
735 | default: | 744 | default: |
736 | ret_val = GO_TO_PREVIOUS; | 745 | ret_val = GO_TO_PREVIOUS; |
746 | last_screen = (old_previous == next_screen) ? GO_TO_ROOT : old_previous; | ||
737 | break; | 747 | break; |
738 | } | ||
739 | 748 | ||
740 | if (!flush && ret_val != GO_TO_PLUGIN) | 749 | } |
741 | open_plugin_add_path(NULL, NULL, NULL); | ||
742 | 750 | ||
743 | if (ret_val == GO_TO_PREVIOUS) | 751 | if (ret_val != GO_TO_PLUGIN) |
744 | last_screen = (old_previous == next_screen) ? GO_TO_ROOT : old_previous; | 752 | { |
753 | if (opret != OPEN_PLUGIN_NEEDS_FLUSHED || last_screen != GO_TO_WPS) | ||
754 | { | ||
755 | /* Keep the entry in case of GO_TO_PREVIOUS */ | ||
756 | open_plugin_entry.hash = 0; /*remove hash -- prevents flush to disk */ | ||
757 | open_plugin_entry.lang_id = LANG_PREVIOUS_SCREEN; | ||
758 | /*open_plugin_add_path(NULL, NULL, NULL);// clear entry */ | ||
759 | } | ||
760 | } | ||
745 | return ret_val; | 761 | return ret_val; |
746 | } | 762 | } |
747 | 763 | ||
@@ -858,8 +874,12 @@ void root_menu(void) | |||
858 | #endif /* With !CONFIG_TUNER previous_music is always GO_TO_WPS */ | 874 | #endif /* With !CONFIG_TUNER previous_music is always GO_TO_WPS */ |
859 | 875 | ||
860 | case GO_TO_PREVIOUS: | 876 | case GO_TO_PREVIOUS: |
877 | { | ||
861 | next_screen = last_screen; | 878 | next_screen = last_screen; |
879 | if (last_screen == GO_TO_PLUGIN)/* for WPS */ | ||
880 | last_screen = GO_TO_PREVIOUS; | ||
862 | break; | 881 | break; |
882 | } | ||
863 | 883 | ||
864 | case GO_TO_PREVIOUS_BROWSER: | 884 | case GO_TO_PREVIOUS_BROWSER: |
865 | next_screen = previous_browser; | 885 | next_screen = previous_browser; |
@@ -874,7 +894,8 @@ void root_menu(void) | |||
874 | case GO_TO_PLUGIN: | 894 | case GO_TO_PLUGIN: |
875 | { | 895 | { |
876 | char *key; | 896 | char *key; |
877 | if (global_status.last_screen == GO_TO_SHORTCUTMENU) | 897 | if (global_status.last_screen == GO_TO_SHORTCUTMENU && |
898 | last_screen != GO_TO_ROOT) | ||
878 | { | 899 | { |
879 | shortcut_origin = last_screen; | 900 | shortcut_origin = last_screen; |
880 | key = ID2P(LANG_SHORTCUTS); | 901 | key = ID2P(LANG_SHORTCUTS); |
@@ -892,6 +913,9 @@ void root_menu(void) | |||
892 | case GO_TO_SHORTCUTMENU: | 913 | case GO_TO_SHORTCUTMENU: |
893 | key = ID2P(LANG_SHORTCUTS); | 914 | key = ID2P(LANG_SHORTCUTS); |
894 | break; | 915 | break; |
916 | case GO_TO_PREVIOUS: | ||
917 | key = ID2P(LANG_PREVIOUS_SCREEN); | ||
918 | break; | ||
895 | default: | 919 | default: |
896 | key = ID2P(LANG_OPEN_PLUGIN); | 920 | key = ID2P(LANG_OPEN_PLUGIN); |
897 | break; | 921 | break; |
@@ -900,15 +924,23 @@ void root_menu(void) | |||
900 | 924 | ||
901 | next_screen = load_plugin_screen(key); | 925 | next_screen = load_plugin_screen(key); |
902 | 926 | ||
903 | /* shortcuts may take several trips through the GO_TO_PLUGIN case | 927 | if (next_screen == GO_TO_PREVIOUS) |
904 | make sure we preserve and restore the origin */ | ||
905 | if (next_screen == GO_TO_PREVIOUS && shortcut_origin != GO_TO_ROOT) | ||
906 | { | 928 | { |
907 | if (shortcut_origin != GO_TO_WPS) | 929 | /* shortcuts may take several trips through the GO_TO_PLUGIN |
908 | next_screen = shortcut_origin; | 930 | case make sure we preserve and restore the origin */ |
909 | shortcut_origin = GO_TO_ROOT; | 931 | if (shortcut_origin != GO_TO_ROOT) |
932 | { | ||
933 | if (shortcut_origin != GO_TO_WPS) | ||
934 | next_screen = shortcut_origin; | ||
935 | shortcut_origin = GO_TO_ROOT; | ||
936 | } | ||
937 | /* skip GO_TO_PREVIOUS */ | ||
938 | if (last_screen == GO_TO_BROWSEPLUGINS) | ||
939 | { | ||
940 | next_screen = last_screen; | ||
941 | last_screen = GO_TO_PLUGIN; | ||
942 | } | ||
910 | } | 943 | } |
911 | |||
912 | previous_browser = (next_screen != GO_TO_WPS) ? GO_TO_FILEBROWSER : GO_TO_PLUGIN; | 944 | previous_browser = (next_screen != GO_TO_WPS) ? GO_TO_FILEBROWSER : GO_TO_PLUGIN; |
913 | break; | 945 | break; |
914 | } | 946 | } |
diff --git a/apps/tree.c b/apps/tree.c index 7fcced92c8..e35f769a14 100644 --- a/apps/tree.c +++ b/apps/tree.c | |||
@@ -967,11 +967,17 @@ int rockbox_browse(struct browse_context *browse) | |||
967 | if (*tc.dirfilter >= NUM_FILTER_MODES) | 967 | if (*tc.dirfilter >= NUM_FILTER_MODES) |
968 | { | 968 | { |
969 | int last_context; | 969 | int last_context; |
970 | /* don't reset if its the same browse already loaded */ | ||
971 | if (tc.browse != browse || | ||
972 | !(tc.currdir[1] && strcmp(tc.currdir, browse->root) == 0)) | ||
973 | { | ||
974 | tc.browse = browse; | ||
975 | tc.selected_item = 0; | ||
976 | tc.dirlevel = 0; | ||
977 | |||
978 | strlcpy(tc.currdir, browse->root, sizeof(tc.currdir)); | ||
979 | } | ||
970 | 980 | ||
971 | tc.browse = browse; | ||
972 | tc.selected_item = 0; | ||
973 | tc.dirlevel = 0; | ||
974 | strlcpy(tc.currdir, browse->root, sizeof(tc.currdir)); | ||
975 | start_wps = false; | 981 | start_wps = false; |
976 | last_context = curr_context; | 982 | last_context = curr_context; |
977 | 983 | ||