mirror of
https://gitlab.freedesktop.org/gstreamer/gstreamer.git
synced 2024-11-27 12:11:13 +00:00
lv2: add support for saving presets
Plugns supporting the state interface can now save their presets under '.lv2'.
This commit is contained in:
parent
e9a2c4f1e1
commit
adf2092b3d
4 changed files with 112 additions and 8 deletions
|
@ -91,7 +91,9 @@ gst_lv2_filter_load_preset (GstPreset * preset, const gchar * name)
|
|||
static gboolean
|
||||
gst_lv2_filter_save_preset (GstPreset * preset, const gchar * name)
|
||||
{
|
||||
return FALSE;
|
||||
GstLV2Filter *self = (GstLV2Filter *) preset;
|
||||
|
||||
return gst_lv2_save_preset (&self->lv2, (GstObject *) self, name);
|
||||
}
|
||||
|
||||
static gboolean
|
||||
|
@ -104,7 +106,9 @@ gst_lv2_filter_rename_preset (GstPreset * preset, const gchar * old_name,
|
|||
static gboolean
|
||||
gst_lv2_filter_delete_preset (GstPreset * preset, const gchar * name)
|
||||
{
|
||||
return FALSE;
|
||||
GstLV2Filter *self = (GstLV2Filter *) preset;
|
||||
|
||||
return gst_lv2_delete_preset (&self->lv2, (GstObject *) self, name);
|
||||
}
|
||||
|
||||
static gboolean
|
||||
|
|
|
@ -108,7 +108,9 @@ gst_lv2_source_load_preset (GstPreset * preset, const gchar * name)
|
|||
static gboolean
|
||||
gst_lv2_source_save_preset (GstPreset * preset, const gchar * name)
|
||||
{
|
||||
return FALSE;
|
||||
GstLV2Source *self = (GstLV2Source *) preset;
|
||||
|
||||
return gst_lv2_save_preset (&self->lv2, (GstObject *) self, name);
|
||||
}
|
||||
|
||||
static gboolean
|
||||
|
@ -121,7 +123,9 @@ gst_lv2_source_rename_preset (GstPreset * preset, const gchar * old_name,
|
|||
static gboolean
|
||||
gst_lv2_source_delete_preset (GstPreset * preset, const gchar * name)
|
||||
{
|
||||
return FALSE;
|
||||
GstLV2Source *self = (GstLV2Source *) preset;
|
||||
|
||||
return gst_lv2_delete_preset (&self->lv2, (GstObject *) self, name);
|
||||
}
|
||||
|
||||
static gboolean
|
||||
|
|
|
@ -225,7 +225,6 @@ set_port_value (const char *port_symbol, void *data, const void *value,
|
|||
g_object_set (obj, prop_name, fvalue, NULL);
|
||||
}
|
||||
|
||||
|
||||
gboolean
|
||||
gst_lv2_load_preset (GstLV2 * lv2, GstObject * obj, const gchar * name)
|
||||
{
|
||||
|
@ -242,26 +241,120 @@ gst_lv2_load_preset (GstLV2 * lv2, GstObject * obj, const gchar * name)
|
|||
return FALSE;
|
||||
}
|
||||
|
||||
#if 0
|
||||
static const void *
|
||||
get_port_value (const char *port_symbol, void *data, uint32_t * size,
|
||||
uint32_t * type)
|
||||
{
|
||||
gpointer *user_data = (gpointer *) data;
|
||||
GstLV2Class *klass = user_data[0];
|
||||
GstObject *obj = user_data[1];
|
||||
gchar *prop_name = g_hash_table_lookup (klass->sym_to_name, port_symbol);
|
||||
static gfloat fvalue;
|
||||
|
||||
if (!prop_name) {
|
||||
GST_WARNING_OBJECT (obj, "Preset port '%s' is missing", port_symbol);
|
||||
*size = *type = 0;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
*size = sizeof (float);
|
||||
*type = forge.Float;
|
||||
g_object_get (obj, prop_name, &fvalue, NULL);
|
||||
/* FIXME: can we return &lv2->ports.{in,out}[x]; */
|
||||
return &fvalue;
|
||||
}
|
||||
|
||||
gboolean
|
||||
gst_lv2_save_preset (GstLV2 * lv2, GstObject * obj, const gchar * name)
|
||||
{
|
||||
return FALSE;
|
||||
gchar *filename, *basename, *bundle, *dir, *tmp_dir, *s;
|
||||
gpointer user_data[] = { lv2->klass, obj };
|
||||
GstElementFactory *factory;
|
||||
LilvState *state;
|
||||
LilvNode *bundle_dir;
|
||||
LilvInstance *instance = lv2->instance;
|
||||
gboolean res;
|
||||
|
||||
factory = gst_element_get_factory ((GstElement *) obj);
|
||||
basename = g_strdup (gst_element_factory_get_metadata (factory,
|
||||
GST_ELEMENT_METADATA_LONGNAME));
|
||||
s = basename;
|
||||
while ((s = strchr (s, ' '))) {
|
||||
*s = '_';
|
||||
}
|
||||
|
||||
filename = g_strjoin (NULL, name, ".ttl", NULL);
|
||||
bundle = g_strjoin (NULL, basename, "_", name, ".preset.lv2", NULL);
|
||||
/* dir needs to end on a dir separator for the lilv_new_file_uri() to work */
|
||||
dir =
|
||||
g_build_filename (g_get_home_dir (), ".lv2", bundle, G_DIR_SEPARATOR_S,
|
||||
NULL);
|
||||
tmp_dir = g_dir_make_tmp ("gstlv2-XXXXXX", NULL);
|
||||
g_mkdir_with_parents (dir, 0750);
|
||||
|
||||
if (!instance) {
|
||||
/* instance is NULL until we play!! */
|
||||
instance = lilv_plugin_instantiate (lv2->klass->plugin, GST_AUDIO_DEF_RATE,
|
||||
lv2_features);
|
||||
}
|
||||
|
||||
state = lilv_state_new_from_instance (lv2->klass->plugin, instance, &lv2_map,
|
||||
tmp_dir, dir, dir, dir, get_port_value, user_data,
|
||||
LV2_STATE_IS_POD | LV2_STATE_IS_PORTABLE, NULL);
|
||||
|
||||
lilv_state_set_label (state, name);
|
||||
|
||||
res = lilv_state_save (world, &lv2_map, &lv2_unmap, state, /*uri */ NULL, dir,
|
||||
filename) != 0;
|
||||
|
||||
/* reload bundle into the world */
|
||||
bundle_dir = lilv_new_file_uri (world, NULL, dir);
|
||||
lilv_world_unload_bundle (world, bundle_dir);
|
||||
lilv_world_load_bundle (world, bundle_dir);
|
||||
lilv_node_free (bundle_dir);
|
||||
|
||||
lilv_world_load_resource (world, lilv_state_get_uri (state));
|
||||
g_hash_table_insert (lv2->presets, g_strdup (name),
|
||||
lilv_node_duplicate (lilv_state_get_uri (state)));
|
||||
|
||||
lilv_state_free (state);
|
||||
if (!lv2->instance) {
|
||||
lilv_instance_free (instance);
|
||||
}
|
||||
|
||||
g_free (tmp_dir);
|
||||
g_free (dir);
|
||||
g_free (bundle);
|
||||
g_free (filename);
|
||||
g_free (basename);
|
||||
|
||||
return res;
|
||||
}
|
||||
|
||||
#if 0
|
||||
gboolean
|
||||
gst_lv2_rename_preset (GstLV2 * lv2, GstObject * obj,
|
||||
const gchar * old_name, const gchar * new_name)
|
||||
{
|
||||
/* need to relabel the preset */
|
||||
return FALSE;
|
||||
}
|
||||
#endif
|
||||
|
||||
gboolean
|
||||
gst_lv2_delete_preset (GstLV2 * lv2, GstObject * obj, const gchar * name)
|
||||
{
|
||||
LilvNode *preset = g_hash_table_lookup (lv2->presets, name);
|
||||
LilvState *state = lilv_state_new_from_world (world, &lv2_map, preset);
|
||||
|
||||
lilv_world_unload_resource (world, lilv_state_get_uri (state));
|
||||
lilv_state_delete (world, state);
|
||||
lilv_state_free (state);
|
||||
|
||||
g_hash_table_remove (lv2->presets, name);
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
/* api helpers */
|
||||
|
|
|
@ -106,6 +106,9 @@ void gst_lv2_host_init (void);
|
|||
|
||||
gchar **gst_lv2_get_preset_names (GstLV2 * lv2, GstObject * obj);
|
||||
gboolean gst_lv2_load_preset (GstLV2 * lv2, GstObject * obj, const gchar * name);
|
||||
gboolean gst_lv2_save_preset (GstLV2 * lv2, GstObject * obj, const gchar * name);
|
||||
gboolean gst_lv2_delete_preset (GstLV2 * lv2, GstObject * obj, const gchar * name);
|
||||
|
||||
|
||||
void gst_lv2_init (GstLV2 * lv2, GstLV2Class * lv2_class);
|
||||
void gst_lv2_finalize (GstLV2 * lv2);
|
||||
|
|
Loading…
Reference in a new issue