+
+static void
+gtk_frame_get_preferred_size (GtkWidget *request,
+ GtkOrientation orientation,
+ gint *minimum_size,
+ gint *natural_size)
+{
+ GtkFrame *frame = GTK_FRAME (request);
+ GtkFramePrivate *priv = frame->priv;
+ GtkStyleContext *context;
+ GtkStateFlags state;
+ GtkBorder padding;
+ GtkWidget *widget = GTK_WIDGET (request);
+ GtkWidget *child;
+ GtkBin *bin = GTK_BIN (widget);
+ gint child_min, child_nat;
+ gint minimum, natural;
+ guint border_width;
+
+ context = gtk_widget_get_style_context (widget);
+ state = gtk_widget_get_state_flags (widget);
+
+ gtk_style_context_save (context);
+ gtk_style_context_add_class (context, GTK_STYLE_CLASS_FRAME);
+ gtk_style_context_get_padding (context, state, &padding);
+
+ if (priv->label_widget && gtk_widget_get_visible (priv->label_widget))
+ {
+ if (orientation == GTK_ORIENTATION_HORIZONTAL)
+ {
+ gtk_widget_get_preferred_width (priv->label_widget,
+ &child_min, &child_nat);
+ minimum = child_min + 2 * LABEL_PAD + 2 * LABEL_SIDE_PAD;
+ natural = child_nat + 2 * LABEL_PAD + 2 * LABEL_SIDE_PAD;
+ }
+ else
+ {
+ gtk_widget_get_preferred_height (priv->label_widget,
+ &child_min, &child_nat);
+ minimum = MAX (0, child_min - padding.top);
+ natural = MAX (0, child_nat - padding.top);
+ }
+ }
+ else
+ {
+ minimum = 0;
+ natural = 0;
+ }
+
+ child = gtk_bin_get_child (bin);
+ if (child && gtk_widget_get_visible (child))
+ {
+ if (orientation == GTK_ORIENTATION_HORIZONTAL)
+ {
+ gtk_widget_get_preferred_width (child,
+ &child_min, &child_nat);
+ minimum = MAX (minimum, child_min);
+ natural = MAX (natural, child_nat);
+ }
+ else
+ {
+ gtk_widget_get_preferred_height (child,
+ &child_min, &child_nat);
+ minimum += child_min;
+ natural += child_nat;
+ }
+ }
+
+ border_width = gtk_container_get_border_width (GTK_CONTAINER (widget));
+
+ if (orientation == GTK_ORIENTATION_HORIZONTAL)
+ {
+ minimum += (border_width * 2) + padding.left + padding.right;
+ natural += (border_width * 2) + padding.left + padding.right;
+ }
+ else
+ {
+ minimum += (border_width * 2) + padding.top + padding.bottom;
+ natural += (border_width * 2) + padding.top + padding.bottom;
+ }
+
+ if (minimum_size)
+ *minimum_size = minimum;
+
+ if (natural_size)
+ *natural_size = natural;
+
+ gtk_style_context_restore (context);
+}
+
+static void
+gtk_frame_get_preferred_width (GtkWidget *widget,
+ gint *minimum_size,
+ gint *natural_size)
+{
+ gtk_frame_get_preferred_size (widget, GTK_ORIENTATION_HORIZONTAL, minimum_size, natural_size);
+}
+
+static void
+gtk_frame_get_preferred_height (GtkWidget *widget,
+ gint *minimum_size,
+ gint *natural_size)
+{
+ gtk_frame_get_preferred_size (widget, GTK_ORIENTATION_VERTICAL, minimum_size, natural_size);
+}
+
+
+static void
+gtk_frame_get_preferred_height_for_width (GtkWidget *request,
+ gint width,
+ gint *minimum_height,
+ gint *natural_height)
+{
+ GtkWidget *widget = GTK_WIDGET (request);
+ GtkWidget *child;
+ GtkFrame *frame = GTK_FRAME (widget);
+ GtkFramePrivate *priv = frame->priv;
+ GtkBin *bin = GTK_BIN (widget);
+ GtkStyleContext *context;
+ GtkStateFlags state;
+ GtkBorder padding;
+ gint child_min, child_nat, label_width;
+ gint minimum, natural;
+ guint border_width;
+
+ context = gtk_widget_get_style_context (widget);
+ state = gtk_widget_get_state_flags (widget);
+
+ gtk_style_context_save (context);
+ gtk_style_context_add_class (context, GTK_STYLE_CLASS_FRAME);
+ gtk_style_context_get_padding (context, state, &padding);
+
+ border_width = gtk_container_get_border_width (GTK_CONTAINER (widget));
+ minimum = (border_width * 2) + padding.top + padding.bottom;
+ natural = (border_width * 2) + padding.top + padding.bottom;
+
+ width -= (border_width * 2) + padding.left + padding.right;
+ label_width = width - 2 * LABEL_PAD + 2 * LABEL_SIDE_PAD;
+
+ if (priv->label_widget && gtk_widget_get_visible (priv->label_widget))
+ {
+ gtk_widget_get_preferred_height_for_width (priv->label_widget,
+ label_width, &child_min, &child_nat);
+ minimum += child_min;
+ natural += child_nat;
+ }
+
+ child = gtk_bin_get_child (bin);
+ if (child && gtk_widget_get_visible (child))
+ {
+ gtk_widget_get_preferred_height_for_width (child,
+ width, &child_min, &child_nat);
+ minimum += child_min;
+ natural += child_nat;
+ }
+
+ if (minimum_height)
+ *minimum_height = minimum;
+
+ if (natural_height)
+ *natural_height = natural;
+
+ gtk_style_context_restore (context);
+}
+
+static void
+gtk_frame_get_preferred_width_for_height (GtkWidget *widget,
+ gint height,
+ gint *minimum_width,
+ gint *natural_width)
+{
+ GTK_WIDGET_GET_CLASS (widget)->get_preferred_width (widget, minimum_width, natural_width);
+}
+