On Fri, Jul 06, 2007 at 10:44:52AM +0100, Matthew Allum wrote:
Audio visualisation would be very cool btw, something I've wanted to
have a shot at. I hope you intend to share code :)
Using the playbin changes that you committed today and some code digging
I came up with the attached code. It turns out that the playbin element
had visualization support all along...similar to the custom audio-sink
and video-sink functions (the property is "vis-plugin").
With this I get some visualizations when playing but it doesn't look
right, the visualization is only shown at very brief intervals and then
overwritten with the solid color of the stage again...I'm not sure what
I'm doing wrong...
--
David Härdeman
#include <clutter-gst/clutter-gst.h>
#include <string.h>
#include <stdlib.h>
#define WIDTH 640
#define HEIGTH 480
#define SCALE 2
#define FPS 25
#define VISUALIZATION "goom"
static void
die(char *msg)
{
g_error(msg);
exit(EXIT_FAILURE);
}
static gboolean
filter_features (GstPluginFeature * feature, gpointer data)
{
GstElementFactory *f;
if (!GST_IS_ELEMENT_FACTORY (feature))
return FALSE;
f = GST_ELEMENT_FACTORY (feature);
if (!g_strrstr (gst_element_factory_get_klass (f), "Visualization"))
return FALSE;
return TRUE;
}
static void
add_visualization(ClutterGstVideoTexture *video_texture)
{
GList *features;
GList *feature;
GstElementFactory *tmp;
GstElementFactory *fac = NULL;
GstElement *vis_element;
GstElement *vis_capsfilter;
GstElement *playbin;
GstPad *pad;
GstCaps *caps;
features = gst_registry_feature_filter(gst_registry_get_default(),
filter_features, FALSE, NULL);
for (feature = features; feature; feature = feature->next) {
tmp = GST_ELEMENT_FACTORY(feature->data);
fprintf(stderr, "Found visualization: %s\n", GST_PLUGIN_FEATURE_NAME(tmp));
if (!strcmp(GST_PLUGIN_FEATURE_NAME(tmp), VISUALIZATION))
fac = tmp;
}
g_list_free(features);
if (!fac)
die("Failed to find visualization");
else
fprintf(stderr, "Using visualization " VISUALIZATION "\n");
vis_element = gst_element_factory_create(fac, "vis_element");
if (!GST_IS_ELEMENT(vis_element))
die("Failed to create vis");
vis_capsfilter = gst_element_factory_make("capsfilter", "vis_capsfilter");
if (!GST_IS_ELEMENT(vis_capsfilter))
die("Failed to create caps");
gst_element_link_pads(vis_element, "src", vis_capsfilter, "sink");
/* Get allowed output caps from visualisation element */
pad = gst_element_get_pad(vis_element, "src");
caps = gst_pad_get_allowed_caps(pad);
gst_object_unref(pad);
/* Can we fixate ? */
if (caps && !gst_caps_is_fixed(caps)) {
guint i;
caps = gst_caps_make_writable(caps);
/* Get visualization size */
for (i = 0; i < gst_caps_get_size (caps); ++i) {
GstStructure *s = gst_caps_get_structure (caps, i);
/* Fixate */
gst_structure_fixate_field_nearest_int(s, "width", WIDTH / SCALE);
gst_structure_fixate_field_nearest_int(s, "height", HEIGTH / SCALE);
gst_structure_fixate_field_nearest_fraction(s, "framerate", FPS, 1);
}
/* set this */
g_object_set(vis_capsfilter, "caps", caps, NULL);
}
playbin = clutter_gst_video_texture_get_playbin(video_texture);
g_object_set(playbin, "vis-plugin", vis_element, NULL);
}
int
main (int argc, char *argv[])
{
ClutterActor *stage;
ClutterActor *video;
ClutterColor stage_color = { 0x00, 0x00, 0x00, 0xff };
if (argc < 2)
die("Missing argument");
clutter_init(&argc, &argv);
gst_init(&argc, &argv);
stage = clutter_stage_get_default();
clutter_stage_set_color(CLUTTER_STAGE(stage), &stage_color);
clutter_actor_set_size(stage, WIDTH, HEIGTH);
video = g_object_new(CLUTTER_GST_TYPE_VIDEO_TEXTURE, "sync-size", FALSE, "tiled", FALSE, NULL);
if (!video)
die("Failed to create video texture");
clutter_media_set_filename(CLUTTER_MEDIA(video), argv[1]);
clutter_group_add(CLUTTER_GROUP(stage), video);
clutter_actor_set_size(video, WIDTH, HEIGTH);
add_visualization(CLUTTER_GST_VIDEO_TEXTURE(video));
clutter_media_set_volume(CLUTTER_MEDIA(video), 1.0);
clutter_media_set_playing(CLUTTER_MEDIA(video), TRUE);
clutter_actor_show_all(stage);
g_signal_connect(stage, "key-press-event", G_CALLBACK(clutter_main_quit), NULL);
clutter_main();
return EXIT_SUCCESS;
}