actor: Coalesce needs_[xy]_expand() into one method
[profile/ivi/clutter.git] / clutter / clutter-bin-layout.c
index 09dd897..f8245b1 100644 (file)
  *
  * <example id="example-clutter-bin-layout">
  *  <title>How to pack actors inside a BinLayout</title>
- *  <para>The following code shows how to build a composite actor with
- *  a texture and a background, and add controls overlayed on top. The
- *  background is set to fill the whole allocation, whilst the texture
- *  is centered; there is a control in the top right corner and a label
- *  in the bottom, filling out the whole allocated width.</para>
  *  <programlisting>
- *  ClutterLayoutManager *manager;
- *  ClutterActor *box;
- *
- *  /&ast; create the layout first &ast;/
- *  layout = clutter_bin_layout_new (CLUTTER_BIN_ALIGNMENT_CENTER,
- *                                   CLUTTER_BIN_ALIGNMENT_CENTER);
- *  box = clutter_box_new (layout); /&ast; then the container &ast;/
- *
- *  /&ast; we can use the layout object to add actors &ast;/
- *  clutter_bin_layout_add (CLUTTER_BIN_LAYOUT (layout), background,
- *                          CLUTTER_BIN_ALIGNMENT_FILL,
- *                          CLUTTER_BIN_ALIGNMENT_FILL);
- *  clutter_bin_layout_add (CLUTTER_BIN_LAYOUT (layout), icon,
- *                          CLUTTER_BIN_ALIGNMENT_CENTER,
- *                          CLUTTER_BIN_ALIGNMENT_CENTER);
- *
- *  /&ast; align to the bottom left &ast;/
- *  clutter_bin_layout_add (CLUTTER_BIN_LAYOUT (layout), label,
- *                          CLUTTER_BIN_ALIGNMENT_START,
- *                          CLUTTER_BIN_ALIGNMENT_END);
- *  /&ast; align to the top right &ast;/
- *  clutter_bin_layout_add (CLUTTER_BIN_LAYOUT (layout), button,
- *                          CLUTTER_BIN_ALIGNMENT_END,
- *                          CLUTTER_BIN_ALIGNMENT_START);
+ * <xi:include xmlns:xi="http://www.w3.org/2001/XInclude" parse="text" href="../../../../tests/interactive/test-bin-layout.c">
+ *   <xi:fallback>FIXME: MISSING XINCLUDE CONTENT</xi:fallback>
+ * </xi:include>
  *  </programlisting>
  * </example>
  *
 
 #define CLUTTER_DISABLE_DEPRECATION_WARNINGS
 #include "deprecated/clutter-container.h"
+#include "deprecated/clutter-bin-layout.h"
 
-#include "clutter-actor.h"
+#include "clutter-actor-private.h"
 #include "clutter-animatable.h"
-#include "clutter-bin-layout.h"
 #include "clutter-child-meta.h"
 #include "clutter-debug.h"
 #include "clutter-enum-types.h"
@@ -153,6 +127,8 @@ enum
 static GParamSpec *layer_props[PROP_LAYER_LAST] = { NULL, };
 static GParamSpec *bin_props[PROP_LAST] = { NULL, };
 
+GType clutter_bin_layer_get_type (void);
+
 G_DEFINE_TYPE (ClutterBinLayer,
                clutter_bin_layer,
                CLUTTER_TYPE_LAYOUT_META);
