Revamp completion popup positioning
This commit is contained in:
parent
af9ec62b25
commit
8960da4c2f
1 changed files with 77 additions and 36 deletions
|
@ -277,43 +277,97 @@ midori_location_action_create_model (void)
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
midori_location_action_popup_position (GtkWidget* popup,
|
midori_location_action_popup_position (MidoriLocationAction* action,
|
||||||
GtkWidget* widget)
|
gint matches)
|
||||||
{
|
{
|
||||||
|
GtkWidget* popup = action->popup;
|
||||||
|
GtkWidget* widget = action->entry;
|
||||||
GdkWindow* window = gtk_widget_get_window (widget);
|
GdkWindow* window = gtk_widget_get_window (widget);
|
||||||
gint wx, wy;
|
gint wx, wy, x_border, y_border, items;
|
||||||
GtkRequisition menu_req;
|
GtkRequisition menu_req;
|
||||||
GtkRequisition widget_req;
|
GtkRequisition widget_req;
|
||||||
GdkScreen* screen;
|
GdkScreen* screen;
|
||||||
gint monitor_num;
|
gint monitor_num;
|
||||||
GdkRectangle monitor;
|
GdkRectangle monitor;
|
||||||
GtkAllocation allocation;
|
GtkAllocation alloc;
|
||||||
|
gint height, sep, width, toplevel_height;
|
||||||
|
gboolean above;
|
||||||
|
GtkWidget* scrolled = gtk_widget_get_parent (action->treeview);
|
||||||
|
GtkWidget* toplevel;
|
||||||
|
GtkTreePath* path;
|
||||||
|
|
||||||
|
if (!window)
|
||||||
|
return;
|
||||||
|
|
||||||
|
gtk_widget_get_allocation (widget, &alloc);
|
||||||
|
#if GTK_CHECK_VERSION (3, 0, 0)
|
||||||
|
gtk_widget_get_preferred_size (widget, &widget_req, NULL);
|
||||||
|
#else
|
||||||
|
gtk_widget_size_request (widget, &widget_req);
|
||||||
|
#endif
|
||||||
gdk_window_get_origin (window, &wx, &wy);
|
gdk_window_get_origin (window, &wx, &wy);
|
||||||
|
|
||||||
if (!gtk_widget_get_has_window (widget))
|
#if GTK_CHECK_VERSION (3, 0, 0)
|
||||||
{
|
|
||||||
GtkAllocation alloc;
|
|
||||||
gtk_widget_get_allocation (widget, &alloc);
|
|
||||||
wx += alloc.x;
|
wx += alloc.x;
|
||||||
wy += alloc.y;
|
wy += alloc.y + (alloc.height - widget_req.height) / 2;
|
||||||
}
|
#endif
|
||||||
|
/* _gtk_entry_get_borders (GTK_ENTRY (widget), &x_border, &y_border); */
|
||||||
|
x_border = y_border = 0;
|
||||||
|
|
||||||
gtk_widget_size_request (popup, &menu_req);
|
gtk_tree_view_column_cell_get_size (
|
||||||
gtk_widget_size_request (widget, &widget_req);
|
gtk_tree_view_get_column (GTK_TREE_VIEW (action->treeview), 0),
|
||||||
|
NULL, NULL, NULL, NULL, &height);
|
||||||
|
gtk_widget_style_get (action->treeview, "vertical-separator", &sep, NULL);
|
||||||
|
height += sep;
|
||||||
|
gtk_widget_realize (action->treeview);
|
||||||
|
|
||||||
|
/* Constrain to screen/ window size */
|
||||||
screen = gtk_widget_get_screen (widget);
|
screen = gtk_widget_get_screen (widget);
|
||||||
monitor_num = gdk_screen_get_monitor_at_window (screen, window);
|
monitor_num = gdk_screen_get_monitor_at_window (screen, window);
|
||||||
gdk_screen_get_monitor_geometry (screen, monitor_num, &monitor);
|
gdk_screen_get_monitor_geometry (screen, monitor_num, &monitor);
|
||||||
|
toplevel = gtk_widget_get_toplevel (widget);
|
||||||
if (wy + widget_req.height + menu_req.height <= monitor.y + monitor.height
|
gtk_window_get_size (GTK_WINDOW (toplevel), NULL, &toplevel_height);
|
||||||
|| wy - monitor.y < (monitor.y + monitor.height) - (wy + widget_req.height))
|
toplevel_height = MIN (toplevel_height, monitor.height);
|
||||||
wy += widget_req.height;
|
if (wy > toplevel_height / 2)
|
||||||
|
items = MIN (matches, ((monitor.y + wy) / height) - 1);
|
||||||
else
|
else
|
||||||
|
items = MIN (matches, ((toplevel_height - wy) / height) - 1);
|
||||||
|
width = MIN (alloc.width, monitor.width) - 2 * x_border;
|
||||||
|
|
||||||
|
gtk_tree_view_columns_autosize (GTK_TREE_VIEW (action->treeview));
|
||||||
|
#if GTK_CHECK_VERSION (3, 0, 0)
|
||||||
|
gtk_widget_set_size_request (scrolled, width, -1);
|
||||||
|
gtk_scrolled_window_set_min_content_width (GTK_SCROLLED_WINDOW (scrolled), width);
|
||||||
|
gtk_scrolled_window_set_min_content_height (GTK_SCROLLED_WINDOW (scrolled), items * height);
|
||||||
|
gtk_widget_get_preferred_size (popup, &menu_req, NULL);
|
||||||
|
#else
|
||||||
|
gtk_widget_set_size_request (scrolled, width, items * height);
|
||||||
|
gtk_widget_size_request (popup, &menu_req);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
if (wx < monitor.x)
|
||||||
|
wx = monitor.x;
|
||||||
|
else if (wx + menu_req.width > monitor.x + monitor.width)
|
||||||
|
wx = monitor.x + monitor.width - menu_req.width;
|
||||||
|
|
||||||
|
if (wy + widget_req.height + menu_req.height <= monitor.y + monitor.height ||
|
||||||
|
wy - monitor.y < (monitor.y + monitor.height) - (wy + widget_req.height))
|
||||||
|
{
|
||||||
|
wy += widget_req.height;
|
||||||
|
above = FALSE;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
wy -= menu_req.height;
|
wy -= menu_req.height;
|
||||||
|
above = TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
path = gtk_tree_path_new_from_indices (above ? matches - 1 : 0, -1);
|
||||||
|
gtk_tree_view_scroll_to_cell (GTK_TREE_VIEW (action->treeview), path,
|
||||||
|
NULL, FALSE, 0.0, 0.0);
|
||||||
|
gtk_tree_path_free (path);
|
||||||
|
|
||||||
gtk_window_move (GTK_WINDOW (popup), wx, wy);
|
gtk_window_move (GTK_WINDOW (popup), wx, wy);
|
||||||
gtk_widget_get_allocation (widget, &allocation);
|
|
||||||
gtk_window_resize (GTK_WINDOW (popup), allocation.width, 1);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static gboolean
|
static gboolean
|
||||||
|
@ -357,8 +411,7 @@ midori_location_action_popup_timeout_cb (gpointer data)
|
||||||
gint result;
|
gint result;
|
||||||
static sqlite3_stmt* stmt;
|
static sqlite3_stmt* stmt;
|
||||||
const gchar* sqlcmd;
|
const gchar* sqlcmd;
|
||||||
gint matches, searches, height, screen_height, browser_height, sep;
|
gint matches, searches;
|
||||||
MidoriBrowser* browser;
|
|
||||||
GtkStyle* style;
|
GtkStyle* style;
|
||||||
|
|
||||||
if (!action->entry || !gtk_widget_has_focus (action->entry) || !action->history)
|
if (!action->entry || !gtk_widget_has_focus (action->entry) || !action->history)
|
||||||
|
@ -557,22 +610,10 @@ midori_location_action_popup_timeout_cb (gpointer data)
|
||||||
gtk_window_set_screen (GTK_WINDOW (action->popup),
|
gtk_window_set_screen (GTK_WINDOW (action->popup),
|
||||||
gtk_widget_get_screen (action->entry));
|
gtk_widget_get_screen (action->entry));
|
||||||
gtk_window_set_transient_for (GTK_WINDOW (action->popup), GTK_WINDOW (toplevel));
|
gtk_window_set_transient_for (GTK_WINDOW (action->popup), GTK_WINDOW (toplevel));
|
||||||
gtk_tree_view_columns_autosize (GTK_TREE_VIEW (action->treeview));
|
gtk_widget_show_all (action->popup);
|
||||||
}
|
}
|
||||||
|
|
||||||
browser = midori_browser_get_for_widget (action->entry);
|
midori_location_action_popup_position (action, matches + searches);
|
||||||
column = gtk_tree_view_get_column (GTK_TREE_VIEW (action->treeview), 0);
|
|
||||||
gtk_tree_view_column_cell_get_size (column, NULL, NULL, NULL, NULL, &height);
|
|
||||||
screen_height = gdk_screen_get_height (gtk_widget_get_screen (action->popup));
|
|
||||||
gtk_window_get_size (GTK_WINDOW (browser), NULL, &browser_height);
|
|
||||||
screen_height = MIN (MIN (browser_height, screen_height / 1.5), screen_height / 1.5);
|
|
||||||
gtk_widget_style_get (action->treeview, "vertical-separator", &sep, NULL);
|
|
||||||
/* FIXME: Instead of 1.5 we should relate to the height of one line */
|
|
||||||
height = MIN (matches * height + (matches + searches) * sep
|
|
||||||
+ searches * height / 1.5, screen_height);
|
|
||||||
gtk_widget_set_size_request (action->treeview, -1, height);
|
|
||||||
midori_location_action_popup_position (action->popup, action->entry);
|
|
||||||
gtk_widget_show_all (action->popup);
|
|
||||||
|
|
||||||
return FALSE;
|
return FALSE;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue