static void
mex_grid_view_allocate (ClutterActor           *actor,
                        const ClutterActorBox  *box,
                        ClutterAllocationFlags  flags)
{
  MexGridViewPrivate *priv = MEX_GRID_VIEW (actor)->priv;
  gfloat menu_min_width, menu_width, grid_width;
  ClutterActorBox child_box;

  CLUTTER_ACTOR_CLASS (mex_grid_view_parent_class)->allocate (actor, box,
                                                              flags);

  /* menu */
  clutter_actor_get_preferred_width (priv->menu_layout, -1, &menu_min_width,
                                     &menu_width);
  mx_widget_get_available_area (MX_WIDGET (actor), box, &child_box);
  child_box.x2 = child_box.x1 + MAX (MENU_MIN_WIDTH, menu_width);

  if (priv->state == STATE_CLOSING_STAGE2)
    clutter_actor_box_interpolate (&child_box, &priv->target_box,
                                   clutter_alpha_get_alpha (priv->alpha),
                                   &child_box);

  clutter_actor_allocate (priv->menu_layout, &child_box, flags);


  /* grid */
  mx_widget_get_available_area (MX_WIDGET (actor), box, &child_box);

  child_box.y1 += GRID_TOP_PADDING;
  child_box.x1 = child_box.x1 + MENU_MIN_WIDTH;

  grid_width = child_box.x2 - child_box.x1;

  if (priv->state == STATE_OPENING)
    child_box.x2 = child_box.x1 + grid_width * clutter_alpha_get_alpha (priv->alpha);
  else if (priv->state == STATE_CLOSING_STAGE1)
    child_box.x2 = child_box.x1 + grid_width * (1 - clutter_alpha_get_alpha (priv->alpha));
  else if (priv->state == STATE_CLOSED || priv->state == STATE_CLOSING_STAGE2)
    child_box.x2 = child_box.x1;
  clutter_actor_allocate (priv->grid_layout, &child_box, flags);
}
Exemple #2
0
static void
mex_info_bar_allocate (ClutterActor           *actor,
                       const ClutterActorBox  *box,
                       ClutterAllocationFlags  flags)
{
  ClutterActorBox child_box;
  MexInfoBarPrivate *priv = MEX_INFO_BAR (actor)->priv;

  CLUTTER_ACTOR_CLASS (mex_info_bar_parent_class)->
    allocate (actor, box, flags);

  mx_widget_get_available_area (MX_WIDGET (actor), box, &child_box);
  clutter_actor_allocate (priv->group, &child_box, flags);
}
static void
mex_media_controls_allocate (ClutterActor           *actor,
                             const ClutterActorBox  *box,
                             ClutterAllocationFlags  flags)
{
    ClutterActorBox child_box;
    MexMediaControlsPrivate *priv = MEX_MEDIA_CONTROLS (actor)->priv;

    CLUTTER_ACTOR_CLASS (mex_media_controls_parent_class)->
    allocate (actor, box, flags);

    mx_widget_get_available_area (MX_WIDGET (actor), box, &child_box);
    clutter_actor_allocate (priv->vbox, &child_box, flags);
}
Exemple #4
0
static void
mx_frame_allocate (ClutterActor          *self,
                   const ClutterActorBox *box,
                   ClutterAllocationFlags flags)
{
    MxFramePrivate *priv = ((MxFrame *) self)->priv;
    ClutterActorBox childbox;

    CLUTTER_ACTOR_CLASS (mx_frame_parent_class)->allocate (self, box, flags);

    if (priv->child)
    {
        mx_widget_get_available_area (MX_WIDGET (self), box, &childbox);
        clutter_actor_allocate (priv->child, &childbox, flags);
    }
}
static void
mex_clock_bin_allocate (ClutterActor           *actor,
                        const ClutterActorBox  *box,
                        ClutterAllocationFlags  flags)
{
  ClutterActorBox childbox;
  MexClockBinPrivate *priv = MEX_CLOCK_BIN (actor)->priv;

  CLUTTER_ACTOR_CLASS (mex_clock_bin_parent_class)->
    allocate (actor, box, flags);

  if (priv->child)
    {
      mx_widget_get_available_area (MX_WIDGET (actor), box, &childbox);
      clutter_actor_allocate (priv->child, &childbox, flags);
    }
}
Exemple #6
0
static void
mx_toggle_allocate (ClutterActor          *actor,
                    const ClutterActorBox *box,
                    ClutterAllocationFlags flags)
{
  MxTogglePrivate *priv = MX_TOGGLE (actor)->priv;
  ClutterActorBox handle_box, child_box;
  CoglHandle background;
  gfloat handle_w;
  gfloat toggle_pos;

  CLUTTER_ACTOR_CLASS (mx_toggle_parent_class)->allocate (actor, box, flags);

  mx_widget_get_available_area (MX_WIDGET (actor), box, &child_box);

  /* background-image don't get stretched, so adjust the child box so that the
   * handle appears in the correct place.
   */
  background = mx_widget_get_background_texture (MX_WIDGET (actor));
  if (background)
    {
      gfloat width;
      MxPadding padding;

      mx_widget_get_padding (MX_WIDGET (actor), &padding);
      width = cogl_texture_get_width (background);
      width -= padding.left + padding.right;

      child_box.x1 += (child_box.x2 - child_box.x1) / 2.f;
      child_box.x1 -= width / 2.f;
      child_box.x2 = child_box.x1 + width;
    }

  clutter_actor_get_preferred_width (priv->handle, -1, NULL, &handle_w);
  toggle_pos = child_box.x2 - handle_w - child_box.x1;
  priv->slide_length = toggle_pos;

  toggle_pos = toggle_pos * priv->position;

  handle_box.x1 = (gint) (child_box.x1 + toggle_pos);
  handle_box.y1 = child_box.y1;
  handle_box.x2 = handle_box.x1 + handle_w;
  handle_box.y2 = child_box.y2;

  clutter_actor_allocate (priv->handle, &handle_box, flags);
}
Exemple #7
0
static void
mx_toolbar_allocate (ClutterActor           *actor,
                     const ClutterActorBox  *box,
                     ClutterAllocationFlags  flags)
{
  MxToolbarPrivate *priv = MX_TOOLBAR (actor)->priv;
  ClutterActorBox childbox, avail;
  gfloat close_w;

  CLUTTER_ACTOR_CLASS (mx_toolbar_parent_class)->allocate (actor, box, flags);

  mx_widget_get_available_area (MX_WIDGET (actor), box, &avail);

  if (priv->close_button)
    {
      gfloat pref_h;

      clutter_actor_get_preferred_size (priv->close_button,
                                        NULL, NULL, &close_w, &pref_h);
      childbox.x1 = avail.x2 - close_w;
      childbox.y1 = avail.y1;
      childbox.x2 = avail.x2;
      childbox.y2 = avail.y2;

      clutter_actor_allocate (priv->close_button, &childbox, flags);
    }
  else
    {
      close_w = 0;
    }

  if (priv->child)
    {
      childbox.x1 = avail.x1;
      childbox.y1 = avail.y1;
      childbox.x2 = MAX (childbox.x1, avail.x2 - close_w - SPACING);
      childbox.y2 = MAX (childbox.y1, avail.y2);

      clutter_actor_allocate (priv->child, &childbox, flags);
    }
}
static void
mx_stack_allocate (ClutterActor           *actor,
                   const ClutterActorBox  *box,
                   ClutterAllocationFlags  flags)
{
  GList *c;
  ClutterActorBox avail_space;

  MxStackPrivate *priv = MX_STACK (actor)->priv;

  CLUTTER_ACTOR_CLASS (mx_stack_parent_class)->allocate (actor, box, flags);

  mx_widget_get_available_area (MX_WIDGET (actor), box, &avail_space);

  memcpy (&priv->allocation, box, sizeof (priv->allocation));

  for (c = priv->children; c; c = c->next)
    {
      gboolean x_fill, y_fill, fit, crop;
      MxAlign x_align, y_align;

      ClutterActor *child = c->data;
      ClutterActorBox child_box = avail_space;

      if (!CLUTTER_ACTOR_IS_VISIBLE (child))
        continue;

      clutter_container_child_get (CLUTTER_CONTAINER (actor),
                                   child,
                                   "x-fill", &x_fill,
                                   "y-fill", &y_fill,
                                   "x-align", &x_align,
                                   "y-align", &y_align,
                                   "fit", &fit,
                                   "crop", &crop,
                                   NULL);

      /* when "crop" is set, fit and fill properties are ignored */
      if (crop)
        {
          gfloat available_height, available_width;
          gfloat natural_width, natural_height;
          gfloat ratio_width, ratio_height, ratio_child;

          available_width  = avail_space.x2 - avail_space.x1;
          available_height = avail_space.y2 - avail_space.y1;

          clutter_actor_get_preferred_size (child,
                                            NULL, NULL,
                                            &natural_width,
                                            &natural_height);

          ratio_child = natural_width / natural_height;
          ratio_width = available_width / natural_width;
          ratio_height = available_height / natural_height;
          if (ratio_width > ratio_height)
            {
              natural_width = available_width;
              natural_height = natural_width / ratio_child;
            }
          else
            {
              natural_height = available_height;
              natural_width = ratio_child * natural_height;
            }

          child_box.x1 = (available_width - natural_width) / 2;
          child_box.y1 = (available_height - natural_height) / 2;
          child_box.x2 = natural_width;
          child_box.y2 = natural_height;

          clutter_actor_allocate (child, &child_box, flags);
          continue;
        }

      /* when "fit" is set, fill properties are ignored */
      if (fit)
        {
          gfloat available_height, available_width, width, height;
          gfloat min_width, natural_width, min_height, natural_height;
          ClutterRequestMode request_mode;

          available_height = avail_space.y2 - avail_space.y1;
          available_width  = avail_space.x2 - avail_space.x1;
          request_mode = clutter_actor_get_request_mode (child);

          if (request_mode == CLUTTER_REQUEST_HEIGHT_FOR_WIDTH)
            {
              clutter_actor_get_preferred_width (child, available_height,
                                                 &min_width,
                                                 &natural_width);
              width = CLAMP (natural_width, min_width, available_width);

              clutter_actor_get_preferred_height (child, width,
                                                  &min_height,
                                                  &natural_height);
              height = CLAMP (natural_height, min_height, available_height);
            }
          else
            {
              clutter_actor_get_preferred_height (child, available_width,
                                                  &min_height,
                                                  &natural_height);
              height = CLAMP (natural_height, min_height, available_height);

              clutter_actor_get_preferred_width (child, height,
                                                 &min_width,
                                                 &natural_width);
              width = CLAMP (natural_width, min_width, available_width);
            }

          child_box.x1 = 0;
          child_box.y1 = 0;

          switch (x_align)
            {
            case MX_ALIGN_START:
              break;
            case MX_ALIGN_MIDDLE:
              child_box.x1 += (gint)(available_width / 2 - width / 2);
              break;

            case MX_ALIGN_END:
              child_box.x1 = avail_space.x2 - width;
              break;
            }

          switch (y_align)
            {
            case MX_ALIGN_START:
              break;
            case MX_ALIGN_MIDDLE:
              child_box.y1 += (gint)(available_height / 2 - height / 2);
              break;

            case MX_ALIGN_END:
              child_box.y1 = avail_space.y2 - height;
              break;
            }

          child_box.x2 = child_box.x1 + width;
          child_box.y2 = child_box.y1 + height;

          clutter_actor_allocate (child, &child_box, flags);
          continue;
        }

      /* Adjust the available space when not filling, otherwise
       * actors that support width-for-height or height-for-width
       * allocation won't shrink correctly.
       */
      if (!x_fill)
        {
          gfloat width;

          clutter_actor_get_preferred_width (child, -1, NULL, &width);

          switch (x_align)
            {
            case MX_ALIGN_START:
              break;
            case MX_ALIGN_MIDDLE:
              child_box.x1 += (gint)((avail_space.x2 - avail_space.x1) / 2 -
                                     width / 2);
              break;

            case MX_ALIGN_END:
              child_box.x1 = avail_space.x2 - width;
              break;
            }

          child_box.x2 = child_box.x1 + width;
          if (child_box.x2 > avail_space.x2)
            child_box.x2 = avail_space.x2;
          if (child_box.x1 < avail_space.x1)
            child_box.x1 = avail_space.x1;
        }

      if (!y_fill)
        {
          gfloat height;

          clutter_actor_get_preferred_height (child, -1, NULL, &height);

          switch (y_align)
            {
            case MX_ALIGN_START:
              break;
            case MX_ALIGN_MIDDLE:
              child_box.y1 += (gint)((avail_space.y2 - avail_space.y1) / 2 -
                                     height / 2);
              break;

            case MX_ALIGN_END:
              child_box.y1 = avail_space.y2 - height;
              break;
            }

          child_box.y2 = child_box.y1 + height;
          if (child_box.y2 > avail_space.y2)
            child_box.y2 = avail_space.y2;
          if (child_box.y1 < avail_space.y1)
            child_box.y1 = avail_space.y1;
        }

      mx_allocate_align_fill (child,
                              &child_box,
                              x_align,
                              y_align,
                              x_fill,
                              y_fill);

      clutter_actor_allocate (child, &child_box, flags);
    }
}
static void
mx_label_allocate (ClutterActor          *actor,
                   const ClutterActorBox *box,
                   ClutterAllocationFlags flags)
{
  MxLabelPrivate *priv = MX_LABEL (actor)->priv;
  gboolean label_did_fade = priv->label_should_fade;

  ClutterActorClass *parent_class;
  ClutterActorBox child_box;
  gboolean x_fill, y_fill;
  gfloat avail_width;

  parent_class = CLUTTER_ACTOR_CLASS (mx_label_parent_class);
  parent_class->allocate (actor, box, flags);

  mx_widget_get_available_area (MX_WIDGET (actor), box, &child_box);
  avail_width = child_box.x2 - child_box.x1;

  /* The default behaviour of ClutterText is to align to the
   * top-left when it gets more space than is needed. Because
   * of this behaviour, if we're aligning to the left, we can
   * assign all our horizontal space to the label without
   * measuring it (i.e. x-fill), and the same applies for
   * aligning to the top and vertical space.
   */
  x_fill = (priv->x_align == MX_ALIGN_START) ? TRUE : FALSE;
  y_fill = (priv->y_align == MX_ALIGN_START) ? TRUE : FALSE;

  mx_allocate_align_fill (priv->label, &child_box, priv->x_align,
                          priv->y_align, x_fill, y_fill);

  priv->label_should_fade = FALSE;

  if (priv->fade_out)
    {
      /* If we're fading out, make sure the label has its full width
       * allocated. This ensures that the offscreen effect has the full
       * label inside its texture.
       */
      gfloat label_width;

      clutter_actor_get_preferred_width (priv->label, -1, NULL, &label_width);

      if (label_width > avail_width)
        {
          priv->label_should_fade = TRUE;
          child_box.x2 = child_box.x1 + label_width;
        }

      mx_fade_effect_set_bounds (MX_FADE_EFFECT (priv->fade_effect),
                                 0, 0, MIN (label_width, avail_width), 0);
    }

  /* Allocate the label */
  clutter_actor_allocate (priv->label, &child_box, flags);

  if (priv->show_tooltip)
    {
      PangoLayout *layout;
      const gchar *text;

      layout = clutter_text_get_layout (CLUTTER_TEXT (priv->label));

      if (pango_layout_is_ellipsized (layout))
        text = clutter_text_get_text (CLUTTER_TEXT (priv->label));
      else
        text = NULL;

      mx_widget_set_tooltip_text (MX_WIDGET (actor), text);
    }

  /* Animate in/out the faded end of the label */
  if (label_did_fade != priv->label_should_fade)
    {
      /* Begin/reverse the fading timeline when necessary */
      if (priv->label_should_fade)
        clutter_timeline_set_direction (priv->fade_timeline,
                                        CLUTTER_TIMELINE_FORWARD);
      else
        clutter_timeline_set_direction (priv->fade_timeline,
                                        CLUTTER_TIMELINE_BACKWARD);

      if (!clutter_timeline_is_playing (priv->fade_timeline))
        clutter_timeline_rewind (priv->fade_timeline);

      clutter_timeline_start (priv->fade_timeline);
    }
}