2807 lines
111 KiB
Diff
2807 lines
111 KiB
Diff
diff -up firefox-51.0/widget/gtk/gtk3drawing.cpp.old firefox-51.0/widget/gtk/gtk3drawing.cpp
|
|
--- firefox-51.0/widget/gtk/gtk3drawing.cpp.old 2017-01-18 16:24:56.375732107 +0100
|
|
+++ firefox-51.0/widget/gtk/gtk3drawing.cpp 2017-01-10 11:28:15.000000000 +0100
|
|
@@ -18,16 +18,6 @@
|
|
|
|
#include <math.h>
|
|
|
|
-static GtkWidget* gProtoLayout;
|
|
-static GtkWidget* gComboBoxWidget;
|
|
-static GtkWidget* gComboBoxButtonWidget;
|
|
-static GtkWidget* gComboBoxArrowWidget;
|
|
-static GtkWidget* gComboBoxSeparatorWidget;
|
|
-static GtkWidget* gComboBoxEntryWidget;
|
|
-static GtkWidget* gComboBoxEntryTextareaWidget;
|
|
-static GtkWidget* gComboBoxEntryButtonWidget;
|
|
-static GtkWidget* gComboBoxEntryArrowWidget;
|
|
-
|
|
static style_prop_t style_prop_func;
|
|
static gboolean have_arrow_scaling;
|
|
static gboolean checkbox_check_state;
|
|
@@ -46,6 +36,10 @@ static gboolean is_initialized;
|
|
static gint
|
|
moz_gtk_get_tab_thickness(GtkStyleContext *style);
|
|
|
|
+static gint
|
|
+moz_gtk_menu_item_paint(WidgetNodeType widget, cairo_t *cr, GdkRectangle* rect,
|
|
+ GtkWidgetState* state, GtkTextDirection direction);
|
|
+
|
|
static GtkStateFlags
|
|
GetStateFlagsFromGtkWidgetState(GtkWidgetState* state)
|
|
{
|
|
@@ -79,212 +73,6 @@ moz_gtk_enable_style_props(style_prop_t
|
|
return MOZ_GTK_SUCCESS;
|
|
}
|
|
|
|
-static gint
|
|
-setup_widget_prototype(GtkWidget* widget)
|
|
-{
|
|
- if (!gProtoLayout) {
|
|
- gProtoLayout = GetWidget(MOZ_GTK_WINDOW_CONTAINER);
|
|
- }
|
|
- gtk_container_add(GTK_CONTAINER(gProtoLayout), widget);
|
|
- return MOZ_GTK_SUCCESS;
|
|
-}
|
|
-
|
|
-/* We need to have pointers to the inner widgets (button, separator, arrow)
|
|
- * of the ComboBox to get the correct rendering from theme engines which
|
|
- * special cases their look. Since the inner layout can change, we ask GTK
|
|
- * to NULL our pointers when they are about to become invalid because the
|
|
- * corresponding widgets don't exist anymore. It's the role of
|
|
- * g_object_add_weak_pointer().
|
|
- * Note that if we don't find the inner widgets (which shouldn't happen), we
|
|
- * fallback to use generic "non-inner" widgets, and they don't need that kind
|
|
- * of weak pointer since they are explicit children of gProtoLayout and as
|
|
- * such GTK holds a strong reference to them. */
|
|
-static void
|
|
-moz_gtk_get_combo_box_inner_button(GtkWidget *widget, gpointer client_data)
|
|
-{
|
|
- if (GTK_IS_TOGGLE_BUTTON(widget)) {
|
|
- gComboBoxButtonWidget = widget;
|
|
- g_object_add_weak_pointer(G_OBJECT(widget),
|
|
- (gpointer *) &gComboBoxButtonWidget);
|
|
- gtk_widget_realize(widget);
|
|
- }
|
|
-}
|
|
-
|
|
-static void
|
|
-moz_gtk_get_combo_box_button_inner_widgets(GtkWidget *widget,
|
|
- gpointer client_data)
|
|
-{
|
|
- if (GTK_IS_SEPARATOR(widget)) {
|
|
- gComboBoxSeparatorWidget = widget;
|
|
- g_object_add_weak_pointer(G_OBJECT(widget),
|
|
- (gpointer *) &gComboBoxSeparatorWidget);
|
|
- } else if (GTK_IS_ARROW(widget)) {
|
|
- gComboBoxArrowWidget = widget;
|
|
- g_object_add_weak_pointer(G_OBJECT(widget),
|
|
- (gpointer *) &gComboBoxArrowWidget);
|
|
- } else
|
|
- return;
|
|
- gtk_widget_realize(widget);
|
|
-}
|
|
-
|
|
-static gint
|
|
-ensure_combo_box_widgets()
|
|
-{
|
|
- GtkWidget* buttonChild;
|
|
-
|
|
- if (gComboBoxButtonWidget && gComboBoxArrowWidget)
|
|
- return MOZ_GTK_SUCCESS;
|
|
-
|
|
- /* Create a ComboBox if needed */
|
|
- if (!gComboBoxWidget) {
|
|
- gComboBoxWidget = gtk_combo_box_new();
|
|
- setup_widget_prototype(gComboBoxWidget);
|
|
- }
|
|
-
|
|
- /* Get its inner Button */
|
|
- gtk_container_forall(GTK_CONTAINER(gComboBoxWidget),
|
|
- moz_gtk_get_combo_box_inner_button,
|
|
- NULL);
|
|
-
|
|
- if (gComboBoxButtonWidget) {
|
|
- /* Get the widgets inside the Button */
|
|
- buttonChild = gtk_bin_get_child(GTK_BIN(gComboBoxButtonWidget));
|
|
- if (GTK_IS_BOX(buttonChild)) {
|
|
- /* appears-as-list = FALSE, cell-view = TRUE; the button
|
|
- * contains an hbox. This hbox is there because the ComboBox
|
|
- * needs to place a cell renderer, a separator, and an arrow in
|
|
- * the button when appears-as-list is FALSE. */
|
|
- gtk_container_forall(GTK_CONTAINER(buttonChild),
|
|
- moz_gtk_get_combo_box_button_inner_widgets,
|
|
- NULL);
|
|
- } else if(GTK_IS_ARROW(buttonChild)) {
|
|
- /* appears-as-list = TRUE, or cell-view = FALSE;
|
|
- * the button only contains an arrow */
|
|
- gComboBoxArrowWidget = buttonChild;
|
|
- g_object_add_weak_pointer(G_OBJECT(buttonChild), (gpointer *)
|
|
- &gComboBoxArrowWidget);
|
|
- gtk_widget_realize(gComboBoxArrowWidget);
|
|
- }
|
|
- } else {
|
|
- /* Shouldn't be reached with current internal gtk implementation; we
|
|
- * use a generic toggle button as last resort fallback to avoid
|
|
- * crashing. */
|
|
- gComboBoxButtonWidget = GetWidget(MOZ_GTK_TOGGLE_BUTTON);
|
|
- }
|
|
-
|
|
- if (!gComboBoxArrowWidget) {
|
|
- /* Shouldn't be reached with current internal gtk implementation;
|
|
- * we gButtonArrowWidget as last resort fallback to avoid
|
|
- * crashing. */
|
|
- gComboBoxArrowWidget = GetWidget(MOZ_GTK_BUTTON_ARROW);
|
|
- }
|
|
-
|
|
- /* We don't test the validity of gComboBoxSeparatorWidget since there
|
|
- * is none when "appears-as-list" = TRUE or "cell-view" = FALSE; if it
|
|
- * is invalid we just won't paint it. */
|
|
-
|
|
- return MOZ_GTK_SUCCESS;
|
|
-}
|
|
-
|
|
-/* We need to have pointers to the inner widgets (entry, button, arrow) of
|
|
- * the ComboBoxEntry to get the correct rendering from theme engines which
|
|
- * special cases their look. Since the inner layout can change, we ask GTK
|
|
- * to NULL our pointers when they are about to become invalid because the
|
|
- * corresponding widgets don't exist anymore. It's the role of
|
|
- * g_object_add_weak_pointer().
|
|
- * Note that if we don't find the inner widgets (which shouldn't happen), we
|
|
- * fallback to use generic "non-inner" widgets, and they don't need that kind
|
|
- * of weak pointer since they are explicit children of gProtoLayout and as
|
|
- * such GTK holds a strong reference to them. */
|
|
-static void
|
|
-moz_gtk_get_combo_box_entry_inner_widgets(GtkWidget *widget,
|
|
- gpointer client_data)
|
|
-{
|
|
- if (GTK_IS_TOGGLE_BUTTON(widget)) {
|
|
- gComboBoxEntryButtonWidget = widget;
|
|
- g_object_add_weak_pointer(G_OBJECT(widget),
|
|
- (gpointer *) &gComboBoxEntryButtonWidget);
|
|
- } else if (GTK_IS_ENTRY(widget)) {
|
|
- gComboBoxEntryTextareaWidget = widget;
|
|
- g_object_add_weak_pointer(G_OBJECT(widget),
|
|
- (gpointer *) &gComboBoxEntryTextareaWidget);
|
|
- } else
|
|
- return;
|
|
- gtk_widget_realize(widget);
|
|
-}
|
|
-
|
|
-static void
|
|
-moz_gtk_get_combo_box_entry_arrow(GtkWidget *widget, gpointer client_data)
|
|
-{
|
|
- if (GTK_IS_ARROW(widget)) {
|
|
- gComboBoxEntryArrowWidget = widget;
|
|
- g_object_add_weak_pointer(G_OBJECT(widget),
|
|
- (gpointer *) &gComboBoxEntryArrowWidget);
|
|
- gtk_widget_realize(widget);
|
|
- }
|
|
-}
|
|
-
|
|
-static gint
|
|
-ensure_combo_box_entry_widgets()
|
|
-{
|
|
- GtkWidget* buttonChild;
|
|
-
|
|
- if (gComboBoxEntryTextareaWidget &&
|
|
- gComboBoxEntryButtonWidget &&
|
|
- gComboBoxEntryArrowWidget)
|
|
- return MOZ_GTK_SUCCESS;
|
|
-
|
|
- /* Create a ComboBoxEntry if needed */
|
|
- if (!gComboBoxEntryWidget) {
|
|
- gComboBoxEntryWidget = gtk_combo_box_new_with_entry();
|
|
- setup_widget_prototype(gComboBoxEntryWidget);
|
|
- }
|
|
-
|
|
- /* Get its inner Entry and Button */
|
|
- gtk_container_forall(GTK_CONTAINER(gComboBoxEntryWidget),
|
|
- moz_gtk_get_combo_box_entry_inner_widgets,
|
|
- NULL);
|
|
-
|
|
- if (!gComboBoxEntryTextareaWidget) {
|
|
- gComboBoxEntryTextareaWidget = GetWidget(MOZ_GTK_ENTRY);
|
|
- }
|
|
-
|
|
- if (gComboBoxEntryButtonWidget) {
|
|
- /* Get the Arrow inside the Button */
|
|
- buttonChild = gtk_bin_get_child(GTK_BIN(gComboBoxEntryButtonWidget));
|
|
- if (GTK_IS_BOX(buttonChild)) {
|
|
- /* appears-as-list = FALSE, cell-view = TRUE; the button
|
|
- * contains an hbox. This hbox is there because the ComboBox
|
|
- * needs to place a cell renderer, a separator, and an arrow in
|
|
- * the button when appears-as-list is FALSE. */
|
|
- gtk_container_forall(GTK_CONTAINER(buttonChild),
|
|
- moz_gtk_get_combo_box_entry_arrow,
|
|
- NULL);
|
|
- } else if(GTK_IS_ARROW(buttonChild)) {
|
|
- /* appears-as-list = TRUE, or cell-view = FALSE;
|
|
- * the button only contains an arrow */
|
|
- gComboBoxEntryArrowWidget = buttonChild;
|
|
- g_object_add_weak_pointer(G_OBJECT(buttonChild), (gpointer *)
|
|
- &gComboBoxEntryArrowWidget);
|
|
- gtk_widget_realize(gComboBoxEntryArrowWidget);
|
|
- }
|
|
- } else {
|
|
- /* Shouldn't be reached with current internal gtk implementation;
|
|
- * we use a generic toggle button as last resort fallback to avoid
|
|
- * crashing. */
|
|
- gComboBoxEntryButtonWidget = GetWidget(MOZ_GTK_TOGGLE_BUTTON);
|
|
- }
|
|
-
|
|
- if (!gComboBoxEntryArrowWidget) {
|
|
- /* Shouldn't be reached with current internal gtk implementation;
|
|
- * we gButtonArrowWidget as last resort fallback to avoid
|
|
- * crashing. */
|
|
- gComboBoxEntryArrowWidget = GetWidget(MOZ_GTK_BUTTON_ARROW);
|
|
- }
|
|
-
|
|
- return MOZ_GTK_SUCCESS;
|
|
-}
|
|
-
|
|
gint
|
|
moz_gtk_init()
|
|
{
|
|
@@ -336,16 +124,24 @@ moz_gtk_radio_get_metrics(gint* indicato
|
|
return MOZ_GTK_SUCCESS;
|
|
}
|
|
|
|
-gint
|
|
-moz_gtk_get_focus_outline_size(gint* focus_h_width, gint* focus_v_width)
|
|
+static gint
|
|
+moz_gtk_get_focus_outline_size(GtkStyleContext* style,
|
|
+ gint* focus_h_width, gint* focus_v_width)
|
|
{
|
|
GtkBorder border;
|
|
GtkBorder padding;
|
|
- GtkStyleContext *style = ClaimStyleContext(MOZ_GTK_ENTRY);
|
|
gtk_style_context_get_border(style, GTK_STATE_FLAG_NORMAL, &border);
|
|
gtk_style_context_get_padding(style, GTK_STATE_FLAG_NORMAL, &padding);
|
|
*focus_h_width = border.left + padding.left;
|
|
*focus_v_width = border.top + padding.top;
|
|
+ return MOZ_GTK_SUCCESS;
|
|
+}
|
|
+
|
|
+gint
|
|
+moz_gtk_get_focus_outline_size(gint* focus_h_width, gint* focus_v_width)
|
|
+{
|
|
+ GtkStyleContext *style = ClaimStyleContext(MOZ_GTK_ENTRY);
|
|
+ moz_gtk_get_focus_outline_size(style, focus_h_width, focus_v_width);
|
|
ReleaseStyleContext(style);
|
|
return MOZ_GTK_SUCCESS;
|
|
}
|
|
@@ -364,7 +160,7 @@ moz_gtk_menuitem_get_horizontal_padding(
|
|
gint
|
|
moz_gtk_checkmenuitem_get_horizontal_padding(gint* horizontal_padding)
|
|
{
|
|
- GtkStyleContext *style = ClaimStyleContext(MOZ_GTK_CHECKMENUITEM_CONTAINER);
|
|
+ GtkStyleContext *style = ClaimStyleContext(MOZ_GTK_CHECKMENUITEM);
|
|
gtk_style_context_get_style(style,
|
|
"horizontal-padding", horizontal_padding,
|
|
nullptr);
|
|
@@ -636,8 +432,66 @@ calculate_arrow_rect(GtkWidget* arrow, G
|
|
return MOZ_GTK_SUCCESS;
|
|
}
|
|
|
|
+void
|
|
+moz_gtk_get_widget_min_size(WidgetNodeType aGtkWidgetType, int* width,
|
|
+ int* height)
|
|
+{
|
|
+ GtkStyleContext* style = ClaimStyleContext(aGtkWidgetType);
|
|
+ GtkStateFlags state_flags = gtk_style_context_get_state(style);
|
|
+ gtk_style_context_get(style, state_flags,
|
|
+ "min-height", height,
|
|
+ "min-width", width,
|
|
+ nullptr);
|
|
+
|
|
+ GtkBorder border, padding, margin;
|
|
+ gtk_style_context_get_border(style, state_flags, &border);
|
|
+ gtk_style_context_get_padding(style, state_flags, &padding);
|
|
+ gtk_style_context_get_margin(style, state_flags, &margin);
|
|
+ ReleaseStyleContext(style);
|
|
+
|
|
+ *width += border.left + border.right + margin.left + margin.right +
|
|
+ padding.left + padding.right;
|
|
+ *height += border.top + border.bottom + margin.top + margin.bottom +
|
|
+ padding.top + padding.bottom;
|
|
+}
|
|
+
|
|
+static void
|
|
+Inset(GdkRectangle* rect, GtkBorder& aBorder)
|
|
+{
|
|
+ MOZ_ASSERT(rect);
|
|
+ rect->x += aBorder.left;
|
|
+ rect->y += aBorder.top;
|
|
+ rect->width -= aBorder.left + aBorder.right;
|
|
+ rect->height -= aBorder.top + aBorder.bottom;
|
|
+}
|
|
+
|
|
+// Inset a rectangle by the margins specified in a style context.
|
|
+static void
|
|
+InsetByMargin(GdkRectangle* rect, GtkStyleContext* style)
|
|
+{
|
|
+ MOZ_ASSERT(rect);
|
|
+ GtkBorder margin;
|
|
+
|
|
+ gtk_style_context_get_margin(style, gtk_style_context_get_state(style),
|
|
+ &margin);
|
|
+ Inset(rect, margin);
|
|
+}
|
|
+
|
|
+// Inset a rectangle by the border and padding specified in a style context.
|
|
+static void
|
|
+InsetByBorderPadding(GdkRectangle* rect, GtkStyleContext* style)
|
|
+{
|
|
+ GtkStateFlags state = gtk_style_context_get_state(style);
|
|
+ GtkBorder padding, border;
|
|
+
|
|
+ gtk_style_context_get_padding(style, state, &padding);
|
|
+ Inset(rect, padding);
|
|
+ gtk_style_context_get_border(style, state, &border);
|
|
+ Inset(rect, border);
|
|
+}
|
|
+
|
|
static gint
|
|
-moz_gtk_scrollbar_button_paint(cairo_t *cr, GdkRectangle* rect,
|
|
+moz_gtk_scrollbar_button_paint(cairo_t *cr, const GdkRectangle* aRect,
|
|
GtkWidgetState* state,
|
|
GtkScrollbarButtonFlags flags,
|
|
GtkTextDirection direction)
|
|
@@ -675,32 +529,38 @@ moz_gtk_scrollbar_button_paint(cairo_t *
|
|
gtk_style_context_add_class(style, GTK_STYLE_CLASS_TOP);
|
|
}
|
|
|
|
- /* Scrollbar button has to be inset by trough_border because its DOM element
|
|
- * is filling width of vertical scrollbar's track (or height in case
|
|
- * of horizontal scrollbars). */
|
|
-
|
|
- MozGtkScrollbarMetrics metrics;
|
|
- moz_gtk_get_scrollbar_metrics(&metrics);
|
|
- if (flags & MOZ_GTK_STEPPER_VERTICAL) {
|
|
- rect->x += metrics.trough_border;
|
|
- rect->width = metrics.slider_width;
|
|
+ GdkRectangle rect = *aRect;
|
|
+ if (gtk_check_version(3,20,0) == nullptr) {
|
|
+ // The "trough-border" is not used since GTK 3.20. The stepper margin
|
|
+ // box occupies the full width of the "contents" gadget content box.
|
|
+ InsetByMargin(&rect, style);
|
|
} else {
|
|
- rect->y += metrics.trough_border;
|
|
- rect->height = metrics.slider_width;
|
|
+ // Scrollbar button has to be inset by trough_border because its DOM
|
|
+ // element is filling width of vertical scrollbar's track (or height
|
|
+ // in case of horizontal scrollbars).
|
|
+ MozGtkScrollbarMetrics metrics;
|
|
+ moz_gtk_get_scrollbar_metrics(&metrics);
|
|
+ if (flags & MOZ_GTK_STEPPER_VERTICAL) {
|
|
+ rect.x += metrics.trough_border;
|
|
+ rect.width = metrics.slider_width;
|
|
+ } else {
|
|
+ rect.y += metrics.trough_border;
|
|
+ rect.height = metrics.slider_width;
|
|
+ }
|
|
}
|
|
|
|
- gtk_render_background(style, cr, rect->x, rect->y, rect->width, rect->height);
|
|
- gtk_render_frame(style, cr, rect->x, rect->y, rect->width, rect->height);
|
|
+ gtk_render_background(style, cr, rect.x, rect.y, rect.width, rect.height);
|
|
+ gtk_render_frame(style, cr, rect.x, rect.y, rect.width, rect.height);
|
|
|
|
- arrow_rect.width = rect->width / 2;
|
|
- arrow_rect.height = rect->height / 2;
|
|
+ arrow_rect.width = rect.width / 2;
|
|
+ arrow_rect.height = rect.height / 2;
|
|
|
|
gfloat arrow_scaling;
|
|
gtk_style_context_get_style(style, "arrow-scaling", &arrow_scaling, NULL);
|
|
|
|
- gdouble arrow_size = MIN(rect->width, rect->height) * arrow_scaling;
|
|
- arrow_rect.x = rect->x + (rect->width - arrow_size) / 2;
|
|
- arrow_rect.y = rect->y + (rect->height - arrow_size) / 2;
|
|
+ gdouble arrow_size = MIN(rect.width, rect.height) * arrow_scaling;
|
|
+ arrow_rect.x = rect.x + (rect.width - arrow_size) / 2;
|
|
+ arrow_rect.y = rect.y + (rect.height - arrow_size) / 2;
|
|
|
|
if (state_flags & GTK_STATE_FLAG_ACTIVE) {
|
|
gtk_style_context_get_style(style,
|
|
@@ -742,19 +602,23 @@ moz_gtk_update_scrollbar_style(GtkStyleC
|
|
|
|
static void
|
|
moz_gtk_draw_styled_frame(GtkStyleContext* style, cairo_t *cr,
|
|
- GdkRectangle* rect, bool drawFocus)
|
|
+ const GdkRectangle* aRect, bool drawFocus)
|
|
{
|
|
- gtk_render_background(style, cr, rect->x, rect->y, rect->width, rect->height);
|
|
- gtk_render_frame(style, cr, rect->x, rect->y, rect->width, rect->height);
|
|
+ GdkRectangle rect = *aRect;
|
|
+ if (gtk_check_version(3, 6, 0) == nullptr) {
|
|
+ InsetByMargin(&rect, style);
|
|
+ }
|
|
+ gtk_render_background(style, cr, rect.x, rect.y, rect.width, rect.height);
|
|
+ gtk_render_frame(style, cr, rect.x, rect.y, rect.width, rect.height);
|
|
if (drawFocus) {
|
|
gtk_render_focus(style, cr,
|
|
- rect->x, rect->y, rect->width, rect->height);
|
|
+ rect.x, rect.y, rect.width, rect.height);
|
|
}
|
|
}
|
|
|
|
static gint
|
|
moz_gtk_scrollbar_trough_paint(WidgetNodeType widget,
|
|
- cairo_t *cr, GdkRectangle* rect,
|
|
+ cairo_t *cr, const GdkRectangle* rect,
|
|
GtkWidgetState* state,
|
|
GtkScrollbarTrackFlags flags,
|
|
GtkTextDirection direction)
|
|
@@ -766,26 +630,28 @@ moz_gtk_scrollbar_trough_paint(WidgetNod
|
|
ReleaseStyleContext(style);
|
|
}
|
|
|
|
- bool isHorizontal = (widget == MOZ_GTK_SCROLLBAR_HORIZONTAL);
|
|
- GtkStyleContext* style;
|
|
+ GtkStyleContext* style = ClaimStyleContext(widget, direction);
|
|
+ moz_gtk_draw_styled_frame(style, cr, rect, state->focused);
|
|
+ ReleaseStyleContext(style);
|
|
|
|
- // Draw all child CSS Nodes for Gtk >= 3.20
|
|
- if (gtk_check_version(3, 20, 0) == nullptr) {
|
|
- style = ClaimStyleContext(widget, direction);
|
|
- moz_gtk_update_scrollbar_style(style, widget, direction);
|
|
- moz_gtk_draw_styled_frame(style, cr, rect, state->focused);
|
|
- ReleaseStyleContext(style);
|
|
+ return MOZ_GTK_SUCCESS;
|
|
+}
|
|
|
|
- style = ClaimStyleContext(isHorizontal ?
|
|
- MOZ_GTK_SCROLLBAR_CONTENTS_HORIZONTAL :
|
|
- MOZ_GTK_SCROLLBAR_CONTENTS_VERTICAL,
|
|
- direction);
|
|
- moz_gtk_draw_styled_frame(style, cr, rect, state->focused);
|
|
- ReleaseStyleContext(style);
|
|
- }
|
|
- style = ClaimStyleContext(isHorizontal ?
|
|
- MOZ_GTK_SCROLLBAR_TROUGH_HORIZONTAL :
|
|
- MOZ_GTK_SCROLLBAR_TROUGH_VERTICAL,
|
|
+static gint
|
|
+moz_gtk_scrollbar_paint(WidgetNodeType widget,
|
|
+ cairo_t *cr, const GdkRectangle* rect,
|
|
+ GtkWidgetState* state,
|
|
+ GtkTextDirection direction)
|
|
+{
|
|
+ GtkStyleContext* style = ClaimStyleContext(widget, direction);
|
|
+ moz_gtk_update_scrollbar_style(style, widget, direction);
|
|
+
|
|
+ moz_gtk_draw_styled_frame(style, cr, rect, state->focused);
|
|
+
|
|
+ ReleaseStyleContext(style);
|
|
+ style = ClaimStyleContext((widget == MOZ_GTK_SCROLLBAR_HORIZONTAL) ?
|
|
+ MOZ_GTK_SCROLLBAR_CONTENTS_HORIZONTAL :
|
|
+ MOZ_GTK_SCROLLBAR_CONTENTS_VERTICAL,
|
|
direction);
|
|
moz_gtk_draw_styled_frame(style, cr, rect, state->focused);
|
|
ReleaseStyleContext(style);
|
|
@@ -795,21 +661,21 @@ moz_gtk_scrollbar_trough_paint(WidgetNod
|
|
|
|
static gint
|
|
moz_gtk_scrollbar_thumb_paint(WidgetNodeType widget,
|
|
- cairo_t *cr, GdkRectangle* rect,
|
|
+ cairo_t *cr, const GdkRectangle* aRect,
|
|
GtkWidgetState* state,
|
|
GtkTextDirection direction)
|
|
{
|
|
GtkStateFlags state_flags = GetStateFlagsFromGtkWidgetState(state);
|
|
- GtkBorder margin;
|
|
|
|
+ GdkRectangle rect = *aRect;
|
|
GtkStyleContext* style = ClaimStyleContext(widget, direction, state_flags);
|
|
- gtk_style_context_get_margin (style, state_flags, &margin);
|
|
+ InsetByMargin(&rect, style);
|
|
|
|
gtk_render_slider(style, cr,
|
|
- rect->x + margin.left,
|
|
- rect->y + margin.top,
|
|
- rect->width - margin.left - margin.right,
|
|
- rect->height - margin.top - margin.bottom,
|
|
+ rect.x,
|
|
+ rect.y,
|
|
+ rect.width,
|
|
+ rect.height,
|
|
(widget == MOZ_GTK_SCROLLBAR_THUMB_HORIZONTAL) ?
|
|
GTK_ORIENTATION_HORIZONTAL : GTK_ORIENTATION_VERTICAL);
|
|
|
|
@@ -980,65 +846,31 @@ moz_gtk_vpaned_paint(cairo_t *cr, GdkRec
|
|
static gint
|
|
moz_gtk_entry_paint(cairo_t *cr, GdkRectangle* rect,
|
|
GtkWidgetState* state,
|
|
- GtkWidget* widget, GtkTextDirection direction)
|
|
+ GtkStyleContext* style)
|
|
{
|
|
gint x = rect->x, y = rect->y, width = rect->width, height = rect->height;
|
|
- GtkStyleContext* style;
|
|
int draw_focus_outline_only = state->depressed; // NS_THEME_FOCUS_OUTLINE
|
|
|
|
- gtk_widget_set_direction(widget, direction);
|
|
-
|
|
- style = gtk_widget_get_style_context(widget);
|
|
-
|
|
if (draw_focus_outline_only) {
|
|
// Inflate the given 'rect' with the focus outline size.
|
|
gint h, v;
|
|
- moz_gtk_get_focus_outline_size(&h, &v);
|
|
+ moz_gtk_get_focus_outline_size(style, &h, &v);
|
|
rect->x -= h;
|
|
rect->width += 2 * h;
|
|
rect->y -= v;
|
|
rect->height += 2 * v;
|
|
width = rect->width;
|
|
height = rect->height;
|
|
- }
|
|
-
|
|
- /* gtkentry.c uses two windows, one for the entire widget and one for the
|
|
- * text area inside it. The background of both windows is set to the "base"
|
|
- * color of the new state in gtk_entry_state_changed, but only the inner
|
|
- * textarea window uses gtk_paint_flat_box when exposed */
|
|
-
|
|
- /* This gets us a lovely greyish disabledish look */
|
|
- gtk_widget_set_sensitive(widget, !state->disabled);
|
|
-
|
|
- gtk_style_context_save(style);
|
|
- gtk_style_context_add_class(style, GTK_STYLE_CLASS_ENTRY);
|
|
-
|
|
- /* Now paint the shadow and focus border.
|
|
- * We do like in gtk_entry_draw_frame, we first draw the shadow, a tad
|
|
- * smaller when focused if the focus is not interior, then the focus. */
|
|
-
|
|
- if (state->focused && !state->disabled) {
|
|
- /* This will get us the lit borders that focused textboxes enjoy on
|
|
- * some themes. */
|
|
- gtk_style_context_set_state(style, GTK_STATE_FLAG_FOCUSED);
|
|
- }
|
|
-
|
|
- if (state->disabled) {
|
|
- gtk_style_context_set_state(style, GTK_STATE_FLAG_INSENSITIVE);
|
|
- }
|
|
-
|
|
- if (!draw_focus_outline_only) {
|
|
+ } else {
|
|
gtk_render_background(style, cr, x, y, width, height);
|
|
}
|
|
gtk_render_frame(style, cr, x, y, width, height);
|
|
|
|
- gtk_style_context_restore(style);
|
|
-
|
|
return MOZ_GTK_SUCCESS;
|
|
}
|
|
|
|
static gint
|
|
-moz_gtk_text_view_paint(cairo_t *cr, GdkRectangle* rect,
|
|
+moz_gtk_text_view_paint(cairo_t *cr, GdkRectangle* aRect,
|
|
GtkWidgetState* state,
|
|
GtkTextDirection direction)
|
|
{
|
|
@@ -1046,24 +878,29 @@ moz_gtk_text_view_paint(cairo_t *cr, Gdk
|
|
|
|
GtkStyleContext* style_frame =
|
|
ClaimStyleContext(MOZ_GTK_SCROLLED_WINDOW, direction, state_flags);
|
|
- gtk_render_frame(style_frame, cr, rect->x, rect->y, rect->width, rect->height);
|
|
+ gtk_render_frame(style_frame, cr,
|
|
+ aRect->x, aRect->y, aRect->width, aRect->height);
|
|
+
|
|
+ GdkRectangle rect = *aRect;
|
|
+ InsetByBorderPadding(&rect, style_frame);
|
|
|
|
- GtkBorder border, padding;
|
|
- gtk_style_context_get_border(style_frame, state_flags, &border);
|
|
- gtk_style_context_get_padding(style_frame, state_flags, &padding);
|
|
ReleaseStyleContext(style_frame);
|
|
|
|
GtkStyleContext* style =
|
|
ClaimStyleContext(MOZ_GTK_TEXT_VIEW, direction, state_flags);
|
|
-
|
|
- gint xthickness = border.left + padding.left;
|
|
- gint ythickness = border.top + padding.top;
|
|
-
|
|
- gtk_render_background(style, cr,
|
|
- rect->x + xthickness, rect->y + ythickness,
|
|
- rect->width - 2 * xthickness,
|
|
- rect->height - 2 * ythickness);
|
|
-
|
|
+ gtk_render_background(style, cr, rect.x, rect.y, rect.width, rect.height);
|
|
+ ReleaseStyleContext(style);
|
|
+ // There is a separate "text" window, which usually provides the
|
|
+ // background behind the text. However, this is transparent in Ambiance
|
|
+ // for GTK 3.20, in which case the MOZ_GTK_TEXT_VIEW background is
|
|
+ // visible.
|
|
+ // Workaround for Bug 1328899 - We don't want "selected" background color
|
|
+ // for active view class here which is set by Ambiance theme.
|
|
+ if (state->focused && !state->disabled) {
|
|
+ state_flags = static_cast<GtkStateFlags>(GTK_STATE_FLAG_FOCUSED);
|
|
+ }
|
|
+ style = ClaimStyleContext(MOZ_GTK_TEXT_VIEW_TEXT, direction, state_flags);
|
|
+ gtk_render_background(style, cr, rect.x, rect.y, rect.width, rect.height);
|
|
ReleaseStyleContext(style);
|
|
|
|
return MOZ_GTK_SUCCESS;
|
|
@@ -1198,34 +1035,37 @@ moz_gtk_combo_box_paint(cairo_t *cr, Gdk
|
|
GtkStyleContext* style;
|
|
GtkRequisition arrow_req;
|
|
|
|
- ensure_combo_box_widgets();
|
|
+ GtkWidget* comboBoxButton = GetWidget(MOZ_GTK_COMBOBOX_BUTTON);
|
|
+ GtkWidget* comboBoxArrow = GetWidget(MOZ_GTK_COMBOBOX_ARROW);
|
|
|
|
/* Also sets the direction on gComboBoxButtonWidget, which is then
|
|
* inherited by the separator and arrow */
|
|
moz_gtk_button_paint(cr, rect, state, GTK_RELIEF_NORMAL,
|
|
- gComboBoxButtonWidget, direction);
|
|
+ comboBoxButton, direction);
|
|
|
|
- calculate_button_inner_rect(gComboBoxButtonWidget,
|
|
- rect, &arrow_rect, direction);
|
|
+ calculate_button_inner_rect(comboBoxButton, rect, &arrow_rect, direction);
|
|
/* Now arrow_rect contains the inner rect ; we want to correct the width
|
|
* to what the arrow needs (see gtk_combo_box_size_allocate) */
|
|
- gtk_widget_get_preferred_size(gComboBoxArrowWidget, NULL, &arrow_req);
|
|
+ gtk_widget_get_preferred_size(comboBoxArrow, NULL, &arrow_req);
|
|
+
|
|
if (direction == GTK_TEXT_DIR_LTR)
|
|
arrow_rect.x += arrow_rect.width - arrow_req.width;
|
|
arrow_rect.width = arrow_req.width;
|
|
|
|
- calculate_arrow_rect(gComboBoxArrowWidget,
|
|
+ calculate_arrow_rect(comboBoxArrow,
|
|
&arrow_rect, &real_arrow_rect, direction);
|
|
|
|
- style = gtk_widget_get_style_context(gComboBoxArrowWidget);
|
|
+ style = ClaimStyleContext(MOZ_GTK_COMBOBOX_ARROW);
|
|
gtk_render_arrow(style, cr, ARROW_DOWN,
|
|
real_arrow_rect.x, real_arrow_rect.y,
|
|
real_arrow_rect.width);
|
|
+ ReleaseStyleContext(style);
|
|
|
|
/* If there is no separator in the theme, there's nothing left to do. */
|
|
- if (!gComboBoxSeparatorWidget)
|
|
+ GtkWidget* widget = GetWidget(MOZ_GTK_COMBOBOX_SEPARATOR);
|
|
+ if (!widget)
|
|
return MOZ_GTK_SUCCESS;
|
|
- style = gtk_widget_get_style_context(gComboBoxSeparatorWidget);
|
|
+ style = gtk_widget_get_style_context(widget);
|
|
gtk_style_context_get_style(style,
|
|
"wide-separators", &wide_separators,
|
|
"separator-width", &separator_width,
|
|
@@ -1309,15 +1149,14 @@ moz_gtk_combo_box_entry_button_paint(cai
|
|
GtkStateFlags state_flags = GetStateFlagsFromGtkWidgetState(state);
|
|
GtkStyleContext* style;
|
|
|
|
- ensure_combo_box_entry_widgets();
|
|
-
|
|
+ GtkWidget* comboBoxEntry = GetWidget(MOZ_GTK_COMBOBOX_ENTRY_BUTTON);
|
|
moz_gtk_button_paint(cr, rect, state, GTK_RELIEF_NORMAL,
|
|
- gComboBoxEntryButtonWidget, direction);
|
|
+ comboBoxEntry, direction);
|
|
+ calculate_button_inner_rect(comboBoxEntry, rect, &arrow_rect, direction);
|
|
|
|
- calculate_button_inner_rect(gComboBoxEntryButtonWidget,
|
|
- rect, &arrow_rect, direction);
|
|
if (state_flags & GTK_STATE_FLAG_ACTIVE) {
|
|
- gtk_style_context_get_style(gtk_widget_get_style_context(gComboBoxEntryButtonWidget),
|
|
+ style = gtk_widget_get_style_context(comboBoxEntry);
|
|
+ gtk_style_context_get_style(style,
|
|
"child-displacement-x", &x_displacement,
|
|
"child-displacement-y", &y_displacement,
|
|
NULL);
|
|
@@ -1325,15 +1164,14 @@ moz_gtk_combo_box_entry_button_paint(cai
|
|
arrow_rect.y += y_displacement;
|
|
}
|
|
|
|
- calculate_arrow_rect(gComboBoxEntryArrowWidget,
|
|
+ calculate_arrow_rect(GetWidget(MOZ_GTK_COMBOBOX_ENTRY_ARROW),
|
|
&arrow_rect, &real_arrow_rect, direction);
|
|
|
|
- style = gtk_widget_get_style_context(gComboBoxEntryArrowWidget);
|
|
-
|
|
+ style = ClaimStyleContext(MOZ_GTK_COMBOBOX_ENTRY_ARROW);
|
|
gtk_render_arrow(style, cr, ARROW_DOWN,
|
|
real_arrow_rect.x, real_arrow_rect.y,
|
|
real_arrow_rect.width);
|
|
-
|
|
+ ReleaseStyleContext(style);
|
|
return MOZ_GTK_SUCCESS;
|
|
}
|
|
|
|
@@ -1353,7 +1191,6 @@ moz_gtk_container_paint(cairo_t *cr, Gdk
|
|
}
|
|
|
|
ReleaseStyleContext(style);
|
|
-
|
|
return MOZ_GTK_SUCCESS;
|
|
}
|
|
|
|
@@ -1439,13 +1276,52 @@ moz_gtk_toolbar_separator_paint(cairo_t
|
|
}
|
|
|
|
static gint
|
|
-moz_gtk_tooltip_paint(cairo_t *cr, GdkRectangle* rect,
|
|
+moz_gtk_tooltip_paint(cairo_t *cr, const GdkRectangle* aRect,
|
|
GtkTextDirection direction)
|
|
{
|
|
+ // Tooltip widget is made in GTK3 as following tree:
|
|
+ // Tooltip window
|
|
+ // Horizontal Box
|
|
+ // Icon (not supported by Firefox)
|
|
+ // Label
|
|
+ // Each element can be fully styled by CSS of GTK theme.
|
|
+ // We have to draw all elements with appropriate offset and right dimensions.
|
|
+
|
|
+ // Tooltip drawing
|
|
GtkStyleContext* style = ClaimStyleContext(MOZ_GTK_TOOLTIP, direction);
|
|
- gtk_render_background(style, cr, rect->x, rect->y, rect->width, rect->height);
|
|
- gtk_render_frame(style, cr, rect->x, rect->y, rect->width, rect->height);
|
|
- ReleaseStyleContext(style);
|
|
+ GdkRectangle rect = *aRect;
|
|
+ gtk_render_background(style, cr, rect.x, rect.y, rect.width, rect.height);
|
|
+ gtk_render_frame(style, cr, rect.x, rect.y, rect.width, rect.height);
|
|
+ ReleaseStyleContext(style);
|
|
+
|
|
+ // Horizontal Box drawing
|
|
+ //
|
|
+ // The box element has hard-coded 6px margin-* GtkWidget properties, which
|
|
+ // are added between the window dimensions and the CSS margin box of the
|
|
+ // horizontal box. The frame of the tooltip window is drawn in the
|
|
+ // 6px margin.
|
|
+ // For drawing Horizontal Box we have to inset drawing area by that 6px
|
|
+ // plus its CSS margin.
|
|
+ GtkStyleContext* boxStyle = ClaimStyleContext(MOZ_GTK_TOOLTIP_BOX, direction);
|
|
+
|
|
+ rect.x += 6;
|
|
+ rect.y += 6;
|
|
+ rect.width -= 12;
|
|
+ rect.height -= 12;
|
|
+
|
|
+ InsetByMargin(&rect, boxStyle);
|
|
+ gtk_render_background(boxStyle, cr, rect.x, rect.y, rect.width, rect.height);
|
|
+ gtk_render_frame(boxStyle, cr, rect.x, rect.y, rect.width, rect.height);
|
|
+
|
|
+ // Label drawing
|
|
+ InsetByBorderPadding(&rect, boxStyle);
|
|
+ ReleaseStyleContext(boxStyle);
|
|
+
|
|
+ GtkStyleContext* labelStyle =
|
|
+ ClaimStyleContext(MOZ_GTK_TOOLTIP_BOX_LABEL, direction);
|
|
+ moz_gtk_draw_styled_frame(labelStyle, cr, &rect, false);
|
|
+ ReleaseStyleContext(labelStyle);
|
|
+
|
|
return MOZ_GTK_SUCCESS;
|
|
}
|
|
|
|
@@ -1454,17 +1330,9 @@ moz_gtk_resizer_paint(cairo_t *cr, GdkRe
|
|
GtkWidgetState* state,
|
|
GtkTextDirection direction)
|
|
{
|
|
- GtkStyleContext* style;
|
|
-
|
|
- // gtk_render_handle() draws a background, so use GtkTextView and its
|
|
- // GTK_STYLE_CLASS_VIEW to match the background with textarea elements.
|
|
- // The resizer is drawn with shaded variants of the background color, and
|
|
- // so a transparent background would lead to a transparent resizer.
|
|
- style = ClaimStyleContext(MOZ_GTK_TEXT_VIEW, GTK_TEXT_DIR_LTR,
|
|
- GetStateFlagsFromGtkWidgetState(state));
|
|
- // TODO - we need to save/restore style when gtk 3.20 CSS node path
|
|
- // is used
|
|
- gtk_style_context_add_class(style, GTK_STYLE_CLASS_GRIP);
|
|
+ GtkStyleContext* style =
|
|
+ ClaimStyleContext(MOZ_GTK_RESIZER, GTK_TEXT_DIR_LTR,
|
|
+ GetStateFlagsFromGtkWidgetState(state));
|
|
|
|
// Workaround unico not respecting the text direction for resizers.
|
|
// See bug 1174248.
|
|
@@ -1511,17 +1379,8 @@ moz_gtk_progress_chunk_paint(cairo_t *cr
|
|
GtkTextDirection direction,
|
|
WidgetNodeType widget)
|
|
{
|
|
- GtkStyleContext* style;
|
|
-
|
|
- if (gtk_check_version(3, 20, 0) != nullptr) {
|
|
- /* Ask for MOZ_GTK_PROGRESS_TROUGH instead of MOZ_GTK_PROGRESSBAR
|
|
- * because ClaimStyleContext() saves/restores that style */
|
|
- style = ClaimStyleContext(MOZ_GTK_PROGRESS_TROUGH, direction);
|
|
- gtk_style_context_remove_class(style, GTK_STYLE_CLASS_TROUGH);
|
|
- gtk_style_context_add_class(style, GTK_STYLE_CLASS_PROGRESSBAR);
|
|
- } else {
|
|
- style = ClaimStyleContext(MOZ_GTK_PROGRESS_CHUNK, direction);
|
|
- }
|
|
+ GtkStyleContext* style =
|
|
+ ClaimStyleContext(MOZ_GTK_PROGRESS_CHUNK, direction);
|
|
|
|
if (widget == MOZ_GTK_PROGRESS_CHUNK_INDETERMINATE ||
|
|
widget == MOZ_GTK_PROGRESS_CHUNK_VERTICAL_INDETERMINATE) {
|
|
@@ -1905,6 +1764,13 @@ static gint
|
|
moz_gtk_menu_separator_paint(cairo_t *cr, GdkRectangle* rect,
|
|
GtkTextDirection direction)
|
|
{
|
|
+ GtkWidgetState defaultState = { 0 };
|
|
+ moz_gtk_menu_item_paint(MOZ_GTK_MENUSEPARATOR, cr, rect,
|
|
+ &defaultState, direction);
|
|
+
|
|
+ if (gtk_get_minor_version() >= 20)
|
|
+ return MOZ_GTK_SUCCESS;
|
|
+
|
|
GtkStyleContext* style;
|
|
gboolean wide_separators;
|
|
gint separator_height;
|
|
@@ -1952,36 +1818,39 @@ moz_gtk_menu_item_paint(WidgetNodeType w
|
|
GtkWidgetState* state, GtkTextDirection direction)
|
|
{
|
|
gint x, y, w, h;
|
|
+ guint minorVersion = gtk_get_minor_version();
|
|
+ GtkStateFlags state_flags = GetStateFlagsFromGtkWidgetState(state);
|
|
|
|
- if (state->inHover && !state->disabled) {
|
|
- GtkStateFlags state_flags = GetStateFlagsFromGtkWidgetState(state);
|
|
- GtkStyleContext* style =
|
|
- ClaimStyleContext(widget, direction, state_flags);
|
|
-
|
|
- bool pre_3_6 = gtk_check_version(3, 6, 0) != nullptr;
|
|
- if (pre_3_6) {
|
|
- // GTK+ 3.4 saves the style context and adds the menubar class to
|
|
- // menubar children, but does each of these only when drawing, not
|
|
- // during layout.
|
|
- gtk_style_context_save(style);
|
|
- if (widget == MOZ_GTK_MENUBARITEM) {
|
|
- gtk_style_context_add_class(style, GTK_STYLE_CLASS_MENUBAR);
|
|
- }
|
|
+ // GTK versions prior to 3.8 render the background and frame only when not
|
|
+ // a separator and in hover prelight.
|
|
+ if (minorVersion < 8 && (widget == MOZ_GTK_MENUSEPARATOR ||
|
|
+ !(state_flags & GTK_STATE_FLAG_PRELIGHT)))
|
|
+ return MOZ_GTK_SUCCESS;
|
|
+
|
|
+ GtkStyleContext* style = ClaimStyleContext(widget, direction, state_flags);
|
|
+
|
|
+ if (minorVersion < 6) {
|
|
+ // GTK+ 3.4 saves the style context and adds the menubar class to
|
|
+ // menubar children, but does each of these only when drawing, not
|
|
+ // during layout.
|
|
+ gtk_style_context_save(style);
|
|
+ if (widget == MOZ_GTK_MENUBARITEM) {
|
|
+ gtk_style_context_add_class(style, GTK_STYLE_CLASS_MENUBAR);
|
|
}
|
|
+ }
|
|
|
|
- x = rect->x;
|
|
- y = rect->y;
|
|
- w = rect->width;
|
|
- h = rect->height;
|
|
+ x = rect->x;
|
|
+ y = rect->y;
|
|
+ w = rect->width;
|
|
+ h = rect->height;
|
|
|
|
- gtk_render_background(style, cr, x, y, w, h);
|
|
- gtk_render_frame(style, cr, x, y, w, h);
|
|
+ gtk_render_background(style, cr, x, y, w, h);
|
|
+ gtk_render_frame(style, cr, x, y, w, h);
|
|
|
|
- if (pre_3_6) {
|
|
- gtk_style_context_restore(style);
|
|
- }
|
|
- ReleaseStyleContext(style);
|
|
+ if (minorVersion < 6) {
|
|
+ gtk_style_context_restore(style);
|
|
}
|
|
+ ReleaseStyleContext(style);
|
|
|
|
return MOZ_GTK_SUCCESS;
|
|
}
|
|
@@ -2001,16 +1870,16 @@ moz_gtk_menu_arrow_paint(cairo_t *cr, Gd
|
|
return MOZ_GTK_SUCCESS;
|
|
}
|
|
|
|
-// See gtk_real_check_menu_item_draw_indicator() for reference.
|
|
+// For reference, see gtk_check_menu_item_size_allocate() in GTK versions after
|
|
+// 3.20 and gtk_real_check_menu_item_draw_indicator() in earlier versions.
|
|
static gint
|
|
-moz_gtk_check_menu_item_paint(cairo_t *cr, GdkRectangle* rect,
|
|
+moz_gtk_check_menu_item_paint(WidgetNodeType widgetType,
|
|
+ cairo_t *cr, GdkRectangle* rect,
|
|
GtkWidgetState* state,
|
|
- gboolean checked, gboolean isradio,
|
|
- GtkTextDirection direction)
|
|
+ gboolean checked, GtkTextDirection direction)
|
|
{
|
|
GtkStateFlags state_flags = GetStateFlagsFromGtkWidgetState(state);
|
|
GtkStyleContext* style;
|
|
- GtkBorder padding;
|
|
gint indicator_size, horizontal_padding;
|
|
gint x, y;
|
|
|
|
@@ -2020,35 +1889,44 @@ moz_gtk_check_menu_item_paint(cairo_t *c
|
|
state_flags = static_cast<GtkStateFlags>(state_flags|checkbox_check_state);
|
|
}
|
|
|
|
- style = ClaimStyleContext(isradio ? MOZ_GTK_RADIOMENUITEM_CONTAINER :
|
|
- MOZ_GTK_CHECKMENUITEM_CONTAINER,
|
|
- direction);
|
|
+ bool pre_3_20 = gtk_get_minor_version() < 20;
|
|
+ gint offset;
|
|
+ style = ClaimStyleContext(widgetType, direction);
|
|
gtk_style_context_get_style(style,
|
|
"indicator-size", &indicator_size,
|
|
"horizontal-padding", &horizontal_padding,
|
|
NULL);
|
|
+ if (pre_3_20) {
|
|
+ GtkBorder padding;
|
|
+ gtk_style_context_get_padding(style, state_flags, &padding);
|
|
+ offset = horizontal_padding + padding.left + 2;
|
|
+ } else {
|
|
+ GdkRectangle r = { 0 };
|
|
+ InsetByMargin(&r, style);
|
|
+ InsetByBorderPadding(&r, style);
|
|
+ offset = r.x;
|
|
+ }
|
|
ReleaseStyleContext(style);
|
|
|
|
- style = ClaimStyleContext(isradio ? MOZ_GTK_RADIOMENUITEM :
|
|
- MOZ_GTK_CHECKMENUITEM,
|
|
- direction, state_flags);
|
|
- gtk_style_context_get_padding(style, state_flags, &padding);
|
|
- gint offset = padding.left + 2;
|
|
+ bool isRadio = (widgetType == MOZ_GTK_RADIOMENUITEM);
|
|
+ WidgetNodeType indicatorType = isRadio ? MOZ_GTK_RADIOMENUITEM_INDICATOR
|
|
+ : MOZ_GTK_CHECKMENUITEM_INDICATOR;
|
|
+ style = ClaimStyleContext(indicatorType, direction, state_flags);
|
|
|
|
if (direction == GTK_TEXT_DIR_RTL) {
|
|
- x = rect->width - indicator_size - offset - horizontal_padding;
|
|
+ x = rect->width - indicator_size - offset;
|
|
}
|
|
else {
|
|
- x = rect->x + offset + horizontal_padding;
|
|
+ x = rect->x + offset;
|
|
}
|
|
y = rect->y + (rect->height - indicator_size) / 2;
|
|
|
|
- if (gtk_check_version(3, 20, 0) == nullptr) {
|
|
+ if (!pre_3_20) {
|
|
gtk_render_background(style, cr, x, y, indicator_size, indicator_size);
|
|
gtk_render_frame(style, cr, x, y, indicator_size, indicator_size);
|
|
}
|
|
|
|
- if (isradio) {
|
|
+ if (isRadio) {
|
|
gtk_render_option(style, cr, x, y, indicator_size, indicator_size);
|
|
} else {
|
|
gtk_render_check(style, cr, x, y, indicator_size, indicator_size);
|
|
@@ -2074,6 +1952,20 @@ moz_gtk_info_bar_paint(cairo_t *cr, GdkR
|
|
}
|
|
|
|
static void
|
|
+moz_gtk_add_style_margin(GtkStyleContext* style,
|
|
+ gint* left, gint* top, gint* right, gint* bottom)
|
|
+{
|
|
+ GtkBorder margin;
|
|
+
|
|
+ gtk_style_context_get_margin(style, GTK_STATE_FLAG_NORMAL, &margin);
|
|
+
|
|
+ *left += margin.left;
|
|
+ *right += margin.right;
|
|
+ *top += margin.top;
|
|
+ *bottom += margin.bottom;
|
|
+}
|
|
+
|
|
+static void
|
|
moz_gtk_add_style_border(GtkStyleContext* style,
|
|
gint* left, gint* top, gint* right, gint* bottom)
|
|
{
|
|
@@ -2101,6 +1993,15 @@ moz_gtk_add_style_padding(GtkStyleContex
|
|
*bottom += padding.bottom;
|
|
}
|
|
|
|
+static void moz_gtk_add_margin_border_padding(GtkStyleContext *style,
|
|
+ gint* left, gint* top,
|
|
+ gint* right, gint* bottom)
|
|
+{
|
|
+ moz_gtk_add_style_margin(style, left, top, right, bottom);
|
|
+ moz_gtk_add_style_border(style, left, top, right, bottom);
|
|
+ moz_gtk_add_style_padding(style, left, top, right, bottom);
|
|
+}
|
|
+
|
|
gint
|
|
moz_gtk_get_widget_border(WidgetNodeType widget, gint* left, gint* top,
|
|
gint* right, gint* bottom, GtkTextDirection direction,
|
|
@@ -2129,9 +2030,6 @@ moz_gtk_get_widget_border(WidgetNodeType
|
|
if (widget == MOZ_GTK_TOOLBAR_BUTTON)
|
|
gtk_style_context_restore(style);
|
|
|
|
- // XXX: Subtract 1 pixel from the border to account for the added
|
|
- // -moz-focus-inner border (Bug 1228281).
|
|
- *left -= 1; *top -= 1; *right -= 1; *bottom -= 1;
|
|
moz_gtk_add_style_border(style, left, top, right, bottom);
|
|
|
|
ReleaseStyleContext(style);
|
|
@@ -2179,12 +2077,10 @@ moz_gtk_get_widget_border(WidgetNodeType
|
|
w = GetWidget(MOZ_GTK_TREE_HEADER_SORTARROW);
|
|
break;
|
|
case MOZ_GTK_DROPDOWN_ENTRY:
|
|
- ensure_combo_box_entry_widgets();
|
|
- w = gComboBoxEntryTextareaWidget;
|
|
+ w = GetWidget(MOZ_GTK_COMBOBOX_ENTRY_TEXTAREA);
|
|
break;
|
|
case MOZ_GTK_DROPDOWN_ARROW:
|
|
- ensure_combo_box_entry_widgets();
|
|
- w = gComboBoxEntryButtonWidget;
|
|
+ w = GetWidget(MOZ_GTK_COMBOBOX_ENTRY_BUTTON);
|
|
break;
|
|
case MOZ_GTK_DROPDOWN:
|
|
{
|
|
@@ -2196,32 +2092,33 @@ moz_gtk_get_widget_border(WidgetNodeType
|
|
GtkRequisition arrow_req;
|
|
GtkBorder border;
|
|
|
|
- ensure_combo_box_widgets();
|
|
-
|
|
- *left = *top = *right = *bottom =
|
|
- gtk_container_get_border_width(GTK_CONTAINER(gComboBoxButtonWidget));
|
|
-
|
|
- style = gtk_widget_get_style_context(gComboBoxButtonWidget);
|
|
-
|
|
+ *left = *top = *right = *bottom =
|
|
+ gtk_container_get_border_width(GTK_CONTAINER(
|
|
+ GetWidget(MOZ_GTK_COMBOBOX_BUTTON)));
|
|
+ style = ClaimStyleContext(MOZ_GTK_COMBOBOX_BUTTON);
|
|
moz_gtk_add_style_padding(style, left, top, right, bottom);
|
|
moz_gtk_add_style_border(style, left, top, right, bottom);
|
|
+ ReleaseStyleContext(style);
|
|
|
|
/* If there is no separator, don't try to count its width. */
|
|
separator_width = 0;
|
|
- if (gComboBoxSeparatorWidget) {
|
|
- style = gtk_widget_get_style_context(gComboBoxSeparatorWidget);
|
|
+ GtkWidget* comboBoxSeparator = GetWidget(MOZ_GTK_COMBOBOX_SEPARATOR);
|
|
+ if (comboBoxSeparator) {
|
|
+ style = gtk_widget_get_style_context(comboBoxSeparator);
|
|
gtk_style_context_get_style(style,
|
|
"wide-separators", &wide_separators,
|
|
"separator-width", &separator_width,
|
|
NULL);
|
|
|
|
if (!wide_separators) {
|
|
- gtk_style_context_get_border(style, GTK_STATE_FLAG_NORMAL, &border);
|
|
+ gtk_style_context_get_border(style, GTK_STATE_FLAG_NORMAL,
|
|
+ &border);
|
|
separator_width = border.left;
|
|
}
|
|
}
|
|
|
|
- gtk_widget_get_preferred_size(gComboBoxArrowWidget, NULL, &arrow_req);
|
|
+ gtk_widget_get_preferred_size(GetWidget(MOZ_GTK_COMBOBOX_ARROW),
|
|
+ NULL, &arrow_req);
|
|
|
|
if (direction == GTK_TEXT_DIR_RTL)
|
|
*left += separator_width + arrow_req.width;
|
|
@@ -2271,12 +2168,15 @@ moz_gtk_get_widget_border(WidgetNodeType
|
|
{
|
|
// Bug 1274143 for MOZ_GTK_MENUBARITEM
|
|
WidgetNodeType type =
|
|
- widget == MOZ_GTK_MENUBARITEM || widget == MOZ_GTK_MENUITEM ?
|
|
- MOZ_GTK_MENUITEM : MOZ_GTK_CHECKMENUITEM_CONTAINER;
|
|
+ widget == MOZ_GTK_MENUBARITEM ? MOZ_GTK_MENUITEM : widget;
|
|
style = ClaimStyleContext(type);
|
|
|
|
- moz_gtk_add_style_padding(style, left, top, right, bottom);
|
|
-
|
|
+ if (gtk_get_minor_version() < 20) {
|
|
+ moz_gtk_add_style_padding(style, left, top, right, bottom);
|
|
+ } else {
|
|
+ moz_gtk_add_margin_border_padding(style,
|
|
+ left, top, right, bottom);
|
|
+ }
|
|
ReleaseStyleContext(style);
|
|
return MOZ_GTK_SUCCESS;
|
|
}
|
|
@@ -2285,12 +2185,81 @@ moz_gtk_get_widget_border(WidgetNodeType
|
|
break;
|
|
case MOZ_GTK_TOOLTIP:
|
|
{
|
|
- style = ClaimStyleContext(MOZ_GTK_TOOLTIP);
|
|
- moz_gtk_add_style_border(style, left, top, right, bottom);
|
|
- moz_gtk_add_style_padding(style, left, top, right, bottom);
|
|
- ReleaseStyleContext(style);
|
|
+ // In GTK 3 there are 6 pixels of additional margin around the box.
|
|
+ // See details there:
|
|
+ // https://github.com/GNOME/gtk/blob/5ea69a136bd7e4970b3a800390e20314665aaed2/gtk/ui/gtktooltipwindow.ui#L11
|
|
+ *left = *right = *top = *bottom = 6;
|
|
+
|
|
+ // We also need to add margin/padding/borders from Tooltip content.
|
|
+ // Tooltip contains horizontal box, where icon and label is put.
|
|
+ // We ignore icon as long as we don't have support for it.
|
|
+ GtkStyleContext* boxStyle = ClaimStyleContext(MOZ_GTK_TOOLTIP_BOX);
|
|
+ moz_gtk_add_margin_border_padding(boxStyle,
|
|
+ left, top, right, bottom);
|
|
+ ReleaseStyleContext(boxStyle);
|
|
+
|
|
+ GtkStyleContext* labelStyle = ClaimStyleContext(MOZ_GTK_TOOLTIP_BOX_LABEL);
|
|
+ moz_gtk_add_margin_border_padding(labelStyle,
|
|
+ left, top, right, bottom);
|
|
+ ReleaseStyleContext(labelStyle);
|
|
+
|
|
return MOZ_GTK_SUCCESS;
|
|
}
|
|
+ case MOZ_GTK_SCROLLBAR_VERTICAL:
|
|
+ case MOZ_GTK_SCROLLBAR_TROUGH_HORIZONTAL:
|
|
+ {
|
|
+ if (gtk_check_version(3,20,0) == nullptr) {
|
|
+ style = ClaimStyleContext(widget);
|
|
+ moz_gtk_add_margin_border_padding(style, left, top, right, bottom);
|
|
+ ReleaseStyleContext(style);
|
|
+ if (widget == MOZ_GTK_SCROLLBAR_VERTICAL) {
|
|
+ style = ClaimStyleContext(MOZ_GTK_SCROLLBAR_CONTENTS_VERTICAL);
|
|
+ moz_gtk_add_margin_border_padding(style, left, top, right, bottom);
|
|
+ ReleaseStyleContext(style);
|
|
+ }
|
|
+ } else {
|
|
+ MozGtkScrollbarMetrics metrics;
|
|
+ moz_gtk_get_scrollbar_metrics(&metrics);
|
|
+ /* Top and bottom border for whole vertical scrollbar, top and bottom
|
|
+ * border for horizontal track - to correctly position thumb element */
|
|
+ *top = *bottom = metrics.trough_border;
|
|
+ }
|
|
+ return MOZ_GTK_SUCCESS;
|
|
+ }
|
|
+ break;
|
|
+
|
|
+ case MOZ_GTK_SCROLLBAR_HORIZONTAL:
|
|
+ case MOZ_GTK_SCROLLBAR_TROUGH_VERTICAL:
|
|
+ {
|
|
+ if (gtk_check_version(3,20,0) == nullptr) {
|
|
+ style = ClaimStyleContext(widget);
|
|
+ moz_gtk_add_margin_border_padding(style, left, top, right, bottom);
|
|
+ ReleaseStyleContext(style);
|
|
+ if (widget == MOZ_GTK_SCROLLBAR_HORIZONTAL) {
|
|
+ style = ClaimStyleContext(MOZ_GTK_SCROLLBAR_CONTENTS_HORIZONTAL);
|
|
+ moz_gtk_add_margin_border_padding(style, left, top, right, bottom);
|
|
+ ReleaseStyleContext(style);
|
|
+ }
|
|
+ } else {
|
|
+ MozGtkScrollbarMetrics metrics;
|
|
+ moz_gtk_get_scrollbar_metrics(&metrics);
|
|
+ *left = *right = metrics.trough_border;
|
|
+ }
|
|
+ return MOZ_GTK_SUCCESS;
|
|
+ }
|
|
+ break;
|
|
+
|
|
+ case MOZ_GTK_SCROLLBAR_THUMB_HORIZONTAL:
|
|
+ case MOZ_GTK_SCROLLBAR_THUMB_VERTICAL:
|
|
+ {
|
|
+ if (gtk_check_version(3,20,0) == nullptr) {
|
|
+ style = ClaimStyleContext(widget);
|
|
+ moz_gtk_add_margin_border_padding(style, left, top, right, bottom);
|
|
+ ReleaseStyleContext(style);
|
|
+ }
|
|
+ return MOZ_GTK_SUCCESS;
|
|
+ }
|
|
+ break;
|
|
/* These widgets have no borders, since they are not containers. */
|
|
case MOZ_GTK_CHECKBUTTON_LABEL:
|
|
case MOZ_GTK_RADIOBUTTON_LABEL:
|
|
@@ -2299,10 +2268,6 @@ moz_gtk_get_widget_border(WidgetNodeType
|
|
case MOZ_GTK_CHECKBUTTON:
|
|
case MOZ_GTK_RADIOBUTTON:
|
|
case MOZ_GTK_SCROLLBAR_BUTTON:
|
|
- case MOZ_GTK_SCROLLBAR_HORIZONTAL:
|
|
- case MOZ_GTK_SCROLLBAR_VERTICAL:
|
|
- case MOZ_GTK_SCROLLBAR_THUMB_HORIZONTAL:
|
|
- case MOZ_GTK_SCROLLBAR_THUMB_VERTICAL:
|
|
case MOZ_GTK_SCALE_THUMB_HORIZONTAL:
|
|
case MOZ_GTK_SCALE_THUMB_VERTICAL:
|
|
case MOZ_GTK_GRIPPER:
|
|
@@ -2390,9 +2355,9 @@ moz_gtk_get_combo_box_entry_button_size(
|
|
* as well as the minimum arrow size and its padding
|
|
* */
|
|
GtkRequisition requisition;
|
|
- ensure_combo_box_entry_widgets();
|
|
|
|
- gtk_widget_get_preferred_size(gComboBoxEntryButtonWidget, NULL, &requisition);
|
|
+ gtk_widget_get_preferred_size(GetWidget(MOZ_GTK_COMBOBOX_ENTRY_BUTTON),
|
|
+ NULL, &requisition);
|
|
*width = requisition.width;
|
|
*height = requisition.height;
|
|
|
|
@@ -2421,8 +2386,7 @@ moz_gtk_get_arrow_size(WidgetNodeType wi
|
|
GtkWidget* widget;
|
|
switch (widgetType) {
|
|
case MOZ_GTK_DROPDOWN:
|
|
- ensure_combo_box_widgets();
|
|
- widget = gComboBoxArrowWidget;
|
|
+ widget = GetWidget(MOZ_GTK_COMBOBOX_ARROW);
|
|
break;
|
|
default:
|
|
widget = GetWidget(MOZ_GTK_BUTTON_ARROW);
|
|
@@ -2588,6 +2552,9 @@ moz_gtk_get_scalethumb_metrics(GtkOrient
|
|
gint
|
|
moz_gtk_get_scrollbar_metrics(MozGtkScrollbarMetrics *metrics)
|
|
{
|
|
+ // For Gtk >= 3.20 scrollbar metrics are ignored
|
|
+ MOZ_ASSERT(gtk_check_version(3, 20, 0) != nullptr);
|
|
+
|
|
GtkStyleContext* style = ClaimStyleContext(MOZ_GTK_SCROLLBAR_VERTICAL);
|
|
gtk_style_context_get_style(style,
|
|
"slider_width", &metrics->slider_width,
|
|
@@ -2598,40 +2565,9 @@ moz_gtk_get_scrollbar_metrics(MozGtkScro
|
|
nullptr);
|
|
ReleaseStyleContext(style);
|
|
|
|
- if(!gtk_check_version(3, 20, 0)) {
|
|
- style = ClaimStyleContext(MOZ_GTK_SCROLLBAR_THUMB_VERTICAL);
|
|
- gtk_style_context_get(style, gtk_style_context_get_state(style),
|
|
- "min-height", &metrics->min_slider_size, nullptr);
|
|
- ReleaseStyleContext(style);
|
|
- }
|
|
-
|
|
return MOZ_GTK_SUCCESS;
|
|
}
|
|
|
|
-gboolean
|
|
-moz_gtk_images_in_menus()
|
|
-{
|
|
- gboolean result;
|
|
- GtkSettings* settings;
|
|
-
|
|
- settings = gtk_widget_get_settings(GetWidget(MOZ_GTK_IMAGEMENUITEM));
|
|
-
|
|
- g_object_get(settings, "gtk-menu-images", &result, NULL);
|
|
- return result;
|
|
-}
|
|
-
|
|
-gboolean
|
|
-moz_gtk_images_in_buttons()
|
|
-{
|
|
- gboolean result;
|
|
- GtkSettings* settings;
|
|
-
|
|
- settings = gtk_widget_get_settings(GetWidget(MOZ_GTK_BUTTON));
|
|
-
|
|
- g_object_get(settings, "gtk-button-images", &result, NULL);
|
|
- return result;
|
|
-}
|
|
-
|
|
/* cairo_t *cr argument has to be a system-cairo. */
|
|
gint
|
|
moz_gtk_widget_paint(WidgetNodeType widget, cairo_t *cr,
|
|
@@ -2672,10 +2608,25 @@ moz_gtk_widget_paint(WidgetNodeType widg
|
|
break;
|
|
case MOZ_GTK_SCROLLBAR_HORIZONTAL:
|
|
case MOZ_GTK_SCROLLBAR_VERTICAL:
|
|
- return moz_gtk_scrollbar_trough_paint(widget, cr, rect,
|
|
- state,
|
|
- (GtkScrollbarTrackFlags) flags,
|
|
- direction);
|
|
+ if (gtk_check_version(3,20,0) == nullptr) {
|
|
+ return moz_gtk_scrollbar_paint(widget, cr, rect, state, direction);
|
|
+ } else {
|
|
+ WidgetNodeType trough_widget = (widget == MOZ_GTK_SCROLLBAR_HORIZONTAL) ?
|
|
+ MOZ_GTK_SCROLLBAR_TROUGH_HORIZONTAL : MOZ_GTK_SCROLLBAR_TROUGH_VERTICAL;
|
|
+ return moz_gtk_scrollbar_trough_paint(trough_widget, cr, rect,
|
|
+ state,
|
|
+ (GtkScrollbarTrackFlags) flags,
|
|
+ direction);
|
|
+ }
|
|
+ break;
|
|
+ case MOZ_GTK_SCROLLBAR_TROUGH_HORIZONTAL:
|
|
+ case MOZ_GTK_SCROLLBAR_TROUGH_VERTICAL:
|
|
+ if (gtk_check_version(3,20,0) == nullptr) {
|
|
+ return moz_gtk_scrollbar_trough_paint(widget, cr, rect,
|
|
+ state,
|
|
+ (GtkScrollbarTrackFlags) flags,
|
|
+ direction);
|
|
+ }
|
|
break;
|
|
case MOZ_GTK_SCROLLBAR_THUMB_HORIZONTAL:
|
|
case MOZ_GTK_SCROLLBAR_THUMB_VERTICAL:
|
|
@@ -2702,9 +2653,13 @@ moz_gtk_widget_paint(WidgetNodeType widg
|
|
state, direction);
|
|
break;
|
|
case MOZ_GTK_SPINBUTTON_ENTRY:
|
|
- // TODO - use MOZ_GTK_SPINBUTTON_ENTRY style directly
|
|
- return moz_gtk_entry_paint(cr, rect, state,
|
|
- GetWidget(MOZ_GTK_SPINBUTTON), direction);
|
|
+ {
|
|
+ GtkStyleContext* style = ClaimStyleContext(MOZ_GTK_SPINBUTTON_ENTRY,
|
|
+ direction, GetStateFlagsFromGtkWidgetState(state));
|
|
+ gint ret = moz_gtk_entry_paint(cr, rect, state, style);
|
|
+ ReleaseStyleContext(style);
|
|
+ return ret;
|
|
+ }
|
|
break;
|
|
case MOZ_GTK_GRIPPER:
|
|
return moz_gtk_gripper_paint(cr, rect, state,
|
|
@@ -2729,9 +2684,13 @@ moz_gtk_widget_paint(WidgetNodeType widg
|
|
(GtkExpanderStyle) flags, direction);
|
|
break;
|
|
case MOZ_GTK_ENTRY:
|
|
- return moz_gtk_entry_paint(cr, rect, state, GetWidget(MOZ_GTK_ENTRY),
|
|
- direction);
|
|
- break;
|
|
+ {
|
|
+ GtkStyleContext* style = ClaimStyleContext(MOZ_GTK_ENTRY,
|
|
+ direction, GetStateFlagsFromGtkWidgetState(state));
|
|
+ gint ret = moz_gtk_entry_paint(cr, rect, state, style);
|
|
+ ReleaseStyleContext(style);
|
|
+ return ret;
|
|
+ }
|
|
case MOZ_GTK_TEXT_VIEW:
|
|
return moz_gtk_text_view_paint(cr, rect, state, direction);
|
|
break;
|
|
@@ -2743,9 +2702,13 @@ moz_gtk_widget_paint(WidgetNodeType widg
|
|
state, flags, direction);
|
|
break;
|
|
case MOZ_GTK_DROPDOWN_ENTRY:
|
|
- ensure_combo_box_entry_widgets();
|
|
- return moz_gtk_entry_paint(cr, rect, state,
|
|
- gComboBoxEntryTextareaWidget, direction);
|
|
+ {
|
|
+ GtkStyleContext* style = ClaimStyleContext(MOZ_GTK_COMBOBOX_ENTRY_TEXTAREA,
|
|
+ direction, GetStateFlagsFromGtkWidgetState(state));
|
|
+ gint ret = moz_gtk_entry_paint(cr, rect, state, style);
|
|
+ ReleaseStyleContext(style);
|
|
+ return ret;
|
|
+ }
|
|
break;
|
|
case MOZ_GTK_CHECKBUTTON_CONTAINER:
|
|
case MOZ_GTK_RADIOBUTTON_CONTAINER:
|
|
@@ -2819,10 +2782,8 @@ moz_gtk_widget_paint(WidgetNodeType widg
|
|
break;
|
|
case MOZ_GTK_CHECKMENUITEM:
|
|
case MOZ_GTK_RADIOMENUITEM:
|
|
- return moz_gtk_check_menu_item_paint(cr, rect, state,
|
|
- (gboolean) flags,
|
|
- (widget == MOZ_GTK_RADIOMENUITEM),
|
|
- direction);
|
|
+ return moz_gtk_check_menu_item_paint(widget, cr, rect, state,
|
|
+ (gboolean) flags, direction);
|
|
break;
|
|
case MOZ_GTK_SPLITTER_HORIZONTAL:
|
|
return moz_gtk_vpaned_paint(cr, rect, state);
|
|
@@ -2870,16 +2831,6 @@ moz_gtk_shutdown()
|
|
/* This will destroy all of our widgets */
|
|
ResetWidgetCache();
|
|
|
|
- gProtoLayout = NULL;
|
|
- gComboBoxWidget = NULL;
|
|
- gComboBoxButtonWidget = NULL;
|
|
- gComboBoxSeparatorWidget = NULL;
|
|
- gComboBoxArrowWidget = NULL;
|
|
- gComboBoxEntryWidget = NULL;
|
|
- gComboBoxEntryButtonWidget = NULL;
|
|
- gComboBoxEntryArrowWidget = NULL;
|
|
- gComboBoxEntryTextareaWidget = NULL;
|
|
-
|
|
is_initialized = FALSE;
|
|
|
|
return MOZ_GTK_SUCCESS;
|
|
diff -up firefox-51.0/widget/gtk/gtkdrawing.h.old firefox-51.0/widget/gtk/gtkdrawing.h
|
|
--- firefox-51.0/widget/gtk/gtkdrawing.h.old 2017-01-16 17:16:53.000000000 +0100
|
|
+++ firefox-51.0/widget/gtk/gtkdrawing.h 2017-01-06 10:20:43.000000000 +0100
|
|
@@ -145,8 +145,11 @@ typedef enum {
|
|
MOZ_GTK_ENTRY,
|
|
/* Paints a GtkExpander. */
|
|
MOZ_GTK_EXPANDER,
|
|
- /* Paints a GtkTextView. */
|
|
+ /* Paints a GtkTextView or gets the style context corresponding to the
|
|
+ root node of a GtkTextView. */
|
|
MOZ_GTK_TEXT_VIEW,
|
|
+ /* The "text" window or node of a GtkTextView */
|
|
+ MOZ_GTK_TEXT_VIEW_TEXT,
|
|
/* Paints a GtkOptionMenu. */
|
|
MOZ_GTK_DROPDOWN,
|
|
/* Paints a dropdown arrow (a GtkButton containing a down GtkArrow). */
|
|
@@ -160,11 +163,15 @@ typedef enum {
|
|
MOZ_GTK_TOOLBAR_SEPARATOR,
|
|
/* Paints a GtkToolTip */
|
|
MOZ_GTK_TOOLTIP,
|
|
+ /* Paints a GtkBox from GtkToolTip */
|
|
+ MOZ_GTK_TOOLTIP_BOX,
|
|
+ /* Paints a GtkLabel of GtkToolTip */
|
|
+ MOZ_GTK_TOOLTIP_BOX_LABEL,
|
|
/* Paints a GtkFrame (e.g. a status bar panel). */
|
|
MOZ_GTK_FRAME,
|
|
/* Paints the border of a GtkFrame */
|
|
MOZ_GTK_FRAME_BORDER,
|
|
- /* Paints a resize grip for a GtkWindow */
|
|
+ /* Paints a resize grip for a GtkTextView */
|
|
MOZ_GTK_RESIZER,
|
|
/* Paints a GtkProgressBar. */
|
|
MOZ_GTK_PROGRESSBAR,
|
|
@@ -210,11 +217,13 @@ typedef enum {
|
|
MOZ_GTK_MENUBARITEM,
|
|
/* Paints items of popup menus. */
|
|
MOZ_GTK_MENUITEM,
|
|
- MOZ_GTK_IMAGEMENUITEM,
|
|
- MOZ_GTK_CHECKMENUITEM_CONTAINER,
|
|
- MOZ_GTK_RADIOMENUITEM_CONTAINER,
|
|
+ /* Paints a menuitem with check indicator, or the gets the style context for
|
|
+ a menuitem that contains a checkbox. */
|
|
MOZ_GTK_CHECKMENUITEM,
|
|
+ /* Gets the style context for a checkbox in a check menuitem. */
|
|
+ MOZ_GTK_CHECKMENUITEM_INDICATOR,
|
|
MOZ_GTK_RADIOMENUITEM,
|
|
+ MOZ_GTK_RADIOMENUITEM_INDICATOR,
|
|
MOZ_GTK_MENUSEPARATOR,
|
|
/* GtkVPaned base class */
|
|
MOZ_GTK_SPLITTER_HORIZONTAL,
|
|
@@ -230,6 +239,22 @@ typedef enum {
|
|
MOZ_GTK_WINDOW_CONTAINER,
|
|
/* Paints a GtkInfoBar, for notifications. */
|
|
MOZ_GTK_INFO_BAR,
|
|
+ /* Used for widget tree construction. */
|
|
+ MOZ_GTK_COMBOBOX,
|
|
+ /* Paints a GtkComboBox button widget. */
|
|
+ MOZ_GTK_COMBOBOX_BUTTON,
|
|
+ /* Paints a GtkComboBox arrow widget. */
|
|
+ MOZ_GTK_COMBOBOX_ARROW,
|
|
+ /* Paints a GtkComboBox separator widget. */
|
|
+ MOZ_GTK_COMBOBOX_SEPARATOR,
|
|
+ /* Used for widget tree construction. */
|
|
+ MOZ_GTK_COMBOBOX_ENTRY,
|
|
+ /* Paints a GtkComboBox entry widget. */
|
|
+ MOZ_GTK_COMBOBOX_ENTRY_TEXTAREA,
|
|
+ /* Paints a GtkComboBox entry button widget. */
|
|
+ MOZ_GTK_COMBOBOX_ENTRY_BUTTON,
|
|
+ /* Paints a GtkComboBox entry arrow widget. */
|
|
+ MOZ_GTK_COMBOBOX_ENTRY_ARROW,
|
|
/* Used for scrolled window shell. */
|
|
MOZ_GTK_SCROLLED_WINDOW,
|
|
|
|
@@ -505,23 +530,18 @@ gint
|
|
moz_gtk_get_tab_thickness(WidgetNodeType aNodeType);
|
|
|
|
/**
|
|
- * Get a boolean which indicates whether or not to use images in menus.
|
|
- * If TRUE, use images in menus.
|
|
- */
|
|
-gboolean moz_gtk_images_in_menus(void);
|
|
-
|
|
-/**
|
|
- * Get a boolean which indicates whether or not to use images in buttons.
|
|
- * If TRUE, use images in buttons.
|
|
- */
|
|
-gboolean moz_gtk_images_in_buttons(void);
|
|
-
|
|
-/**
|
|
* Get a boolean which indicates whether the theme draws scrollbar buttons.
|
|
* If TRUE, draw scrollbar buttons.
|
|
*/
|
|
gboolean moz_gtk_has_scrollbar_buttons(void);
|
|
|
|
+/**
|
|
+ * Get minimum widget size as sum of margin, padding, border and min-width,
|
|
+ * min-height.
|
|
+ */
|
|
+void moz_gtk_get_widget_min_size(WidgetNodeType aGtkWidgetType, int* width,
|
|
+ int* height);
|
|
+
|
|
#if (MOZ_WIDGET_GTK == 2)
|
|
#ifdef __cplusplus
|
|
}
|
|
diff -up firefox-51.0/widget/gtk/mozgtk/mozgtk.c.old firefox-51.0/widget/gtk/mozgtk/mozgtk.c
|
|
--- firefox-51.0/widget/gtk/mozgtk/mozgtk.c.old 2017-01-18 16:26:11.416376760 +0100
|
|
+++ firefox-51.0/widget/gtk/mozgtk/mozgtk.c 2016-12-21 13:10:28.000000000 +0100
|
|
@@ -9,6 +9,7 @@ STUB(gdk_atom_name)
|
|
STUB(gdk_beep)
|
|
STUB(gdk_cairo_create)
|
|
STUB(gdk_color_free)
|
|
+STUB(gdk_color_parse)
|
|
STUB(gdk_cursor_new_for_display)
|
|
STUB(gdk_cursor_new_from_name)
|
|
STUB(gdk_cursor_new_from_pixbuf)
|
|
@@ -244,7 +245,6 @@ STUB(gtk_icon_theme_get_icon_sizes)
|
|
STUB(gtk_icon_theme_lookup_by_gicon)
|
|
STUB(gtk_icon_theme_lookup_icon)
|
|
STUB(gtk_image_get_type)
|
|
-STUB(gtk_image_menu_item_new)
|
|
STUB(gtk_image_new)
|
|
STUB(gtk_image_new_from_stock)
|
|
STUB(gtk_image_set_from_pixbuf)
|
|
@@ -577,10 +577,10 @@ STUB(gtk_tree_view_column_get_button)
|
|
STUB(gtk_widget_get_preferred_size)
|
|
STUB(gtk_widget_get_state_flags)
|
|
STUB(gtk_widget_get_style_context)
|
|
-STUB(gtk_widget_path_append_for_widget)
|
|
STUB(gtk_widget_path_append_type)
|
|
STUB(gtk_widget_path_copy)
|
|
STUB(gtk_widget_path_free)
|
|
+STUB(gtk_widget_path_iter_add_class)
|
|
STUB(gtk_widget_path_new)
|
|
STUB(gtk_widget_path_unref)
|
|
STUB(gtk_widget_set_visual)
|
|
@@ -612,6 +612,9 @@ STUB(gdkx_visual_get)
|
|
STUB(gtk_object_get_type)
|
|
#endif
|
|
|
|
+#ifndef GTK3_SYMBOLS
|
|
+// Only define the following workaround when using GTK3, which we detect
|
|
+// by checking if GTK3 stubs are not provided.
|
|
#include <X11/Xlib.h>
|
|
// Bug 1271100
|
|
// We need to trick system Cairo into not using the XShm extension due to
|
|
@@ -625,4 +628,5 @@ XShmQueryExtension(Display* aDisplay)
|
|
{
|
|
return False;
|
|
}
|
|
+#endif
|
|
|
|
diff -up firefox-51.0/widget/gtk/nsLookAndFeel.cpp.old firefox-51.0/widget/gtk/nsLookAndFeel.cpp
|
|
--- firefox-51.0/widget/gtk/nsLookAndFeel.cpp.old 2017-01-18 16:25:23.072605687 +0100
|
|
+++ firefox-51.0/widget/gtk/nsLookAndFeel.cpp 2017-01-06 10:20:43.000000000 +0100
|
|
@@ -47,9 +47,6 @@ nsLookAndFeel::nsLookAndFeel()
|
|
: nsXPLookAndFeel(),
|
|
#if (MOZ_WIDGET_GTK == 2)
|
|
mStyle(nullptr),
|
|
-#else
|
|
- mBackgroundStyle(nullptr),
|
|
- mButtonStyle(nullptr),
|
|
#endif
|
|
mDefaultFontCached(false), mButtonFontCached(false),
|
|
mFieldFontCached(false), mMenuFontCached(false)
|
|
@@ -61,13 +58,27 @@ nsLookAndFeel::~nsLookAndFeel()
|
|
{
|
|
#if (MOZ_WIDGET_GTK == 2)
|
|
g_object_unref(mStyle);
|
|
-#else
|
|
- g_object_unref(mBackgroundStyle);
|
|
- g_object_unref(mButtonStyle);
|
|
#endif
|
|
}
|
|
|
|
#if MOZ_WIDGET_GTK != 2
|
|
+// Modifies color |*aDest| as if a pattern of color |aSource| was painted with
|
|
+// CAIRO_OPERATOR_OVER to a surface with color |*aDest|.
|
|
+static void
|
|
+ApplyColorOver(const GdkRGBA& aSource, GdkRGBA* aDest) {
|
|
+ gdouble sourceCoef = aSource.alpha;
|
|
+ gdouble destCoef = aDest->alpha * (1.0 - sourceCoef);
|
|
+ gdouble resultAlpha = sourceCoef + destCoef;
|
|
+ if (resultAlpha != 0.0) { // don't divide by zero
|
|
+ destCoef /= resultAlpha;
|
|
+ sourceCoef /= resultAlpha;
|
|
+ aDest->red = sourceCoef * aSource.red + destCoef * aDest->red;
|
|
+ aDest->green = sourceCoef * aSource.green + destCoef * aDest->green;
|
|
+ aDest->blue = sourceCoef * aSource.blue + destCoef * aDest->blue;
|
|
+ aDest->alpha = resultAlpha;
|
|
+ }
|
|
+}
|
|
+
|
|
static void
|
|
GetLightAndDarkness(const GdkRGBA& aColor,
|
|
double* aLightness, double* aDarkness)
|
|
@@ -157,30 +168,55 @@ GetUnicoBorderGradientColors(GtkStyleCon
|
|
return result;
|
|
}
|
|
|
|
-
|
|
-static void
|
|
+// Sets |aLightColor| and |aDarkColor| to colors from |aContext|. Returns
|
|
+// true if |aContext| uses these colors to render a visible border.
|
|
+// If returning false, then the colors returned are a fallback from the
|
|
+// border-color value even though |aContext| does not use these colors to
|
|
+// render a border.
|
|
+static bool
|
|
GetBorderColors(GtkStyleContext* aContext,
|
|
GdkRGBA* aLightColor, GdkRGBA* aDarkColor)
|
|
{
|
|
- if (GetUnicoBorderGradientColors(aContext, aLightColor, aDarkColor))
|
|
- return;
|
|
-
|
|
+ // Determine whether the border on this style context is visible.
|
|
GtkStateFlags state = gtk_style_context_get_state(aContext);
|
|
+ GtkBorderStyle borderStyle;
|
|
+ gtk_style_context_get(aContext, state, GTK_STYLE_PROPERTY_BORDER_STYLE,
|
|
+ &borderStyle, nullptr);
|
|
+ bool visible = borderStyle != GTK_BORDER_STYLE_NONE &&
|
|
+ borderStyle != GTK_BORDER_STYLE_HIDDEN;
|
|
+ if (visible) {
|
|
+ // GTK has an initial value of zero for border-widths, and so themes
|
|
+ // need to explicitly set border-widths to make borders visible.
|
|
+ GtkBorder border;
|
|
+ gtk_style_context_get_border(aContext, GTK_STATE_FLAG_NORMAL, &border);
|
|
+ visible = border.top != 0 || border.right != 0 ||
|
|
+ border.bottom != 0 || border.left != 0;
|
|
+ }
|
|
+
|
|
+ if (visible &&
|
|
+ GetUnicoBorderGradientColors(aContext, aLightColor, aDarkColor))
|
|
+ return true;
|
|
+
|
|
+ // The initial value for the border-color is the foreground color, and so
|
|
+ // this will usually return a color distinct from the background even if
|
|
+ // there is no visible border detected.
|
|
gtk_style_context_get_border_color(aContext, state, aDarkColor);
|
|
// TODO GTK3 - update aLightColor
|
|
// for GTK_BORDER_STYLE_INSET/OUTSET/GROVE/RIDGE border styles.
|
|
// https://bugzilla.mozilla.org/show_bug.cgi?id=978172#c25
|
|
*aLightColor = *aDarkColor;
|
|
+ return visible;
|
|
}
|
|
|
|
-static void
|
|
+static bool
|
|
GetBorderColors(GtkStyleContext* aContext,
|
|
nscolor* aLightColor, nscolor* aDarkColor)
|
|
{
|
|
GdkRGBA lightColor, darkColor;
|
|
- GetBorderColors(aContext, &lightColor, &darkColor);
|
|
+ bool ret = GetBorderColors(aContext, &lightColor, &darkColor);
|
|
*aLightColor = GDK_RGBA_TO_NS_RGBA(lightColor);
|
|
*aDarkColor = GDK_RGBA_TO_NS_RGBA(darkColor);
|
|
+ return ret;
|
|
}
|
|
#endif
|
|
|
|
@@ -352,30 +388,39 @@ nsLookAndFeel::NativeGetColor(ColorID aI
|
|
break;
|
|
#else
|
|
// css2 http://www.w3.org/TR/REC-CSS2/ui.html#system-colors
|
|
- case eColorID_activeborder:
|
|
+ case eColorID_activeborder: {
|
|
// active window border
|
|
- gtk_style_context_get_border_color(mBackgroundStyle,
|
|
+ GtkStyleContext *style = ClaimStyleContext(MOZ_GTK_WINDOW);
|
|
+ gtk_style_context_get_border_color(style,
|
|
GTK_STATE_FLAG_NORMAL, &gdk_color);
|
|
aColor = GDK_RGBA_TO_NS_RGBA(gdk_color);
|
|
+ ReleaseStyleContext(style);
|
|
break;
|
|
- case eColorID_inactiveborder:
|
|
+ }
|
|
+ case eColorID_inactiveborder: {
|
|
// inactive window border
|
|
- gtk_style_context_get_border_color(mBackgroundStyle,
|
|
- GTK_STATE_FLAG_INSENSITIVE,
|
|
+ GtkStyleContext *style = ClaimStyleContext(MOZ_GTK_WINDOW);
|
|
+ gtk_style_context_get_border_color(style,
|
|
+ GTK_STATE_FLAG_INSENSITIVE,
|
|
&gdk_color);
|
|
aColor = GDK_RGBA_TO_NS_RGBA(gdk_color);
|
|
+ ReleaseStyleContext(style);
|
|
break;
|
|
+ }
|
|
case eColorID_graytext: // disabled text in windows, menus, etc.
|
|
case eColorID_inactivecaptiontext: // text in inactive window caption
|
|
aColor = sMenuTextInactive;
|
|
break;
|
|
- case eColorID_inactivecaption:
|
|
+ case eColorID_inactivecaption: {
|
|
// inactive window caption
|
|
- gtk_style_context_get_background_color(mBackgroundStyle,
|
|
+ GtkStyleContext *style = ClaimStyleContext(MOZ_GTK_WINDOW);
|
|
+ gtk_style_context_get_background_color(style,
|
|
GTK_STATE_FLAG_INSENSITIVE,
|
|
&gdk_color);
|
|
aColor = GDK_RGBA_TO_NS_RGBA(gdk_color);
|
|
+ ReleaseStyleContext(style);
|
|
break;
|
|
+ }
|
|
#endif
|
|
case eColorID_infobackground:
|
|
// tooltip background color
|
|
@@ -496,18 +541,24 @@ nsLookAndFeel::NativeGetColor(ColorID aI
|
|
case eColorID__moz_fieldtext:
|
|
aColor = sMozFieldText;
|
|
break;
|
|
- case eColorID__moz_buttondefault:
|
|
- // default button border color
|
|
- gtk_style_context_get_border_color(mButtonStyle,
|
|
+ case eColorID__moz_buttondefault: {
|
|
+ // default button border color
|
|
+ GtkStyleContext *style = ClaimStyleContext(MOZ_GTK_BUTTON);
|
|
+ gtk_style_context_get_border_color(style,
|
|
GTK_STATE_FLAG_NORMAL, &gdk_color);
|
|
aColor = GDK_RGBA_TO_NS_RGBA(gdk_color);
|
|
+ ReleaseStyleContext(style);
|
|
break;
|
|
- case eColorID__moz_buttonhoverface:
|
|
- gtk_style_context_get_background_color(mButtonStyle,
|
|
+ }
|
|
+ case eColorID__moz_buttonhoverface: {
|
|
+ GtkStyleContext *style = ClaimStyleContext(MOZ_GTK_BUTTON);
|
|
+ gtk_style_context_get_background_color(style,
|
|
GTK_STATE_FLAG_PRELIGHT,
|
|
&gdk_color);
|
|
aColor = GDK_RGBA_TO_NS_RGBA(gdk_color);
|
|
+ ReleaseStyleContext(style);
|
|
break;
|
|
+ }
|
|
case eColorID__moz_buttonhovertext:
|
|
aColor = sButtonHoverText;
|
|
break;
|
|
@@ -784,12 +835,6 @@ nsLookAndFeel::GetIntImpl(IntID aID, int
|
|
case eIntID_SpellCheckerUnderlineStyle:
|
|
aResult = NS_STYLE_TEXT_DECORATION_STYLE_WAVY;
|
|
break;
|
|
- case eIntID_ImagesInMenus:
|
|
- aResult = moz_gtk_images_in_menus();
|
|
- break;
|
|
- case eIntID_ImagesInButtons:
|
|
- aResult = moz_gtk_images_in_buttons();
|
|
- break;
|
|
case eIntID_MenuBarDrag:
|
|
aResult = sMenuSupportsDrag;
|
|
break;
|
|
@@ -1010,16 +1055,6 @@ nsLookAndFeel::GetFontImpl(FontID aID, n
|
|
return true;
|
|
}
|
|
|
|
-#if (MOZ_WIDGET_GTK == 3)
|
|
-static GtkStyleContext*
|
|
-create_context(GtkWidgetPath *path)
|
|
-{
|
|
- GtkStyleContext *style = gtk_style_context_new();
|
|
- gtk_style_context_set_path(style, path);
|
|
- return(style);
|
|
-}
|
|
-#endif
|
|
-
|
|
void
|
|
nsLookAndFeel::Init()
|
|
{
|
|
@@ -1110,78 +1145,54 @@ nsLookAndFeel::Init()
|
|
g_object_set(settings, dark_setting, FALSE, nullptr);
|
|
}
|
|
|
|
- GtkWidgetPath *path = gtk_widget_path_new();
|
|
- gtk_widget_path_append_type(path, GTK_TYPE_WINDOW);
|
|
-
|
|
- mBackgroundStyle = create_context(path);
|
|
- gtk_style_context_add_class(mBackgroundStyle, GTK_STYLE_CLASS_BACKGROUND);
|
|
-
|
|
- mButtonStyle = create_context(path);
|
|
- gtk_style_context_add_class(mButtonStyle, GTK_STYLE_CLASS_BUTTON);
|
|
-
|
|
// Scrollbar colors
|
|
- style = create_context(path);
|
|
- gtk_style_context_add_class(style, GTK_STYLE_CLASS_SCROLLBAR);
|
|
- gtk_style_context_add_class(style, GTK_STYLE_CLASS_TROUGH);
|
|
+ style = ClaimStyleContext(MOZ_GTK_SCROLLBAR_TROUGH_VERTICAL);
|
|
gtk_style_context_get_background_color(style, GTK_STATE_FLAG_NORMAL, &color);
|
|
sMozScrollbar = GDK_RGBA_TO_NS_RGBA(color);
|
|
- g_object_unref(style);
|
|
+ ReleaseStyleContext(style);
|
|
|
|
// Window colors
|
|
- style = create_context(path);
|
|
- gtk_style_context_save(style);
|
|
- gtk_style_context_add_class(style, GTK_STYLE_CLASS_BACKGROUND);
|
|
+ style = ClaimStyleContext(MOZ_GTK_WINDOW);
|
|
gtk_style_context_get_background_color(style, GTK_STATE_FLAG_NORMAL, &color);
|
|
sMozWindowBackground = GDK_RGBA_TO_NS_RGBA(color);
|
|
gtk_style_context_get_color(style, GTK_STATE_FLAG_NORMAL, &color);
|
|
sMozWindowText = GDK_RGBA_TO_NS_RGBA(color);
|
|
- gtk_style_context_restore(style);
|
|
- g_object_unref(style);
|
|
+ ReleaseStyleContext(style);
|
|
|
|
// tooltip foreground and background
|
|
style = ClaimStyleContext(MOZ_GTK_TOOLTIP);
|
|
gtk_style_context_get_background_color(style, GTK_STATE_FLAG_NORMAL, &color);
|
|
sInfoBackground = GDK_RGBA_TO_NS_RGBA(color);
|
|
- {
|
|
- GtkStyleContext* boxStyle =
|
|
- CreateStyleForWidget(gtk_box_new(GTK_ORIENTATION_HORIZONTAL, 0),
|
|
- style);
|
|
- GtkStyleContext* labelStyle =
|
|
- CreateStyleForWidget(gtk_label_new(nullptr), boxStyle);
|
|
- gtk_style_context_get_color(labelStyle, GTK_STATE_FLAG_NORMAL, &color);
|
|
- g_object_unref(labelStyle);
|
|
- g_object_unref(boxStyle);
|
|
- }
|
|
- sInfoText = GDK_RGBA_TO_NS_RGBA(color);
|
|
ReleaseStyleContext(style);
|
|
|
|
- // menu foreground & menu background
|
|
- GtkWidget *accel_label = gtk_accel_label_new("M");
|
|
- GtkWidget *menuitem = gtk_menu_item_new();
|
|
- GtkWidget *menu = gtk_menu_new();
|
|
-
|
|
- g_object_ref_sink(menu);
|
|
-
|
|
- gtk_container_add(GTK_CONTAINER(menuitem), accel_label);
|
|
- gtk_menu_shell_append(GTK_MENU_SHELL(menu), menuitem);
|
|
-
|
|
- style = gtk_widget_get_style_context(accel_label);
|
|
+ style = ClaimStyleContext(MOZ_GTK_TOOLTIP_BOX_LABEL);
|
|
gtk_style_context_get_color(style, GTK_STATE_FLAG_NORMAL, &color);
|
|
- sMenuText = GDK_RGBA_TO_NS_RGBA(color);
|
|
- gtk_style_context_get_color(style, GTK_STATE_FLAG_INSENSITIVE, &color);
|
|
- sMenuTextInactive = GDK_RGBA_TO_NS_RGBA(color);
|
|
+ sInfoText = GDK_RGBA_TO_NS_RGBA(color);
|
|
+ ReleaseStyleContext(style);
|
|
|
|
- style = gtk_widget_get_style_context(menu);
|
|
+ style = ClaimStyleContext(MOZ_GTK_MENUITEM);
|
|
+ {
|
|
+ GtkStyleContext* accelStyle =
|
|
+ CreateStyleForWidget(gtk_accel_label_new("M"), style);
|
|
+ gtk_style_context_get_color(accelStyle, GTK_STATE_FLAG_NORMAL, &color);
|
|
+ sMenuText = GDK_RGBA_TO_NS_RGBA(color);
|
|
+ gtk_style_context_get_color(accelStyle, GTK_STATE_FLAG_INSENSITIVE, &color);
|
|
+ sMenuTextInactive = GDK_RGBA_TO_NS_RGBA(color);
|
|
+ g_object_unref(accelStyle);
|
|
+ }
|
|
+ ReleaseStyleContext(style);
|
|
+
|
|
+ style = ClaimStyleContext(MOZ_GTK_MENUPOPUP);
|
|
gtk_style_context_get_background_color(style, GTK_STATE_FLAG_NORMAL, &color);
|
|
sMenuBackground = GDK_RGBA_TO_NS_RGBA(color);
|
|
+ ReleaseStyleContext(style);
|
|
|
|
- style = gtk_widget_get_style_context(menuitem);
|
|
+ style = ClaimStyleContext(MOZ_GTK_MENUITEM);
|
|
gtk_style_context_get_background_color(style, GTK_STATE_FLAG_PRELIGHT, &color);
|
|
sMenuHover = GDK_RGBA_TO_NS_RGBA(color);
|
|
gtk_style_context_get_color(style, GTK_STATE_FLAG_PRELIGHT, &color);
|
|
sMenuHoverText = GDK_RGBA_TO_NS_RGBA(color);
|
|
-
|
|
- g_object_unref(menu);
|
|
+ ReleaseStyleContext(style);
|
|
#endif
|
|
|
|
// button styles
|
|
@@ -1192,9 +1203,6 @@ nsLookAndFeel::Init()
|
|
GtkWidget *combobox = gtk_combo_box_new();
|
|
GtkWidget *comboboxLabel = gtk_label_new("M");
|
|
gtk_container_add(GTK_CONTAINER(combobox), comboboxLabel);
|
|
-#else
|
|
- GtkWidget *combobox = gtk_combo_box_new_with_entry();
|
|
- GtkWidget *comboboxLabel = gtk_bin_get_child(GTK_BIN(combobox));
|
|
#endif
|
|
GtkWidget *window = gtk_window_new(GTK_WINDOW_POPUP);
|
|
GtkWidget *treeView = gtk_tree_view_new();
|
|
@@ -1208,7 +1216,9 @@ nsLookAndFeel::Init()
|
|
gtk_container_add(GTK_CONTAINER(parent), button);
|
|
gtk_container_add(GTK_CONTAINER(parent), treeView);
|
|
gtk_container_add(GTK_CONTAINER(parent), linkButton);
|
|
+#if (MOZ_WIDGET_GTK == 2)
|
|
gtk_container_add(GTK_CONTAINER(parent), combobox);
|
|
+#endif
|
|
gtk_container_add(GTK_CONTAINER(parent), menuBar);
|
|
gtk_menu_shell_append(GTK_MENU_SHELL(menuBar), menuBarItem);
|
|
gtk_container_add(GTK_CONTAINER(window), parent);
|
|
@@ -1291,11 +1301,19 @@ nsLookAndFeel::Init()
|
|
}
|
|
#else
|
|
// Text colors
|
|
- style = gtk_widget_get_style_context(textView);
|
|
- gtk_style_context_save(style);
|
|
- gtk_style_context_add_class(style, GTK_STYLE_CLASS_VIEW);
|
|
- gtk_style_context_get_background_color(style, GTK_STATE_FLAG_NORMAL, &color);
|
|
- sMozFieldBackground = GDK_RGBA_TO_NS_RGBA(color);
|
|
+ GdkRGBA bgColor;
|
|
+ // If the text window background is translucent, then the background of
|
|
+ // the textview root node is visible.
|
|
+ style = ClaimStyleContext(MOZ_GTK_TEXT_VIEW);
|
|
+ gtk_style_context_get_background_color(style, GTK_STATE_FLAG_NORMAL,
|
|
+ &bgColor);
|
|
+ ReleaseStyleContext(style);
|
|
+
|
|
+ style = ClaimStyleContext(MOZ_GTK_TEXT_VIEW_TEXT);
|
|
+ gtk_style_context_get_background_color(style, GTK_STATE_FLAG_NORMAL,
|
|
+ &color);
|
|
+ ApplyColorOver(color, &bgColor);
|
|
+ sMozFieldBackground = GDK_RGBA_TO_NS_RGBA(bgColor);
|
|
gtk_style_context_get_color(style, GTK_STATE_FLAG_NORMAL, &color);
|
|
sMozFieldText = GDK_RGBA_TO_NS_RGBA(color);
|
|
|
|
@@ -1308,26 +1326,34 @@ nsLookAndFeel::Init()
|
|
static_cast<GtkStateFlags>(GTK_STATE_FLAG_FOCUSED|GTK_STATE_FLAG_SELECTED),
|
|
&color);
|
|
sTextSelectedText = GDK_RGBA_TO_NS_RGBA(color);
|
|
- gtk_style_context_restore(style);
|
|
+ ReleaseStyleContext(style);
|
|
|
|
- // Button text, background, border
|
|
- style = gtk_widget_get_style_context(label);
|
|
- gtk_style_context_get_color(style, GTK_STATE_FLAG_NORMAL, &color);
|
|
- sButtonText = GDK_RGBA_TO_NS_RGBA(color);
|
|
- gtk_style_context_get_color(style, GTK_STATE_FLAG_PRELIGHT, &color);
|
|
- sButtonHoverText = GDK_RGBA_TO_NS_RGBA(color);
|
|
+ // Button text color
|
|
+ style = ClaimStyleContext(MOZ_GTK_BUTTON);
|
|
+ {
|
|
+ GtkStyleContext* labelStyle =
|
|
+ CreateStyleForWidget(gtk_label_new("M"), style);
|
|
+ gtk_style_context_get_color(labelStyle, GTK_STATE_FLAG_NORMAL, &color);
|
|
+ sButtonText = GDK_RGBA_TO_NS_RGBA(color);
|
|
+ gtk_style_context_get_color(labelStyle, GTK_STATE_FLAG_PRELIGHT, &color);
|
|
+ sButtonHoverText = GDK_RGBA_TO_NS_RGBA(color);
|
|
+ g_object_unref(labelStyle);
|
|
+ }
|
|
+ ReleaseStyleContext(style);
|
|
|
|
// Combobox text color
|
|
- style = gtk_widget_get_style_context(comboboxLabel);
|
|
+ style = ClaimStyleContext(MOZ_GTK_COMBOBOX_ENTRY_TEXTAREA);
|
|
gtk_style_context_get_color(style, GTK_STATE_FLAG_NORMAL, &color);
|
|
sComboBoxText = GDK_RGBA_TO_NS_RGBA(color);
|
|
+ ReleaseStyleContext(style);
|
|
|
|
// Menubar text and hover text colors
|
|
- style = gtk_widget_get_style_context(menuBarItem);
|
|
+ style = ClaimStyleContext(MOZ_GTK_MENUBARITEM);
|
|
gtk_style_context_get_color(style, GTK_STATE_FLAG_NORMAL, &color);
|
|
sMenuBarText = GDK_RGBA_TO_NS_RGBA(color);
|
|
gtk_style_context_get_color(style, GTK_STATE_FLAG_PRELIGHT, &color);
|
|
sMenuBarHoverText = GDK_RGBA_TO_NS_RGBA(color);
|
|
+ ReleaseStyleContext(style);
|
|
|
|
// GTK's guide to fancy odd row background colors:
|
|
// 1) Check if a theme explicitly defines an odd row color
|
|
@@ -1335,7 +1361,7 @@ nsLookAndFeel::Init()
|
|
// slightly by a hardcoded value (gtkstyle.c)
|
|
// 3) If neither are defined, take the base background color and
|
|
// darken that by a hardcoded value
|
|
- style = gtk_widget_get_style_context(treeView);
|
|
+ style = ClaimStyleContext(MOZ_GTK_TREEVIEW);
|
|
|
|
// Get odd row background color
|
|
gtk_style_context_save(style);
|
|
@@ -1343,12 +1369,21 @@ nsLookAndFeel::Init()
|
|
gtk_style_context_get_background_color(style, GTK_STATE_FLAG_NORMAL, &color);
|
|
sOddCellBackground = GDK_RGBA_TO_NS_RGBA(color);
|
|
gtk_style_context_restore(style);
|
|
+ ReleaseStyleContext(style);
|
|
|
|
- gtk_widget_path_free(path);
|
|
-
|
|
+ // GtkFrame has a "border" subnode on which Adwaita draws the border.
|
|
+ // Some themes do not draw on this node but draw a border on the widget
|
|
+ // root node, so check the root node if no border is found on the border
|
|
+ // node.
|
|
style = ClaimStyleContext(MOZ_GTK_FRAME_BORDER);
|
|
- GetBorderColors(style, &sFrameOuterLightBorder, &sFrameInnerDarkBorder);
|
|
+ bool themeUsesColors =
|
|
+ GetBorderColors(style, &sFrameOuterLightBorder, &sFrameInnerDarkBorder);
|
|
ReleaseStyleContext(style);
|
|
+ if (!themeUsesColors) {
|
|
+ style = ClaimStyleContext(MOZ_GTK_FRAME);
|
|
+ GetBorderColors(style, &sFrameOuterLightBorder, &sFrameInnerDarkBorder);
|
|
+ ReleaseStyleContext(style);
|
|
+ }
|
|
|
|
// GtkInfoBar
|
|
// TODO - Use WidgetCache for it?
|
|
@@ -1419,12 +1454,6 @@ nsLookAndFeel::RefreshImpl()
|
|
#if (MOZ_WIDGET_GTK == 2)
|
|
g_object_unref(mStyle);
|
|
mStyle = nullptr;
|
|
-#else
|
|
- g_object_unref(mBackgroundStyle);
|
|
- g_object_unref(mButtonStyle);
|
|
-
|
|
- mBackgroundStyle = nullptr;
|
|
- mButtonStyle = nullptr;
|
|
#endif
|
|
|
|
Init();
|
|
diff -up firefox-51.0/widget/gtk/nsNativeThemeGTK.cpp.old firefox-51.0/widget/gtk/nsNativeThemeGTK.cpp
|
|
--- firefox-51.0/widget/gtk/nsNativeThemeGTK.cpp.old 2017-01-16 17:16:53.000000000 +0100
|
|
+++ firefox-51.0/widget/gtk/nsNativeThemeGTK.cpp 2016-10-31 11:52:13.000000000 +0100
|
|
@@ -149,19 +149,15 @@ static void SetWidgetStateSafe(uint8_t *
|
|
aSafeVector[key >> 3] |= (1 << (key & 7));
|
|
}
|
|
|
|
-static GtkTextDirection GetTextDirection(nsIFrame* aFrame)
|
|
+/* static */ GtkTextDirection
|
|
+nsNativeThemeGTK::GetTextDirection(nsIFrame* aFrame)
|
|
{
|
|
- if (!aFrame)
|
|
- return GTK_TEXT_DIR_NONE;
|
|
-
|
|
- switch (aFrame->StyleVisibility()->mDirection) {
|
|
- case NS_STYLE_DIRECTION_RTL:
|
|
- return GTK_TEXT_DIR_RTL;
|
|
- case NS_STYLE_DIRECTION_LTR:
|
|
- return GTK_TEXT_DIR_LTR;
|
|
- }
|
|
-
|
|
- return GTK_TEXT_DIR_NONE;
|
|
+ // IsFrameRTL() treats vertical-rl modes as right-to-left (in addition to
|
|
+ // horizontal text with direction=RTL), rather than just considering the
|
|
+ // text direction. GtkTextDirection does not have distinct values for
|
|
+ // vertical writing modes, but considering the block flow direction is
|
|
+ // important for resizers and scrollbar elements, at least.
|
|
+ return IsFrameRTL(aFrame) ? GTK_TEXT_DIR_RTL : GTK_TEXT_DIR_LTR;
|
|
}
|
|
|
|
// Returns positive for negative margins (otherwise 0).
|
|
@@ -429,6 +425,20 @@ nsNativeThemeGTK::GetGtkWidgetAndState(u
|
|
else
|
|
*aWidgetFlags = 0;
|
|
break;
|
|
+ case NS_THEME_SCROLLBARTRACK_HORIZONTAL:
|
|
+ if (gtk_check_version(3,20,0) == nullptr) {
|
|
+ aGtkWidgetType = MOZ_GTK_SCROLLBAR_TROUGH_HORIZONTAL;
|
|
+ } else {
|
|
+ return false;
|
|
+ }
|
|
+ break;
|
|
+ case NS_THEME_SCROLLBARTRACK_VERTICAL:
|
|
+ if (gtk_check_version(3,20,0) == nullptr) {
|
|
+ aGtkWidgetType = MOZ_GTK_SCROLLBAR_TROUGH_VERTICAL;
|
|
+ } else {
|
|
+ return false;
|
|
+ }
|
|
+ break;
|
|
case NS_THEME_SCROLLBARTHUMB_VERTICAL:
|
|
aGtkWidgetType = MOZ_GTK_SCROLLBAR_THUMB_VERTICAL;
|
|
break;
|
|
@@ -1105,14 +1115,7 @@ nsNativeThemeGTK::DrawWidgetBackground(n
|
|
{
|
|
GtkWidgetState state;
|
|
WidgetNodeType gtkWidgetType;
|
|
- // For resizer drawing, we want IsFrameRTL, which treats vertical-rl modes
|
|
- // as right-to-left (in addition to horizontal text with direction=RTL),
|
|
- // rather than just considering the text direction.
|
|
- // This will make resizers on vertically-oriented elements render properly.
|
|
- GtkTextDirection direction =
|
|
- aWidgetType == NS_THEME_RESIZER
|
|
- ? (IsFrameRTL(aFrame) ? GTK_TEXT_DIR_RTL : GTK_TEXT_DIR_LTR)
|
|
- : GetTextDirection(aFrame);
|
|
+ GtkTextDirection direction = GetTextDirection(aFrame);
|
|
gint flags;
|
|
if (!GetGtkWidgetAndState(aWidgetType, aFrame, gtkWidgetType, &state,
|
|
&flags))
|
|
@@ -1248,6 +1251,21 @@ nsNativeThemeGTK::DrawWidgetBackground(n
|
|
return NS_OK;
|
|
}
|
|
|
|
+WidgetNodeType
|
|
+nsNativeThemeGTK::NativeThemeToGtkTheme(uint8_t aWidgetType, nsIFrame* aFrame)
|
|
+{
|
|
+ WidgetNodeType gtkWidgetType;
|
|
+ gint unusedFlags;
|
|
+
|
|
+ if (!GetGtkWidgetAndState(aWidgetType, aFrame, gtkWidgetType, nullptr,
|
|
+ &unusedFlags))
|
|
+ {
|
|
+ MOZ_ASSERT_UNREACHABLE("Unknown native widget to gtk widget mapping");
|
|
+ return MOZ_GTK_WINDOW;
|
|
+ }
|
|
+ return gtkWidgetType;
|
|
+}
|
|
+
|
|
NS_IMETHODIMP
|
|
nsNativeThemeGTK::GetWidgetBorder(nsDeviceContext* aContext, nsIFrame* aFrame,
|
|
uint8_t aWidgetType, nsIntMargin* aResult)
|
|
@@ -1255,24 +1273,6 @@ nsNativeThemeGTK::GetWidgetBorder(nsDevi
|
|
GtkTextDirection direction = GetTextDirection(aFrame);
|
|
aResult->top = aResult->left = aResult->right = aResult->bottom = 0;
|
|
switch (aWidgetType) {
|
|
- case NS_THEME_SCROLLBAR_VERTICAL:
|
|
- case NS_THEME_SCROLLBARTRACK_HORIZONTAL:
|
|
- {
|
|
- MozGtkScrollbarMetrics metrics;
|
|
- moz_gtk_get_scrollbar_metrics(&metrics);
|
|
- /* Top and bottom border for whole vertical scrollbar, top and bottom
|
|
- * border for horizontal track - to correctly position thumb element */
|
|
- aResult->top = aResult->bottom = metrics.trough_border;
|
|
- }
|
|
- break;
|
|
- case NS_THEME_SCROLLBAR_HORIZONTAL:
|
|
- case NS_THEME_SCROLLBARTRACK_VERTICAL:
|
|
- {
|
|
- MozGtkScrollbarMetrics metrics;
|
|
- moz_gtk_get_scrollbar_metrics(&metrics);
|
|
- aResult->left = aResult->right = metrics.trough_border;
|
|
- }
|
|
- break;
|
|
case NS_THEME_TOOLBOX:
|
|
// gtk has no toolbox equivalent. So, although we map toolbox to
|
|
// gtk's 'toolbar' for purposes of painting the widget background,
|
|
@@ -1312,8 +1312,9 @@ nsNativeThemeGTK::GetWidgetBorder(nsDevi
|
|
default:
|
|
{
|
|
WidgetNodeType gtkWidgetType;
|
|
+ gint unusedFlags;
|
|
if (GetGtkWidgetAndState(aWidgetType, aFrame, gtkWidgetType, nullptr,
|
|
- nullptr)) {
|
|
+ &unusedFlags)) {
|
|
moz_gtk_get_widget_border(gtkWidgetType, &aResult->left, &aResult->top,
|
|
&aResult->right, &aResult->bottom, direction,
|
|
IsFrameContentNodeInNamespace(aFrame, kNameSpaceID_XHTML));
|
|
@@ -1426,22 +1427,33 @@ nsNativeThemeGTK::GetMinimumWidgetSize(n
|
|
case NS_THEME_SCROLLBARBUTTON_UP:
|
|
case NS_THEME_SCROLLBARBUTTON_DOWN:
|
|
{
|
|
- MozGtkScrollbarMetrics metrics;
|
|
- moz_gtk_get_scrollbar_metrics(&metrics);
|
|
+ if (gtk_check_version(3,20,0) == nullptr) {
|
|
+ moz_gtk_get_widget_min_size(MOZ_GTK_SCROLLBAR_BUTTON,
|
|
+ &(aResult->width), &(aResult->height));
|
|
+ } else {
|
|
+ MozGtkScrollbarMetrics metrics;
|
|
+ moz_gtk_get_scrollbar_metrics(&metrics);
|
|
+
|
|
+ aResult->width = metrics.slider_width;
|
|
+ aResult->height = metrics.stepper_size;
|
|
+ }
|
|
|
|
- aResult->width = metrics.slider_width;
|
|
- aResult->height = metrics.stepper_size;
|
|
*aIsOverridable = false;
|
|
}
|
|
break;
|
|
case NS_THEME_SCROLLBARBUTTON_LEFT:
|
|
case NS_THEME_SCROLLBARBUTTON_RIGHT:
|
|
{
|
|
- MozGtkScrollbarMetrics metrics;
|
|
- moz_gtk_get_scrollbar_metrics(&metrics);
|
|
+ if (gtk_check_version(3,20,0) == nullptr) {
|
|
+ moz_gtk_get_widget_min_size(MOZ_GTK_SCROLLBAR_BUTTON,
|
|
+ &(aResult->width), &(aResult->height));
|
|
+ } else {
|
|
+ MozGtkScrollbarMetrics metrics;
|
|
+ moz_gtk_get_scrollbar_metrics(&metrics);
|
|
|
|
- aResult->width = metrics.stepper_size;
|
|
- aResult->height = metrics.slider_width;
|
|
+ aResult->width = metrics.stepper_size;
|
|
+ aResult->height = metrics.slider_width;
|
|
+ }
|
|
*aIsOverridable = false;
|
|
}
|
|
break;
|
|
@@ -1468,39 +1480,65 @@ nsNativeThemeGTK::GetMinimumWidgetSize(n
|
|
* the thumb isn't a direct child of the scrollbar, unlike the buttons
|
|
* or track. So add a minimum size to the track as well to prevent a
|
|
* 0-width scrollbar. */
|
|
- MozGtkScrollbarMetrics metrics;
|
|
- moz_gtk_get_scrollbar_metrics(&metrics);
|
|
+ if (gtk_check_version(3,20,0) == nullptr) {
|
|
+ // Thumb min dimensions to start with
|
|
+ WidgetNodeType thumbType = aWidgetType == NS_THEME_SCROLLBAR_VERTICAL ?
|
|
+ MOZ_GTK_SCROLLBAR_THUMB_VERTICAL : MOZ_GTK_SCROLLBAR_THUMB_HORIZONTAL;
|
|
+ moz_gtk_get_widget_min_size(thumbType, &(aResult->width), &(aResult->height));
|
|
+
|
|
+ // Add scrollbar's borders
|
|
+ nsIntMargin border;
|
|
+ nsNativeThemeGTK::GetWidgetBorder(aFrame->PresContext()->DeviceContext(),
|
|
+ aFrame, aWidgetType, &border);
|
|
+ aResult->width += border.left + border.right;
|
|
+ aResult->height += border.top + border.bottom;
|
|
+
|
|
+ // Add track's borders
|
|
+ uint8_t trackType = aWidgetType == NS_THEME_SCROLLBAR_VERTICAL ?
|
|
+ NS_THEME_SCROLLBARTRACK_VERTICAL : NS_THEME_SCROLLBARTRACK_HORIZONTAL;
|
|
+ nsNativeThemeGTK::GetWidgetBorder(aFrame->PresContext()->DeviceContext(),
|
|
+ aFrame, trackType, &border);
|
|
+ aResult->width += border.left + border.right;
|
|
+ aResult->height += border.top + border.bottom;
|
|
+ } else {
|
|
+ MozGtkScrollbarMetrics metrics;
|
|
+ moz_gtk_get_scrollbar_metrics(&metrics);
|
|
|
|
- // Require room for the slider in the track if we don't have buttons.
|
|
- bool hasScrollbarButtons = moz_gtk_has_scrollbar_buttons();
|
|
+ // Require room for the slider in the track if we don't have buttons.
|
|
+ bool hasScrollbarButtons = moz_gtk_has_scrollbar_buttons();
|
|
|
|
- if (aWidgetType == NS_THEME_SCROLLBAR_VERTICAL) {
|
|
- aResult->width = metrics.slider_width + 2 * metrics.trough_border;
|
|
- if (!hasScrollbarButtons)
|
|
- aResult->height = metrics.min_slider_size + 2 * metrics.trough_border;
|
|
- } else {
|
|
- aResult->height = metrics.slider_width + 2 * metrics.trough_border;
|
|
- if (!hasScrollbarButtons)
|
|
- aResult->width = metrics.min_slider_size + 2 * metrics.trough_border;
|
|
+ if (aWidgetType == NS_THEME_SCROLLBAR_VERTICAL) {
|
|
+ aResult->width = metrics.slider_width + 2 * metrics.trough_border;
|
|
+ if (!hasScrollbarButtons)
|
|
+ aResult->height = metrics.min_slider_size + 2 * metrics.trough_border;
|
|
+ } else {
|
|
+ aResult->height = metrics.slider_width + 2 * metrics.trough_border;
|
|
+ if (!hasScrollbarButtons)
|
|
+ aResult->width = metrics.min_slider_size + 2 * metrics.trough_border;
|
|
+ }
|
|
+ *aIsOverridable = false;
|
|
}
|
|
|
|
- *aIsOverridable = false;
|
|
}
|
|
break;
|
|
case NS_THEME_SCROLLBARTHUMB_VERTICAL:
|
|
case NS_THEME_SCROLLBARTHUMB_HORIZONTAL:
|
|
{
|
|
- MozGtkScrollbarMetrics metrics;
|
|
- moz_gtk_get_scrollbar_metrics(&metrics);
|
|
-
|
|
- if (aWidgetType == NS_THEME_SCROLLBARTHUMB_VERTICAL) {
|
|
- aResult->width = metrics.slider_width;
|
|
- aResult->height = metrics.min_slider_size;
|
|
+ if (gtk_check_version(3,20,0) == nullptr) {
|
|
+ moz_gtk_get_widget_min_size(NativeThemeToGtkTheme(aWidgetType, aFrame),
|
|
+ &(aResult->width), &(aResult->height));
|
|
} else {
|
|
- aResult->height = metrics.slider_width;
|
|
- aResult->width = metrics.min_slider_size;
|
|
- }
|
|
+ MozGtkScrollbarMetrics metrics;
|
|
+ moz_gtk_get_scrollbar_metrics(&metrics);
|
|
|
|
+ if (aWidgetType == NS_THEME_SCROLLBARTHUMB_VERTICAL) {
|
|
+ aResult->width = metrics.slider_width;
|
|
+ aResult->height = metrics.min_slider_size;
|
|
+ } else {
|
|
+ aResult->height = metrics.slider_width;
|
|
+ aResult->width = metrics.min_slider_size;
|
|
+ }
|
|
+ }
|
|
*aIsOverridable = false;
|
|
}
|
|
break;
|
|
diff -up firefox-51.0/widget/gtk/nsNativeThemeGTK.h.old firefox-51.0/widget/gtk/nsNativeThemeGTK.h
|
|
--- firefox-51.0/widget/gtk/nsNativeThemeGTK.h.old 2016-07-25 22:22:07.000000000 +0200
|
|
+++ firefox-51.0/widget/gtk/nsNativeThemeGTK.h 2016-10-27 16:22:27.000000000 +0200
|
|
@@ -74,6 +74,7 @@ protected:
|
|
virtual ~nsNativeThemeGTK();
|
|
|
|
private:
|
|
+ GtkTextDirection GetTextDirection(nsIFrame* aFrame);
|
|
gint GetTabMarginPixels(nsIFrame* aFrame);
|
|
bool GetGtkWidgetAndState(uint8_t aWidgetType, nsIFrame* aFrame,
|
|
WidgetNodeType& aGtkWidgetType,
|
|
@@ -82,6 +83,7 @@ private:
|
|
nsIntMargin* aExtra);
|
|
|
|
void RefreshWidgetWindow(nsIFrame* aFrame);
|
|
+ WidgetNodeType NativeThemeToGtkTheme(uint8_t aWidgetType, nsIFrame* aFrame);
|
|
|
|
uint8_t mDisabledWidgetTypes[32];
|
|
uint8_t mSafeWidgetStates[1024]; // 256 widgets * 32 bits per widget
|
|
diff -up firefox-51.0/widget/gtk/WidgetStyleCache.cpp.old firefox-51.0/widget/gtk/WidgetStyleCache.cpp
|
|
--- firefox-51.0/widget/gtk/WidgetStyleCache.cpp.old 2017-01-16 17:16:53.000000000 +0100
|
|
+++ firefox-51.0/widget/gtk/WidgetStyleCache.cpp 2017-01-06 10:20:43.000000000 +0100
|
|
@@ -33,7 +33,6 @@ static GtkWidget*
|
|
CreateWindowWidget()
|
|
{
|
|
GtkWidget *widget = gtk_window_new(GTK_WINDOW_POPUP);
|
|
- gtk_widget_realize(widget);
|
|
gtk_widget_set_name(widget, "MozillaGtkWidget");
|
|
return widget;
|
|
}
|
|
@@ -50,7 +49,6 @@ static void
|
|
AddToWindowContainer(GtkWidget* widget)
|
|
{
|
|
gtk_container_add(GTK_CONTAINER(GetWidget(MOZ_GTK_WINDOW_CONTAINER)), widget);
|
|
- gtk_widget_realize(widget);
|
|
}
|
|
|
|
static GtkWidget*
|
|
@@ -142,7 +140,6 @@ CreateToolbarWidget()
|
|
{
|
|
GtkWidget* widget = gtk_toolbar_new();
|
|
gtk_container_add(GTK_CONTAINER(GetWidget(MOZ_GTK_GRIPPER)), widget);
|
|
- gtk_widget_realize(widget);
|
|
return widget;
|
|
}
|
|
|
|
@@ -183,7 +180,6 @@ CreateButtonArrowWidget()
|
|
{
|
|
GtkWidget* widget = gtk_arrow_new(GTK_ARROW_DOWN, GTK_SHADOW_OUT);
|
|
gtk_container_add(GTK_CONTAINER(GetWidget(MOZ_GTK_TOGGLE_BUTTON)), widget);
|
|
- gtk_widget_realize(widget);
|
|
gtk_widget_show(widget);
|
|
return widget;
|
|
}
|
|
@@ -205,19 +201,235 @@ CreateEntryWidget()
|
|
}
|
|
|
|
static GtkWidget*
|
|
-CreateScrolledWindowWidget()
|
|
+CreateComboBoxWidget()
|
|
{
|
|
- GtkWidget* widget = gtk_scrolled_window_new(nullptr, nullptr);
|
|
+ GtkWidget* widget = gtk_combo_box_new();
|
|
AddToWindowContainer(widget);
|
|
return widget;
|
|
}
|
|
|
|
+typedef struct
|
|
+{
|
|
+ GType type;
|
|
+ GtkWidget** widget;
|
|
+} GtkInnerWidgetInfo;
|
|
+
|
|
+static void
|
|
+GetInnerWidget(GtkWidget* widget, gpointer client_data)
|
|
+{
|
|
+ auto info = static_cast<GtkInnerWidgetInfo*>(client_data);
|
|
+
|
|
+ if (G_TYPE_CHECK_INSTANCE_TYPE(widget, info->type)) {
|
|
+ *info->widget = widget;
|
|
+ }
|
|
+}
|
|
+
|
|
+static GtkWidget*
|
|
+CreateComboBoxButtonWidget()
|
|
+{
|
|
+ GtkWidget* comboBox = GetWidget(MOZ_GTK_COMBOBOX);
|
|
+ GtkWidget* comboBoxButton = nullptr;
|
|
+
|
|
+ /* Get its inner Button */
|
|
+ GtkInnerWidgetInfo info = { GTK_TYPE_TOGGLE_BUTTON,
|
|
+ &comboBoxButton };
|
|
+ gtk_container_forall(GTK_CONTAINER(comboBox),
|
|
+ GetInnerWidget, &info);
|
|
+
|
|
+ if (!comboBoxButton) {
|
|
+ /* Shouldn't be reached with current internal gtk implementation; we
|
|
+ * use a generic toggle button as last resort fallback to avoid
|
|
+ * crashing. */
|
|
+ comboBoxButton = GetWidget(MOZ_GTK_TOGGLE_BUTTON);
|
|
+ } else {
|
|
+ /* We need to have pointers to the inner widgets (button, separator, arrow)
|
|
+ * of the ComboBox to get the correct rendering from theme engines which
|
|
+ * special cases their look. Since the inner layout can change, we ask GTK
|
|
+ * to NULL our pointers when they are about to become invalid because the
|
|
+ * corresponding widgets don't exist anymore. It's the role of
|
|
+ * g_object_add_weak_pointer().
|
|
+ * Note that if we don't find the inner widgets (which shouldn't happen), we
|
|
+ * fallback to use generic "non-inner" widgets, and they don't need that kind
|
|
+ * of weak pointer since they are explicit children of gProtoLayout and as
|
|
+ * such GTK holds a strong reference to them. */
|
|
+ g_object_add_weak_pointer(G_OBJECT(comboBoxButton),
|
|
+ reinterpret_cast<gpointer *>(sWidgetStorage) +
|
|
+ MOZ_GTK_COMBOBOX_BUTTON);
|
|
+ }
|
|
+
|
|
+ return comboBoxButton;
|
|
+}
|
|
+
|
|
+static GtkWidget*
|
|
+CreateComboBoxArrowWidget()
|
|
+{
|
|
+ GtkWidget* comboBoxButton = GetWidget(MOZ_GTK_COMBOBOX_BUTTON);
|
|
+ GtkWidget* comboBoxArrow = nullptr;
|
|
+
|
|
+ /* Get the widgets inside the Button */
|
|
+ GtkWidget* buttonChild = gtk_bin_get_child(GTK_BIN(comboBoxButton));
|
|
+ if (GTK_IS_BOX(buttonChild)) {
|
|
+ /* appears-as-list = FALSE, cell-view = TRUE; the button
|
|
+ * contains an hbox. This hbox is there because the ComboBox
|
|
+ * needs to place a cell renderer, a separator, and an arrow in
|
|
+ * the button when appears-as-list is FALSE. */
|
|
+ GtkInnerWidgetInfo info = { GTK_TYPE_ARROW,
|
|
+ &comboBoxArrow };
|
|
+ gtk_container_forall(GTK_CONTAINER(buttonChild),
|
|
+ GetInnerWidget, &info);
|
|
+ } else if (GTK_IS_ARROW(buttonChild)) {
|
|
+ /* appears-as-list = TRUE, or cell-view = FALSE;
|
|
+ * the button only contains an arrow */
|
|
+ comboBoxArrow = buttonChild;
|
|
+ }
|
|
+
|
|
+ if (!comboBoxArrow) {
|
|
+ /* Shouldn't be reached with current internal gtk implementation;
|
|
+ * we gButtonArrowWidget as last resort fallback to avoid
|
|
+ * crashing. */
|
|
+ comboBoxArrow = GetWidget(MOZ_GTK_BUTTON_ARROW);
|
|
+ } else {
|
|
+ g_object_add_weak_pointer(G_OBJECT(comboBoxArrow),
|
|
+ reinterpret_cast<gpointer *>(sWidgetStorage) +
|
|
+ MOZ_GTK_COMBOBOX_ARROW);
|
|
+ }
|
|
+
|
|
+ return comboBoxArrow;
|
|
+}
|
|
+
|
|
+static GtkWidget*
|
|
+CreateComboBoxSeparatorWidget()
|
|
+{
|
|
+ // Ensure to search for separator only once as it can fail
|
|
+ // TODO - it won't initialize after ResetWidgetCache() call
|
|
+ static bool isMissingSeparator = false;
|
|
+ if (isMissingSeparator)
|
|
+ return nullptr;
|
|
+
|
|
+ /* Get the widgets inside the Button */
|
|
+ GtkWidget* comboBoxSeparator = nullptr;
|
|
+ GtkWidget* buttonChild =
|
|
+ gtk_bin_get_child(GTK_BIN(GetWidget(MOZ_GTK_COMBOBOX_BUTTON)));
|
|
+ if (GTK_IS_BOX(buttonChild)) {
|
|
+ /* appears-as-list = FALSE, cell-view = TRUE; the button
|
|
+ * contains an hbox. This hbox is there because the ComboBox
|
|
+ * needs to place a cell renderer, a separator, and an arrow in
|
|
+ * the button when appears-as-list is FALSE. */
|
|
+ GtkInnerWidgetInfo info = { GTK_TYPE_SEPARATOR,
|
|
+ &comboBoxSeparator };
|
|
+ gtk_container_forall(GTK_CONTAINER(buttonChild),
|
|
+ GetInnerWidget, &info);
|
|
+ }
|
|
+
|
|
+ if (comboBoxSeparator) {
|
|
+ g_object_add_weak_pointer(G_OBJECT(comboBoxSeparator),
|
|
+ reinterpret_cast<gpointer *>(sWidgetStorage) +
|
|
+ MOZ_GTK_COMBOBOX_SEPARATOR);
|
|
+ } else {
|
|
+ /* comboBoxSeparator may be NULL
|
|
+ * when "appears-as-list" = TRUE or "cell-view" = FALSE;
|
|
+ * if there is no separator, then we just won't paint it. */
|
|
+ isMissingSeparator = true;
|
|
+ }
|
|
+
|
|
+ return comboBoxSeparator;
|
|
+}
|
|
+
|
|
+static GtkWidget*
|
|
+CreateComboBoxEntryWidget()
|
|
+{
|
|
+ GtkWidget* widget = gtk_combo_box_new_with_entry();
|
|
+ AddToWindowContainer(widget);
|
|
+ return widget;
|
|
+}
|
|
+
|
|
+static GtkWidget*
|
|
+CreateComboBoxEntryTextareaWidget()
|
|
+{
|
|
+ GtkWidget* comboBoxTextarea = nullptr;
|
|
+
|
|
+ /* Get its inner Entry and Button */
|
|
+ GtkInnerWidgetInfo info = { GTK_TYPE_ENTRY,
|
|
+ &comboBoxTextarea };
|
|
+ gtk_container_forall(GTK_CONTAINER(GetWidget(MOZ_GTK_COMBOBOX_ENTRY)),
|
|
+ GetInnerWidget, &info);
|
|
+
|
|
+ if (!comboBoxTextarea) {
|
|
+ comboBoxTextarea = GetWidget(MOZ_GTK_ENTRY);
|
|
+ } else {
|
|
+ g_object_add_weak_pointer(G_OBJECT(comboBoxTextarea),
|
|
+ reinterpret_cast<gpointer *>(sWidgetStorage) +
|
|
+ MOZ_GTK_COMBOBOX_ENTRY);
|
|
+ }
|
|
+
|
|
+ return comboBoxTextarea;
|
|
+}
|
|
+
|
|
+static GtkWidget*
|
|
+CreateComboBoxEntryButtonWidget()
|
|
+{
|
|
+ GtkWidget* comboBoxButton = nullptr;
|
|
+
|
|
+ /* Get its inner Entry and Button */
|
|
+ GtkInnerWidgetInfo info = { GTK_TYPE_TOGGLE_BUTTON,
|
|
+ &comboBoxButton };
|
|
+ gtk_container_forall(GTK_CONTAINER(GetWidget(MOZ_GTK_COMBOBOX_ENTRY)),
|
|
+ GetInnerWidget, &info);
|
|
+
|
|
+ if (!comboBoxButton) {
|
|
+ comboBoxButton = GetWidget(MOZ_GTK_TOGGLE_BUTTON);
|
|
+ } else {
|
|
+ g_object_add_weak_pointer(G_OBJECT(comboBoxButton),
|
|
+ reinterpret_cast<gpointer *>(sWidgetStorage) +
|
|
+ MOZ_GTK_COMBOBOX_ENTRY_BUTTON);
|
|
+ }
|
|
+
|
|
+ return comboBoxButton;
|
|
+}
|
|
+
|
|
static GtkWidget*
|
|
-CreateTextViewWidget()
|
|
+CreateComboBoxEntryArrowWidget()
|
|
{
|
|
- GtkWidget* widget = gtk_text_view_new();
|
|
- gtk_container_add(GTK_CONTAINER(GetWidget(MOZ_GTK_SCROLLED_WINDOW)),
|
|
- widget);
|
|
+ GtkWidget* comboBoxArrow = nullptr;
|
|
+
|
|
+ /* Get the Arrow inside the Button */
|
|
+ GtkWidget* buttonChild =
|
|
+ gtk_bin_get_child(GTK_BIN(GetWidget(MOZ_GTK_COMBOBOX_ENTRY_BUTTON)));
|
|
+
|
|
+ if (GTK_IS_BOX(buttonChild)) {
|
|
+ /* appears-as-list = FALSE, cell-view = TRUE; the button
|
|
+ * contains an hbox. This hbox is there because the ComboBox
|
|
+ * needs to place a cell renderer, a separator, and an arrow in
|
|
+ * the button when appears-as-list is FALSE. */
|
|
+ GtkInnerWidgetInfo info = { GTK_TYPE_ARROW,
|
|
+ &comboBoxArrow };
|
|
+ gtk_container_forall(GTK_CONTAINER(buttonChild),
|
|
+ GetInnerWidget, &info);
|
|
+ } else if (GTK_IS_ARROW(buttonChild)) {
|
|
+ /* appears-as-list = TRUE, or cell-view = FALSE;
|
|
+ * the button only contains an arrow */
|
|
+ comboBoxArrow = buttonChild;
|
|
+ }
|
|
+
|
|
+ if (!comboBoxArrow) {
|
|
+ /* Shouldn't be reached with current internal gtk implementation;
|
|
+ * we gButtonArrowWidget as last resort fallback to avoid
|
|
+ * crashing. */
|
|
+ comboBoxArrow = GetWidget(MOZ_GTK_BUTTON_ARROW);
|
|
+ } else {
|
|
+ g_object_add_weak_pointer(G_OBJECT(comboBoxArrow),
|
|
+ reinterpret_cast<gpointer *>(sWidgetStorage) +
|
|
+ MOZ_GTK_COMBOBOX_ENTRY_ARROW);
|
|
+ }
|
|
+
|
|
+ return comboBoxArrow;
|
|
+}
|
|
+
|
|
+static GtkWidget*
|
|
+CreateScrolledWindowWidget()
|
|
+{
|
|
+ GtkWidget* widget = gtk_scrolled_window_new(nullptr, nullptr);
|
|
+ AddToWindowContainer(widget);
|
|
return widget;
|
|
}
|
|
|
|
@@ -227,7 +439,6 @@ CreateMenuSeparatorWidget()
|
|
GtkWidget* widget = gtk_separator_menu_item_new();
|
|
gtk_menu_shell_append(GTK_MENU_SHELL(GetWidget(MOZ_GTK_MENUPOPUP)),
|
|
widget);
|
|
- gtk_widget_realize(widget);
|
|
return widget;
|
|
}
|
|
|
|
@@ -306,15 +517,6 @@ CreateVPanedWidget()
|
|
}
|
|
|
|
static GtkWidget*
|
|
-CreateImageMenuItemWidget()
|
|
-{
|
|
- GtkWidget* widget = gtk_image_menu_item_new();
|
|
- gtk_menu_shell_append(GTK_MENU_SHELL(GetWidget(MOZ_GTK_MENUPOPUP)), widget);
|
|
- gtk_widget_realize(widget);
|
|
- return widget;
|
|
-}
|
|
-
|
|
-static GtkWidget*
|
|
CreateScaleWidget(GtkOrientation aOrientation)
|
|
{
|
|
GtkWidget* widget = gtk_scale_new(aOrientation, nullptr);
|
|
@@ -380,8 +582,6 @@ CreateWidget(WidgetNodeType aWidgetType)
|
|
return CreateEntryWidget();
|
|
case MOZ_GTK_SCROLLED_WINDOW:
|
|
return CreateScrolledWindowWidget();
|
|
- case MOZ_GTK_TEXT_VIEW:
|
|
- return CreateTextViewWidget();
|
|
case MOZ_GTK_TREEVIEW:
|
|
return CreateTreeViewWidget();
|
|
case MOZ_GTK_TREE_HEADER_CELL:
|
|
@@ -392,14 +592,28 @@ CreateWidget(WidgetNodeType aWidgetType)
|
|
return CreateHPanedWidget();
|
|
case MOZ_GTK_SPLITTER_VERTICAL:
|
|
return CreateVPanedWidget();
|
|
- case MOZ_GTK_IMAGEMENUITEM:
|
|
- return CreateImageMenuItemWidget();
|
|
case MOZ_GTK_SCALE_HORIZONTAL:
|
|
return CreateScaleWidget(GTK_ORIENTATION_HORIZONTAL);
|
|
case MOZ_GTK_SCALE_VERTICAL:
|
|
return CreateScaleWidget(GTK_ORIENTATION_VERTICAL);
|
|
case MOZ_GTK_NOTEBOOK:
|
|
return CreateNotebookWidget();
|
|
+ case MOZ_GTK_COMBOBOX:
|
|
+ return CreateComboBoxWidget();
|
|
+ case MOZ_GTK_COMBOBOX_BUTTON:
|
|
+ return CreateComboBoxButtonWidget();
|
|
+ case MOZ_GTK_COMBOBOX_ARROW:
|
|
+ return CreateComboBoxArrowWidget();
|
|
+ case MOZ_GTK_COMBOBOX_SEPARATOR:
|
|
+ return CreateComboBoxSeparatorWidget();
|
|
+ case MOZ_GTK_COMBOBOX_ENTRY:
|
|
+ return CreateComboBoxEntryWidget();
|
|
+ case MOZ_GTK_COMBOBOX_ENTRY_TEXTAREA:
|
|
+ return CreateComboBoxEntryTextareaWidget();
|
|
+ case MOZ_GTK_COMBOBOX_ENTRY_BUTTON:
|
|
+ return CreateComboBoxEntryButtonWidget();
|
|
+ case MOZ_GTK_COMBOBOX_ENTRY_ARROW:
|
|
+ return CreateComboBoxEntryArrowWidget();
|
|
default:
|
|
/* Not implemented */
|
|
return nullptr;
|
|
@@ -474,9 +688,20 @@ CreateCSSNode(const char* aName, GtkStyl
|
|
reinterpret_cast<void (*)(GtkWidgetPath *, gint, const char *)>
|
|
(dlsym(RTLD_DEFAULT, "gtk_widget_path_iter_set_object_name"));
|
|
|
|
- GtkWidgetPath* path = aParentStyle ?
|
|
- gtk_widget_path_copy(gtk_style_context_get_path(aParentStyle)) :
|
|
- gtk_widget_path_new();
|
|
+ GtkWidgetPath* path;
|
|
+ if (aParentStyle) {
|
|
+ path = gtk_widget_path_copy(gtk_style_context_get_path(aParentStyle));
|
|
+ // Copy classes from the parent style context to its corresponding node in
|
|
+ // the path, because GTK will only match against ancestor classes if they
|
|
+ // are on the path.
|
|
+ GList* classes = gtk_style_context_list_classes(aParentStyle);
|
|
+ for (GList* link = classes; link; link = link->next) {
|
|
+ gtk_widget_path_iter_add_class(path, -1, static_cast<gchar*>(link->data));
|
|
+ }
|
|
+ g_list_free(classes);
|
|
+ } else {
|
|
+ path = gtk_widget_path_new();
|
|
+ }
|
|
|
|
gtk_widget_path_append_type(path, aType);
|
|
|
|
@@ -508,13 +733,38 @@ GetWidgetRootStyle(WidgetNodeType aNodeT
|
|
case MOZ_GTK_MENUITEM:
|
|
style = CreateStyleForWidget(gtk_menu_item_new(), MOZ_GTK_MENUPOPUP);
|
|
break;
|
|
- case MOZ_GTK_CHECKMENUITEM_CONTAINER:
|
|
+ case MOZ_GTK_CHECKMENUITEM:
|
|
style = CreateStyleForWidget(gtk_check_menu_item_new(), MOZ_GTK_MENUPOPUP);
|
|
break;
|
|
- case MOZ_GTK_RADIOMENUITEM_CONTAINER:
|
|
+ case MOZ_GTK_RADIOMENUITEM:
|
|
style = CreateStyleForWidget(gtk_radio_menu_item_new(nullptr),
|
|
MOZ_GTK_MENUPOPUP);
|
|
break;
|
|
+ case MOZ_GTK_TEXT_VIEW:
|
|
+ style = CreateStyleForWidget(gtk_text_view_new(),
|
|
+ MOZ_GTK_SCROLLED_WINDOW);
|
|
+ break;
|
|
+ case MOZ_GTK_TOOLTIP:
|
|
+ if (gtk_check_version(3, 20, 0) != nullptr) {
|
|
+ // The tooltip style class is added first in CreateTooltipWidget()
|
|
+ // and transfered to style in CreateStyleForWidget().
|
|
+ GtkWidget* tooltipWindow = CreateTooltipWidget();
|
|
+ style = CreateStyleForWidget(tooltipWindow, nullptr);
|
|
+ gtk_widget_destroy(tooltipWindow); // Release GtkWindow self-reference.
|
|
+ } else {
|
|
+ // We create this from the path because GtkTooltipWindow is not public.
|
|
+ style = CreateCSSNode("tooltip", nullptr, GTK_TYPE_TOOLTIP);
|
|
+ gtk_style_context_add_class(style, GTK_STYLE_CLASS_BACKGROUND);
|
|
+ }
|
|
+ break;
|
|
+ case MOZ_GTK_TOOLTIP_BOX:
|
|
+ style = CreateStyleForWidget(gtk_box_new(GTK_ORIENTATION_HORIZONTAL, 0),
|
|
+ MOZ_GTK_TOOLTIP);
|
|
+ break;
|
|
+ case MOZ_GTK_TOOLTIP_BOX_LABEL:
|
|
+ style = CreateStyleForWidget(gtk_label_new(nullptr),
|
|
+ MOZ_GTK_TOOLTIP_BOX);
|
|
+ break;
|
|
default:
|
|
GtkWidget* widget = GetWidget(aNodeType);
|
|
MOZ_ASSERT(widget);
|
|
@@ -576,6 +826,10 @@ GetCssNodeStyleInternal(WidgetNodeType a
|
|
style = CreateChildCSSNode(GTK_STYLE_CLASS_SLIDER,
|
|
MOZ_GTK_SCROLLBAR_TROUGH_VERTICAL);
|
|
break;
|
|
+ case MOZ_GTK_SCROLLBAR_BUTTON:
|
|
+ style = CreateChildCSSNode(GTK_STYLE_CLASS_BUTTON,
|
|
+ MOZ_GTK_SCROLLBAR_CONTENTS_VERTICAL);
|
|
+ break;
|
|
case MOZ_GTK_RADIOBUTTON:
|
|
style = CreateChildCSSNode(GTK_STYLE_CLASS_RADIO,
|
|
MOZ_GTK_RADIOBUTTON_CONTAINER);
|
|
@@ -584,13 +838,13 @@ GetCssNodeStyleInternal(WidgetNodeType a
|
|
style = CreateChildCSSNode(GTK_STYLE_CLASS_CHECK,
|
|
MOZ_GTK_CHECKBUTTON_CONTAINER);
|
|
break;
|
|
- case MOZ_GTK_RADIOMENUITEM:
|
|
+ case MOZ_GTK_RADIOMENUITEM_INDICATOR:
|
|
style = CreateChildCSSNode(GTK_STYLE_CLASS_RADIO,
|
|
- MOZ_GTK_RADIOMENUITEM_CONTAINER);
|
|
+ MOZ_GTK_RADIOMENUITEM);
|
|
break;
|
|
- case MOZ_GTK_CHECKMENUITEM:
|
|
+ case MOZ_GTK_CHECKMENUITEM_INDICATOR:
|
|
style = CreateChildCSSNode(GTK_STYLE_CLASS_CHECK,
|
|
- MOZ_GTK_CHECKMENUITEM_CONTAINER);
|
|
+ MOZ_GTK_CHECKMENUITEM);
|
|
break;
|
|
case MOZ_GTK_PROGRESS_TROUGH:
|
|
/* Progress bar background (trough) */
|
|
@@ -601,11 +855,6 @@ GetCssNodeStyleInternal(WidgetNodeType a
|
|
style = CreateChildCSSNode("progress",
|
|
MOZ_GTK_PROGRESS_TROUGH);
|
|
break;
|
|
- case MOZ_GTK_TOOLTIP:
|
|
- // We create this from the path because GtkTooltipWindow is not public.
|
|
- style = CreateCSSNode("tooltip", nullptr, GTK_TYPE_TOOLTIP);
|
|
- gtk_style_context_add_class(style, GTK_STYLE_CLASS_BACKGROUND);
|
|
- break;
|
|
case MOZ_GTK_GRIPPER:
|
|
// TODO - create from CSS node
|
|
return GetWidgetStyleWithClass(MOZ_GTK_GRIPPER,
|
|
@@ -622,10 +871,28 @@ GetCssNodeStyleInternal(WidgetNodeType a
|
|
// TODO - create from CSS node
|
|
return GetWidgetStyleWithClass(MOZ_GTK_SCROLLED_WINDOW,
|
|
GTK_STYLE_CLASS_FRAME);
|
|
- case MOZ_GTK_TEXT_VIEW:
|
|
- // TODO - create from CSS node
|
|
- return GetWidgetStyleWithClass(MOZ_GTK_TEXT_VIEW,
|
|
- GTK_STYLE_CLASS_VIEW);
|
|
+ case MOZ_GTK_TEXT_VIEW_TEXT:
|
|
+ case MOZ_GTK_RESIZER:
|
|
+ style = CreateChildCSSNode("text", MOZ_GTK_TEXT_VIEW);
|
|
+ if (aNodeType == MOZ_GTK_RESIZER) {
|
|
+ // The "grip" class provides the correct builtin icon from
|
|
+ // gtk_render_handle(). The icon is drawn with shaded variants of
|
|
+ // the background color, and so a transparent background would lead to
|
|
+ // a transparent resizer. gtk_render_handle() also uses the
|
|
+ // background color to draw a background, and so this style otherwise
|
|
+ // matches what is used in GtkTextView to match the background with
|
|
+ // textarea elements.
|
|
+ GdkRGBA color;
|
|
+ gtk_style_context_get_background_color(style, GTK_STATE_FLAG_NORMAL,
|
|
+ &color);
|
|
+ if (color.alpha == 0.0) {
|
|
+ g_object_unref(style);
|
|
+ style = CreateStyleForWidget(gtk_text_view_new(),
|
|
+ MOZ_GTK_SCROLLED_WINDOW);
|
|
+ }
|
|
+ gtk_style_context_add_class(style, GTK_STYLE_CLASS_GRIP);
|
|
+ }
|
|
+ break;
|
|
case MOZ_GTK_FRAME_BORDER:
|
|
style = CreateChildCSSNode("border", MOZ_GTK_FRAME);
|
|
break;
|
|
@@ -728,27 +995,20 @@ GetWidgetStyleInternal(WidgetNodeType aN
|
|
case MOZ_GTK_CHECKBUTTON:
|
|
return GetWidgetStyleWithClass(MOZ_GTK_CHECKBUTTON_CONTAINER,
|
|
GTK_STYLE_CLASS_CHECK);
|
|
- case MOZ_GTK_RADIOMENUITEM:
|
|
- return GetWidgetStyleWithClass(MOZ_GTK_RADIOMENUITEM_CONTAINER,
|
|
+ case MOZ_GTK_RADIOMENUITEM_INDICATOR:
|
|
+ return GetWidgetStyleWithClass(MOZ_GTK_RADIOMENUITEM,
|
|
GTK_STYLE_CLASS_RADIO);
|
|
- case MOZ_GTK_CHECKMENUITEM:
|
|
- return GetWidgetStyleWithClass(MOZ_GTK_CHECKMENUITEM_CONTAINER,
|
|
+ case MOZ_GTK_CHECKMENUITEM_INDICATOR:
|
|
+ return GetWidgetStyleWithClass(MOZ_GTK_CHECKMENUITEM,
|
|
GTK_STYLE_CLASS_CHECK);
|
|
case MOZ_GTK_PROGRESS_TROUGH:
|
|
return GetWidgetStyleWithClass(MOZ_GTK_PROGRESSBAR,
|
|
GTK_STYLE_CLASS_TROUGH);
|
|
- case MOZ_GTK_TOOLTIP: {
|
|
- GtkStyleContext* style = sStyleStorage[aNodeType];
|
|
- if (style)
|
|
- return style;
|
|
-
|
|
- // The tooltip style class is added first in CreateTooltipWidget() so
|
|
- // that gtk_widget_path_append_for_widget() in CreateStyleForWidget()
|
|
- // will find it.
|
|
- GtkWidget* tooltipWindow = CreateTooltipWidget();
|
|
- style = CreateStyleForWidget(tooltipWindow, nullptr);
|
|
- gtk_widget_destroy(tooltipWindow); // Release GtkWindow self-reference.
|
|
- sStyleStorage[aNodeType] = style;
|
|
+ case MOZ_GTK_PROGRESS_CHUNK: {
|
|
+ GtkStyleContext* style =
|
|
+ GetWidgetStyleWithClass(MOZ_GTK_PROGRESSBAR,
|
|
+ GTK_STYLE_CLASS_PROGRESSBAR);
|
|
+ gtk_style_context_remove_class(style, GTK_STYLE_CLASS_TROUGH);
|
|
return style;
|
|
}
|
|
case MOZ_GTK_GRIPPER:
|
|
@@ -763,9 +1023,25 @@ GetWidgetStyleInternal(WidgetNodeType aN
|
|
case MOZ_GTK_SCROLLED_WINDOW:
|
|
return GetWidgetStyleWithClass(MOZ_GTK_SCROLLED_WINDOW,
|
|
GTK_STYLE_CLASS_FRAME);
|
|
- case MOZ_GTK_TEXT_VIEW:
|
|
- return GetWidgetStyleWithClass(MOZ_GTK_TEXT_VIEW,
|
|
- GTK_STYLE_CLASS_VIEW);
|
|
+ case MOZ_GTK_TEXT_VIEW_TEXT:
|
|
+ case MOZ_GTK_RESIZER: {
|
|
+ // GTK versions prior to 3.20 do not have the view class on the root
|
|
+ // node, but add this to determine the background for the text window.
|
|
+ GtkStyleContext* style =
|
|
+ GetWidgetStyleWithClass(MOZ_GTK_TEXT_VIEW, GTK_STYLE_CLASS_VIEW);
|
|
+ if (aNodeType == MOZ_GTK_RESIZER) {
|
|
+ // The "grip" class provides the correct builtin icon from
|
|
+ // gtk_render_handle(). The icon is drawn with shaded variants of
|
|
+ // the background color, and so a transparent background would lead to
|
|
+ // a transparent resizer. gtk_render_handle() also uses the
|
|
+ // background color to draw a background, and so this style otherwise
|
|
+ // matches MOZ_GTK_TEXT_VIEW_TEXT to match the background with
|
|
+ // textarea elements. GtkTextView creates a separate text window and
|
|
+ // so the background should not be transparent.
|
|
+ gtk_style_context_add_class(style, GTK_STYLE_CLASS_GRIP);
|
|
+ }
|
|
+ return style;
|
|
+ }
|
|
case MOZ_GTK_FRAME_BORDER:
|
|
return GetWidgetRootStyle(MOZ_GTK_FRAME);
|
|
case MOZ_GTK_TREEVIEW_VIEW:
|