diff options
Diffstat (limited to 'test/test_port.c')
-rw-r--r-- | test/test_port.c | 331 |
1 files changed, 331 insertions, 0 deletions
diff --git a/test/test_port.c b/test/test_port.c new file mode 100644 index 0000000..63f8bd0 --- /dev/null +++ b/test/test_port.c @@ -0,0 +1,331 @@ +/* + Copyright 2007-2020 David Robillard <http://drobilla.net> + + Permission to use, copy, modify, and/or distribute this software for any + purpose with or without fee is hereby granted, provided that the above + copyright notice and this permission notice appear in all copies. + + THIS SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES + WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF + MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR + ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES + WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN + ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF + OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. +*/ + +#undef NDEBUG + +#include "lilv_test_utils.h" + +#include "lilv/lilv.h" + +#include <assert.h> +#include <stdbool.h> +#include <string.h> + +static const char* const plugin_ttl = "\ +@prefix lv2ev: <http://lv2plug.in/ns/ext/event#> . \n\ +:plug\n\ + a lv2:Plugin ;\n\ + doap:name \"Test plugin\" ;\n\ + doap:homepage <http://example.org/someplug> ;\n\ + lv2:port [\n\ + a lv2:ControlPort ;\n\ + a lv2:InputPort ;\n\ + lv2:index 0 ;\n\ + lv2:symbol \"foo\" ;\n\ + lv2:name \"store\" ;\n\ + lv2:name \"Laden\"@de-de ;\n\ + lv2:name \"Geschaeft\"@de-at ;\n\ + lv2:name \"tienda\"@es ;\n\ + rdfs:comment \"comment\"@en , \"commentaires\"@fr ;\n\ + lv2:portProperty lv2:integer ;\n\ + lv2:minimum -1.0 ;\n\ + lv2:maximum 1.0 ;\n\ + lv2:default 0.5 ;\n\ + lv2:scalePoint [\n\ + rdfs:label \"Sin\";\n\ + rdf:value 3\n\ + ] ;\n\ + lv2:scalePoint [\n\ + rdfs:label \"Cos\";\n\ + rdf:value 4\n\ + ]\n\ + ] , [\n\ + a lv2:EventPort ;\n\ + a lv2:InputPort ;\n\ + lv2:index 1 ;\n\ + lv2:symbol \"event_in\" ;\n\ + lv2:name \"Event Input\" ;\n\ + lv2ev:supportsEvent <http://example.org/event> ;\n\ + atom:supports <http://example.org/atomEvent>\n\ + ] , [\n\ + a lv2:AudioPort ;\n\ + a lv2:InputPort ;\n\ + lv2:index 2 ;\n\ + lv2:symbol \"audio_in\" ;\n\ + lv2:name \"Audio Input\" ;\n\ + ] , [\n\ + a lv2:AudioPort ;\n\ + a lv2:OutputPort ;\n\ + lv2:index 3 ;\n\ + lv2:symbol \"audio_out\" ;\n\ + lv2:name \"Audio Output\" ;\n\ + ] .\n"; + +int +main(void) +{ + LilvTestEnv* const env = lilv_test_env_new(); + LilvWorld* const world = env->world; + + if (start_bundle(env, SIMPLE_MANIFEST_TTL, plugin_ttl)) { + return 1; + } + + const LilvPlugins* plugins = lilv_world_get_all_plugins(world); + const LilvPlugin* plug = lilv_plugins_get_by_uri(plugins, env->plugin1_uri); + assert(plug); + + LilvNode* psym = lilv_new_string(world, "foo"); + const LilvPort* p = lilv_plugin_get_port_by_index(plug, 0); + const LilvPort* p2 = lilv_plugin_get_port_by_symbol(plug, psym); + lilv_node_free(psym); + assert(p != NULL); + assert(p2 != NULL); + assert(p == p2); + + LilvNode* nopsym = lilv_new_string(world, "thisaintnoportfoo"); + const LilvPort* p3 = lilv_plugin_get_port_by_symbol(plug, nopsym); + assert(p3 == NULL); + lilv_node_free(nopsym); + + // Try getting an invalid property + LilvNode* num = lilv_new_int(world, 1); + LilvNodes* nothing = lilv_port_get_value(plug, p, num); + assert(!nothing); + lilv_node_free(num); + + LilvNode* audio_class = + lilv_new_uri(world, "http://lv2plug.in/ns/lv2core#AudioPort"); + LilvNode* control_class = + lilv_new_uri(world, "http://lv2plug.in/ns/lv2core#ControlPort"); + LilvNode* in_class = + lilv_new_uri(world, "http://lv2plug.in/ns/lv2core#InputPort"); + LilvNode* out_class = + lilv_new_uri(world, "http://lv2plug.in/ns/lv2core#OutputPort"); + + assert(lilv_nodes_size(lilv_port_get_classes(plug, p)) == 2); + assert(lilv_plugin_get_num_ports(plug) == 4); + assert(lilv_port_is_a(plug, p, control_class)); + assert(lilv_port_is_a(plug, p, in_class)); + assert(!lilv_port_is_a(plug, p, audio_class)); + + LilvNodes* port_properties = lilv_port_get_properties(plug, p); + assert(lilv_nodes_size(port_properties) == 1); + lilv_nodes_free(port_properties); + + // Untranslated name (current locale is set to "C" in main) + assert(!strcmp(lilv_node_as_string(lilv_port_get_symbol(plug, p)), "foo")); + LilvNode* name = lilv_port_get_name(plug, p); + assert(!strcmp(lilv_node_as_string(name), "store")); + lilv_node_free(name); + + // Exact language match + set_env("LANG", "de_DE"); + name = lilv_port_get_name(plug, p); + assert(!strcmp(lilv_node_as_string(name), "Laden")); + lilv_node_free(name); + + // Exact language match (with charset suffix) + set_env("LANG", "de_AT.utf8"); + name = lilv_port_get_name(plug, p); + assert(!strcmp(lilv_node_as_string(name), "Geschaeft")); + lilv_node_free(name); + + // Partial language match (choose value translated for different country) + set_env("LANG", "de_CH"); + name = lilv_port_get_name(plug, p); + assert((!strcmp(lilv_node_as_string(name), "Laden")) || + (!strcmp(lilv_node_as_string(name), "Geschaeft"))); + lilv_node_free(name); + + // Partial language match (choose country-less language tagged value) + set_env("LANG", "es_MX"); + name = lilv_port_get_name(plug, p); + assert(!strcmp(lilv_node_as_string(name), "tienda")); + lilv_node_free(name); + + // No language match (choose untranslated value) + set_env("LANG", "cn"); + name = lilv_port_get_name(plug, p); + assert(!strcmp(lilv_node_as_string(name), "store")); + lilv_node_free(name); + + // Invalid language + set_env("LANG", "1!"); + name = lilv_port_get_name(plug, p); + assert(!strcmp(lilv_node_as_string(name), "store")); + lilv_node_free(name); + + set_env("LANG", "en_CA.utf-8"); + + // Language tagged value with no untranslated values + LilvNode* rdfs_comment = lilv_new_uri(world, LILV_NS_RDFS "comment"); + LilvNodes* comments = lilv_port_get_value(plug, p, rdfs_comment); + assert(!strcmp(lilv_node_as_string(lilv_nodes_get_first(comments)), + "comment")); + LilvNode* comment = lilv_port_get(plug, p, rdfs_comment); + assert(!strcmp(lilv_node_as_string(comment), "comment")); + lilv_node_free(comment); + lilv_nodes_free(comments); + + set_env("LANG", "fr"); + + comments = lilv_port_get_value(plug, p, rdfs_comment); + assert(!strcmp(lilv_node_as_string(lilv_nodes_get_first(comments)), + "commentaires")); + lilv_nodes_free(comments); + + set_env("LANG", "cn"); + + comments = lilv_port_get_value(plug, p, rdfs_comment); + assert(!comments); + lilv_nodes_free(comments); + + lilv_node_free(rdfs_comment); + + set_env("LANG", "C"); // Reset locale + + LilvScalePoints* points = lilv_port_get_scale_points(plug, p); + assert(lilv_scale_points_size(points) == 2); + + LilvIter* sp_iter = lilv_scale_points_begin(points); + const LilvScalePoint* sp0 = lilv_scale_points_get(points, sp_iter); + assert(sp0); + sp_iter = lilv_scale_points_next(points, sp_iter); + const LilvScalePoint* sp1 = lilv_scale_points_get(points, sp_iter); + assert(sp1); + + assert(((!strcmp(lilv_node_as_string(lilv_scale_point_get_label(sp0)), + "Sin") && + lilv_node_as_float(lilv_scale_point_get_value(sp0)) == 3) && + (!strcmp(lilv_node_as_string(lilv_scale_point_get_label(sp1)), + "Cos") && + lilv_node_as_float(lilv_scale_point_get_value(sp1)) == 4)) || + ((!strcmp(lilv_node_as_string(lilv_scale_point_get_label(sp0)), + "Cos") && + lilv_node_as_float(lilv_scale_point_get_value(sp0)) == 4) && + (!strcmp(lilv_node_as_string(lilv_scale_point_get_label(sp1)), + "Sin") && + lilv_node_as_float(lilv_scale_point_get_value(sp1)) == 3))); + + LilvNode* homepage_p = + lilv_new_uri(world, "http://usefulinc.com/ns/doap#homepage"); + LilvNodes* homepages = lilv_plugin_get_value(plug, homepage_p); + assert(lilv_nodes_size(homepages) == 1); + assert(!strcmp(lilv_node_as_string(lilv_nodes_get_first(homepages)), + "http://example.org/someplug")); + + LilvNode *min, *max, *def; + lilv_port_get_range(plug, p, &def, &min, &max); + assert(def); + assert(min); + assert(max); + assert(lilv_node_as_float(def) == 0.5); + assert(lilv_node_as_float(min) == -1.0); + assert(lilv_node_as_float(max) == 1.0); + + LilvNode* integer_prop = + lilv_new_uri(world, "http://lv2plug.in/ns/lv2core#integer"); + LilvNode* toggled_prop = + lilv_new_uri(world, "http://lv2plug.in/ns/lv2core#toggled"); + + assert(lilv_port_has_property(plug, p, integer_prop)); + assert(!lilv_port_has_property(plug, p, toggled_prop)); + + const LilvPort* ep = lilv_plugin_get_port_by_index(plug, 1); + + LilvNode* event_type = lilv_new_uri(world, "http://example.org/event"); + LilvNode* event_type_2 = + lilv_new_uri(world, "http://example.org/otherEvent"); + LilvNode* atom_event = lilv_new_uri(world, "http://example.org/atomEvent"); + assert(lilv_port_supports_event(plug, ep, event_type)); + assert(!lilv_port_supports_event(plug, ep, event_type_2)); + assert(lilv_port_supports_event(plug, ep, atom_event)); + + LilvNode* name_p = lilv_new_uri(world, "http://lv2plug.in/ns/lv2core#name"); + LilvNodes* names = lilv_port_get_value(plug, p, name_p); + assert(lilv_nodes_size(names) == 1); + assert(!strcmp(lilv_node_as_string(lilv_nodes_get_first(names)), "store")); + lilv_nodes_free(names); + + LilvNode* true_val = lilv_new_bool(world, true); + LilvNode* false_val = lilv_new_bool(world, false); + + assert(!lilv_node_equals(true_val, false_val)); + + lilv_world_set_option(world, LILV_OPTION_FILTER_LANG, false_val); + names = lilv_port_get_value(plug, p, name_p); + assert(lilv_nodes_size(names) == 4); + lilv_nodes_free(names); + lilv_world_set_option(world, LILV_OPTION_FILTER_LANG, true_val); + + lilv_node_free(false_val); + lilv_node_free(true_val); + + names = lilv_port_get_value(plug, ep, name_p); + assert(lilv_nodes_size(names) == 1); + assert(!strcmp(lilv_node_as_string(lilv_nodes_get_first(names)), + "Event Input")); + + const LilvPort* ap_in = lilv_plugin_get_port_by_index(plug, 2); + + assert(lilv_port_is_a(plug, ap_in, in_class)); + assert(!lilv_port_is_a(plug, ap_in, out_class)); + assert(lilv_port_is_a(plug, ap_in, audio_class)); + assert(!lilv_port_is_a(plug, ap_in, control_class)); + + const LilvPort* ap_out = lilv_plugin_get_port_by_index(plug, 3); + + assert(lilv_port_is_a(plug, ap_out, out_class)); + assert(!lilv_port_is_a(plug, ap_out, in_class)); + assert(lilv_port_is_a(plug, ap_out, audio_class)); + assert(!lilv_port_is_a(plug, ap_out, control_class)); + + assert(lilv_plugin_get_num_ports_of_class( + plug, control_class, in_class, NULL) == 1); + assert( + lilv_plugin_get_num_ports_of_class(plug, audio_class, in_class, NULL) == + 1); + assert(lilv_plugin_get_num_ports_of_class( + plug, audio_class, out_class, NULL) == 1); + + lilv_nodes_free(names); + lilv_node_free(name_p); + + lilv_node_free(integer_prop); + lilv_node_free(toggled_prop); + lilv_node_free(event_type); + lilv_node_free(event_type_2); + lilv_node_free(atom_event); + + lilv_node_free(min); + lilv_node_free(max); + lilv_node_free(def); + + lilv_node_free(homepage_p); + lilv_nodes_free(homepages); + + lilv_scale_points_free(points); + lilv_node_free(control_class); + lilv_node_free(audio_class); + lilv_node_free(out_class); + lilv_node_free(in_class); + + delete_bundle(env); + lilv_test_env_free(env); + + return 0; +} |