shell: Start implementing the popup surface type

This lands the basic behavior of the popup surface type, but there are still
a number of details to be worked out.  Mainly there's a hardcoded timeout
to handle the case of releasing the popup button outside any of the
client windows, which triggers popup_end if it happens after the timeout.
Maybe we just need to add that as an argument, or we could add a new event
that fires in this case to let the client decide whether it ends the popup
or not.
This commit is contained in:
Kristian Høgsberg
2012-01-04 22:19:14 -05:00
parent dade64968c
commit b3cca0a411
5 changed files with 176 additions and 26 deletions
+10 -12
View File
@@ -128,19 +128,19 @@ sigchild_handler(int s)
}
static void
show_menu(struct panel *panel, struct input *input)
show_menu(struct panel *panel, struct input *input, uint32_t time)
{
int32_t x, y, width = 200, height = 200;
struct display *display;
int32_t x, y;
static const char *entries[] = {
"Roy", "Pris", "Leon", "Zhora"
};
input_get_position(input, &x, &y);
display = window_get_display(panel->window);
panel->menu = window_create_transient(display, panel->window,
x - 10, y - 10, width, height);
window_set_user_data(panel->menu, panel);
panel->menu = window_create_menu(window_get_display(panel->window),
input, time, panel->window,
x - 10, y - 10, entries, 4);
window_draw(panel->menu);
window_flush(panel->menu);
window_schedule_redraw(panel->menu);
}
static void
@@ -253,9 +253,7 @@ panel_button_handler(struct window *window,
panel_activate_item(panel, pi);
} else if (button == BTN_RIGHT) {
if (state)
show_menu(panel, input);
else
window_destroy(panel->menu);
show_menu(panel, input, time);
}
}
+3 -3
View File
@@ -167,7 +167,7 @@ key_handler(struct window *window, struct input *input, uint32_t time,
}
static void
show_menu(struct resizor *resizor, struct input *input)
show_menu(struct resizor *resizor, struct input *input, uint32_t time)
{
int32_t x, y;
static const char *entries[] = {
@@ -176,7 +176,7 @@ show_menu(struct resizor *resizor, struct input *input)
input_get_position(input, &x, &y);
resizor->menu = window_create_menu(resizor->display,
resizor->window,
input, time, resizor->window,
x - 10, y - 10, entries, 4);
window_schedule_redraw(resizor->menu);
@@ -192,7 +192,7 @@ button_handler(struct window *window,
switch (button) {
case BTN_RIGHT:
if (state)
show_menu(resizor, input);
show_menu(resizor, input, time);
break;
}
}
+21 -5
View File
@@ -1799,8 +1799,20 @@ handle_configure(void *data, struct wl_shell_surface *shell_surface,
}
}
static void
handle_popup_done(void *data, struct wl_shell_surface *shell_surface)
{
struct window *window = data;
/* FIXME: Need more context in this event, at least the input
* device. Or just use wl_callback. */
window_destroy(window);
}
static const struct wl_shell_surface_listener shell_surface_listener = {
handle_configure,
handle_popup_done
};
void
@@ -2108,6 +2120,7 @@ window_create_transient(struct display *display, struct window *parent,
struct menu {
struct window *window;
const char **entries;
uint32_t time;
int current;
int count;
};
@@ -2159,7 +2172,7 @@ menu_button_handler(struct window *window,
struct menu *menu = data;
/* Either relase after press-drag-release or click-motion-click. */
if (state == 0 && 0 <= menu->current && menu->current < menu->count)
if (state == 0 && time - menu->time > 500)
window_destroy(window);
}
@@ -2209,7 +2222,8 @@ menu_redraw_handler(struct window *window, void *data)
}
struct window *
window_create_menu(struct display *display, struct window *parent,
window_create_menu(struct display *display,
struct input *input, uint32_t time, struct window *parent,
int32_t x, int32_t y, const char **entries, int count)
{
struct window *window;
@@ -2226,14 +2240,16 @@ window_create_menu(struct display *display, struct window *parent,
menu->window = window;
menu->entries = entries;
menu->count = count;
menu->time = time;
window->decoration = 0;
window->type = TYPE_MENU;
window->x = x;
window->y = y;
wl_shell_surface_set_transient(window->shell_surface,
window->parent->shell_surface,
window->x, window->y, 0);
wl_shell_surface_set_popup(window->shell_surface,
input->input_device, time,
window->parent->shell_surface,
window->x, window->y, 0);
window_set_motion_handler(window, menu_motion_handler);
window_set_enter_handler(window, menu_enter_handler);
+2 -1
View File
@@ -203,7 +203,8 @@ struct window *
window_create_transient(struct display *display, struct window *parent,
int32_t x, int32_t y, int32_t width, int32_t height);
struct window *
window_create_menu(struct display *display, struct window *parent,
window_create_menu(struct display *display,
struct input *input, uint32_t time, struct window *parent,
int32_t x, int32_t y, const char **entries, int count);
void