[totem/wip/hadess/glsink: 12/12] backend: Use better placeholder when there's no video




commit 5e5805c58e34b870ebc3c37114b8c70b1674cb0b
Author: Bastien Nocera <hadess hadess net>
Date:   Tue Feb 1 17:44:57 2022 +0100

    backend: Use better placeholder when there's no video
    
    When there's no video because we're playing an audio-only file, or
    because a plugin is missing, show a placeholder that corresponds to that
    type of media.
    
    See https://gitlab.gnome.org/Teams/Design/icon-development-kit/-/issues/44

 data/icons/meson.build                        | 12 ++++++
 data/icons/symbolic/audio-only-symbolic.svg   |  2 +
 data/icons/symbolic/broken-video-symbolic.svg |  2 +
 src/backend/bacon-video-widget.c              | 59 +++++++++++++++++++++------
 4 files changed, 63 insertions(+), 12 deletions(-)
---
diff --git a/data/icons/meson.build b/data/icons/meson.build
index 1d61003c2..f1a12b601 100644
--- a/data/icons/meson.build
+++ b/data/icons/meson.build
@@ -8,3 +8,15 @@ install_data(
   rename : [application_id + '-symbolic.svg'],
   install_dir: join_paths(totem_datadir, 'icons', 'hicolor', 'symbolic', 'apps')
 )
+
+icons = [
+  'audio-only-symbolic.svg',
+  'broken-video-symbolic.svg'
+]
+
+foreach icon: icons
+  install_data(
+    join_paths('symbolic', icon),
+    install_dir: join_paths(totem_datadir, 'icons', 'hicolor', 'scalable', 'status')
+  )
+endforeach
diff --git a/data/icons/symbolic/audio-only-symbolic.svg b/data/icons/symbolic/audio-only-symbolic.svg
new file mode 100644
index 000000000..53ef2e0fb
--- /dev/null
+++ b/data/icons/symbolic/audio-only-symbolic.svg
@@ -0,0 +1,2 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<svg xmlns="http://www.w3.org/2000/svg"; height="16px" viewBox="0 0 16 16" width="16px"><path d="m 1.972656 
3.773438 c -0.132812 0.007812 -0.257812 0.070312 -0.34375 0.167968 c -1.066406 1.210938 -1.628906 2.585938 
-1.628906 3.984375 c 0 1.402344 0.558594 2.8125 1.617188 4.105469 c 0.175781 0.214844 0.488281 0.246094 
0.703124 0.070312 c 0.214844 -0.175781 0.246094 -0.488281 0.070313 -0.703124 c -0.945313 -1.152344 -1.390625 
-2.332032 -1.390625 -3.472657 c 0 -1.136719 0.441406 -2.261719 1.378906 -3.320312 c 0.089844 -0.101563 
0.132813 -0.230469 0.125 -0.363281 c -0.007812 -0.132813 -0.070312 -0.257813 -0.171875 -0.347657 c -0.097656 
-0.085937 -0.226562 -0.128906 -0.359375 -0.121093 z m 11.984375 0 c -0.105469 0.011718 -0.207031 0.054687 
-0.285156 0.121093 c -0.101563 0.089844 -0.160156 0.214844 -0.167969 0.347657 c -0.007812 0.132812 0.035156 
0.261718 0.121094 0.363281 c 0.9375 1.058593 1.378906 2.183593 1.378906 3.320312 c 0 1.140625 -0.445312 
2.320313 -1.390625 3.472657 c -0.171875 
 0.214843 -0.140625 0.527343 0.074219 0.703124 c 0.210938 0.175782 0.527344 0.144532 0.699219 -0.070312 c 
1.0625 -1.292969 1.617187 -2.703125 1.617187 -4.105469 c 0 -1.398437 -0.558594 -2.773437 -1.628906 -3.984375 
c -0.105469 -0.121094 -0.261719 -0.183594 -0.417969 -0.167968 z m -8.101562 0.164062 c -0.480469 0.023438 
-0.855469 0.417969 -0.855469 0.898438 v 6.359374 c 0 0.3125 0.167969 0.601563 0.441406 0.753907 c 0.273438 
0.148437 0.605469 0.144531 0.871094 -0.023438 l 5.265625 -3.246093 c 0.238281 -0.144532 0.378906 -0.402344 
0.382813 -0.679688 c 0 -0.277344 -0.144532 -0.535156 -0.378907 -0.683594 l -5.203125 -3.246094 c -0.15625 
-0.097656 -0.339844 -0.144531 -0.523437 -0.132812 z m -2.359375 1.050781 c -0.160156 -0.003906 -0.3125 
0.066407 -0.410156 0.195313 c -0.679688 0.886718 -1.070313 1.824218 -1.078126 2.792968 c -0.011718 0.964844 
0.363282 1.921876 1.085938 2.835938 c 0.167969 0.214844 0.484375 0.25 0.699219 0.082031 c 0.214843 -0.171875 
0.253906 -0.488281 0.082031 -0.703125
  c -0.617188 -0.777344 -0.875 -1.5 -0.867188 -2.203125 c 0.003907 -0.707031 0.285157 -1.429687 0.871094 
