mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2025-02-28 00:46:37 +00:00
ges: Add an init option to set media paths for moved assets
Allowing user to easily set a set of paths to look for moved assets instead of needing the to re implement that logic over and over. https://bugzilla.gnome.org/show_bug.cgi?id=740714
This commit is contained in:
parent
c8b2ab8dbb
commit
58d525a4e7
5 changed files with 122 additions and 108 deletions
|
@ -183,6 +183,10 @@ G_GNUC_INTERNAL gchar * ges_project_try_updating_id (GESProject *s
|
||||||
G_GNUC_INTERNAL void ges_project_add_loading_asset (GESProject *project,
|
G_GNUC_INTERNAL void ges_project_add_loading_asset (GESProject *project,
|
||||||
GType extractable_type,
|
GType extractable_type,
|
||||||
const gchar *id);
|
const gchar *id);
|
||||||
|
G_GNUC_INTERNAL gboolean ges_add_missing_uri_relocation_path (const gchar * option_name,
|
||||||
|
const gchar * value,
|
||||||
|
gpointer udata,
|
||||||
|
GError ** error);
|
||||||
|
|
||||||
/************************************************
|
/************************************************
|
||||||
* *
|
* *
|
||||||
|
|
|
@ -46,6 +46,9 @@
|
||||||
#include "ges.h"
|
#include "ges.h"
|
||||||
#include "ges-internal.h"
|
#include "ges-internal.h"
|
||||||
|
|
||||||
|
static GPtrArray *new_paths = NULL;
|
||||||
|
static GHashTable *tried_uris = NULL;
|
||||||
|
|
||||||
/* TODO We should rely on both extractable_type and @id to identify
|
/* TODO We should rely on both extractable_type and @id to identify
|
||||||
* a Asset, not only @id
|
* a Asset, not only @id
|
||||||
*/
|
*/
|
||||||
|
@ -249,6 +252,105 @@ ges_project_extract (GESAsset * project, GError ** error)
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
_add_media_new_paths_recursing (const gchar * value)
|
||||||
|
{
|
||||||
|
GFileInfo *info;
|
||||||
|
GFileEnumerator *fenum;
|
||||||
|
GFile *file = g_file_new_for_uri (value);
|
||||||
|
|
||||||
|
if (!(fenum = g_file_enumerate_children (file,
|
||||||
|
"standard::*", G_FILE_QUERY_INFO_NONE, NULL, NULL))) {
|
||||||
|
GST_INFO ("%s is not a folder", value);
|
||||||
|
|
||||||
|
goto done;
|
||||||
|
}
|
||||||
|
|
||||||
|
GST_INFO ("Adding folder: %s", value);
|
||||||
|
g_ptr_array_add (new_paths, g_strdup (value));
|
||||||
|
for (info = g_file_enumerator_next_file (fenum, NULL, NULL);
|
||||||
|
info; info = g_file_enumerator_next_file (fenum, NULL, NULL)) {
|
||||||
|
|
||||||
|
if (g_file_info_get_file_type (info) == G_FILE_TYPE_DIRECTORY) {
|
||||||
|
GFile *f = g_file_enumerator_get_child (fenum, info);
|
||||||
|
gchar *uri = g_file_get_uri (f);
|
||||||
|
|
||||||
|
_add_media_new_paths_recursing (uri);
|
||||||
|
gst_object_unref (f);
|
||||||
|
g_free (uri);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
done:
|
||||||
|
gst_object_unref (file);
|
||||||
|
if (fenum)
|
||||||
|
gst_object_unref (fenum);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
gboolean
|
||||||
|
ges_add_missing_uri_relocation_path (const gchar * option_name,
|
||||||
|
const gchar * value, gpointer udata, GError ** error)
|
||||||
|
{
|
||||||
|
g_return_val_if_fail (gst_uri_is_valid (value), FALSE);
|
||||||
|
|
||||||
|
if (new_paths == NULL)
|
||||||
|
new_paths = g_ptr_array_new_with_free_func (g_free);
|
||||||
|
|
||||||
|
g_print ("\n\nOption name %s\n\n", option_name);
|
||||||
|
if (g_strcmp0 (option_name, "--sample-path-recurse") == 0 ||
|
||||||
|
g_strcmp0 (option_name, "-R") == 0) {
|
||||||
|
_add_media_new_paths_recursing (value);
|
||||||
|
} else {
|
||||||
|
GST_INFO ("Adding folder: %s", value);
|
||||||
|
g_ptr_array_add (new_paths, g_strdup (value));
|
||||||
|
}
|
||||||
|
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
static gchar *
|
||||||
|
ges_missing_uri_default (GESProject * self, GError * error,
|
||||||
|
GESAsset * wrong_asset)
|
||||||
|
{
|
||||||
|
guint i;
|
||||||
|
const gchar *old_uri = ges_asset_get_id (wrong_asset);
|
||||||
|
|
||||||
|
if (new_paths == NULL)
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
if (tried_uris == NULL)
|
||||||
|
tried_uris = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, NULL);
|
||||||
|
|
||||||
|
for (i = 0; i < new_paths->len; i++) {
|
||||||
|
gchar *basename, *res;
|
||||||
|
|
||||||
|
basename = g_path_get_basename (old_uri);
|
||||||
|
res = g_build_filename (new_paths->pdata[i], basename, NULL);
|
||||||
|
g_free (basename);
|
||||||
|
|
||||||
|
if (g_strcmp0 (old_uri, res) == 0) {
|
||||||
|
g_hash_table_add (tried_uris, res);
|
||||||
|
} else if (g_hash_table_lookup (tried_uris, res)) {
|
||||||
|
GST_DEBUG_OBJECT (self, "File already tried: %s", res);
|
||||||
|
g_free (res);
|
||||||
|
} else {
|
||||||
|
g_hash_table_add (tried_uris, g_strdup (res));
|
||||||
|
GST_DEBUG_OBJECT (self, "Trying: %s\n", res);
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
ges_uri_assets_validate_uri (const gchar * nid)
|
||||||
|
{
|
||||||
|
if (tried_uris)
|
||||||
|
g_hash_table_remove (tried_uris, nid);
|
||||||
|
}
|
||||||
|
|
||||||
/* GObject vmethod implementation */
|
/* GObject vmethod implementation */
|
||||||
static void
|
static void
|
||||||
_dispose (GObject * object)
|
_dispose (GObject * object)
|
||||||
|
@ -318,7 +420,7 @@ ges_project_class_init (GESProjectClass * klass)
|
||||||
g_type_class_add_private (klass, sizeof (GESProjectPrivate));
|
g_type_class_add_private (klass, sizeof (GESProjectPrivate));
|
||||||
|
|
||||||
klass->asset_added = NULL;
|
klass->asset_added = NULL;
|
||||||
klass->missing_uri = NULL;
|
klass->missing_uri = ges_missing_uri_default;
|
||||||
klass->loading_error = NULL;
|
klass->loading_error = NULL;
|
||||||
klass->asset_removed = NULL;
|
klass->asset_removed = NULL;
|
||||||
object_class->get_property = (GObjectGetPropertyFunc) _get_property;
|
object_class->get_property = (GObjectGetPropertyFunc) _get_property;
|
||||||
|
|
|
@ -59,7 +59,7 @@ struct _GESProjectClass
|
||||||
GESAsset * asset);
|
GESAsset * asset);
|
||||||
void (*asset_removed) (GESProject * self,
|
void (*asset_removed) (GESProject * self,
|
||||||
GESAsset * asset);
|
GESAsset * asset);
|
||||||
gboolean (*missing_uri) (GESProject * self,
|
gchar * (*missing_uri) (GESProject * self,
|
||||||
GError * error,
|
GError * error,
|
||||||
GESAsset * wrong_asset);
|
GESAsset * wrong_asset);
|
||||||
gboolean (*loading_error) (GESProject * self,
|
gboolean (*loading_error) (GESProject * self,
|
||||||
|
|
13
ges/ges.c
13
ges/ges.c
|
@ -18,6 +18,13 @@
|
||||||
* Boston, MA 02110-1301, USA.
|
* Boston, MA 02110-1301, USA.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
/* TODO
|
||||||
|
* Add a deinit function
|
||||||
|
*
|
||||||
|
* Do not forget to
|
||||||
|
* + g_ptr_array_unref (new_paths);
|
||||||
|
* + g_hash_table_unref (tried_uris);
|
||||||
|
*/
|
||||||
|
|
||||||
#ifdef HAVE_CONFIG_H
|
#ifdef HAVE_CONFIG_H
|
||||||
#include "config.h"
|
#include "config.h"
|
||||||
|
@ -155,6 +162,12 @@ ges_init_get_option_group (void)
|
||||||
(gpointer) parse_goption_arg,
|
(gpointer) parse_goption_arg,
|
||||||
"Print the GStreamer Editing Services version",
|
"Print the GStreamer Editing Services version",
|
||||||
NULL},
|
NULL},
|
||||||
|
{"sample-paths", 'P', 0, G_OPTION_ARG_CALLBACK,
|
||||||
|
&ges_add_missing_uri_relocation_path,
|
||||||
|
"List of pathes to look assets in if they were moved"},
|
||||||
|
{"sample-path-recurse", 'R', 0, G_OPTION_ARG_CALLBACK,
|
||||||
|
&ges_add_missing_uri_relocation_path,
|
||||||
|
"Same as above, but recursing into the folder"},
|
||||||
{NULL}
|
{NULL}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -43,9 +43,7 @@ static gboolean disable_mixing = FALSE;
|
||||||
static GESPipeline *pipeline = NULL;
|
static GESPipeline *pipeline = NULL;
|
||||||
static gboolean seenerrors = FALSE;
|
static gboolean seenerrors = FALSE;
|
||||||
static gchar *save_path = NULL;
|
static gchar *save_path = NULL;
|
||||||
static GPtrArray *new_paths = NULL;
|
|
||||||
static GMainLoop *mainloop;
|
static GMainLoop *mainloop;
|
||||||
static GHashTable *tried_uris;
|
|
||||||
static GESTrackType track_types = GES_TRACK_TYPE_AUDIO | GES_TRACK_TYPE_VIDEO;
|
static GESTrackType track_types = GES_TRACK_TYPE_AUDIO | GES_TRACK_TYPE_VIDEO;
|
||||||
static GESTimeline *timeline;
|
static GESTimeline *timeline;
|
||||||
static gboolean needs_set_state;
|
static gboolean needs_set_state;
|
||||||
|
@ -94,56 +92,6 @@ get_flags_from_string (GType type, const gchar * str_flags)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static void
|
|
||||||
_add_media_new_paths_recursing (const gchar * value)
|
|
||||||
{
|
|
||||||
GFileInfo *info;
|
|
||||||
GFileEnumerator *fenum;
|
|
||||||
GFile *file = g_file_new_for_uri (value);
|
|
||||||
|
|
||||||
if (!(fenum = g_file_enumerate_children (file,
|
|
||||||
"standard::*", G_FILE_QUERY_INFO_NONE, NULL, NULL))) {
|
|
||||||
GST_INFO ("%s is not a folder", value);
|
|
||||||
|
|
||||||
goto done;
|
|
||||||
}
|
|
||||||
|
|
||||||
GST_INFO ("Adding folder: %s", value);
|
|
||||||
g_ptr_array_add (new_paths, g_strdup (value));
|
|
||||||
for (info = g_file_enumerator_next_file (fenum, NULL, NULL);
|
|
||||||
info; info = g_file_enumerator_next_file (fenum, NULL, NULL)) {
|
|
||||||
|
|
||||||
if (g_file_info_get_file_type (info) == G_FILE_TYPE_DIRECTORY) {
|
|
||||||
GFile *f = g_file_enumerator_get_child (fenum, info);
|
|
||||||
gchar *uri = g_file_get_uri (f);
|
|
||||||
|
|
||||||
_add_media_new_paths_recursing (uri);
|
|
||||||
gst_object_unref (f);
|
|
||||||
g_free (uri);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
done:
|
|
||||||
gst_object_unref (file);
|
|
||||||
if (fenum)
|
|
||||||
gst_object_unref (fenum);
|
|
||||||
}
|
|
||||||
|
|
||||||
static gboolean
|
|
||||||
_add_media_path (const gchar * option_name, const gchar * value,
|
|
||||||
gpointer udata, GError ** error)
|
|
||||||
{
|
|
||||||
g_return_val_if_fail (gst_uri_is_valid (value), FALSE);
|
|
||||||
|
|
||||||
if (g_strcmp0 (option_name, "--sample-path-recurse") == 0) {
|
|
||||||
_add_media_new_paths_recursing (value);
|
|
||||||
} else {
|
|
||||||
GST_INFO ("Adding folder: %s", value);
|
|
||||||
g_ptr_array_add (new_paths, g_strdup (value));
|
|
||||||
}
|
|
||||||
|
|
||||||
return TRUE;
|
|
||||||
}
|
|
||||||
|
|
||||||
static gboolean
|
static gboolean
|
||||||
parse_track_type (const gchar * option_name, const gchar * value,
|
parse_track_type (const gchar * option_name, const gchar * value,
|
||||||
|
@ -175,46 +123,6 @@ thumbnail_cb (gpointer pipeline)
|
||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
|
|
||||||
gchar *
|
|
||||||
ges_launch_get_new_uri_from_wrong_uri (const gchar * old_uri)
|
|
||||||
{
|
|
||||||
gint i;
|
|
||||||
|
|
||||||
for (i = 0; i < new_paths->len; i++) {
|
|
||||||
gchar *basename, *res;
|
|
||||||
|
|
||||||
basename = g_path_get_basename (old_uri);
|
|
||||||
res = g_build_filename (new_paths->pdata[i], basename, NULL);
|
|
||||||
g_free (basename);
|
|
||||||
|
|
||||||
if (g_strcmp0 (old_uri, res) == 0) {
|
|
||||||
g_hash_table_add (tried_uris, res);
|
|
||||||
} else if (g_hash_table_lookup (tried_uris, res)) {
|
|
||||||
GST_DEBUG ("File already tried: %s\n", res);
|
|
||||||
g_free (res);
|
|
||||||
} else {
|
|
||||||
g_hash_table_add (tried_uris, g_strdup (res));
|
|
||||||
return res;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
ges_launch_validate_uri (const gchar * nid)
|
|
||||||
{
|
|
||||||
g_hash_table_remove (tried_uris, nid);
|
|
||||||
}
|
|
||||||
|
|
||||||
static gchar *
|
|
||||||
source_moved_cb (GESProject * project, GError * error, GESAsset * asset)
|
|
||||||
{
|
|
||||||
const gchar *old_uri = ges_asset_get_id (asset);
|
|
||||||
|
|
||||||
return ges_launch_get_new_uri_from_wrong_uri (old_uri);
|
|
||||||
}
|
|
||||||
|
|
||||||
static void
|
static void
|
||||||
error_loading_asset_cb (GESProject * project, GError * error,
|
error_loading_asset_cb (GESProject * project, GError * error,
|
||||||
const gchar * failed_id, GType extractable_type)
|
const gchar * failed_id, GType extractable_type)
|
||||||
|
@ -313,10 +221,6 @@ create_timeline (int nbargs, gchar ** argv, const gchar * proj_uri,
|
||||||
GstClockTime next_trans_dur = 0;
|
GstClockTime next_trans_dur = 0;
|
||||||
GESProject *project = ges_project_new (proj_uri);
|
GESProject *project = ges_project_new (proj_uri);
|
||||||
|
|
||||||
if (new_paths->len)
|
|
||||||
g_signal_connect (project, "missing-uri",
|
|
||||||
G_CALLBACK (source_moved_cb), NULL);
|
|
||||||
|
|
||||||
g_signal_connect (project, "error-loading-asset",
|
g_signal_connect (project, "error-loading-asset",
|
||||||
G_CALLBACK (error_loading_asset_cb), NULL);
|
G_CALLBACK (error_loading_asset_cb), NULL);
|
||||||
|
|
||||||
|
@ -822,11 +726,6 @@ main (int argc, gchar ** argv)
|
||||||
"Output status information and property notifications", NULL},
|
"Output status information and property notifications", NULL},
|
||||||
{"exclude", 'X', 0, G_OPTION_ARG_NONE, &exclude_args,
|
{"exclude", 'X', 0, G_OPTION_ARG_NONE, &exclude_args,
|
||||||
"Do not output status information of <type>", "<type1>,<type2>,..."},
|
"Do not output status information of <type>", "<type1>,<type2>,..."},
|
||||||
{"sample-paths", 'P', 0, G_OPTION_ARG_CALLBACK, &_add_media_path,
|
|
||||||
"List of pathes to look assets in if they were moved"},
|
|
||||||
{"sample-path-recurse", 'R', 0, G_OPTION_ARG_CALLBACK,
|
|
||||||
&_add_media_path,
|
|
||||||
"Same as above, but recursing into the folder"},
|
|
||||||
{"track-types", 'p', 0, G_OPTION_ARG_CALLBACK, &parse_track_type,
|
{"track-types", 'p', 0, G_OPTION_ARG_CALLBACK, &parse_track_type,
|
||||||
"Defines the track types to be created"},
|
"Defines the track types to be created"},
|
||||||
{"mute", 0, 0, G_OPTION_ARG_NONE, &mute,
|
{"mute", 0, 0, G_OPTION_ARG_NONE, &mute,
|
||||||
|
@ -859,7 +758,6 @@ main (int argc, gchar ** argv)
|
||||||
|
|
||||||
setlocale (LC_ALL, "");
|
setlocale (LC_ALL, "");
|
||||||
|
|
||||||
new_paths = g_ptr_array_new_with_free_func (g_free);
|
|
||||||
ctx = g_option_context_new ("- plays or renders a timeline.");
|
ctx = g_option_context_new ("- plays or renders a timeline.");
|
||||||
g_option_context_set_summary (ctx,
|
g_option_context_set_summary (ctx,
|
||||||
"ges-launch renders a timeline, which can be specified on the commandline,\n"
|
"ges-launch renders a timeline, which can be specified on the commandline,\n"
|
||||||
|
@ -898,6 +796,7 @@ main (int argc, gchar ** argv)
|
||||||
" -f \"application/ogg:video/x-theora|<presence>:audio/x-vorbis\"");
|
" -f \"application/ogg:video/x-theora|<presence>:audio/x-vorbis\"");
|
||||||
g_option_context_add_main_entries (ctx, options, NULL);
|
g_option_context_add_main_entries (ctx, options, NULL);
|
||||||
g_option_context_add_group (ctx, gst_init_get_option_group ());
|
g_option_context_add_group (ctx, gst_init_get_option_group ());
|
||||||
|
g_option_context_add_group (ctx, ges_init_get_option_group ());
|
||||||
|
|
||||||
if (!g_option_context_parse (ctx, &argc, &argv, &err)) {
|
if (!g_option_context_parse (ctx, &argc, &argv, &err)) {
|
||||||
g_printerr ("Error initializing: %s\n", err->message);
|
g_printerr ("Error initializing: %s\n", err->message);
|
||||||
|
@ -926,7 +825,6 @@ main (int argc, gchar ** argv)
|
||||||
return ges_validate_print_action_types ((const gchar **) argv + 1,
|
return ges_validate_print_action_types ((const gchar **) argv + 1,
|
||||||
argc - 1);
|
argc - 1);
|
||||||
|
|
||||||
tried_uris = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, NULL);
|
|
||||||
if (((!load_path && !scenario && (argc < 4)))) {
|
if (((!load_path && !scenario && (argc < 4)))) {
|
||||||
g_printf ("%s", g_option_context_get_help (ctx, TRUE, NULL));
|
g_printf ("%s", g_option_context_get_help (ctx, TRUE, NULL));
|
||||||
g_option_context_free (ctx);
|
g_option_context_free (ctx);
|
||||||
|
@ -1055,9 +953,6 @@ main (int argc, gchar ** argv)
|
||||||
if (seenerrors == FALSE)
|
if (seenerrors == FALSE)
|
||||||
seenerrors = validate_res;
|
seenerrors = validate_res;
|
||||||
|
|
||||||
g_hash_table_unref (tried_uris);
|
|
||||||
g_ptr_array_unref (new_paths);
|
|
||||||
|
|
||||||
#ifdef G_OS_UNIX
|
#ifdef G_OS_UNIX
|
||||||
g_source_remove (signal_watch_id);
|
g_source_remove (signal_watch_id);
|
||||||
#endif
|
#endif
|
||||||
|
|
Loading…
Reference in a new issue