From 70f5b755b00d5eab576ed897a8301367b0e367a6 Mon Sep 17 00:00:00 2001 From: Volodymyr Riazantsev Date: Sat, 16 Jul 2016 02:53:25 -0400 Subject: [PATCH] ivi-shell: layer-controller-ti: Improve functionality Functionality improved: * can launch multiple application on start * handle keyboard focus: - TAB-LEFTALT can be used for switch focus - focus history; - focus on new application. Signed-off-by: Volodymyr Riazantsev Signed-off-by: Karthik Ramanan --- ivi-shell/ivi-layout-controller-ti.c | 167 +++++++++++++++++++++++++++++++---- 1 file changed, 148 insertions(+), 19 deletions(-) diff --git a/ivi-shell/ivi-layout-controller-ti.c b/ivi-shell/ivi-layout-controller-ti.c index 4a2d648..9be51d1 100644 --- a/ivi-shell/ivi-layout-controller-ti.c +++ b/ivi-shell/ivi-layout-controller-ti.c @@ -30,6 +30,8 @@ #include #include +#include + #include "ivi-layout-export.h" #ifndef container_of @@ -85,6 +87,7 @@ struct hmi_controller_layer { int32_t width; int32_t height; int32_t num_surfaces; + int32_t focus; pid_t pid; struct wl_list link; struct wl_list screen_link; @@ -96,8 +99,10 @@ struct hmi_controller_surface { void *controller; void *ivisurf; struct wl_list link; + struct wl_list focus_link; struct wl_listener destroy_listener; int conf_num; + int focus; }; struct hmi_controller_screen { @@ -106,11 +111,12 @@ struct hmi_controller_screen { }; struct hmi_server_setting { - uint32_t base_layer_id; - int32_t panel_height; - char *ivi_homescreen; - char *homescreen_app; - struct wl_array rules; + uint32_t base_layer_id; + int32_t panel_height; + char *ivi_homescreen; + char *homescreen_app; + struct wl_array autolaunch_apps; + struct wl_array rules; }; struct hmi_controller { @@ -126,6 +132,7 @@ struct hmi_controller { struct wl_listener destroy_listener; struct wl_client *user_interface; struct wl_list layers_list; + struct wl_list focus_history_list; }; @@ -350,12 +357,59 @@ exit: } static void +move_kbd_focus(struct hmi_controller_surface *ivisurf, struct hmi_controller *hmi_ctrl, bool history) +{ + struct hmi_controller_layer *layer; + struct hmi_controller_surface *surf; + struct weston_seat *seat; + struct weston_keyboard *keyboard; + struct weston_surface *surface; + + wl_list_for_each(layer, &hmi_ctrl->layers_list, link) { + wl_list_for_each(surf, &layer->surfaces_list, link) { + if (surf->focus) { + surf->focus = 0; + wl_list_insert(&hmi_ctrl->focus_history_list, &surf->focus_link); + break; + } + } + } + + wl_list_for_each(seat, &hmi_ctrl->compositor->seat_list, link) { + if(!strcmp("default", seat->seat_name)) + break; + } + + keyboard = weston_seat_get_keyboard(seat); + + if (!keyboard) + return; + + if (ivisurf) { + surface = ivi_controller_interface->surface_get_weston_surface(ivisurf->ivisurf); + weston_keyboard_set_focus(keyboard, surface); + ivisurf->focus = 1; + + if (NULL != ivisurf->focus_link.next) + wl_list_remove(&ivisurf->focus_link); + + } else if (history && !wl_list_empty(&hmi_ctrl->focus_history_list)) { + struct hmi_controller_surface *s = + wl_container_of(hmi_ctrl->focus_history_list.next, s, focus_link); + wl_list_remove(&s->focus_link); + surface = ivi_controller_interface->surface_get_weston_surface(s->ivisurf); + weston_keyboard_set_focus(keyboard, surface); + s->focus = 1; + } +} + +static void set_notification_create_surface(struct ivi_layout_surface *ivisurf, void *userdata) { struct hmi_controller *hmi_ctrl = userdata; - struct hmi_controller_layer *hmi_ctrl_layer = NULL; - struct hmi_controller_surface *hmi_ctrl_surf = NULL; + struct hmi_controller_layer *hmi_ctrl_layer; + struct hmi_controller_surface *hmi_ctrl_surf; struct ivi_layout_layer *dest_layer; struct weston_surface *surface; @@ -378,6 +432,7 @@ set_notification_create_surface(struct ivi_layout_surface *ivisurf, hmi_ctrl_surf = calloc(1, sizeof(*hmi_ctrl_surf)); hmi_ctrl_surf->ivisurf = ivisurf; wl_list_init(&hmi_ctrl_surf->link); + wl_list_init(&hmi_ctrl_surf->focus_link); wl_list_insert(&hmi_ctrl_layer->surfaces_list, &hmi_ctrl_surf->link); @@ -419,6 +474,9 @@ remove: wl_list_remove(&surf->link); + if (surf->focus) + move_kbd_focus(NULL, hmi_ctrl, true); + ivi_controller_interface->layer_remove_surface(dest_layer, ivisurf); if (wl_list_empty(&hmi_ctrl_layer->surfaces_list)) { @@ -451,9 +509,10 @@ set_notification_configure_surface(struct ivi_layout_surface *ivisurf, void *userdata) { struct hmi_controller *hmi_ctrl = userdata; - struct hmi_controller_layer *hmi_ctrl_layer = NULL; + struct hmi_controller_layer *hmi_ctrl_layer; struct weston_surface *surface; - struct hmi_controller_surface *hmi_ctrl_surf = NULL; + struct weston_seat *seat = NULL; + struct hmi_controller_surface *hmi_ctrl_surf; int src_rect[4] = {0}; int dest_rect[4] = {0}; @@ -511,6 +570,16 @@ found: dest_rect[3] = hmi_ctrl_layer->rule->dest_rect[3] > 0 ? hmi_ctrl_layer->rule->dest_rect[3] : dest_rect[3] ; } + + if (hmi_ctrl_layer->rule->autofocus) { + + wl_list_for_each(seat, &hmi_ctrl->compositor->seat_list, link) { + if(!strcmp("default", seat->seat_name)) + break; + } + + move_kbd_focus(hmi_ctrl_surf, hmi_ctrl, false); + } } ivi_controller_interface->surface_set_source_rectangle(ivisurf @@ -522,6 +591,7 @@ found: , dest_rect[2], dest_rect[3]); ivi_controller_interface->surface_set_visibility(ivisurf, true); + ivi_controller_interface->commit_changes(); hmi_ctrl_surf->conf_num++; @@ -543,14 +613,9 @@ hmi_server_setting_create(struct weston_compositor *ec) weston_config_section_get_uint(shell_section, "base-layer-id", &setting->base_layer_id, 1000); - if ((shell_section = weston_config_get_section(config, "ivi-autolaunch", - NULL, NULL))) { - weston_config_section_get_string(shell_section, "path", - &setting->homescreen_app, NULL); - } - - wl_array_init(&setting->rules); + wl_array_init(&setting->autolaunch_apps); + wl_array_init(&setting->autolaunch_apps); while (weston_config_next_section(config, &shell_section, &name)) { int screen_id; @@ -564,6 +629,12 @@ hmi_server_setting_create(struct weston_compositor *ec) char *buff; struct hmi_launch_rule *rule = NULL; + if (!strcmp(name, "ivi-autolaunch")) { + char **s = wl_array_add(&setting->autolaunch_apps, sizeof(*s)); + weston_config_section_get_string(shell_section, "path", s, NULL); + continue; + } + if (0 != strcmp(name, "ivi-layout-rule")) continue; @@ -573,7 +644,7 @@ hmi_server_setting_create(struct weston_compositor *ec) weston_config_section_get_int(shell_section, "order", &order, -1); weston_config_section_get_int(shell_section, "mode", &mode, -1); - weston_config_section_get_int(shell_section, "focus_on", &focus_on, -1); + weston_config_section_get_int(shell_section, "focus_on", &focus_on, 0); weston_config_section_get_int(shell_section, "screen", &screen_id, -1); if (0 == weston_config_section_get_string(shell_section, "crop_rect", @@ -631,8 +702,10 @@ hmi_controller_destroy(struct wl_listener *listener, void *data) static void hmi_controller_launch_homescreen(struct hmi_controller *hmi_ctrl) { - if (hmi_ctrl->hmi_setting->homescreen_app) { - if(system(hmi_ctrl->hmi_setting->homescreen_app)) { + char **app; + + wl_array_for_each(app, &hmi_ctrl->hmi_setting->autolaunch_apps) { + if(system(*app)) { ; } } @@ -674,6 +747,7 @@ hmi_controller_create(struct weston_compositor *ec) &hmi_ctrl->destroy_listener); wl_list_init(&hmi_ctrl->layers_list); + wl_list_init(&hmi_ctrl->focus_history_list); free(pp_screen); pp_screen = NULL; @@ -719,6 +793,57 @@ initialize(struct hmi_controller *hmi_ctrl) return 1; } +static void +switch_focus_bindings(struct weston_keyboard *keyboard, uint32_t time, + uint32_t key, void *data) +{ + struct hmi_controller *hmi_ctrl = data; + struct hmi_controller_layer *hmi_ctrl_layer, *next_l, *cycle_l = NULL; + struct hmi_controller_surface *hmi_ctrl_surf; + bool pp = false; + + wl_list_for_each(hmi_ctrl_layer, &hmi_ctrl->layers_list, link) { + wl_list_for_each(hmi_ctrl_surf, &hmi_ctrl_layer->surfaces_list, link) { + if (hmi_ctrl_surf->focus) { + goto ff; + } + } + } + + hmi_ctrl_surf = NULL; + pp = true; + +ff: + wl_list_for_each(next_l, &hmi_ctrl->layers_list, link) { + + if (pp) { + if (next_l->rule && next_l->rule->autofocus) { + cycle_l = next_l; + break; + } + } else { + if (next_l == hmi_ctrl_layer) { + pp = true; + continue; + } else { + if (next_l->rule && next_l->rule->autofocus) { + cycle_l = next_l; + break; + } + } + } + } + + if (!cycle_l) + return; + + move_kbd_focus(container_of(cycle_l->surfaces_list.next + , struct hmi_controller_surface + , link) + , hmi_ctrl, false); +} + + /***************************************************************************** * exported functions ****************************************************************************/ @@ -753,5 +878,9 @@ controller_module_init(struct weston_compositor *ec, hmi_controller_launch_homescreen(hmi_ctrl); + weston_compositor_add_key_binding(ec, KEY_TAB , MODIFIER_ALT, + switch_focus_bindings, hmi_ctrl); + weston_install_debug_key_binding(ec, 0); + return 0; } -- 2.4.5