-2.195312 c 0.167969 -0.21875 0.128906 -0.53125 -0.089844 -0.699219 c -0.085937 -0.066406 -0.1875 -0.101562 
-0.292968 -0.105469 z m 9.015625 0 c -0.109375 0.003907 -0.210938 0.039063 -0.292969 0.105469 c -0.21875 
0.164062 -0.261719 0.480469 -0.09375 0.699219 c 0.585938 0.765625 0.867188 1.488281 0.875 2.195312 c 0.007812 
0.703125 -0.253906 1.425781 -0.867188 2.203125 c -0.171874 0.214844 -0.136718 0.53125 0.078126 0.703125 c 
0.21875 0.167969 0.53125 0.132813 0.703124 -0.082031 c 0.722657 -0.914062 1.097657 -1.871094 1.085938 
-2.835938 c -0.011719 -0.96875 -0.398438 -1.90625 -1.082031 -2.792968 c -0.09375 -0.128906 -0.25 -0.199219 
-0.40625 -0.195313 z m 0 0" fill="#2e3436"/></svg>
diff --git a/data/icons/symbolic/broken-video-symbolic.svg b/data/icons/symbolic/broken-video-symbolic.svg
new file mode 100644
index 000000000..066e1fb26
--- /dev/null
+++ b/data/icons/symbolic/broken-video-symbolic.svg
@@ -0,0 +1,2 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<svg xmlns="http://www.w3.org/2000/svg"; height="16px" viewBox="0 0 16 16" width="16px"><g 
fill="#2e3436"><path d="m 2.398438 3 c -1.328126 0 -2.398438 1.070312 -2.398438 2.398438 v 7.203124 c 0 
1.328126 1.070312 2.398438 2.398438 2.398438 h 1.394531 l 1.707031 -6 h -1.5 l 1.5 -6 z m 0 0"/><path d="m 8 
1 l -1.5 6 h 1.5 l -1.707031 6 h 3.308593 c 1.328126 0 2.398438 -1.070312 2.398438 -2.398438 v -7.203124 c 0 
-1.328126 -1.070312 -2.398438 -2.398438 -2.398438 z m 4 6 l 3 3 h 1 v -6 h -1 z m 0 0"/></g></svg>
diff --git a/src/backend/bacon-video-widget.c b/src/backend/bacon-video-widget.c
index 4b4aa2a09..eed9677db 100644
--- a/src/backend/bacon-video-widget.c
+++ b/src/backend/bacon-video-widget.c
@@ -85,7 +85,7 @@
 #define DEFAULT_USER_AGENT "Videos/"VERSION
 
 #define DEFAULT_CONTROLS_WIDTH 600             /* In pixels */
-#define LOGO_SIZE 256                          /* Maximum size of the logo */
+#define LOGO_SIZE 64                           /* Maximum size of the logo */
 #define REWIND_OR_PREVIOUS 4000
 
 #define MAX_NETWORK_SPEED 10752
@@ -171,6 +171,7 @@ struct _BaconVideoWidget
   guint                        fill_id;
 
   gboolean                     media_has_video;
+  gboolean                     media_has_unsupported_video;
   gboolean                     media_has_audio;
   gint                         seekable; /* -1 = don't know, FALSE = no */
   gint64                       stream_length;
@@ -188,6 +189,7 @@ struct _BaconVideoWidget
   gboolean                     got_redirect;
 
   GtkWidget                   *stack;
+  GtkWidget                   *video_widget;
 
   GdkCursor                   *cursor;
 
