Example #1
0
void
mex_player_set_idle_mode (MexPlayer *player,
                          gboolean   idle)
{
  MexPlayerPrivate *priv = player->priv;

  if (priv->idle_mode == idle)
    return;

  priv->idle_mode = idle;

  mex_player_set_controls_visible (player, !idle);

  if (idle)
    {
      gchar *tmp;

      clutter_actor_hide (priv->controls);
      clutter_actor_hide (priv->info_panel);
      mx_widget_set_disabled (MX_WIDGET (player), TRUE);
      clutter_actor_set_reactive (CLUTTER_ACTOR (player), FALSE);

      if (priv->content) {
        save_old_content (player);
        g_object_unref (priv->content);
        priv->content = NULL;
      }

      tmp = g_strconcat ("file://", mex_get_data_dir (),
                         "/common/style/background-loop.mkv", NULL);
      clutter_media_set_uri (priv->media, tmp);
      g_free (tmp);

      clutter_media_set_playing (priv->media, TRUE);

      /* we're idle so we don't mind the screensaver coming on */
       mex_screensaver_uninhibit (priv->screensaver);
    }
  else
    {
      clutter_actor_show (priv->controls);
      clutter_actor_show (priv->info_panel);
      mx_widget_set_disabled (MX_WIDGET (player), FALSE);
      clutter_actor_set_reactive (CLUTTER_ACTOR (player), TRUE);
      clutter_media_set_playing (priv->media, FALSE);
      clutter_media_set_uri (priv->media, NULL);

      /* we're playing real content so don't allow the screensaver */
      mex_screensaver_inhibit (priv->screensaver);
    }
}
Example #2
0
void
mex_info_bar_show_buttons (MexInfoBar *self, gboolean visible)
{
  MexInfoBarPrivate *priv = self->priv;

  /* use opacity to show and hide the buttons to ensure the correct amount of
   * space is always allocated for them */

  clutter_actor_set_opacity (priv->settings_button, 0xff * visible);
  clutter_actor_set_opacity (priv->back_button, 0xff * !visible);

  mx_widget_set_disabled (MX_WIDGET (priv->settings_button), !visible);
  mx_widget_set_disabled (MX_WIDGET (priv->back_button), visible);
}
static void
mex_volume_control_init (MexVolumeControl *self)
{
  MexVolumeControlPrivate *priv = self->priv = VOLUME_CONTROL_PRIVATE (self);
  gchar *new_style_class;
  MexPlayer *player;
  MexMusicPlayer *music;

  player = mex_player_get_default ();
  priv->media = mex_player_get_clutter_media (player);

  music = mex_music_player_get_default ();
  priv->music = mex_music_player_get_clutter_media (music);

  priv->volume = mx_button_new ();
  mx_widget_set_disabled (MX_WIDGET (priv->volume), TRUE);

  priv->vol_value = clutter_media_get_audio_volume (priv->media);

  /* The media sound can also be changed from another process changint the
   * stream audio with pulse audio, adjust the volume on those changes */
  g_signal_connect (priv->media, "notify::audio-volume",
                    G_CALLBACK (on_audio_volume_changed), self);
  g_signal_connect (priv->music, "notify::audio-volume",
                    G_CALLBACK (on_audio_volume_changed), self);

  new_style_class = g_strdup_printf ("volume-%.0f", priv->vol_value * 10);

  mx_stylable_set_style_class (MX_STYLABLE (priv->volume), new_style_class);
  g_free (new_style_class);

  clutter_actor_add_child (CLUTTER_ACTOR (self), priv->volume);
}
Example #4
0
static gboolean
mex_player_set_controls_visible (MexPlayer *player,
                                 gboolean   visible)
{
  MexPlayerPrivate *priv = player->priv;
  gfloat pos;
  ClutterStage *stage;
  MxFocusManager *fmanager;

  stage = (ClutterStage*) clutter_actor_get_stage (CLUTTER_ACTOR (player));
  fmanager = mx_focus_manager_get_for_stage (stage);

  pos = clutter_actor_get_height (priv->controls);
  if (visible)
    {
      priv->controls_prev_visible = FALSE;
      priv->controls_visible = TRUE;

      mx_widget_set_disabled (MX_WIDGET (priv->controls), FALSE);

      clutter_actor_animate (priv->controls, CLUTTER_EASE_IN_SINE, 250,
                             "opacity", 0xff,
                             "anchor-y", 0.0,
                             NULL);

      mex_player_restart_timer (player);

      if (priv->related_tile)
        {
          mx_focus_manager_push_focus_with_hint (fmanager,
                                                 MX_FOCUSABLE (priv->related_tile),
                                                 MX_FOCUS_HINT_PRIOR);

          g_object_unref (priv->related_tile);
          priv->related_tile = NULL;
        }
      else
        {
          mx_focus_manager_push_focus (fmanager, MX_FOCUSABLE (priv->controls));
        }
    }

  if (!visible)
    {
      priv->controls_visible = FALSE;
      clutter_actor_animate (priv->controls, CLUTTER_EASE_IN_SINE, 250,
                             "opacity", 0x00,
                             "anchor-y", -pos,
                             NULL);

      if (priv->hide_controls_source)
        {
          g_source_remove (priv->hide_controls_source);
          priv->hide_controls_source = 0;
        }
    }

  return TRUE;
}
static void
mex_media_controls_notify_can_seek_cb (ClutterMedia     *media,
                                       GParamSpec       *pspec,
                                       MexMediaControls *self)
{
    MexMediaControlsPrivate *priv = self->priv;
    gboolean can_seek = clutter_media_get_can_seek (media);

    mx_widget_set_disabled (MX_WIDGET (priv->slider), !can_seek);
}
Example #6
0
void
mex_player_set_idle_mode (MexPlayer *player,
                          gboolean   idle)
{
  MexPlayerPrivate *priv = player->priv;

  if (priv->idle_mode == idle)
    return;

  priv->idle_mode = idle;

  if (idle)
    {
      clutter_actor_hide (priv->controls);
      clutter_actor_hide (priv->info_panel);
      mx_widget_set_disabled (MX_WIDGET (player), TRUE);

      if (priv->content) {
        save_old_content (player);
        g_object_unref (priv->content);
        priv->content = NULL;
      }

      clutter_media_set_uri (priv->media,
                             "file://" PKGDATADIR "/style/background-loop.mkv");
      clutter_media_set_playing (priv->media, TRUE);

      /* we're idle so we don't mind the screensaver coming on */
       mex_screensaver_uninhibit (priv->screensaver);
    }
  else
    {
      clutter_actor_show (priv->controls);
      clutter_actor_show (priv->info_panel);
      mx_widget_set_disabled (MX_WIDGET (player), FALSE);
      clutter_media_set_playing (priv->media, FALSE);
      clutter_media_set_uri (priv->media, NULL);

      /* we're playing real content so don't allow the screensaver */
      mex_screensaver_inhibit (priv->screensaver);
    }
}
void
mpd_storage_device_tile_show_message_full (MpdStorageDeviceTile  *self,
                                           char const            *message,
                                           bool                   replace_buttons,
                                           unsigned int           timeout_s,
                                           GSourceFunc            function,
                                           void                  *data)
{
  MpdStorageDeviceTilePrivate *priv = GET_PRIVATE (self);

  g_return_if_fail (MPD_IS_STORAGE_DEVICE_TILE (self));

  if (priv->message == NULL)
  {
    ClutterText *text;
    priv->message = mx_label_new_with_text (message);
    mx_stylable_set_style_class (MX_STYLABLE (priv->message), "message");
    text = (ClutterText *) mx_label_get_clutter_text (MX_LABEL (priv->message));
    clutter_text_set_line_wrap (text, true);
    clutter_text_set_line_wrap_mode (text, PANGO_WRAP_WORD);
    clutter_text_set_single_line_mode (text, false);
    clutter_text_set_ellipsize (text, PANGO_ELLIPSIZE_NONE);
    mx_box_layout_add_actor_with_properties (MX_BOX_LAYOUT (self), priv->message,
                                             2,
                                             "x-align", MX_ALIGN_MIDDLE,
                                             NULL);
  }

  if (replace_buttons)
  {
    mx_widget_set_disabled (MX_WIDGET (priv->open), true);
    mx_widget_set_disabled (MX_WIDGET (priv->eject), true);
    clutter_container_remove_actor (CLUTTER_CONTAINER (self), priv->import);
  }

  mx_label_set_text (MX_LABEL (priv->message), message);

  if (timeout_s)
  {
    g_timeout_add_seconds (timeout_s, function, data);
  }
}
static void
_mount_eject_cb (GMount       *mount,
                 GAsyncResult *result,
                 gpointer      data)
{
  GError *error = NULL;

  g_return_if_fail (MPD_IS_STORAGE_DEVICE_TILE (data));

  g_mount_eject_with_operation_finish (mount, result, &error);
  if (error)
  {
    /* TODO inform user */
    mx_widget_set_disabled (MX_WIDGET (data), FALSE);
    g_warning ("%s : %s", G_STRLOC, error->message);
    g_clear_error (&error);
  }
}
static void
_vol_eject_cb (GVolume      *volume,
               GAsyncResult *result,
               gpointer      data)
{
  GError *error = NULL;

  g_return_if_fail (MPD_IS_STORAGE_DEVICE_TILE (data));

  g_volume_eject_with_operation_finish (volume, result, &error);
  if (error)
  {
    mpd_storage_device_tile_show_message (
                            MPD_STORAGE_DEVICE_TILE (data),
                            get_eject_failed_message (),
                            false);

    mx_widget_set_disabled (MX_WIDGET (data), FALSE);
    g_warning ("%s : %s", G_STRLOC, error->message);
    g_clear_error (&error);
  }
}
Example #10
0
static void
mex_player_init (MexPlayer *self)
{
  MexPlayerPrivate *priv;

  self->priv = priv = PLAYER_PRIVATE (self);

#ifdef USE_PLAYER_CLUTTER_GST
  priv->media = (ClutterMedia *) clutter_gst_video_texture_new ();

  /* We want to keep a reference to the media here to ensure consistency with
   * the D-BUS client interface behaviour
   */
  g_object_ref_sink (priv->media);

  clutter_container_add_actor (CLUTTER_CONTAINER (self),
                               CLUTTER_ACTOR (priv->media));
  clutter_texture_set_keep_aspect_ratio (CLUTTER_TEXTURE (priv->media), TRUE);
  clutter_container_child_set (CLUTTER_CONTAINER (self),
                               CLUTTER_ACTOR (priv->media),
                               "fit", TRUE, NULL);

  /* Use progressive download when possible. Don't enable that yet, the
   * behaviour of seeking in the non already downloaded part of the stream
   * is not great. Either disable seeking in that case or find out why.*/
#if 0
  video_texture = CLUTTER_GST_VIDEO_TEXTURE (priv->media);
  clutter_gst_video_texture_set_buffering_mode (video_texture,
						CLUTTER_GST_BUFFERING_MODE_DOWNLOAD);
#endif
#else
#ifdef USE_PLAYER_DBUS
  priv->media = (ClutterMedia *) mex_player_client_new ();
#else
#ifdef USE_PLAYER_SURFACE
  priv->media = (ClutterMedia *) mex_surface_player_new ();
#else
#error Unexpected player setup
#endif
#endif
#endif

  g_signal_connect (priv->media, "eos", G_CALLBACK (media_eos_cb), self);
  g_signal_connect (priv->media, "notify::playing",
                    G_CALLBACK (media_playing_cb), self);
  g_signal_connect (priv->media, "notify::progress",
                    G_CALLBACK (media_update_progress), self);


#if defined(USE_PLAYER_SURFACE) || defined (USE_PLAYER_CLUTTER_GST)
  {
    GError *error = NULL;
    priv->bridge = mex_media_dbus_bridge_new (priv->media);
    if (!mex_media_dbus_bridge_register (priv->bridge, &error))
      {
        g_warning (G_STRLOC ": Error registering player on D-BUS");
        g_clear_error (&error);
      }
  }
#endif

  /* add info panel */
  priv->info_panel = mex_info_panel_new (MEX_INFO_PANEL_MODE_FULL);
  mx_widget_set_disabled (MX_WIDGET (priv->info_panel), TRUE);
  clutter_container_add_actor (CLUTTER_CONTAINER (self), priv->info_panel);
  clutter_container_child_set (CLUTTER_CONTAINER (self), priv->info_panel,
                               "y-fill", FALSE, "y-align", MX_ALIGN_END,
                               NULL);
  clutter_actor_set_opacity (priv->info_panel, 0);

  /* add media controls */
  priv->controls = mex_media_controls_new ();
  g_signal_connect (priv->controls, "stopped", G_CALLBACK (controls_stopped_cb),
                    self);
  mex_media_controls_set_media (MEX_MEDIA_CONTROLS (priv->controls),
                                priv->media);
  clutter_container_add_actor (CLUTTER_CONTAINER (self), priv->controls);
  clutter_container_child_set (CLUTTER_CONTAINER (self), priv->controls,
                               "y-fill", FALSE, "y-align", MX_ALIGN_END,
                               NULL);

  priv->screensaver = mex_screensaver_new ();

  /* start in idle mode */
  mex_player_set_idle_mode (MEX_PLAYER (self), TRUE);
}
Example #11
0
static gboolean
mex_player_key_press_event (ClutterActor    *actor,
                            ClutterKeyEvent *event)
{
  MexPlayerPrivate *priv = MEX_PLAYER (actor)->priv;
  ClutterStage *stage;
  MxFocusManager *fmanager;

  stage = (ClutterStage*) clutter_actor_get_stage (actor);
  fmanager = mx_focus_manager_get_for_stage (stage);

  switch (event->keyval)
    {
    case CLUTTER_KEY_Down:
        {
          if (!priv->controls_visible && !priv->info_visible)
            return mex_player_set_controls_visible (MEX_PLAYER (actor), TRUE);
          break;
        }

    case MEX_KEY_INFO:
        {
          MexContent *content;

          content = priv->content;

          if (priv->info_visible)
            {
              /* hide the info panel */
              clutter_actor_animate (priv->info_panel, CLUTTER_EASE_IN_SINE,
                                     250, "opacity", 0x00, NULL);

              mx_widget_set_disabled (MX_WIDGET (priv->info_panel), TRUE);
              mx_widget_set_disabled (MX_WIDGET (priv->controls), FALSE);

              priv->info_visible = FALSE;

              if (priv->controls_prev_visible)
                mex_player_set_controls_visible (MEX_PLAYER (actor), TRUE);
            }
          else
            {
              /* if you're pressing info button while the media controls are up
               set them as previously visible */
              if (priv->controls_visible)
                priv->controls_prev_visible = TRUE;

              MxFocusable *focusable;
              focusable = mx_focus_manager_get_focused (fmanager);
              if (MEX_IS_CONTENT_TILE (focusable) &&
                  priv->controls_prev_visible == TRUE)
                {
                  content =
                    mex_content_view_get_content (MEX_CONTENT_VIEW (focusable));

                  /* to avoid any accidental leak */
                  if (priv->related_tile)
                    {
                      g_object_unref (priv->related_tile);
                      priv->related_tile = NULL;
                    }
                  priv->related_tile = g_object_ref (focusable);
                }

              mex_content_view_set_content (MEX_CONTENT_VIEW (priv->info_panel),
                                            content);

              /* show the info panel */
              clutter_actor_animate (priv->info_panel, CLUTTER_EASE_IN_SINE,
                                     250, "opacity", 0xff, NULL);

              mx_widget_set_disabled (MX_WIDGET (priv->info_panel), FALSE);
              mx_widget_set_disabled (MX_WIDGET (priv->controls), TRUE);

              priv->info_visible = TRUE;

              mex_player_set_controls_visible (MEX_PLAYER (actor), FALSE);

              mex_push_focus (MX_FOCUSABLE (priv->info_panel));
            }

          return TRUE;
        }
    }

  return FALSE;
}
Example #12
0
/* MexContentView implementation */
static void
mex_player_set_content (MexContentView *view,
                        MexContent     *content)
{
  MexPlayerPrivate *priv = MEX_PLAYER (view)->priv;

  if (priv->model)
    mex_media_controls_set_content (MEX_MEDIA_CONTROLS (priv->controls),
                                    content, priv->model);

  if (priv->related_tile)
    {
      g_object_unref (priv->related_tile);
      priv->related_tile = NULL;
    }

  if (content)
    {
      const gchar *sposition, *sduration;

      if (priv->content) {
        save_old_content (MEX_PLAYER (view));
        g_object_unref (priv->content);
        priv->content = NULL;
      }

      priv->content = g_object_ref_sink (content);

      sposition = mex_content_get_metadata (content,
                                            MEX_CONTENT_METADATA_LAST_POSITION);
      sduration = mex_content_get_metadata (content,
                                            MEX_CONTENT_METADATA_DURATION);


      if (sduration &&
          !mex_media_controls_get_playing_queue (MEX_MEDIA_CONTROLS (priv->controls)))
        priv->duration = atoi (sduration);
      else
        priv->duration = 0;

      if (priv->duration > 0)
        {
          if (sposition)
            {
              int position = atoi (sposition);
              priv->position = (gdouble) position / (gdouble) priv->duration;
            }
          else
            {
              priv->position = 0.0;
            }
        }

      if (MEX_IS_PROGRAM (content))
        {
          mex_program_get_stream (MEX_PROGRAM (content),
                                  mex_get_stream_cb,
                                  view);
        }
      else
        {
          const gchar *uri;

          uri = mex_content_get_metadata (content,
                                          MEX_CONTENT_METADATA_STREAM);
          mex_get_stream_cb (NULL, uri, NULL, view);
        }

      if (priv->info_visible)
        {
          clutter_actor_animate (priv->info_panel, CLUTTER_EASE_IN_SINE,
                                 250, "opacity", 0x00, NULL);
          mx_widget_set_disabled (MX_WIDGET (priv->info_panel), TRUE);
          priv->info_visible = FALSE;
        }

      mex_player_set_controls_visible (MEX_PLAYER (view), TRUE);
    }
  else {
    if (priv->content) {
      g_object_unref (priv->content);
      priv->content = NULL;
    }
  }
}
static void
_tile_eject_cb (MpdStorageDeviceTile  *tile,
                MpdDevicesTile        *self)
{
  MpdDevicesTilePrivate *priv = GET_PRIVATE (self);
  char const  *uri;
  GList       *mounts;
  GList       *iter;

  uri = mpd_storage_device_tile_get_mount_point (tile);

  mounts = g_volume_monitor_get_mounts (priv->monitor);
  iter = g_list_find_custom (mounts, uri, (GCompareFunc) _find_mount_cb);
  if (iter)
  {
    GMount *mount = G_MOUNT (iter->data);
    GDrive *drive;
    GVolume *vol;
    gboolean ejected = TRUE;

    drive = g_mount_get_drive (mount);
    vol = g_mount_get_volume (mount);

    if (drive && g_drive_can_eject (drive)) {
      g_debug ("%s() ejecting drive %s", __FUNCTION__, uri);
      g_drive_eject_with_operation (drive,
                                    G_MOUNT_UNMOUNT_NONE, NULL, NULL,
                                    (GAsyncReadyCallback)_drive_eject_cb,
                                    tile);
    } else if (vol && g_volume_can_eject (vol)) {
      g_debug ("%s() ejecting volume %s", __FUNCTION__, uri);
      g_volume_eject_with_operation (vol,
                                     G_MOUNT_UNMOUNT_NONE, NULL, NULL,
                                     (GAsyncReadyCallback)_vol_eject_cb,
                                     tile);
    } else if (g_mount_can_eject (mount)) {
      g_debug ("%s() ejecting mount %s", __FUNCTION__, uri);
      g_mount_eject_with_operation (mount,
                                    G_MOUNT_UNMOUNT_NONE, NULL, NULL,
                                    (GAsyncReadyCallback) _mount_eject_cb,
                                    tile);
    } else if (g_mount_can_unmount (mount)) {
      g_debug ("%s() unmounting mount %s", __FUNCTION__, uri);
      g_mount_unmount_with_operation (mount,
                                      G_MOUNT_UNMOUNT_NONE, NULL, NULL,
                                     (GAsyncReadyCallback) _mount_unmount_cb,
                                     tile);
    } else {
      ejected = FALSE;
      g_warning ("Eject or unmount not possible");
    }

    mx_widget_set_disabled (MX_WIDGET (tile), ejected);
    /* TODO: inform user of ejection with text inside the tile:
     * For that (and other reasons) this code really should be inside
     * MpdStorageDeviceTile  */

    /* TODO: we want to start a 2s timeout here, and if not done sync'ing when
     * expired show the message "Ejecting ..." */

    if (drive) {
      g_object_unref (drive);
    }
    if (vol) {
      g_object_unref (vol);
    }
  }

  g_list_foreach (mounts, (GFunc) g_object_unref, NULL);
  g_list_free (mounts);
}