@@ -339,14 +315,14 @@ clutter_bin_layout_get_preferred_width (ClutterLayoutManager *manager,
                                         gfloat               *nat_width_p)
 {
   ClutterActor *actor = CLUTTER_ACTOR (container);
+  ClutterActorIter iter;
   ClutterActor *child;
   gfloat min_width, nat_width;
 
   min_width = nat_width = 0.0;
 
-  for (child = clutter_actor_get_first_child (actor);
-       child != NULL;
-       child = clutter_actor_get_next_sibling (child))
+  clutter_actor_iter_init (&iter, actor);
+  while (clutter_actor_iter_next (&iter, &child))
     {
       gfloat minimum, natural;
 
@@ -373,14 +349,14 @@ clutter_bin_layout_get_preferred_height (ClutterLayoutManager *manager,
                                          gfloat               *nat_height_p)
 {
   ClutterActor *actor = CLUTTER_ACTOR (container);
+  ClutterActorIter iter;
   ClutterActor *child;
   gfloat min_height, nat_height;
 
   min_height = nat_height = 0.0;
 
-  for (child = clutter_actor_get_first_child (actor);
-       child != NULL;
-       child = clutter_actor_get_next_sibling (child))
+  clutter_actor_iter_init (&iter, actor);
+  while (clutter_actor_iter_next (&iter, &child))
     {
       gfloat minimum, natural;
 
@@ -421,6 +397,27 @@ get_bin_alignment_factor (ClutterBinAlignment alignment)
   return 0.0;
 }
 
+static gdouble
+get_actor_align_factor (ClutterActorAlign alignment)
+{
+  switch (alignment)
+    {
+    case CLUTTER_ACTOR_ALIGN_CENTER:
+      return 0.5;
+
+    case CLUTTER_ACTOR_ALIGN_START:
+      return 0.0;
+
+    case CLUTTER_ACTOR_ALIGN_END:
+      return 1.0;
+
+    case CLUTTER_ACTOR_ALIGN_FILL:
+      return 0.0;
+    }
+
+  return 0.0;
+}
+
 static void
 clutter_bin_layout_allocate (ClutterLayoutManager   *manager,
                              ClutterContainer       *container,
@@ -430,15 +427,15 @@ clutter_bin_layout_allocate (ClutterLayoutManager   *manager,
   gfloat allocation_x, allocation_y;
   gfloat available_w, available_h;
   ClutterActor *actor, *child;
+  ClutterActorIter iter;
 
   clutter_actor_box_get_origin (allocation, &allocation_x, &allocation_y);
   clutter_actor_box_get_size (allocation, &available_w, &available_h);
 
   actor = CLUTTER_ACTOR (container);
 
-  for (child = clutter_actor_get_first_child (actor);
-       child != NULL;
-       child = clutter_actor_get_next_sibling (child))
+  clutter_actor_iter_init (&iter, actor);
+  while (clutter_actor_iter_next (&iter, &child))
     {
       ClutterLayoutMeta *meta;
       ClutterBinLayer *layer;
@@ -464,10 +461,33 @@ clutter_bin_layout_allocate (ClutterLayoutManager   *manager,
       child_alloc.x2 = available_w;
       child_alloc.y2 = available_h;
 
-      x_fill = (layer->x_align == CLUTTER_BIN_ALIGNMENT_FILL);
-      y_fill = (layer->y_align == CLUTTER_BIN_ALIGNMENT_FILL);
-      x_align = get_bin_alignment_factor (layer->x_align);
-      y_align = get_bin_alignment_factor (layer->y_align);
+      if (clutter_actor_needs_expand (child, CLUTTER_ORIENTATION_HORIZONTAL))
+        {
+          ClutterActorAlign align;
+
+          align = _clutter_actor_get_effective_x_align (child);
+          x_fill = align == CLUTTER_ACTOR_ALIGN_FILL;
+          x_align = get_actor_align_factor (align);
+        }
+      else
+        {
+          x_fill = (layer->x_align == CLUTTER_BIN_ALIGNMENT_FILL);
+          x_align = get_bin_alignment_factor (layer->x_align);
+        }
+
+      if (clutter_actor_needs_expand (child, CLUTTER_ORIENTATION_VERTICAL))
+        {
+          ClutterActorAlign align;
+
+          align = clutter_actor_get_y_align (child);
+          y_fill = align == CLUTTER_ACTOR_ALIGN_FILL;
+          y_align = get_actor_align_factor (align);
+        }
+      else
+        {
+          y_fill = (layer->y_align == CLUTTER_BIN_ALIGNMENT_FILL);
+          y_align = get_bin_alignment_factor (layer->y_align);
+        }
 
       clutter_actor_allocate_align_fill (child, &child_alloc,
                                          x_align, y_align,
@@ -580,6 +600,9 @@ clutter_bin_layout_class_init (ClutterBinLayoutClass *klass)
    * by the #ClutterBinLayout
    *
    * Since: 1.2
+   *
+   * Deprecated: 1.12: Use the #ClutterActor:x-expand and the
+   *   #ClutterActor:x-align properties on #ClutterActor instead.
    */
   bin_props[PROP_X_ALIGN] =
     g_param_spec_enum ("x-align",
@@ -597,6 +620,9 @@ clutter_bin_layout_class_init (ClutterBinLayoutClass *klass)
    * by the #ClutterBinLayout
    *
    * Since: 1.2
+   *
+   * Deprecated: 1.12: Use the #ClutterActor:y-expand and the
+   *   #ClutterActor:y-align properties on #ClutterActor instead.
    */
   bin_props[PROP_Y_ALIGN] =
     g_param_spec_enum ("y-align",
@@ -609,22 +635,14 @@ clutter_bin_layout_class_init (ClutterBinLayoutClass *klass)
 
   gobject_class->set_property = clutter_bin_layout_set_property;
   gobject_class->get_property = clutter_bin_layout_get_property;
-  g_object_class_install_properties (gobject_class,
-                                     PROP_LAST,
-                                     bin_props);
-
-  layout_class->get_preferred_width =
-    clutter_bin_layout_get_preferred_width;
-  layout_class->get_preferred_height =
-    clutter_bin_layout_get_preferred_height;
-  layout_class->allocate =
-    clutter_bin_layout_allocate;
-  layout_class->create_child_meta =
-    clutter_bin_layout_create_child_meta;
-  layout_class->get_child_meta_type =
-    clutter_bin_layout_get_child_meta_type;
-  layout_class->set_container =
-    clutter_bin_layout_set_container;
+  g_object_class_install_properties (gobject_class, PROP_LAST, bin_props);
+
+  layout_class->get_preferred_width = clutter_bin_layout_get_preferred_width;
+  layout_class->get_preferred_height = clutter_bin_layout_get_preferred_height;
+  layout_class->allocate = clutter_bin_layout_allocate;
+  layout_class->create_child_meta = clutter_bin_layout_create_child_meta;
+  layout_class->get_child_meta_type = clutter_bin_layout_get_child_meta_type;
+  layout_class->set_container = clutter_bin_layout_set_container;
 }
 
 static void
@@ -675,6 +693,9 @@ clutter_bin_layout_new (ClutterBinAlignment x_align,
  * be set as the default alignment policies
  *
  * Since: 1.2
+ *
+ * Deprecated: 1.12: Use the #ClutterActor:x-align and
+ *   #ClutterActor:y-align properties of #ClutterActor instead.
  */
 void
 clutter_bin_layout_set_alignment (ClutterBinLayout    *self,
@@ -733,6 +754,9 @@ clutter_bin_layout_set_alignment (ClutterBinLayout    *self,
  * instead
  *
  * Since: 1.2
+ *
+ * Deprecated: 1.12: Use the #ClutterActor:x-align and the
+ *   #ClutterActor:y-align properties of #ClutterActor instead.
  */
 void
 clutter_bin_layout_get_alignment (ClutterBinLayout    *self,
@@ -799,6 +823,8 @@ clutter_bin_layout_get_alignment (ClutterBinLayout    *self,
  * #ClutterBinLayout
  *
  * Since: 1.2
+ *
+ * Deprecated: 1.12: Use clutter_actor_add_child() instead.
  */
 void
 clutter_bin_layout_add (ClutterBinLayout    *self,