@@ -341,6 +343,25 @@ bvw_check_if_video_decoder_is_missing (BaconVideoWidget * bvw)
 {
   GList *l;
 
+  for (l = bvw->missing_plugins; l != NULL; l = l->next) {
+    GstMessage *msg = GST_MESSAGE (l->data);
+    g_autofree char *d = NULL;
+    char *f;
+
+    if ((d = gst_missing_plugin_message_get_installer_detail (msg))) {
+      if ((f = strstr (d, "|decoder-")) && strstr (f, "video")) {
+       bvw->media_has_unsupported_video = TRUE;
+       break;
+      }
+    }
+  }
+}
+
+static void
+bvw_show_error_if_video_decoder_is_missing (BaconVideoWidget * bvw)
+{
+  GList *l;
+
   if (bvw->media_has_video || bvw->missing_plugins == NULL)
     return;
 
@@ -396,12 +417,16 @@ bacon_video_widget_unrealize (GtkWidget *widget)
 static void
 set_current_actor (BaconVideoWidget *bvw)
 {
-  gboolean draw_logo;
+  const char *page;
 
-  /* If there's only audio draw the logo */
-  draw_logo = bvw->media_has_audio && !bvw->media_has_video;
-  gtk_stack_set_visible_child_name (GTK_STACK (bvw->stack),
-                                   draw_logo ? "logo" : "video");
+  if (bvw->media_has_audio && !bvw->media_has_video)
+    page = "audio-only";
+  else if (bvw->media_has_unsupported_video)
+    page = "broken-video";
+  else
+    page = "video";
+
+  gtk_stack_set_visible_child_name (GTK_STACK (bvw->stack), page);
 }
 
 static void
@@ -1420,6 +1445,8 @@ bvw_check_missing_plugins_error (BaconVideoWidget * bvw, GstMessage * err_msg)
   if (is_error (err, CORE, MISSING_PLUGIN) ||
       is_error (err, STREAM, CODEC_NOT_FOUND) ||
       (is_error (err, STREAM, WRONG_TYPE) && error_src_is_playbin)) {
+    bvw_check_if_video_decoder_is_missing (bvw);
+    set_current_actor (bvw);
     ret = bvw_emit_missing_plugins_signal (bvw, FALSE);
     if (ret) {
       /* If it was handled, stop playback to make sure we're not processing any
@@ -1871,7 +1898,7 @@ bvw_bus_message_cb (GstBus * bus, GstMessage * message, BaconVideoWidget *bvw)
         bvw_update_stream_info (bvw);
         if (!bvw_check_missing_plugins_on_preroll (bvw)) {
           /* show a non-fatal warning message if we can't decode the video */
-          bvw_check_if_video_decoder_is_missing (bvw);
+          bvw_show_error_if_video_decoder_is_missing (bvw);
         }
        /* Now that we have the length, check whether we wanted
         * to pause or to stop the pipeline */
@@ -1880,6 +1907,7 @@ bvw_bus_message_cb (GstBus * bus, GstMessage * message, BaconVideoWidget *bvw)
       } else if (old_state == GST_STATE_PAUSED && new_state == GST_STATE_READY) {
         bvw->media_has_video = FALSE;
         bvw->media_has_audio = FALSE;
+       bvw->media_has_unsupported_video = FALSE;
 
         /* clean metadata cache */
        g_clear_pointer (&bvw->tagcache, gst_tag_list_unref);
@@ -2311,6 +2339,7 @@ parse_stream_info (BaconVideoWidget *bvw)
       "n-video", &n_video, NULL);
 
   bvw->media_has_video = FALSE;
+  bvw->media_has_unsupported_video = FALSE;
   if (n_video > 0) {
     gint i;
 
@@ -3376,6 +3405,7 @@ bacon_video_widget_open (BaconVideoWidget *bvw,
 
   bvw->got_redirect = FALSE;
   bvw->media_has_video = FALSE;
+  bvw->media_has_unsupported_video = FALSE;
   bvw->media_has_audio = FALSE;
 
   /* Flush the bus to make sure we don't get any messages
@@ -5363,14 +5393,19 @@ bacon_video_widget_initable_init (GInitable     *initable,
   } else {
     g_object_set (glsinkbin, "sink", bvw->video_sink, NULL);
   }
-  g_object_get (bvw->video_sink, "widget", &tmp, NULL);
-  gtk_stack_add_named (GTK_STACK (bvw->stack), tmp, "video");
+  g_object_get (bvw->video_sink, "widget", &bvw->video_widget, NULL);
+  gtk_stack_add_named (GTK_STACK (bvw->stack), bvw->video_widget, "video");
+  gtk_widget_show (bvw->video_widget);
+  g_object_unref (bvw->video_widget);
+
+  tmp = gtk_image_new_from_icon_name ("audio-only-symbolic", GTK_ICON_SIZE_DIALOG);
+  gtk_image_set_pixel_size (GTK_IMAGE (tmp), LOGO_SIZE);
+  gtk_stack_add_named (GTK_STACK (bvw->stack), tmp, "audio-only");
   gtk_widget_show (tmp);
-  g_object_unref (tmp);
 
-  tmp = gtk_image_new_from_icon_name (APPLICATION_ID, GTK_ICON_SIZE_DIALOG);
+  tmp = gtk_image_new_from_icon_name ("broken-video-symbolic", GTK_ICON_SIZE_DIALOG);
   gtk_image_set_pixel_size (GTK_IMAGE (tmp), LOGO_SIZE);
-  gtk_stack_add_named (GTK_STACK (bvw->stack), tmp, "logo");
+  gtk_stack_add_named (GTK_STACK (bvw->stack), tmp, "broken-video");
   gtk_widget_show (tmp);
 
   g_object_set (bvw->video_sink,


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]